diff --git a/x-pack/plugins/code/public/components/editor/editor.tsx b/x-pack/plugins/code/public/components/editor/editor.tsx index bf30230f98e60..59195350a0d8a 100644 --- a/x-pack/plugins/code/public/components/editor/editor.tsx +++ b/x-pack/plugins/code/public/components/editor/editor.tsx @@ -57,7 +57,7 @@ export class EditorComponent extends React.Component { public componentDidMount(): void { this.container = document.getElementById('mainEditor') as HTMLElement; - this.monaco = new MonacoHelper(this.container, this.props); + this.monaco = new MonacoHelper(this.container, this.props, this.props.location.search); const { file } = this.props; if (file && file.content) { @@ -100,6 +100,9 @@ export class EditorComponent extends React.Component { ) { this.revealPosition(this.props.revealPosition); } + if (this.monaco && qs !== prevProps.location.search) { + this.monaco.updateUrlQuery(qs); + } if (this.monaco && this.monaco.editor) { if (prevProps.showBlame !== this.props.showBlame && this.props.showBlame) { this.loadBlame(this.props.blames); diff --git a/x-pack/plugins/code/public/components/main/side_tabs.tsx b/x-pack/plugins/code/public/components/main/side_tabs.tsx index ffa6350532737..dcc4e5e11d0b6 100644 --- a/x-pack/plugins/code/public/components/main/side_tabs.tsx +++ b/x-pack/plugins/code/public/components/main/side_tabs.tsx @@ -33,7 +33,7 @@ class CodeSideTabs extends React.PureComponent { if (search.charAt(0) === '?') { qs = search.substr(1); } - const tab = parseQuery(qs).tab; + const tab = parseQuery(qs).sideTab; return tab === Tabs.structure ? Tabs.structure : Tabs.file; } @@ -87,7 +87,7 @@ class CodeSideTabs extends React.PureComponent { const { history } = this.props; const { pathname, search } = history.location; // @ts-ignore - history.push(QueryString.replaceParamInUrl(`${pathname}${search}`, 'tab', tab)); + history.push(QueryString.replaceParamInUrl(`${pathname}${search}`, 'sideTab', tab)); }; public render() { diff --git a/x-pack/plugins/code/public/components/symbol_tree/__test__/__snapshots__/symbol_tree.test.tsx.snap b/x-pack/plugins/code/public/components/symbol_tree/__test__/__snapshots__/symbol_tree.test.tsx.snap index 9e56b677234c5..ec43e344a4ed1 100644 --- a/x-pack/plugins/code/public/components/symbol_tree/__test__/__snapshots__/symbol_tree.test.tsx.snap +++ b/x-pack/plugins/code/public/components/symbol_tree/__test__/__snapshots__/symbol_tree.test.tsx.snap @@ -107,7 +107,7 @@ exports[`render symbol tree correctly 1`] = `
= createMatch({ + path: '/:resource/:org/:repo/:pathType(blob|tree)/:revision/:path*:goto(!.*)?', + url: '/github.com/google/guava/tree/master/guava/src/com/google', + isExact: true, + params: { + resource: 'github.com', + org: 'google', + repo: 'guava', + pathType: PathTypes.tree, + revision: 'master', + path: 'guava/src/com/google', + }, +}); + +const history: History = createHistory({ location, length: 8, action: 'POP' }); test('render symbol tree correctly', () => { const tree = renderer .create( { structureTree: SymbolWithMembers[]; closedPaths: string[]; openSymbolPath: (p: string) => void; @@ -64,6 +64,7 @@ export class CodeSymbolTree extends React.PureComponent; } + const queries = url.parse(this.props.location.search, true).query; return (
{bg} @@ -89,7 +90,7 @@ export class CodeSymbolTree extends React.PureComponent string) { + super(); + } + public static async handleSymbolUri(qname: string, getUrlQuery: () => string) { const result = await EditorService.findSymbolByQname(qname); if (result.symbols.length > 0) { const symbol = result.symbols[0].symbolInformation; @@ -27,7 +30,7 @@ export class EditorService extends StandaloneCodeEditorServiceImpl { if (schema === 'git:') { const { line, character } = symbol.location.range.start; const url = uri + `!L${line + 1}:${character + 1}`; - history.push(url); + history.push(`${url}${getUrlQuery()}`); } } } @@ -52,7 +55,7 @@ export class EditorService extends StandaloneCodeEditorServiceImpl { ) { const { scheme, authority, path } = input.resource; if (scheme === 'symbol') { - await EditorService.handleSymbolUri(authority); + await EditorService.handleSymbolUri(authority, this.getUrlQuery); } else { const uri = `/${authority}${path}`; if (input.options && input.options.selection) { @@ -62,7 +65,7 @@ export class EditorService extends StandaloneCodeEditorServiceImpl { if (currentPath === url) { this.helper!.revealPosition(startLineNumber, startColumn); } else { - history.push(url); + history.push(`${url}${this.getUrlQuery()}`); } } } diff --git a/x-pack/plugins/code/public/monaco/monaco_helper.ts b/x-pack/plugins/code/public/monaco/monaco_helper.ts index f1b6e3871cd58..6253c640e0f80 100644 --- a/x-pack/plugins/code/public/monaco/monaco_helper.ts +++ b/x-pack/plugins/code/public/monaco/monaco_helper.ts @@ -29,7 +29,8 @@ export class MonacoHelper { constructor( public readonly container: HTMLElement, - private readonly editorActions: EditorActions + private readonly editorActions: EditorActions, + private urlQuery: string ) { this.handleCopy = this.handleCopy.bind(this); } @@ -47,7 +48,7 @@ export class MonacoHelper { if (chrome.getInjected('enableLangserversDeveloping', false) === true) { this.monaco.languages.registerDefinitionProvider('go', definitionProvider); } - const codeEditorService = new EditorService(); + const codeEditorService = new EditorService(this.getUrlQuery); codeEditorService.setMonacoHelper(this); this.editor = monaco.editor.create( this.container!, @@ -80,7 +81,7 @@ export class MonacoHelper { this.editor!.layout(); }); }); - registerReferencesAction(this.editor); + registerReferencesAction(this.editor, this.getUrlQuery); const hoverController: HoverController = new HoverController(this.editor); hoverController.setReduxActions(this.editorActions); document.addEventListener('copy', this.handleCopy); @@ -89,6 +90,14 @@ export class MonacoHelper { }); } + updateUrlQuery = (q: string) => { + this.urlQuery = q; + }; + + getUrlQuery = () => { + return this.urlQuery; + }; + public destroy = () => { this.monaco = null; document.removeEventListener('copy', this.handleCopy); diff --git a/x-pack/plugins/code/public/monaco/references/references_action.ts b/x-pack/plugins/code/public/monaco/references/references_action.ts index 58926c8008a59..87664aa7b89d1 100644 --- a/x-pack/plugins/code/public/monaco/references/references_action.ts +++ b/x-pack/plugins/code/public/monaco/references/references_action.ts @@ -5,10 +5,14 @@ */ import { editor } from 'monaco-editor'; import queryString from 'querystring'; +import url from 'url'; import { parseSchema } from '../../../common/uri_util'; import { history } from '../../utils/url'; -export function registerReferencesAction(e: editor.IStandaloneCodeEditor) { +export function registerReferencesAction( + e: editor.IStandaloneCodeEditor, + getUrlQuery: () => string +) { e.addAction({ id: 'editor.action.referenceSearch.trigger', label: 'Find All References', @@ -18,7 +22,7 @@ export function registerReferencesAction(e: editor.IStandaloneCodeEditor) { const position = ed.getPosition(); const { uri } = parseSchema(ed.getModel().uri.toString()); const refUrl = `git:/${uri}!L${position.lineNumber - 1}:${position.column - 1}`; - const queries = queryString.parse(location.search); + const queries = url.parse(getUrlQuery(), true).query; const query = queryString.stringify({ ...queries, tab: 'references', diff --git a/x-pack/plugins/code/public/sagas/editor.ts b/x-pack/plugins/code/public/sagas/editor.ts index c7356023afaae..3041c84b6d6e8 100644 --- a/x-pack/plugins/code/public/sagas/editor.ts +++ b/x-pack/plugins/code/public/sagas/editor.ts @@ -8,6 +8,7 @@ import queryString from 'querystring'; import { Action } from 'redux-actions'; import { kfetch } from 'ui/kfetch'; import { TextDocumentPositionParams } from 'vscode-languageserver'; +import Url from 'url'; import { call, put, select, takeEvery, takeLatest } from 'redux-saga/effects'; import { parseGoto, parseLspUrl, toCanonicalUrl } from '../../common/uri_util'; import { FileTree } from '../../model'; @@ -40,6 +41,7 @@ import { lastRequestPathSelector, refUrlSelector, repoScopeSelector, + urlQueryStringSelector, } from '../selectors'; import { history } from '../utils/url'; import { mainRoutePattern } from './patterns'; @@ -67,10 +69,11 @@ export function* watchLspMethods() { yield takeLatest(String(findReferences), handleReferences); } -function handleCloseReferences(action: Action) { +function* handleCloseReferences(action: Action) { if (action.payload) { - const { pathname, search } = history.location; - const queryParams = queryString.parse(search); + const search = yield select(urlQueryStringSelector); + const { pathname } = history.location; + const queryParams = Url.parse(search, true).query; if (queryParams.tab) { delete queryParams.tab; } diff --git a/x-pack/plugins/code/public/selectors/index.ts b/x-pack/plugins/code/public/selectors/index.ts index 80ec8a8d6e803..476c515b48347 100644 --- a/x-pack/plugins/code/public/selectors/index.ts +++ b/x-pack/plugins/code/public/selectors/index.ts @@ -94,3 +94,5 @@ export const createTreeSelector = (path: string) => (state: RootState) => { export const currentRepoSelector = (state: RootState) => state.repository.currentRepository; export const repoScopeSelector = (state: RootState) => state.search.searchOptions.repoScope; + +export const urlQueryStringSelector = (state: RootState) => state.route.match.location.search;