mirror of
https://github.com/weaveworks/scope.git
synced 2026-07-22 06:46:50 +00:00
Node linking added
This commit is contained in:
@@ -1,15 +1,14 @@
|
||||
import debug from 'debug';
|
||||
import trimStart from 'lodash/trimStart';
|
||||
import reduce from 'lodash/reduce';
|
||||
import map from 'lodash/map';
|
||||
import each from 'lodash/each';
|
||||
import { fromJS } from 'immutable';
|
||||
import find from 'lodash/find';
|
||||
|
||||
import ActionTypes from '../constants/action-types';
|
||||
import { saveGraph } from '../utils/file-utils';
|
||||
import { modulo } from '../utils/math-utils';
|
||||
import { updateRoute } from '../utils/router-utils';
|
||||
import { parseQuery, searchTopology } from '../utils/search-utils';
|
||||
import { updateRoute, parseUrlQuery } from '../utils/router-utils';
|
||||
import { parseQuery } from '../utils/search-utils';
|
||||
import { bufferDeltaUpdate, resumeUpdate,
|
||||
resetUpdateBuffer } from '../utils/update-buffer-utils';
|
||||
import { doControlRequest, getAllNodes, getNodesDelta, getNodeDetails,
|
||||
@@ -17,6 +16,7 @@ import { doControlRequest, getAllNodes, getNodesDelta, getNodeDetails,
|
||||
import { getActiveTopologyOptions,
|
||||
getCurrentTopologyUrl } from '../utils/topology-utils';
|
||||
import { storageSet } from '../utils/storage-utils';
|
||||
import { waterfall } from '../utils/async-utils';
|
||||
|
||||
const log = debug('scope:app-actions');
|
||||
|
||||
@@ -687,34 +687,9 @@ export function toggleTroubleshootingMenu(ev) {
|
||||
};
|
||||
}
|
||||
|
||||
function convertQueryString(paramString) {
|
||||
const pairs = trimStart(paramString, '?').split('&');
|
||||
return reduce(pairs, (result, pair) => {
|
||||
const [k, v] = pair.split('=');
|
||||
result[k] = v;
|
||||
return result;
|
||||
}, {});
|
||||
}
|
||||
|
||||
function waterfall(series, target, cb) {
|
||||
function next(result) {
|
||||
const fn = series.shift();
|
||||
if (fn) {
|
||||
try {
|
||||
fn(result, next);
|
||||
} catch (e) {
|
||||
cb(e);
|
||||
}
|
||||
} else {
|
||||
cb(null, result);
|
||||
}
|
||||
}
|
||||
next(target, next);
|
||||
}
|
||||
|
||||
export function translateUrlParamsToViewState(queryString) {
|
||||
return () => {
|
||||
const params = convertQueryString(queryString);
|
||||
return (dispatch) => {
|
||||
const params = parseUrlQuery(queryString);
|
||||
if (params.node) {
|
||||
// Get the list of topologies
|
||||
fetch('api/topology').then(response => response.json())
|
||||
@@ -729,6 +704,7 @@ export function translateUrlParamsToViewState(queryString) {
|
||||
.then((json) => {
|
||||
// Append each node in the list to the result object.
|
||||
each(json.nodes, (node, id) => {
|
||||
node.topology = topo;
|
||||
result[id] = node;
|
||||
});
|
||||
cb(result);
|
||||
@@ -738,9 +714,14 @@ export function translateUrlParamsToViewState(queryString) {
|
||||
// Run the series
|
||||
waterfall(series, {}, (err, nodes) => {
|
||||
if (err) { throw err; }
|
||||
// const collection = flatten(map(r, ({nodes}) => values(nodes)));
|
||||
const result = searchTopology(fromJS(nodes), { query: params.node });
|
||||
console.log(result.toJS());
|
||||
const match = find(nodes, n => n.label === params.node);
|
||||
|
||||
if (match) {
|
||||
dispatch({
|
||||
type: ActionTypes.ROUTE_FROM_LINK,
|
||||
node: match
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
@@ -47,6 +47,7 @@ const ACTION_TYPES = [
|
||||
'RECEIVE_ERROR',
|
||||
'RESET_LOCAL_VIEW_STATE',
|
||||
'ROUTE_TOPOLOGY',
|
||||
'ROUTE_FROM_LINK',
|
||||
'SELECT_METRIC',
|
||||
'SHOW_HELP',
|
||||
'SET_EXPORTING_GRAPH',
|
||||
|
||||
@@ -16,10 +16,15 @@ const store = configureStore();
|
||||
|
||||
function renderApp() {
|
||||
const App = require('./components/app').default;
|
||||
ReactDOM.render((
|
||||
<Provider store={store}>
|
||||
const DevApp = () => (
|
||||
<div>
|
||||
<App />
|
||||
<DevTools />
|
||||
</div>
|
||||
);
|
||||
ReactDOM.render((
|
||||
<Provider store={store}>
|
||||
<DevApp />
|
||||
</Provider>
|
||||
), document.getElementById('app'));
|
||||
}
|
||||
|
||||
@@ -714,6 +714,19 @@ export function rootReducer(state = initialState, action) {
|
||||
return state.set('showingTroubleshootingMenu', !state.get('showingTroubleshootingMenu'));
|
||||
}
|
||||
|
||||
case ActionTypes.ROUTE_FROM_LINK: {
|
||||
const { id, topology } = action.node;
|
||||
const topologyId = state.get('topologies').find(t => t.get('name') === topology.name).get('id');
|
||||
|
||||
state = state.setIn(['nodeDetails', id], {
|
||||
id,
|
||||
label: action.node.label,
|
||||
origin: null,
|
||||
topologyId,
|
||||
});
|
||||
return state.set('currentTopologyId', topologyId).set('selectedNodeId', id);
|
||||
}
|
||||
|
||||
default: {
|
||||
return state;
|
||||
}
|
||||
|
||||
@@ -1,14 +0,0 @@
|
||||
import { translateUrlParams } from '../router-utils';
|
||||
|
||||
describe('router-utils', () => {
|
||||
it('translates a query to a view state', () => {
|
||||
// const dispatch = createSpy();
|
||||
// const state = Object.assign({}, initialState, {
|
||||
// nodes: [{node_1: 'some_id'}]
|
||||
// });
|
||||
// window.location.search = '?node=node_1';
|
||||
// const page = getRouter(dispatch, state);
|
||||
// expect(page).toBeTruthy();
|
||||
translateUrlParams('?key=value&otherkey=othervalue', []);
|
||||
});
|
||||
});
|
||||
16
client/app/scripts/utils/async-utils.js
Normal file
16
client/app/scripts/utils/async-utils.js
Normal file
@@ -0,0 +1,16 @@
|
||||
|
||||
export function waterfall(series, target, cb) {
|
||||
function next(result) {
|
||||
const fn = series.shift();
|
||||
if (fn) {
|
||||
try {
|
||||
fn(result, next);
|
||||
} catch (e) {
|
||||
cb(e);
|
||||
}
|
||||
} else {
|
||||
cb(null, result);
|
||||
}
|
||||
}
|
||||
next(target, next);
|
||||
}
|
||||
@@ -1,4 +1,6 @@
|
||||
import page from 'page';
|
||||
import reduce from 'lodash/reduce';
|
||||
import trimStart from 'lodash/trimStart';
|
||||
|
||||
import { route } from '../actions/app-actions';
|
||||
import { storageGet, storageSet } from './storage-utils';
|
||||
@@ -71,7 +73,6 @@ export function updateRoute(getState) {
|
||||
.replace('#!/state/', '')
|
||||
.replace('#!/', '') || '{}';
|
||||
const prevState = JSON.parse(decodeURL(urlStateString));
|
||||
|
||||
// back up state in storage as well
|
||||
storageSet(STORAGE_STATE_KEY, stateUrl);
|
||||
|
||||
@@ -86,7 +87,6 @@ export function updateRoute(getState) {
|
||||
export function getRouter(dispatch, initialState) {
|
||||
// strip any trailing '/'s.
|
||||
page.base(window.location.pathname.replace(/\/$/, ''));
|
||||
|
||||
page('/', () => {
|
||||
// recover from storage state on empty URL
|
||||
const storageState = storageGet(STORAGE_STATE_KEY);
|
||||
@@ -108,3 +108,12 @@ export function getRouter(dispatch, initialState) {
|
||||
|
||||
return page;
|
||||
}
|
||||
|
||||
export function parseUrlQuery(queryString) {
|
||||
const pairs = trimStart(queryString, '?').split('&');
|
||||
return reduce(pairs, (result, pair) => {
|
||||
const [k, v] = pair.split('=');
|
||||
result[k] = v;
|
||||
return result;
|
||||
}, {});
|
||||
}
|
||||
|
||||
@@ -76,6 +76,7 @@ function findNodeMatch(nodeMatches, keyPath, text, query, prefix, label, truncat
|
||||
{text, label, start: index, length: firstMatch.length, truncate});
|
||||
}
|
||||
}
|
||||
|
||||
return nodeMatches;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user