Skip to content

Commit

Permalink
fix: precedence of autoCompleteFields vs. endpointUrl and label-value…
Browse files Browse the repository at this point in the history
… mapping for handling form save without click or enter event on combobox option
  • Loading branch information
harshpatel-crest committed Apr 28, 2021
1 parent 5a085e5 commit 0db4606
Show file tree
Hide file tree
Showing 3 changed files with 114 additions and 11 deletions.
4 changes: 2 additions & 2 deletions ui/package.json
Expand Up @@ -20,7 +20,7 @@
"dependencies": {
"@splunk/react-page": "^5.0.0",
"@splunk/react-toast-notifications": "^0.9.0",
"@splunk/react-ui": "^4.0.0",
"@splunk/react-ui": "4.1.0-alpha.sha-696381af",
"@splunk/splunk-utils": "^2.0.0",
"@splunk/themes": "^0.7.0",
"axios": "^0.21.1",
Expand Down Expand Up @@ -57,7 +57,7 @@
"eslint-plugin-jsx-a11y": "^6.4.1",
"eslint-plugin-react": "^7.21.5",
"eslint-plugin-react-hooks": "^4.2.0",
"html-webpack-plugin": "^3.2.0",
"html-webpack-plugin": "^3.2.0",
"prettier": "^2.0.5",
"semantic-release": "^17.4.2",
"stylelint": "^13.0.0",
Expand Down
91 changes: 91 additions & 0 deletions ui/src/main/webapp/components/ComboBoxWrapper.jsx
@@ -0,0 +1,91 @@
import React from 'react';
import PropTypes from 'prop-types';
import ComboBox from '@splunk/react-ui/ComboBox';
import styled from 'styled-components';

const StyledDiv = styled.div`
div:first-child {
width: 300px !important;
}
`;

function ComboBoxWrapper(props) {
const {
value,
name,
error,
placeholder,
disabled,
labelValueMapping,
// isGroup,
...restProps
} = props;

// function getHeadingElement(elem) {
// // Get the next sibling element
// let sibling = elem.previousElementSibling;

// // If the sibling matches our selector, use it
// // If not, jump to the next sibling and continue the loop
// while (sibling) {
// if (!sibling.matches('[data-test="option"]')) {
// return sibling.querySelector('[data-test="heading"]');
// }
// sibling = sibling.previousElementSibling;
// }
// return null;
// }

function handleChange(e, obj) {
let effectiveValue = obj.value;
if (e.target.getAttribute('role') === 'textbox') {
const entry = Array.from(labelValueMapping.entries()).find(([k, v]) => {
if (v instanceof Map) {
return v.get(obj.value);
}
return k === obj.value;
});
if (entry) {
effectiveValue = entry[1] instanceof Map ? entry[1].get(obj.value) : entry[1];
}
}
// else if (isGroup) {
// const target = e.target.closest('button[data-test="option"]');
// const groupName = getHeadingElement(target).innerText.toUpperCase();
// effectiveValue = labelValueMapping.get(groupName).get(obj.value);
// } else {
// effectiveValue = labelValueMapping.get(obj.value);
// }
restProps.handleChange(e, { ...obj, value: effectiveValue });
// restProps.handleChange(e, obj);
}

return (
<StyledDiv>
<ComboBox
value={value}
name={name}
error={error}
placeholder={placeholder}
disabled={disabled}
onChange={handleChange}
inline
>
{restProps.children}
</ComboBox>
</StyledDiv>
);
}

ComboBoxWrapper.propTypes = {
value: PropTypes.string,
name: PropTypes.string,
error: PropTypes.bool,
placeholder: PropTypes.string,
disabled: PropTypes.bool,
labelValueMapping: PropTypes.instanceOf(Map),
isGroup: PropTypes.bool,
handleChange: PropTypes.func.isRequired,
};

export default ComboBoxWrapper;
30 changes: 21 additions & 9 deletions ui/src/main/webapp/components/SingleInputComponent.jsx
Expand Up @@ -10,15 +10,12 @@ import styled from 'styled-components';

import { axiosCallWrapper } from '../util/axiosCallWrapper';
import { filterResponse } from '../util/util';
import ComboBoxWrapper from './ComboBoxWrapper';

const SelectWrapper = styled(Select)`
width: 300px !important;
`;

const ComboBoxWrapper = styled(ComboBox)`
width: 300px !important;
`;

function SingleInputComponent(props) {
const {
field,
Expand All @@ -41,33 +38,47 @@ function SingleInputComponent(props) {
autoCompleteFields,
} = controlOptions;

function handleChange(e, { value: currentValue }) {
restProps.handleChange(field, currentValue);
function handleChange(e, obj) {
console.log(obj);
restProps.handleChange(field, obj.value);
}
const [labelValueMapping, setLabelValueMapping] = useState(null);
// const [isGroup, setIsGroup] = useState(false);
const Option = createSearchChoice ? ComboBox.Option : Select.Option;
const Heading = createSearchChoice ? ComboBox.Heading : Select.Heading;

function generateOptions(items) {
const data = [];
const mapping = new Map();
// let groupFlag = false;
items.forEach((item) => {
if (item.value && item.label) {
// TODO: add conditional label in case of Select
data.push(<Option label={item.label} value={item.value} key={item.value} />);
mapping.set(item.label, item.value);
// data.push(<Option value={item.label} key={item.value} />);
}
if (item.children && item.label) {
// groupFlag = true;
mapping.set(item.label.toUpperCase(), new Map());
data.push(<Heading key={item.label}>{item.label}</Heading>);
item.children.forEach((child) => {
data.push(<Option label={child.label} value={child.value} key={child.value} />);
mapping.get(item.label.toUpperCase()).set(child.label, child.value);
// data.push(<Option value={child.label} key={child.value} />);
});
}
});
setLabelValueMapping(mapping);
// setIsGroup(groupFlag);
return data;
}

const [loading, setLoading] = useState(false);
const [options, setOptions] = useState(null);

useEffect(() => {
if (autoCompleteFields) {
if (!endpointUrl && !referenceName && autoCompleteFields) {
setOptions(generateOptions(autoCompleteFields));
return;
}
Expand Down Expand Up @@ -125,8 +136,9 @@ function SingleInputComponent(props) {
error={error}
placeholder={effectivePlaceholder}
disabled={effectiveDisabled}
onChange={handleChange}
inline
labelValueMapping={labelValueMapping}
// isGroup={isGroup}
handleChange={handleChange}
>
{options && options.length > 0 && options}
</ComboBoxWrapper>
Expand Down

0 comments on commit 0db4606

Please sign in to comment.