瀏覽代碼

SONAR-7149 display a list of sub-components when start searching

tags/5.4-M4
Stas Vilchik 8 年之前
父節點
當前提交
88726dbd19

+ 9
- 2
server/sonar-web/src/main/js/apps/code/actions/index.js 查看文件

@@ -148,7 +148,14 @@ function retrieveComponent (componentKey, bucket) {

let requestTree = (query, baseComponent, dispatch) => {
dispatch(startFetching());
return getTree(baseComponent.key, { q: query, s: 'qualifier,name' })

const params = { s: 'qualifier,name', qualifiers: 'BRC,FIL,UTS' };

if (query) {
params.q = query;
}

return getTree(baseComponent.key, params)
.then(r => dispatch(searchAction(r.components)))
.then(() => dispatch(stopFetching()));
};
@@ -199,7 +206,7 @@ export function browse (componentKey) {
export function search (query, baseComponent) {
return dispatch => {
dispatch(updateQueryAction(query));
if (query) {
if (query != null) {
requestTree(query, baseComponent, dispatch);
} else {
dispatch(searchAction(null));

+ 30
- 3
server/sonar-web/src/main/js/apps/code/components/Code.js 查看文件

@@ -25,7 +25,7 @@ import Components from './Components';
import Breadcrumbs from './Breadcrumbs';
import SourceViewer from './SourceViewer';
import Search from './Search';
import { initComponent, browse } from '../actions';
import { initComponent, browse, search } from '../actions';
import { translate } from '../../../helpers/l10n';


@@ -33,8 +33,12 @@ class Code extends Component {
componentDidMount () {
const { dispatch, component, routing } = this.props;
const selectedKey = (routing.path && decodeURIComponent(routing.path.substr(1))) || component.key;

dispatch(initComponent(component.key, component.breadcrumbs))
.then(() => dispatch(browse(selectedKey)));

this.handleKeyDown = this.handleKeyDown.bind(this);
this.attachShortcuts();
}

componentWillReceiveProps (nextProps) {
@@ -47,11 +51,32 @@ class Code extends Component {
}
}

componentWillUnmount () {
this.removeShortcuts();
}

attachShortcuts () {
window.addEventListener('keyup', this.handleKeyDown);
}

removeShortcuts () {
window.removeEventListener('keyup', this.handleKeyDown);
}

handleBrowse (component) {
const { dispatch } = this.props;
dispatch(browse(component.key));
}

handleKeyDown (e) {
const { dispatch, component, searchQuery } = this.props;

// "t" key
if (e.keyCode === 84 && searchQuery == null) {
dispatch(search('', component));
}
}

render () {
const {
fetching,
@@ -65,7 +90,7 @@ class Code extends Component {
const shouldShowSearchResults = !!searchResults;
const shouldShowSourceViewer = !!sourceViewer;
const shouldShowComponents = !shouldShowSearchResults && !shouldShowSourceViewer && components;
const shouldShowBreadcrumbs = !shouldShowSearchResults && Array.isArray(breadcrumbs) && breadcrumbs.length > 1;
const shouldShowBreadcrumbs = !shouldShowSearchResults && Array.isArray(breadcrumbs) && breadcrumbs.length > 1;

const componentsClassName = classNames('spacer-top', { 'new-loading': fetching });

@@ -80,7 +105,9 @@ class Code extends Component {
<i className="spinner"/>
</div>

<Search component={this.props.component}/>
<div className="page-actions">
<Search component={this.props.component}/>
</div>
</header>

{errorMessage && (

+ 55
- 15
server/sonar-web/src/main/js/apps/code/components/Search.js 查看文件

@@ -21,40 +21,80 @@ import React, { Component } from 'react';
import { connect } from 'react-redux';

import { search } from '../actions';
import { translate } from '../../../helpers/l10n';


class Search extends Component {
componentDidMount () {
this.refs.input.focus();
this.focusSearchInput();
}

componentDidUpdate () {
this.focusSearchInput();
}

focusSearchInput () {
if (this.refs.input) {
this.refs.input.focus();
}
}

handleSearch (e) {
e.preventDefault();
const { dispatch, component } = this.props;
const query = this.refs.input.value;
const query = this.refs.input ? this.refs.input.value : '';
dispatch(search(query, component));
}

handleStopSearch (e) {
e.preventDefault();
const { dispatch } = this.props;
dispatch(search(null));
}

handleKeyDown (e) {
const { dispatch } = this.props;

// "escape" key
if (e.keyCode === 27) {
dispatch(search(null));
}
}

render () {
const { query } = this.props;
const hasQuery = query != null;

return (
<form
onSubmit={this.handleSearch.bind(this)}
className="search-box code-search-box">
<button className="search-box-submit button-clean">
<i className="icon-search"></i>
</button>
<input
ref="input"
onChange={this.handleSearch.bind(this)}
value={query}
className="search-box-input"
type="search"
name="q"
placeholder="Search"
maxLength="100"
autoComplete="off"/>
{hasQuery && (
<input
ref="input"
onChange={this.handleSearch.bind(this)}
onKeyDown={this.handleKeyDown.bind(this)}
value={query}
className="search-box-input"
type="search"
name="q"
placeholder="Search"
maxLength="100"
autoComplete="off"
style={{ visibility: hasQuery ? 'visible': 'hidden' }}/>
)}
{!hasQuery && (
<button className="search-box-submit">
{translate('search_verb')}
</button>
)}
{hasQuery && (
<button
className="search-box-submit"
onClick={this.handleStopSearch.bind(this)}>
{translate('cancel')}
</button>
)}
</form>
);
}

+ 2
- 2
server/sonar-web/src/main/js/apps/code/reducers/index.js 查看文件

@@ -76,7 +76,7 @@ export const initialState = {
breadcrumbs: null,
sourceViewer: null,
searchResults: null,
searchQuery: '',
searchQuery: null,
coverageMetric: null,
baseBreadcrumbs: [],
errorMessage: null
@@ -104,7 +104,7 @@ export function current (state = initialState, action) {
breadcrumbs,
sourceViewer,
searchResults: null,
searchQuery: '',
searchQuery: null,
errorMessage: null
};
case SEARCH:

+ 14
- 7
server/sonar-web/src/main/js/main/nav/templates/nav-shortcuts-help.hbs 查看文件

@@ -23,14 +23,21 @@
</ul>
</div>

<h3 class="shortcuts-section-title">{{t 'shortcuts.section.rules'}}</h3>
<div class="spacer-bottom">
<h3 class="shortcuts-section-title">{{t 'shortcuts.section.rules'}}</h3>
<ul class="shortcuts-list">
<li><span class="shortcut-button">&uarr;</span> <span
class="shortcut-button">&darr;</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.navigate_between_rules'}}</li>
<li><span class="shortcut-button">&rarr;</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.open_details'}}</li>
<li><span class="shortcut-button">&larr;</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.return_to_list'}}</li>
<li><span class="shortcut-button">a</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.activate'}}</li>
<li><span class="shortcut-button">d</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.deactivate'}}</li>
</ul>
</div>

<h3 class="shortcuts-section-title">{{t 'shortcuts.section.code'}}</h3>
<ul class="shortcuts-list">
<li><span class="shortcut-button">&uarr;</span> <span
class="shortcut-button">&darr;</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.navigate_between_rules'}}</li>
<li><span class="shortcut-button">&rarr;</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.open_details'}}</li>
<li><span class="shortcut-button">&larr;</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.return_to_list'}}</li>
<li><span class="shortcut-button">a</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.activate'}}</li>
<li><span class="shortcut-button">d</span> &nbsp;&nbsp; {{t 'shortcuts.section.rules.deactivate'}}</li>
<li><span class="shortcut-button">t</span> &nbsp;&nbsp; {{t 'shortcuts.section.code.search'}}</li>
</ul>
</div>


+ 1
- 1
server/sonar-web/tests/apps/code/store-test.js 查看文件

@@ -225,7 +225,7 @@ describe('Code :: Store', () => {
it('should be reset', () => {
const stateBefore = Object.assign({}, initialState, { searchQuery: 'query' });
expect(current(stateBefore, browseAction(exampleComponent)).searchQuery)
.to.equal('');
.to.be.null;
});
});
describe('errorMessage', () => {

Loading…
取消
儲存