Skip to content

Commit 59e04e5

Browse files
committed
Merge pull request #106 from 10gen/INT-456-QB-backwards-pass
INT-456 QB improvements
2 parents c3f5253 + 9ce87b3 commit 59e04e5

File tree

20 files changed

+1757
-797
lines changed

20 files changed

+1757
-797
lines changed

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@
8686
"moment": "^2.10.3",
8787
"mongodb-extended-json": "^1.3.1",
8888
"mongodb-language-model": "^0.2.1",
89-
"mongodb-schema": "^3.2.1",
89+
"mongodb-schema": "^3.3.0",
9090
"mousetrap": "^1.5.3",
9191
"numeral": "^1.5.3",
9292
"octicons": "https://github.com/github/octicons/archive/v2.2.0.tar.gz",

src/app.js

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,9 +57,13 @@ var Application = View.extend({
5757
*/
5858
instance: 'state',
5959
/**
60-
* @see models/query-options.js
60+
* query options in sync with the data, @see models/query-options.js
6161
*/
6262
queryOptions: 'state',
63+
/**
64+
* temporary query options during query building, @see models/query-options.js
65+
*/
66+
volatileQueryOptions: 'state',
6367
/**
6468
* @see http://learn.humanjavascript.com/react-ampersand/creating-a-router-and-pages
6569
*/
@@ -148,6 +152,7 @@ app.extend({
148152
this.connection = new Connection();
149153
this.connection.use(uri);
150154
this.queryOptions = new QueryOptions();
155+
this.volatileQueryOptions = new QueryOptions();
151156
this.instance = new MongoDBInstance();
152157

153158
// feature flags

src/field-list/index.js

Lines changed: 1 addition & 83 deletions
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,6 @@ var debug = require('debug')('scout:field-list');
77
var _ = require('lodash');
88
var raf = require('raf');
99
var SampledSchema = require('../models/sampled-schema');
10-
var app = require('ampersand-app');
11-
12-
var LeafClause = require('mongodb-language-model').LeafClause;
13-
var Query = require('mongodb-language-model').Query;
1410

1511
function handleCaret(el) {
1612
var $el = $(el);
@@ -41,9 +37,6 @@ var FieldView = View.extend({
4137
fieldListView: 'view',
4238
arrayFieldListView: 'view'
4339
},
44-
children: {
45-
refineClause: LeafClause
46-
},
4740
bindings: {
4841
'model.name': {
4942
hook: 'name'
@@ -93,7 +86,6 @@ var FieldView = View.extend({
9386
}), {
9487
silent: true
9588
});
96-
this.listenTo(this.fieldListView, 'change:refineQuery', this.onRefineClause);
9789
return this.fieldListView;
9890
}
9991
},
@@ -108,64 +100,26 @@ var FieldView = View.extend({
108100
}), {
109101
silent: true
110102
});
111-
this.listenTo(this.arrayFieldListView, 'change:refineQuery', this.onRefineClause);
112103
return this.arrayFieldListView;
113104
}
114105
}
115106
},
116107
initialize: function() {
117108
this.listenTo(this, 'change:visible', this.renderMinicharts);
118-
this.refineClause.key.content = this.model.name;
119109
},
120110
render: function() {
121111
this.renderWithTemplate(this);
122112
this.viewSwitcher = new ViewSwitcher(this.queryByHook('minichart-container'));
123113
},
124-
onRefineClause: function(who) {
125-
if (who.getType() === 'MinichartView') {
126-
this.refineClause.value = who.refineValue;
127-
}
128-
this.parent.trigger('refine', this);
129-
},
130-
prefixClauseKey: function(clause) {
131-
var newClause = new LeafClause();
132-
newClause.key.content = this.model.name + '.' + clause.key.buffer;
133-
newClause.value = clause.value;
134-
return newClause;
135-
},
136-
getClauses: function() {
137-
var clauses = [];
138-
if (this.fieldListView) {
139-
this.fieldListView.refineQuery.clauses.each(function(clause) {
140-
if (clause.valid) {
141-
clauses.push(this.prefixClauseKey(clause));
142-
}
143-
}.bind(this));
144-
}
145-
if (this.arrayFieldListView) {
146-
this.arrayFieldListView.refineQuery.clauses.each(function(clause) {
147-
if (clause.valid) {
148-
clauses.push(this.prefixClauseKey(clause));
149-
}
150-
}.bind(this));
151-
}
152-
if (this.refineClause.valid) {
153-
clauses.push(this.refineClause);
154-
}
155-
return clauses;
156-
},
157114
renderMinicharts: function() {
158115
if (!this.type_model) {
159116
this.type_model = this.model.types.at(0);
160117
}
161-
162118
debug('setting miniview for type_model_id `%s`', this.type_model.getId());
163119
this.minichartView = new MinichartView({
164120
model: this.type_model,
165121
parent: this
166122
});
167-
this.refineClause.value = this.minichartView.refineValue;
168-
this.listenTo(this.minichartView, 'change:refineValue', this.onRefineClause);
169123
this.viewSwitcher.set(this.minichartView);
170124
},
171125
click: function(evt) {
@@ -178,15 +132,7 @@ var FieldView = View.extend({
178132
FieldListView = View.extend({
179133
modelType: 'FieldListView',
180134
session: {
181-
fieldCollectionView: 'view',
182-
refineQuery: {
183-
type: 'state',
184-
required: true,
185-
default: function() {
186-
return new Query();
187-
}
188-
},
189-
queryContext: 'object'
135+
fieldCollectionView: 'view'
190136
},
191137
template: require('./index.jade'),
192138
initialize: function() {
@@ -195,36 +141,8 @@ FieldListView = View.extend({
195141
} else {
196142
this.listenTo(this.parent, 'change:visible', this.makeFieldVisible);
197143
}
198-
this.on('refine', this.onRefineQuery);
199-
if (this.parent.getType() === 'Collection') {
200-
// I'm the global FieldListView, remembering query context
201-
this.queryContext = _.clone(app.queryOptions.query);
202-
}
203-
},
204-
onRefineQuery: function() {
205-
var views = this.fieldCollectionView.views;
206-
var clauses = _.flatten(_.map(views, function(view) {
207-
return view.getClauses();
208-
}));
209-
this.refineQuery = new Query({
210-
clauses: clauses
211-
});
212-
if (this.parent.getType() === 'Collection') {
213-
// fill clauses with query context unless they are further refined by user
214-
this.queryContext.clauses.each(function(clause) {
215-
this.refineQuery.clauses.add(clause);
216-
// if (!_.find(clauses, function(cl) {
217-
// return cl.id === clause.id;
218-
// })) {
219-
// clauses.push(clause);
220-
// }
221-
}.bind(this));
222-
// I'm the global FieldListView, changing query in app
223-
app.queryOptions.query = this.refineQuery;
224-
}
225144
},
226145
makeFieldVisible: function() {
227-
this.queryContext = _.clone(app.queryOptions.query);
228146
var views = this.fieldCollectionView.views;
229147
_.each(views, function(field_view) {
230148
raf(function() {

src/home/collection.js

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,10 @@ var RefineBarView = require('../refine-view');
66
var SamplingMessageView = require('../sampling-message');
77
var MongoDBCollection = require('../models/mongodb-collection');
88
var SampledSchema = require('../models/sampled-schema');
9-
var debug = require('debug')('scout:home:collection');
109
var app = require('ampersand-app');
1110

11+
var debug = require('debug')('scout:home:collection');
12+
1213
var MongoDBCollectionView = View.extend({
1314
modelType: 'Collection',
1415
template: require('./collection.jade'),
@@ -76,6 +77,7 @@ var MongoDBCollectionView = View.extend({
7677
}
7778
this.visible = true;
7879
app.queryOptions.reset();
80+
app.volatileQueryOptions.reset();
7981

8082
this.schema.ns = this.model._id = ns;
8183
debug('updating namespace to `%s`', ns);
@@ -90,6 +92,9 @@ var MongoDBCollectionView = View.extend({
9092
options.message = 'Analyzing documents...';
9193
this.schema.refine(options);
9294
},
95+
/**
96+
* handler for opening the document viewer sidebar.
97+
*/
9398
onSplitterClick: function() {
9499
this.toggle('sidebar_open');
95100
},
@@ -110,7 +115,8 @@ var MongoDBCollectionView = View.extend({
110115
var refineBarView = new RefineBarView({
111116
el: el,
112117
parent: this,
113-
model: app.queryOptions
118+
queryOptions: app.queryOptions,
119+
volatileQueryOptions: app.volatileQueryOptions
114120
});
115121
this.listenTo(refineBarView, 'submit', this.onQueryChanged);
116122
return refineBarView;

src/minicharts/d3fns/boolean.js

Lines changed: 67 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -2,43 +2,79 @@ var d3 = require('d3');
22
var _ = require('lodash');
33
var few = require('./few');
44
var shared = require('./shared');
5+
// var debug = require('debug')('scout:minicharts:boolean');
56

6-
var minicharts_d3fns_boolean = function(opts) {
7-
var values = opts.model.values.toJSON();
8-
9-
// group by true/false
10-
var data = _(values)
11-
.groupBy(function(d) {
12-
return d;
13-
})
14-
.defaults({
15-
false: [],
16-
true: []
17-
})
18-
.map(function(v, k) {
19-
return {
20-
label: k,
21-
value: k === 'true',
22-
count: v.length
23-
};
24-
})
25-
.sortByOrder('label', [false]) // order: false, true
26-
.value();
27-
7+
var minicharts_d3fns_boolean = function() {
8+
// --- beginning chart setup ---
9+
var width = 400;
10+
var height = 100;
11+
var options = {
12+
view: null
13+
};
14+
var fewChart = few();
2815
var margin = shared.margin;
16+
// --- end chart setup ---
17+
18+
function chart(selection) {
19+
selection.each(function(data) {
20+
var el = d3.select(this);
21+
var innerWidth = width - margin.left - margin.right;
22+
var innerHeight = height - margin.top - margin.bottom;
23+
24+
// group by true/false
25+
var grouped = _(data)
26+
.groupBy(function(d) {
27+
return d;
28+
})
29+
.defaults({
30+
false: [],
31+
true: []
32+
})
33+
.map(function(v, k) {
34+
return {
35+
label: k,
36+
value: k === 'true',
37+
count: v.length
38+
};
39+
})
40+
.sortByOrder('label', [false]) // order: false, true
41+
.value();
42+
43+
fewChart
44+
.width(innerWidth)
45+
.height(innerHeight)
46+
.options(options);
47+
48+
var g = el.selectAll('g').data([grouped]);
49+
50+
// append g element if it doesn't exist yet
51+
g.enter()
52+
.append('g')
53+
.attr('transform', 'translate(' + margin.left + ',' + margin.top + ')');
54+
55+
g.call(fewChart);
56+
});
57+
}
2958

30-
var width = opts.width - margin.left - margin.right;
31-
var height = opts.height - margin.top - margin.bottom;
32-
var el = opts.el;
59+
chart.width = function(value) {
60+
if (!arguments.length) return width;
61+
width = value;
62+
return chart;
63+
};
3364

34-
// clear el first
35-
d3.select(el).selectAll('*').remove();
65+
chart.height = function(value) {
66+
if (!arguments.length) return height;
67+
height = value;
68+
return chart;
69+
};
3670

37-
var g = d3.select(el)
38-
.append('g')
39-
.attr('transform', 'translate(' + margin.left + ',' + margin.top + ')');
71+
chart.options = function(value) {
72+
if (!arguments.length) return options;
73+
_.assign(options, value);
74+
return chart;
75+
};
4076

41-
few(data, opts.view, g, width, height);
77+
return chart;
4278
};
4379

4480
module.exports = minicharts_d3fns_boolean;

0 commit comments

Comments
 (0)