@mongoosejs/studio 0.0.13 → 0.0.15
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/frontend/src/list-mixed/list-mixed.html +6 -3
- package/frontend/src/list-mixed/list-mixed.js +22 -0
- package/frontend/src/list-subdocument/list-subdocument.html +5 -2
- package/frontend/src/list-subdocument/list-subdocument.js +21 -1
- package/frontend/src/modal/modal.css +3 -1
- package/frontend/src/models/models.css +15 -0
- package/frontend/src/models/models.html +18 -2
- package/frontend/src/models/models.js +62 -1
- package/package.json +1 -1
- package/osogolf.js +0 -20
|
@@ -1,4 +1,7 @@
|
|
|
1
|
-
<div class="list-mixed">
|
|
2
|
-
<pre
|
|
3
|
-
|
|
1
|
+
<div class="list-mixed tooltip">
|
|
2
|
+
<pre>
|
|
3
|
+
<code ref="MixedCode" class="language-javascript">{{shortenValue}}</code>
|
|
4
|
+
<span class="tooltiptext" @click.stop="copyText(value)">copy 📋</span>
|
|
5
|
+
</pre>
|
|
6
|
+
</div>
|
|
4
7
|
|
|
@@ -3,6 +3,8 @@
|
|
|
3
3
|
const api = require('../api');
|
|
4
4
|
const template = require('./list-mixed.html');
|
|
5
5
|
|
|
6
|
+
const vanillatoast = require('vanillatoasts');
|
|
7
|
+
|
|
6
8
|
require('../appendCSS')(require('./list-mixed.css'));
|
|
7
9
|
|
|
8
10
|
module.exports = app => app.component('list-mixed', {
|
|
@@ -13,7 +15,27 @@ module.exports = app => app.component('list-mixed', {
|
|
|
13
15
|
return this.value;
|
|
14
16
|
}
|
|
15
17
|
},
|
|
18
|
+
methods: {
|
|
19
|
+
copyText(value) {
|
|
20
|
+
const storage = document.createElement('textarea');
|
|
21
|
+
storage.value = JSON.stringify(value);
|
|
22
|
+
const elem = this.$refs.MixedCode;
|
|
23
|
+
elem.appendChild(storage);
|
|
24
|
+
storage.select();
|
|
25
|
+
storage.setSelectionRange(0, 99999);
|
|
26
|
+
document.execCommand('copy');
|
|
27
|
+
elem.removeChild(storage);
|
|
28
|
+
vanillatoast.create({
|
|
29
|
+
title: 'Text copied!',
|
|
30
|
+
type: 'success',
|
|
31
|
+
timeout: 3000,
|
|
32
|
+
icon: 'images/success.png',
|
|
33
|
+
positionClass: 'bottomRight'
|
|
34
|
+
});
|
|
35
|
+
}
|
|
36
|
+
},
|
|
16
37
|
mounted: function() {
|
|
17
38
|
Prism.highlightElement(this.$refs.MixedCode);
|
|
18
39
|
}
|
|
19
40
|
});
|
|
41
|
+
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
-
<div class="list-subdocument">
|
|
2
|
-
<pre
|
|
1
|
+
<div class="list-subdocument tooltip">
|
|
2
|
+
<pre>
|
|
3
|
+
<code ref="SubDocCode" class="language-javascript">{{shortenValue}}</code>
|
|
4
|
+
<span class="tooltiptext" @click.stop="copyText(value)">copy 📋</span>
|
|
5
|
+
</pre>
|
|
3
6
|
</div>
|
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
const api = require('../api');
|
|
4
4
|
const template = require('./list-subdocument.html');
|
|
5
|
+
const vanillatoast = require('vanillatoasts');
|
|
5
6
|
|
|
6
7
|
require('../appendCSS')(require('./list-subdocument.css'));
|
|
7
8
|
|
|
@@ -13,7 +14,26 @@ module.exports = app => app.component('list-subdocument', {
|
|
|
13
14
|
return this.value;
|
|
14
15
|
}
|
|
15
16
|
},
|
|
17
|
+
methods: {
|
|
18
|
+
copyText(value) {
|
|
19
|
+
const storage = document.createElement('textarea');
|
|
20
|
+
storage.value = JSON.stringify(value);
|
|
21
|
+
const elem = this.$refs.SubDocCode;
|
|
22
|
+
elem.appendChild(storage);
|
|
23
|
+
storage.select();
|
|
24
|
+
storage.setSelectionRange(0, 99999);
|
|
25
|
+
document.execCommand('copy');
|
|
26
|
+
elem.removeChild(storage);
|
|
27
|
+
vanillatoast.create({
|
|
28
|
+
title: 'Text copied!',
|
|
29
|
+
type: 'success',
|
|
30
|
+
timeout: 3000,
|
|
31
|
+
icon: 'images/success.png',
|
|
32
|
+
positionClass: 'bottomRight'
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
},
|
|
16
36
|
mounted: function() {
|
|
17
37
|
Prism.highlightElement(this.$refs.SubDocCode);
|
|
18
38
|
}
|
|
19
|
-
});
|
|
39
|
+
});
|
|
@@ -5,6 +5,11 @@
|
|
|
5
5
|
min-height: calc(100% - 56px);
|
|
6
6
|
}
|
|
7
7
|
|
|
8
|
+
.models button.gray {
|
|
9
|
+
color: black;
|
|
10
|
+
background-color: #eee;
|
|
11
|
+
}
|
|
12
|
+
|
|
8
13
|
.models .model-selector {
|
|
9
14
|
background-color: #eee;
|
|
10
15
|
flex-grow: 0;
|
|
@@ -120,4 +125,14 @@
|
|
|
120
125
|
|
|
121
126
|
.models .loader img {
|
|
122
127
|
height: 4em;
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
.models .documents .buttons {
|
|
131
|
+
display: inline-flex;
|
|
132
|
+
justify-content: space-around;
|
|
133
|
+
align-items: baseline;
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
.models .documents .buttons button:not(:last-child) {
|
|
137
|
+
margin-right: 8px;
|
|
123
138
|
}
|
|
@@ -19,13 +19,14 @@
|
|
|
19
19
|
</div>
|
|
20
20
|
<div class="buttons">
|
|
21
21
|
<button @click="shouldShowExportModal = true">Export</button>
|
|
22
|
+
<button @click="shouldShowFieldModal = true">Fields</button>
|
|
22
23
|
</div>
|
|
23
24
|
</div>
|
|
24
25
|
</div>
|
|
25
26
|
<div class="documents-container">
|
|
26
27
|
<table>
|
|
27
28
|
<thead>
|
|
28
|
-
<th v-for="path in
|
|
29
|
+
<th v-for="path in filteredPaths">
|
|
29
30
|
{{path.path}}
|
|
30
31
|
<span class="path-type">
|
|
31
32
|
({{(path.instance || 'unknown')}})
|
|
@@ -36,7 +37,7 @@
|
|
|
36
37
|
</thead>
|
|
37
38
|
<tbody>
|
|
38
39
|
<tr v-for="document in documents" @click="$router.push('/model/' + currentModel + '/document/' + document._id)" :key="document._id">
|
|
39
|
-
<td v-for="schemaPath in
|
|
40
|
+
<td v-for="schemaPath in filteredPaths">
|
|
40
41
|
<component
|
|
41
42
|
:is="getComponentForPath(schemaPath)"
|
|
42
43
|
:value="getValueForPath(document, schemaPath.path)"
|
|
@@ -61,5 +62,20 @@
|
|
|
61
62
|
</export-query-results>
|
|
62
63
|
</template>
|
|
63
64
|
</modal>
|
|
65
|
+
<modal v-if="shouldShowFieldModal">
|
|
66
|
+
<template v-slot:body>
|
|
67
|
+
<div class="modal-exit" @click="shouldShowFieldModal = false; selectedPaths = [...filteredPaths];">×</div>
|
|
68
|
+
<div v-for="(path, index) in schemaPaths" :key="index" style="margin-bottom: 0.5em">
|
|
69
|
+
<input type="checkbox" :id="'path.path'+index" @change="addOrRemove(path)" :value="path.path" :checked="isSelected(path.path)" />
|
|
70
|
+
<label :for="'path' + index">{{path.path}}</label>
|
|
71
|
+
</div>
|
|
72
|
+
<div style="margin-top: 1em">
|
|
73
|
+
<button type="submit" @click="filterDocuments()" style="color: black;margin-right: 0.5em">Filter Selection</button>
|
|
74
|
+
<button type="submit" @click="deselectAll()" class="gray" style="margin-right: 0.5em">Deselect All</button>
|
|
75
|
+
<button type="submit" @click="resetDocuments()" class="gray">Cancel</button>
|
|
76
|
+
|
|
77
|
+
</div>
|
|
78
|
+
</template>
|
|
79
|
+
</modal>
|
|
64
80
|
</div>
|
|
65
81
|
</div>
|
|
@@ -19,6 +19,8 @@ module.exports = app => app.component('models', {
|
|
|
19
19
|
currentModel: null,
|
|
20
20
|
documents: [],
|
|
21
21
|
schemaPaths: [],
|
|
22
|
+
filteredPaths: [],
|
|
23
|
+
selectedPaths: [],
|
|
22
24
|
numDocuments: 0,
|
|
23
25
|
status: 'loading',
|
|
24
26
|
loadedAllDocs: false,
|
|
@@ -27,6 +29,7 @@ module.exports = app => app.component('models', {
|
|
|
27
29
|
filter: null,
|
|
28
30
|
searchText: '',
|
|
29
31
|
shouldShowExportModal: false,
|
|
32
|
+
shouldShowFieldModal: false,
|
|
30
33
|
shouldExport: {},
|
|
31
34
|
sortBy: {},
|
|
32
35
|
query: {},
|
|
@@ -62,6 +65,16 @@ module.exports = app => app.component('models', {
|
|
|
62
65
|
await this.getDocuments();
|
|
63
66
|
}
|
|
64
67
|
|
|
68
|
+
const hashUrl = window.location.hash.replace(/^#/, '');
|
|
69
|
+
if (hashUrl.indexOf('?') !== -1) {
|
|
70
|
+
const searchParams = new URLSearchParams(
|
|
71
|
+
hashUrl.slice(hashUrl.indexOf('?') + 1)
|
|
72
|
+
);
|
|
73
|
+
if (searchParams.has('fields')) {
|
|
74
|
+
this.filteredPaths = searchParams.get('fields').split(',').map(path => ({ path }));
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
|
|
65
78
|
this.status = 'loaded';
|
|
66
79
|
},
|
|
67
80
|
methods: {
|
|
@@ -79,7 +92,6 @@ module.exports = app => app.component('models', {
|
|
|
79
92
|
skip: this.documents.length,
|
|
80
93
|
limit
|
|
81
94
|
});
|
|
82
|
-
console.log('FX', docs.length, limit)
|
|
83
95
|
if (docs.length < limit) {
|
|
84
96
|
this.loadedAllDocs = true;
|
|
85
97
|
}
|
|
@@ -143,6 +155,55 @@ module.exports = app => app.component('models', {
|
|
|
143
155
|
for (const { path } of this.schemaPaths) {
|
|
144
156
|
this.shouldExport[path] = true;
|
|
145
157
|
}
|
|
158
|
+
|
|
159
|
+
this.filteredPaths = [...this.schemaPaths];
|
|
160
|
+
this.selectedPaths = [...this.schemaPaths];
|
|
161
|
+
},
|
|
162
|
+
addOrRemove(path) {
|
|
163
|
+
const exists = this.selectedPaths.findIndex(x => x.path == path.path);
|
|
164
|
+
if (exists > 0) { // remove
|
|
165
|
+
this.selectedPaths.splice(exists, 1);
|
|
166
|
+
} else { // add
|
|
167
|
+
this.selectedPaths.push(path);
|
|
168
|
+
this.selectedPaths = Object.keys(this.selectedPaths).sort((k1, k2) => {
|
|
169
|
+
if (k1 === '_id' && k2 !== '_id') {
|
|
170
|
+
return -1;
|
|
171
|
+
}
|
|
172
|
+
if (k1 !== '_id' && k2 === '_id') {
|
|
173
|
+
return 1;
|
|
174
|
+
}
|
|
175
|
+
return 0;
|
|
176
|
+
}).map(key => this.selectedPaths[key]);
|
|
177
|
+
}
|
|
178
|
+
},
|
|
179
|
+
filterDocuments() {
|
|
180
|
+
this.filteredPaths = [...this.selectedPaths];
|
|
181
|
+
this.shouldShowFieldModal = false;
|
|
182
|
+
const selectedParams = this.filteredPaths.map(x => x.path).join(',');
|
|
183
|
+
|
|
184
|
+
const hashUrl = window.location.hash.replace(/^#/, '');
|
|
185
|
+
if (hashUrl.indexOf('?') === -1) {
|
|
186
|
+
window.history.pushState({}, '', window.location.pathname + '#' + hashUrl + '?fields=' + selectedParams);
|
|
187
|
+
} else {
|
|
188
|
+
const searchParams = new URLSearchParams(
|
|
189
|
+
hashUrl.indexOf('?') === -1 ? '' : hashUrl.slice(hashUrl.indexOf('?') + 1)
|
|
190
|
+
);
|
|
191
|
+
const hashUrlWithoutSearchParams = hashUrl.slice(0, hashUrl.indexOf('?'));
|
|
192
|
+
|
|
193
|
+
searchParams.set('fields', selectedParams);
|
|
194
|
+
window.history.pushState({}, '', window.location.pathname + '#' + hashUrlWithoutSearchParams + '?' + searchParams);
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
},
|
|
198
|
+
resetDocuments() {
|
|
199
|
+
this.selectedPaths = [...this.filteredPaths];
|
|
200
|
+
this.shouldShowFieldModal = false;
|
|
201
|
+
},
|
|
202
|
+
deselectAll() {
|
|
203
|
+
this.selectedPaths = [];
|
|
204
|
+
},
|
|
205
|
+
isSelected(path) {
|
|
206
|
+
return this.selectedPaths.find(x => x.path == path);
|
|
146
207
|
},
|
|
147
208
|
getComponentForPath(schemaPath) {
|
|
148
209
|
if (schemaPath.instance === 'Array') {
|
package/package.json
CHANGED
package/osogolf.js
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
'use strict';
|
|
2
|
-
|
|
3
|
-
const db = require('../../voltmobile/core-api/backend/db');
|
|
4
|
-
const express = require('express');
|
|
5
|
-
const studio = require('./express');
|
|
6
|
-
|
|
7
|
-
run().catch(err => {
|
|
8
|
-
console.error(err);
|
|
9
|
-
process.exit(-1);
|
|
10
|
-
});
|
|
11
|
-
|
|
12
|
-
async function run() {
|
|
13
|
-
const app = express();
|
|
14
|
-
const conn = await db();
|
|
15
|
-
|
|
16
|
-
app.use('/studio', studio('/studio/api', conn));
|
|
17
|
-
|
|
18
|
-
await app.listen(3002);
|
|
19
|
-
console.log('Listening on port 3002');
|
|
20
|
-
}
|