summaryrefslogtreecommitdiff
path: root/app/assets/javascripts/filtered_search/dropdown_utils.js
diff options
context:
space:
mode:
Diffstat (limited to 'app/assets/javascripts/filtered_search/dropdown_utils.js')
-rw-r--r--app/assets/javascripts/filtered_search/dropdown_utils.js296
1 files changed, 148 insertions, 148 deletions
diff --git a/app/assets/javascripts/filtered_search/dropdown_utils.js b/app/assets/javascripts/filtered_search/dropdown_utils.js
index 432b0c0dfd2..bc7c1dffece 100644
--- a/app/assets/javascripts/filtered_search/dropdown_utils.js
+++ b/app/assets/javascripts/filtered_search/dropdown_utils.js
@@ -1,181 +1,181 @@
import FilteredSearchContainer from './container';
-(() => {
- class DropdownUtils {
- static getEscapedText(text) {
- let escapedText = text;
- const hasSpace = text.indexOf(' ') !== -1;
- const hasDoubleQuote = text.indexOf('"') !== -1;
-
- // Encapsulate value with quotes if it has spaces
- // Known side effect: values's with both single and double quotes
- // won't escape properly
- if (hasSpace) {
- if (hasDoubleQuote) {
- escapedText = `'${text}'`;
- } else {
- // Encapsulate singleQuotes or if it hasSpace
- escapedText = `"${text}"`;
- }
+class DropdownUtils {
+ static getEscapedText(text) {
+ let escapedText = text;
+ const hasSpace = text.indexOf(' ') !== -1;
+ const hasDoubleQuote = text.indexOf('"') !== -1;
+
+ // Encapsulate value with quotes if it has spaces
+ // Known side effect: values's with both single and double quotes
+ // won't escape properly
+ if (hasSpace) {
+ if (hasDoubleQuote) {
+ escapedText = `'${text}'`;
+ } else {
+ // Encapsulate singleQuotes or if it hasSpace
+ escapedText = `"${text}"`;
}
-
- return escapedText;
}
- static filterWithSymbol(filterSymbol, input, item) {
- const updatedItem = item;
- const searchInput = gl.DropdownUtils.getSearchInput(input);
+ return escapedText;
+ }
+
+ static filterWithSymbol(filterSymbol, input, item) {
+ const updatedItem = item;
+ const searchInput = gl.DropdownUtils.getSearchInput(input);
- const title = updatedItem.title.toLowerCase();
- let value = searchInput.toLowerCase();
- let symbol = '';
+ const title = updatedItem.title.toLowerCase();
+ let value = searchInput.toLowerCase();
+ let symbol = '';
- // Remove the symbol for filter
- if (value[0] === filterSymbol) {
- symbol = value[0];
- value = value.slice(1);
- }
+ // Remove the symbol for filter
+ if (value[0] === filterSymbol) {
+ symbol = value[0];
+ value = value.slice(1);
+ }
- // Removes the first character if it is a quotation so that we can search
- // with multiple words
- if ((value[0] === '"' || value[0] === '\'') && title.indexOf(' ') !== -1) {
- value = value.slice(1);
- }
+ // Removes the first character if it is a quotation so that we can search
+ // with multiple words
+ if ((value[0] === '"' || value[0] === '\'') && title.indexOf(' ') !== -1) {
+ value = value.slice(1);
+ }
+
+ // Eg. filterSymbol = ~ for labels
+ const matchWithoutSymbol = symbol === filterSymbol && title.indexOf(value) !== -1;
+ const match = title.indexOf(`${symbol}${value}`) !== -1;
- // Eg. filterSymbol = ~ for labels
- const matchWithoutSymbol = symbol === filterSymbol && title.indexOf(value) !== -1;
- const match = title.indexOf(`${symbol}${value}`) !== -1;
+ updatedItem.droplab_hidden = !match && !matchWithoutSymbol;
- updatedItem.droplab_hidden = !match && !matchWithoutSymbol;
+ return updatedItem;
+ }
- return updatedItem;
+ static filterHint(input, item) {
+ const updatedItem = item;
+ const searchInput = gl.DropdownUtils.getSearchQuery(input);
+ const { lastToken, tokens } = gl.FilteredSearchTokenizer.processTokens(searchInput);
+ const lastKey = lastToken.key || lastToken || '';
+ const allowMultiple = item.type === 'array';
+ const itemInExistingTokens = tokens.some(t => t.key === item.hint);
+
+ if (!allowMultiple && itemInExistingTokens) {
+ updatedItem.droplab_hidden = true;
+ } else if (!lastKey || searchInput.split('').last() === ' ') {
+ updatedItem.droplab_hidden = false;
+ } else if (lastKey) {
+ const split = lastKey.split(':');
+ const tokenName = split[0].split(' ').last();
+
+ const match = updatedItem.hint.indexOf(tokenName.toLowerCase()) === -1;
+ updatedItem.droplab_hidden = tokenName ? match : false;
}
- static filterHint(input, item) {
- const updatedItem = item;
- const searchInput = gl.DropdownUtils.getSearchQuery(input);
- const { lastToken, tokens } = gl.FilteredSearchTokenizer.processTokens(searchInput);
- const lastKey = lastToken.key || lastToken || '';
- const allowMultiple = item.type === 'array';
- const itemInExistingTokens = tokens.some(t => t.key === item.hint);
-
- if (!allowMultiple && itemInExistingTokens) {
- updatedItem.droplab_hidden = true;
- } else if (!lastKey || searchInput.split('').last() === ' ') {
- updatedItem.droplab_hidden = false;
- } else if (lastKey) {
- const split = lastKey.split(':');
- const tokenName = split[0].split(' ').last();
-
- const match = updatedItem.hint.indexOf(tokenName.toLowerCase()) === -1;
- updatedItem.droplab_hidden = tokenName ? match : false;
- }
+ return updatedItem;
+ }
+
+ static setDataValueIfSelected(filter, selected) {
+ const dataValue = selected.getAttribute('data-value');
- return updatedItem;
+ if (dataValue) {
+ gl.FilteredSearchDropdownManager.addWordToInput(filter, dataValue, true);
}
- static setDataValueIfSelected(filter, selected) {
- const dataValue = selected.getAttribute('data-value');
+ // Return boolean based on whether it was set
+ return dataValue !== null;
+ }
- if (dataValue) {
- gl.FilteredSearchDropdownManager.addWordToInput(filter, dataValue, true);
- }
+ // Determines the full search query (visual tokens + input)
+ static getSearchQuery(untilInput = false) {
+ const container = FilteredSearchContainer.container;
+ const tokens = [].slice.call(container.querySelectorAll('.tokens-container li'));
+ const values = [];
- // Return boolean based on whether it was set
- return dataValue !== null;
+ if (untilInput) {
+ const inputIndex = _.findIndex(tokens, t => t.classList.contains('input-token'));
+ // Add one to include input-token to the tokens array
+ tokens.splice(inputIndex + 1);
}
- // Determines the full search query (visual tokens + input)
- static getSearchQuery(untilInput = false) {
- const container = FilteredSearchContainer.container;
- const tokens = [].slice.call(container.querySelectorAll('.tokens-container li'));
- const values = [];
+ tokens.forEach((token) => {
+ if (token.classList.contains('js-visual-token')) {
+ const name = token.querySelector('.name');
+ const value = token.querySelector('.value');
+ const symbol = value && value.dataset.symbol ? value.dataset.symbol : '';
+ let valueText = '';
- if (untilInput) {
- const inputIndex = _.findIndex(tokens, t => t.classList.contains('input-token'));
- // Add one to include input-token to the tokens array
- tokens.splice(inputIndex + 1);
- }
+ if (value && value.innerText) {
+ valueText = value.innerText;
+ }
- tokens.forEach((token) => {
- if (token.classList.contains('js-visual-token')) {
- const name = token.querySelector('.name');
- const value = token.querySelector('.value');
- const symbol = value && value.dataset.symbol ? value.dataset.symbol : '';
- let valueText = '';
-
- if (value && value.innerText) {
- valueText = value.innerText;
- }
-
- if (token.className.indexOf('filtered-search-token') !== -1) {
- values.push(`${name.innerText.toLowerCase()}:${symbol}${valueText}`);
- } else {
- values.push(name.innerText);
- }
- } else if (token.classList.contains('input-token')) {
- const { isLastVisualTokenValid } =
- gl.FilteredSearchVisualTokens.getLastVisualTokenBeforeInput();
-
- const input = FilteredSearchContainer.container.querySelector('.filtered-search');
- const inputValue = input && input.value;
-
- if (isLastVisualTokenValid) {
- values.push(inputValue);
- } else {
- const previous = values.pop();
- values.push(`${previous}${inputValue}`);
- }
+ if (token.className.indexOf('filtered-search-token') !== -1) {
+ values.push(`${name.innerText.toLowerCase()}:${symbol}${valueText}`);
+ } else {
+ values.push(name.innerText);
}
- });
+ } else if (token.classList.contains('input-token')) {
+ const { isLastVisualTokenValid } =
+ gl.FilteredSearchVisualTokens.getLastVisualTokenBeforeInput();
- return values.join(' ');
- }
+ const input = FilteredSearchContainer.container.querySelector('.filtered-search');
+ const inputValue = input && input.value;
- static getSearchInput(filteredSearchInput) {
- const inputValue = filteredSearchInput.value;
- const { right } = gl.DropdownUtils.getInputSelectionPosition(filteredSearchInput);
+ if (isLastVisualTokenValid) {
+ values.push(inputValue);
+ } else {
+ const previous = values.pop();
+ values.push(`${previous}${inputValue}`);
+ }
+ }
+ });
- return inputValue.slice(0, right);
- }
+ return values
+ .map(value => value.trim())
+ .join(' ');
+ }
- static getInputSelectionPosition(input) {
- const selectionStart = input.selectionStart;
- let inputValue = input.value;
- // Replace all spaces inside quote marks with underscores
- // (will continue to match entire string until an end quote is found if any)
- // This helps with matching the beginning & end of a token:key
- inputValue = inputValue.replace(/(('[^']*'{0,1})|("[^"]*"{0,1})|:\s+)/g, str => str.replace(/\s/g, '_'));
-
- // Get the right position for the word selected
- // Regex matches first space
- let right = inputValue.slice(selectionStart).search(/\s/);
-
- if (right >= 0) {
- right += selectionStart;
- } else if (right < 0) {
- right = inputValue.length;
- }
+ static getSearchInput(filteredSearchInput) {
+ const inputValue = filteredSearchInput.value;
+ const { right } = gl.DropdownUtils.getInputSelectionPosition(filteredSearchInput);
- // Get the left position for the word selected
- // Regex matches last non-whitespace character
- let left = inputValue.slice(0, right).search(/\S+$/);
+ return inputValue.slice(0, right);
+ }
- if (selectionStart === 0) {
- left = 0;
- } else if (selectionStart === inputValue.length && left < 0) {
- left = inputValue.length;
- } else if (left < 0) {
- left = selectionStart;
- }
+ static getInputSelectionPosition(input) {
+ const selectionStart = input.selectionStart;
+ let inputValue = input.value;
+ // Replace all spaces inside quote marks with underscores
+ // (will continue to match entire string until an end quote is found if any)
+ // This helps with matching the beginning & end of a token:key
+ inputValue = inputValue.replace(/(('[^']*'{0,1})|("[^"]*"{0,1})|:\s+)/g, str => str.replace(/\s/g, '_'));
+
+ // Get the right position for the word selected
+ // Regex matches first space
+ let right = inputValue.slice(selectionStart).search(/\s/);
+
+ if (right >= 0) {
+ right += selectionStart;
+ } else if (right < 0) {
+ right = inputValue.length;
+ }
+
+ // Get the left position for the word selected
+ // Regex matches last non-whitespace character
+ let left = inputValue.slice(0, right).search(/\S+$/);
- return {
- left,
- right,
- };
+ if (selectionStart === 0) {
+ left = 0;
+ } else if (selectionStart === inputValue.length && left < 0) {
+ left = inputValue.length;
+ } else if (left < 0) {
+ left = selectionStart;
}
+
+ return {
+ left,
+ right,
+ };
}
+}
- window.gl = window.gl || {};
- gl.DropdownUtils = DropdownUtils;
-})();
+window.gl = window.gl || {};
+gl.DropdownUtils = DropdownUtils;