Skip to content

Commit be5d3d2

Browse files
Date dependency configuration: allow to add new fields baserow#4228 (baserow#4253)
Date dependency configuration: allow to add new fields from the modal.
1 parent dd9dae9 commit be5d3d2

File tree

4 files changed

+123
-3
lines changed

4 files changed

+123
-3
lines changed
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
{
2+
"type": "feature",
3+
"message": "Allow to add missing fields to date dependency configuration",
4+
"domain": "database",
5+
"issue_number": 4228,
6+
"bullet_points": [],
7+
"created_at": "2025-11-14"
8+
}

enterprise/web-frontend/modules/baserow_enterprise/components/dateDependency/DateDependencyFieldPicker.vue

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,24 @@
1313
:disabled="disabled"
1414
:error="hasError"
1515
size="regular"
16-
@change="$emit('input', $event)"
16+
@change="
17+
isAddNew($event) ? $emit('add-new', $event) : null
18+
$emit('input', $event)
19+
"
1720
>
1821
<DropdownItem
1922
v-for="r in fields"
2023
:key="r.id"
2124
:name="r.name"
2225
:value="r.id"
23-
:icon="r.id ? icon : null"
26+
:icon="r.icon ? r.icon : r.id ? icon : null"
27+
></DropdownItem>
28+
29+
<DropdownItem
30+
v-if="addNew"
31+
:name="$t('dateDependencyModal.addNewField')"
32+
value="add-new"
33+
icon="iconoir-plus"
2434
></DropdownItem>
2535
</Dropdown>
2636
<template #error>{{ errors[0].$message }}</template>
@@ -66,6 +76,7 @@ export default {
6676
default: null,
6777
},
6878
disabled: { type: Boolean, required: false, default: false },
79+
addNew: { type: Boolean, required: false, default: false },
6980
},
7081
computed: {
7182
errorMessageStr() {
@@ -78,5 +89,10 @@ export default {
7889
return Boolean(this.errors?.length > 0)
7990
},
8091
},
92+
methods: {
93+
isAddNew(value) {
94+
return value === 'add-new'
95+
},
96+
},
8197
}
8298
</script>

enterprise/web-frontend/modules/baserow_enterprise/components/dateDependency/DateDependencyModal.vue

Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@
3939
icon="iconoir-calendar"
4040
:errors="v$.dependency.start_date_field_id.$errors"
4141
:field-name="$t('dateDependencyModal.startDateFieldLabel')"
42+
add-new
43+
@add-new="addNewField('start_date_field_id')"
4244
/>
4345
</div>
4446
<div class="col col-6">
@@ -50,6 +52,8 @@
5052
:errors="v$.dependency.end_date_field_id.$errors"
5153
icon="iconoir-calendar"
5254
:field-name="$t('dateDependencyModal.endDateFieldLabel')"
55+
add-new
56+
@add-new="addNewField('end_date_field_id')"
5357
/>
5458
</div>
5559
</div>
@@ -64,6 +68,8 @@
6468
icon="iconoir-clock-rotate-right"
6569
:field-name="$t('dateDependencyModal.durationFieldLabel')"
6670
:helper-text="$t('dateDependencyModal.durationFieldHint')"
71+
add-new
72+
@add-new="addNewField('duration_field_id')"
6773
/>
6874
</div>
6975

