waibu-db 1.1.9 → 1.1.11

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.
@@ -1,5 +1,4 @@
1
- <c:form>
2
- <!-- include waibuDb.partial:/crud/_form.html -->
1
+ <c:wdb-form id="main-form" method="POST" enctype="multipart/form-data">
3
2
  <!-- include waibuDb.partial:/crud/_add-btns.html -->
4
- </c:form>
3
+ </c:wdb-form>
5
4
  <!-- include waibuDb.partial:/crud/_addons.html -->
@@ -1,5 +1,3 @@
1
- <c:div id="main-form">
2
- <!-- include waibuDb.partial:/crud/_form.html -->
3
- </c:div>
1
+ <c:wdb-form tag="div" id="main-form" />
4
2
  <!-- include waibuDb.partial:/crud/_details-btns.html -->
5
3
  <!-- include waibuDb.partial:/crud/_addons.html -->
@@ -1,5 +1,4 @@
1
- <c:form id="main-form">
2
- <!-- include waibuDb.partial:/crud/_form.html -->
1
+ <c:wdb-form id="main-form" method="POST" enctype="multipart/form-data">
3
2
  <!-- include waibuDb.partial:/crud/_edit-btns.html -->
4
- </c:form>
3
+ </c:wdb-form>
5
4
  <!-- include waibuDb.partial:/crud/_addons.html -->