@@ -81,6 +87,8 @@
8187
:helper-text="
8288
$t('dateDependencyModal.dependencyLinkrowFieldHint')
8389
"
90+
add-new
91+
@add-new="addNewField('dependency_linkrow_field_id')"
8492
/>
8593
</div>
8694
</div>
@@ -106,6 +114,7 @@ import { required, requiredIf } from '@vuelidate/validators'
106114
import { ResponseErrorMessage } from '@baserow/modules/core/plugins/clientHandler'
107115
import FieldService from '@baserow/modules/database/services/field'
108116
import { notifyIf } from '@baserow/modules/core/utils/error'
117+
import { getNextAvailableNameInSequence } from '@baserow/modules/core/utils/string'
109118
110119
export default {
111120
name: 'DateDependencyModal',
@@ -210,6 +219,91 @@ export default {
210219
},
211220
},
212221
methods: {
222+
async handleCreateField(value) {
223+
const { forceCreateCallback, newField } = await this.$store.dispatch(
224+
'field/create',
225+
{
226+
...value,
227+
forceCreate: false,
228+
}
229+
)
230+
231+
// The fields store is context-sensitive, and shows fields for the current table
232+
// only, so we should add the field only if the modal has been opened for the
233+
// current table.
234+
if (this.table.id === this.$store.getters['table/getSelectedId']) {
235+
if (_.isFunction(forceCreateCallback)) {
236+
await forceCreateCallback()
237+
}
238+
}
239+
240+
return newField
241+
},
242+
async addNewField(dependencyFieldName) {
243+
try {
244+
return await this._addNewField(dependencyFieldName)
245+
} catch (error) {
246+
notifyIf(error)
247+
}
248+
},
249+
250+
async _addNewField(dependencyFieldName) {
251+
// Defaults for new fields depending on a configuration field.
252+
// We need to have access to instance variables, so this is inside a method.
253+
const FIELDS_DEFAULTS = {
254+
dependency_linkrow_field_id: {
255+
type: 'link_row',
256+
table: this.table,
257+
values: {
258+
link_row_table_id: this.table.id,
259+
name: this.$t('dateDependencyModal.linkRowFieldTitle'),
260+
},
261+
},
262+
duration_field_id: {
263+
type: 'duration',
264+
table: this.table,
265+
values: {
266+
duration_format: 'd h',
267+
table: this.table.id,
268+
name: this.$t('dateDependencyModal.durationFieldLabel'),
269+
},
270+
},
271+
start_date_field_id: {
272+
type: 'date',
273+
table: this.table,
274+
values: {
275+
date_include_time: false,
276+
table: this.table.id,
277+
name: this.$t('dateDependencyModal.startDateFieldLabel'),
278+
},
279+
},
280+
end_date_field_id: {
281+
type: 'date',
282+
table: this.table,
283+
values: {
284+
date_include_time: false,
285+
table: this.table.id,
286+
name: this.$t('dateDependencyModal.endDateFieldLabel'),
287+
},
288+
},
289+
}
290+
291+
const fieldDef = _.clone(FIELDS_DEFAULTS[dependencyFieldName])
292+
293+
const usedFieldNames = _.map(this.fields, 'name')
294+
295+
const fieldName = getNextAvailableNameInSequence(
296+
fieldDef.values.name,
297+
usedFieldNames
298+
)
299+
fieldDef.values.name = fieldName
300+
301+
const fieldCreated = await this.handleCreateField(fieldDef)
302+
// fields is not using fields store, so we need to update it manually
303+
this.fields.push(fieldCreated)
304+
this.dependency[dependencyFieldName] = fieldCreated.id
305+
},
306+
213307
async fetchFields() {
214308
// If the fields are already provided as a prop, we don't need to fetch them
215309
if (this.tableFields?.length > 0) {

enterprise/web-frontend/modules/baserow_enterprise/locales/en.json

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -692,7 +692,9 @@
692692
"advancedSettingsLabel": "Advanced settings",
693693
"includeWeekendsLabel": "Include weekends when calculating durations",
694694
"dependencyFieldForReaderTooltip": "This field is included in date dependency field rule",
695-
"fieldInvalidTitle": "Date dependency field error"
695+
"fieldInvalidTitle": "Date dependency field error",
696+
"addNewField": "Add new field",
697+
"linkRowFieldTitle": "Parents"
696698
},
697699
"dateDependency": {
698700
"invalidChildRow": "Successor row is invalid",

0 commit comments

Comments
 (0)