@@ -5,7 +5,7 @@ async function addHandler ({ req, reply, model, params = {}, template, addOnsHan
5
5
  const { pick, map, merge, defaultsDeep, omit, isEmpty } = this.lib._
6
6
  const options = {}
7
7
  model = model ?? pascalCase(req.params.model)
8
- const { schema } = await getSchemaExt(model, 'add', options)
8
+ const { schema } = await getSchemaExt(model, 'add', { params })
9
9
  if (schema.disabled.includes('create')) return reply.view(templateDisabled, { action: 'add' })
10
10
  // req.query.attachment = true
11
11
  options.fields = schema.view.fields
@@ -5,7 +5,7 @@ async function deleteHandler ({ req, reply, model, params = {}, templateDisabled
5
5
  const { reduce } = this.lib._
6
6
  const options = {}
7
7
  model = model ?? pascalCase(req.params.model)
8
- const { schema } = await getSchemaExt(model, 'add', options)
8
+ const { schema } = await getSchemaExt(model, 'add', { params })
9
9
  if (schema.disabled.includes('remove')) return reply.view(templateDisabled, { action: 'delete' })
10
10
  options.fields = schema.view.fields
11
11
  const ids = (req.body.ids ?? '').split(',')
@@ -4,7 +4,7 @@ async function detailsHandler ({ req, reply, model, params = {}, template, addOn
4
4
  const { merge } = this.lib._
5
5
  const options = {}
6
6
  model = model ?? pascalCase(req.params.model)
7
- const { schema } = await getSchemaExt(model, 'details', options)
7
+ const { schema } = await getSchemaExt(model, 'details', { params })
8
8
  if (schema.disabled.includes('get')) return reply.view(templateDisabled, { action: 'details' })
9
9
  // req.query.attachment = true
10
10
  options.fields = schema.view.fields
@@ -5,7 +5,7 @@ async function editHandler ({ req, reply, model, params = {}, template, addOnsHa
5
5
  const { merge, defaultsDeep } = this.lib._
6
6
  const options = {}
7
7
  model = model ?? pascalCase(req.params.model)
8
- const { schema } = await getSchemaExt(model, 'edit', options)
8
+ const { schema } = await getSchemaExt(model, 'edit', options, { params })
9
9
  if (schema.disabled.includes('update')) return reply.view(templateDisabled, { action: 'edit' })
10
10
  // req.query.attachment = true
11
11
  options.fields = schema.view.fields
@@ -4,7 +4,7 @@ async function exportHandler ({ req, reply, model, params = {}, templateDisabled
4
4
  const { buildUrl } = this.app.waibuMpa
5
5
  const options = {}
6
6
  model = model ?? pascalCase(req.params.model)
7
- const { schema } = await getSchemaExt(model, 'add', options)
7
+ const { schema } = await getSchemaExt(model, 'add', options, { params })
8
8
  if (schema.disabled.includes('find')) return reply.view(templateDisabled, { action: 'list' })
9
9
  options.fields = schema.view.fields
10
10
  const url = buildUrl({ url: req.url, base: req.body.handler })
@@ -5,7 +5,7 @@ async function listHandler ({ req, reply, model, template, params = {}, addOnsHa
5
5
  const qsKey = this.app.waibu.config.qsKey
6
6
  const options = { count: true }
7
7
  model = model ?? pascalCase(req.params.model)
8
- const { schema } = await getSchemaExt(model, 'list')
8
+ const { schema } = await getSchemaExt(model, 'list', { params })
9
9
  if (schema.disabled.includes('find')) return reply.view(templateDisabled, { action: 'list' })
10
10
  for (const key of ['sort', 'limit', 'fields']) {
11
11
  const sessKey = `wdb${model}${upperFirst(key)}`
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "waibu-db",
3
- "version": "1.1.9",
3
+ "version": "1.1.11",
4
4
  "description": "DB Helper",
5
5
  "main": "index.js",
6
6
  "scripts": {
@@ -7,11 +7,15 @@ function getCommons (action, schema, ext, opts = {}) {
7
7
  const label = get(ext, `view.${action}.label`, get(ext, 'common.label', {}))
8
8
  const card = get(ext, `view.${action}.card`, get(ext, 'common.card', true))
9
9
  const hidden = get(ext, `view.${action}.hidden`, get(ext, 'common.hidden', []))
10
+ const disabled = get(ext, `view.${action}.disabled`, get(ext, 'common.disabled', []))
11
+ const x = get(ext, `view.${action}.x`, get(ext, 'common.x', {}))
12
+ const aggregate = get(ext, `view.${action}.stat.aggregate`, get(ext, 'common.stat.aggregate', []))
10
13
  hidden.push(...schema.hidden, ...(opts.hidden ?? []))
11
14
  const allFields = without(map(schema.properties, 'name'), ...hidden)
12
15
  const forFields = get(ext, `view.${action}.fields`, get(ext, 'common.fields', allFields))
13
- set(schema, 'view.stat.aggregate', get(ext, `view.${action}.stat.aggregate`, get(ext, 'common.stat.aggregate', [])))
14
- set(schema, 'view.disabled', get(ext, 'disabled', []))
16
+ set(schema, 'view.stat.aggregate', aggregate)
17
+ set(schema, 'view.disabled', disabled)
18
+ set(schema, 'view.x', x)
15
19
  if (schema.disabled.length > 0) schema.view.disabled.push(...schema.disabled)
16
20
  let fields = []
17
21
  for (const f of forFields) {
@@ -19,6 +23,10 @@ function getCommons (action, schema, ext, opts = {}) {
19
23
  }
20
24
  fields = uniq(without(fields, ...hidden))
21
25
  if (action !== 'add' && !fields.includes('id')) fields.unshift('id')
26
+ let noWrap = get(ext, `view.${action}.noWrap`, get(ext, 'common.noWrap', true))
27
+ if (noWrap === true) noWrap = fields
28
+ else if (noWrap === false) noWrap = []
29
+ set(schema, 'view.noWrap', noWrap)
22
30
  return { fields, allFields, label, card }
23
31
  }
24
32
 
@@ -53,8 +61,11 @@ function customLayout ({ action, schema, ext, layout, allWidgets, readonly }) {
53
61
  }
54
62
  const widget = find(allWidgets, { name: f.name })
55
63
  if (!widget && !f.component) continue
56
- widget.attr = merge({}, widget.attr, omit(f, ['component']))
57
- if (f.component && !readonly.includes(f.name) && action !== 'details') widget.component = f.component
64
+ widget.attr = merge({}, widget.attr, omit(f, ['component', 'componentOpts']))
65
+ if (f.component && !readonly.includes(f.name) && action !== 'details') {
66
+ widget.component = f.component
67
+ widget.componentOpts = f.componentOpts
68
+ }
58
69
  widgets.push(widget)
59
70
  }
60
71
  if (widgets.length > 0) layout.push({ name: item.name, widgets })
@@ -79,7 +90,7 @@ function applyLayout (action, schema, ext) {
79
90
  } else {
80
91
  if (prop.type === 'boolean') {
81
92
  result.component = 'form-select'
82
- result.attr.options = 'false:No true:Yes'
93
+ result.attr.options = 'false|No true|Yes'
83
94
  }
84
95
  if (prop.values) {
85
96
  result.component = 'form-select'
@@ -106,13 +117,16 @@ const handler = {
106
117
  for (const f of get(schema, 'view.qs.fields', '').split(',')) {
107
118
  if (fields.includes(f)) qsFields.push(f)
108
119
  }
109
- let [col, dir] = get(schema, 'view.qs.sort', '').split(':')
110
- if (!fields.includes(col) || !col) col = 'id'
111
- if (!['1', '-1'].includes(dir)) dir = '1'
120
+ const sort = get(schema, 'view.qs.sort')
121
+ if (sort) {
122
+ let [col, dir] = get(schema, 'view.qs.sort', '').split(':')
123
+ if (!fields.includes(col) || !col) col = 'id'
124
+ if (!['1', '-1'].includes(dir)) dir = '1'
125
+ set(schema, 'view.qs.sort', `${col}:${dir}`)
126
+ }
112
127
  set(schema, 'view.label', label)
113
128
  set(schema, 'view.fields', fields)
114
129
  set(schema, 'view.qs.fields', qsFields.join(','))
115
- set(schema, 'view.qs.sort', `${col}:${dir}`)
116
130
  },
117
131
  details: async function (schema, ext, opts) {
118
132
  applyLayout.call(this, 'details', schema, ext, opts)
@@ -132,8 +146,8 @@ async function getSchemaExt (model, view, opts) {
132
146
 
133
147
  let schema = getSchema(model)
134
148
  const base = path.basename(schema.file, path.extname(schema.file))
135
- let ext = await readConfig(`${schema.ns}:/waibuDb/schema/${base}.*`, { ignoreError: true })
136
- const over = await readConfig(`main:/waibuDb/extend/${schema.ns}/schema/${base}.*`, { ignoreError: true })
149
+ let ext = await readConfig(`${schema.ns}:/waibuDb/schema/${base}.*`, { ignoreError: true, opts })
150
+ const over = await readConfig(`main:/waibuDb/extend/${schema.ns}/schema/${base}.*`, { ignoreError: true, opts })
137
151
  ext = defaultsDeep(over, ext)
138
152
  await handler[view].call(this, schema, ext, opts)
139
153
  schema = pick(schema, ['name', 'properties', 'indexes', 'disabled', 'attachment', 'sortables', 'view'])
@@ -10,7 +10,7 @@ async function btnDelete () {
10
10
  const { isEmpty, get } = this.plugin.app.bajo.lib._
11
11
  this.params.noTag = true
12
12
  const schema = get(this, 'component.locals.schema', {})
13
- if (schema.view.disabled.includes('delete')) {
13
+ if (schema.view.disabled.includes('remove')) {
14
14
  this.params.html = ''
15
15
  return
16
16
  }
@@ -22,9 +22,9 @@ async function echarts () {
22
22
  }
23
23
 
24
24
  build = async () => {
25
- const { defaultsDeep, generateId } = this.plugin.app.bajo
25
+ const { generateId } = this.plugin.app.bajo
26
26
  const { base64JsonDecode, jsonStringify } = this.plugin.app.waibuMpa
27
- const { cloneDeep } = this.plugin.app.bajo.lib._
27
+ const { merge, cloneDeep } = this.plugin.app.bajo.lib._
28
28
  this.params.attr.id = generateId('alpha')
29
29
  this.params.attr['x-data'] = `chart${this.params.attr.id}`
30
30
  this.params.attr['@resize.window.debounce.500ms'] = `
@@ -34,7 +34,7 @@ async function echarts () {
34
34
  `
35
35
  let option = cloneDeep(this.defOption)
36
36
  if (this.params.attr.option === true) this.params.attr.option = 'e30='
37
- if (this.params.attr.option) option = defaultsDeep(base64JsonDecode(this.params.attr.option), this.defOption)
37
+ if (this.params.attr.option) option = merge(option, base64JsonDecode(this.params.attr.option))
38
38
  this.params.attr['x-init'] = `
39
39
  $watch('option', val => {
40
40
  if (chart) chart.setOption(val)
@@ -0,0 +1,43 @@
1
+ import wdbBase from '../wdb-base.js'
2
+
3
+ async function form () {
4
+ const WdbBase = await wdbBase.call(this)
5
+
6
+ return class WdbForm extends WdbBase {
7
+ build = async () => {
8
+ const { get, find, filter, forOwn, isEmpty } = this.plugin.lib._
9
+ const { base64JsonEncode } = this.plugin.app.waibuMpa
10
+ const schema = get(this, 'component.locals.schema', {})
11
+ const body = []
12
+ const xModels = get(schema, 'view.x.model', [])
13
+ const xOns = get(schema, 'view.x.on', [])
14
+ for (const l of schema.view.layout) {
15
+ body.push(`<c:fieldset ${schema.view.card === false ? '' : 'card'} ${l.name[0] !== '_' ? ('t:legend="' + l.name + '"') : ''} grid-gutter="2">`)
16
+ for (const w of l.widgets) {
17
+ const prop = find(schema.properties, { name: w.name })
18
+ const attr = [`x-ref="${w.name}"`]
19
+ if (xModels.includes(w.name)) attr.push(`x-model="${w.name}"`)
20
+ forOwn(w.attr, (v, k) => {
21
+ attr.push(`${k}="${v}"`)
22
+ })
23
+ const xon = filter(xOns, { field: w.name })
24
+ for (const o of xon) {
25
+ attr.push(`@${o.bind}="${o.handler}"`)
26
+ }
27
+ if (w.componentOpts) attr.push(`c-opts="${base64JsonEncode(w.componentOpts)}"`)
28
+ body.push(`<c:${w.component} ${w.attr.label ? ('t:label="' + w.attr.label + '"') : ''} data-type="${prop.type}" label-floating name="${w.name}" ${attr.join(' ')} />`)
29
+ }
30
+ body.push('</c:fieldset>')
31
+ }
32
+ const html = await this.component.buildSentence(body, this.component.locals)
33
+ this.params.html = `${html}\n${this.params.html}`
34
+ const xData = get(schema, 'view.x.data', '')
35
+ this.params.attr['x-data'] = isEmpty(xData) ? '' : `{ ${xData} }`
36
+ this.params.attr['x-init'] = get(schema, 'view.x.init', '')
37
+
38
+ this.params.tag = this.params.attr.tag ?? 'form'
39
+ }
40
+ }
41
+ }
42
+
43
+ export default form
@@ -91,6 +91,7 @@ async function table () {
91
91
  head = await this.component.buildTag({ tag: 'div', attr: { flex: 'justify-content:between align-items:end' }, html: content.join('\n') })
92
92
  }
93
93
  let text = this.params.attr.headerNowrap ? '' : 'nowrap'
94
+ if (text === '' && this.isNoWrap(f, schema, group.body.nowrap)) text = 'nowrap'
94
95
  if (this.isRightAligned(f, schema)) text += ' align:end'
95
96
  const attr = { dataKey: f, dataType: prop.type, text }
96
97
  items.push(await this.component.buildTag({ tag: 'th', attr, html: head }))
@@ -146,11 +147,9 @@ async function table () {
146
147
  if (!disableds.includes('get')) attr.style = { cursor: 'pointer' }
147
148
  const cellFormatter = get(schema, `view.cellFormatter.${f}`)
148
149
  if (cellFormatter) merge(attr, await cellFormatter(dataValue, d))
149
- if (!['object', 'array'].includes(prop.type)) {
150
- const noWrap = this.isNoWrap(f, schema, group.body.nowrap) ? 'nowrap' : ''
151
- if (this.isRightAligned(f, schema)) attr.text = `align:end ${noWrap}`
152
- else attr.text = noWrap
153
- }
150
+ const noWrap = this.isNoWrap(f, schema, group.body.nowrap) ? 'nowrap' : ''
151
+ if (this.isRightAligned(f, schema)) attr.text = `align:end ${noWrap}`
152
+ else attr.text = noWrap
154
153
  const lookup = get(schema, `view.lookup.${f}`)
155
154
  if (lookup) {
156
155
  const item = find(lookup.values, set({}, lookup.id ?? 'id', value))
@@ -172,7 +171,7 @@ async function table () {
172
171
  }
173
172
  html.push(await this.component.buildTag({ tag: 'tbody', attr: group.body, html: items.join('\n') }))
174
173
  this.params.attr = omit(this.params.attr, ['sortUpIcon', 'sortDownIcon', 'noSort', 'selection', 'headerNowrap'])
175
- const goDetails = `
174
+ let xData = `
176
175
  goDetails (id) {
177
176
  let url = '${this.params.attr.detailsHref ?? this.component.buildUrl({ base: 'details', prettyUrl })}'
178
177
  if (url === '#') return
@@ -181,8 +180,15 @@ async function table () {
181
180
  window.location.href = url
182
181
  }
183
182
  `
183
+ const xDataView = get(schema, 'view.x.data', '')
184
+ if (!isEmpty(xDataView)) xData += `, ${xDataView}`
185
+ let xInit = ''
186
+ const xInitView = get(schema, 'view.x.init', '')
187
+ if (!isEmpty(xInitView)) xInit += `${xInitView}\n`
188
+
184
189
  if (selection === 'multi') {
185
- this.params.attr['x-data'] = `{
190
+ xData = `{
191
+ ${xData},
186
192
  toggleAll: false,
187
193
  selected: [],
188
194
  toggle (id) {
@@ -190,10 +196,10 @@ async function table () {
190
196
  const idx = this.selected.indexOf(id)
191
197
  this.selected.splice(idx, 1)
192
198
  } else this.selected.push(id)
193
- },
194
- ${goDetails}
199
+ }
195
200
  }`
196
- this.params.attr['x-init'] = `
201
+ xInit = `
202
+ ${xInit}
197
203
  $watch('toggleAll', val => {
198
204
  if (val) {
199
205
  const els = document.getElementsByName('_rt')
@@ -204,21 +210,24 @@ async function table () {
204
210
  $watch('selected', val => $dispatch('on-selection', val))
205
211
  `
206
212
  } else if (selection === 'single') {
207
- this.params.attr['x-data'] = `{
213
+ xData = `{
214
+ ${xData},
208
215
  selected: '',
209
216
  toggle (id) {
210
217
  this.selected = id
211
- },
212
- ${goDetails}
218
+ }
213
219
  }`
214
- this.params.attr['x-init'] = `
220
+ xInit = `
221
+ ${xInit}
215
222
  $watch('selected', val => $dispatch('on-selection', [val]))
216
223
  `
217
224
  } else {
218
- this.params.attr['x-data'] = `{
219
- ${goDetails}
225
+ xData = `{
226
+ ${xData}
220
227
  }`
221
228
  }
229
+ this.params.attr['x-data'] = xData
230
+ this.params.attr['x-init'] = xInit
222
231
  this.params.html = await this.component.buildTag({ tag: 'table', attr: this.params.attr, html: html.join('\n') })
223
232
  }
224
233
  }
@@ -1,12 +0,0 @@
1
- <% for (const l of schema.view.layout) { %>
2
- <c:fieldset <%= schema.view.card === false ? '' : 'card' %> <% if (l.name[0] !== '_') print('t:legend="' + l.name + '"') %> grid-gutter="2">
3
- <% for (const w of l.widgets) {
4
- const prop = _.find(schema.properties, { name: w.name })
5
- const attr = []
6
- _.forOwn(w.attr, (v, k) => {
7
- attr.push(`${k}="${v}"`)
8
- })
9
- print(`<c:${w.component} ${w.attr.label ? ('label="' + _t(w.attr.label) + '"') : ''} data-type="${prop.type}" label-floating name="${w.name}" ${attr.join(' ')} />`)
10
- } %>
11
- </c:fieldset>
12
- <% } %>