Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
{
"type": "refactor",
"message": "Fix missing form data after first render (SSR)",
"issue_origin": "github",
"issue_number": 4268,
"domain": "builder",
"bullet_points": [],
"created_at": "2025-11-17"
}
Original file line number Diff line number Diff line change
Expand Up @@ -62,12 +62,6 @@ export default {
resolvedLabel() {
return ensureString(this.resolveFormula(this.element.label))
},
resolvedDefaultValue() {
return this.elementType.getInitialFormDataValue(
this.element,
this.applicationContext
)
},
allowedExtensions() {
return this.element.allowed_filetypes
.filter((v) => v)
Expand Down Expand Up @@ -121,6 +115,8 @@ export default {
},
},
watch: {
// override the default mixin method because we want to use the one with metadata
resolvedDefaultValue() {},
resolvedDefaultValueWithMetadata: {
handler(value) {
if (process.client) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -171,10 +171,10 @@ export default {
data() {
return {
values: {
label: '',
default_name: '',
default_url: '',
help_text: '',
label: {},
default_name: {},
default_url: {},
help_text: {},
required: false,
multiple: false,
max_filesize: 5,
Expand Down
16 changes: 11 additions & 5 deletions web-frontend/modules/automation/pages/automationWorkflow.vue
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ import WorkflowEditor from '@baserow/modules/automation/components/workflow/Work
import EditorSidePanels from '@baserow/modules/automation/components/workflow/EditorSidePanels'
import { AutomationApplicationType } from '@baserow/modules/automation/applicationTypes'
import { notifyIf } from '@baserow/modules/core/utils/error'
import { StoreItemLookupError } from '@baserow/modules/core/errors'

export default {
name: 'AutomationWorkflow',
Expand Down Expand Up @@ -227,11 +228,12 @@ export default {
parseInt(from.params.automationId)
)
if (automation) {
const workflow = this.$store.getters['automationWorkflow/getById'](
automation,
parseInt(from.params.workflowId)
)
if (workflow) {
try {
const workflow = this.$store.getters['automationWorkflow/getById'](
automation,
parseInt(from.params.workflowId)
)

this.$store.dispatch('automationWorkflowNode/select', {
workflow,
node: null,
Expand All @@ -240,6 +242,10 @@ export default {
application: automation,
data: { _loadedOnce: false },
})
} catch (e) {
if (!(e instanceof StoreItemLookupError)) {
throw e
}
}
}
next()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,33 +20,15 @@

<script>
import formElement from '@baserow/modules/builder/mixins/formElement'
import {
ensureBoolean,
ensureString,
} from '@baserow/modules/core/utils/validator'
import { ensureString } from '@baserow/modules/core/utils/validator'

export default {
name: 'CheckboxElement',
mixins: [formElement],
computed: {
defaultValueResolved() {
try {
return ensureBoolean(this.resolveFormula(this.element.default_value))
} catch {
return false
}
},
resolvedLabel() {
return ensureString(this.resolveFormula(this.element.label))
},
},
watch: {
defaultValueResolved: {
handler(newValue) {
this.inputValue = newValue
},
immediate: true,
},
},
}
</script>
Original file line number Diff line number Diff line change
Expand Up @@ -57,13 +57,7 @@

<script>
import formElement from '@baserow/modules/builder/mixins/formElement'
import {
ensureString,
ensureStringOrInteger,
ensureArray,
ensurePositiveInteger,
} from '@baserow/modules/core/utils/validator'
import { CHOICE_OPTION_TYPES } from '@baserow/modules/builder/enums'
import { ensureString } from '@baserow/modules/core/utils/validator'

export default {
name: 'ChoiceElement',
Expand Down Expand Up @@ -94,78 +88,19 @@ export default {
placeholderResolved() {
return ensureString(this.resolveFormula(this.element.placeholder))
},
defaultValueResolved() {
let converter = ensureString
if (
this.optionsResolved.find(
({ value }) => value !== undefined && value !== null // We skip null values
) &&
Number.isInteger(this.optionsResolved[0].value)
) {
converter = (v) => ensurePositiveInteger(v, { allowNull: true })
}
if (this.element.multiple) {
try {
const existingValues = this.optionsResolved.map(({ value }) => value)
return ensureArray(this.resolveFormula(this.element.default_value))
.map(converter)
.filter((value) => existingValues.includes(value))
} catch {
return []
}
} else {
try {
// Always return a string if we have a default value, otherwise
// set the value to null as single select fields will only skip
// field preparation if the value is null.
const resolvedSingleValue = converter(
this.resolveFormula(this.element.default_value)
)
return resolvedSingleValue === '' ? null : resolvedSingleValue
} catch {
return null
}
}
},
canHaveOptions() {
return !this.elementIsInError
},
optionsResolved() {
switch (this.element.option_type) {
case CHOICE_OPTION_TYPES.MANUAL:
return this.element.options.map(({ name, value }) => ({
name,
value: value === null ? name : value,
}))
case CHOICE_OPTION_TYPES.FORMULAS: {
const formulaValues = ensureArray(
this.resolveFormula(this.element.formula_value)
)
const formulaNames = ensureArray(
this.resolveFormula(this.element.formula_name)
)
return formulaValues.map((value, index) => ({
id: index,
value: ensureStringOrInteger(value),
name: ensureString(
index < formulaValues.length ? formulaNames[index] : value
),
}))
}
default:
return []
}
return this.elementType.getOptionsResolved(
this.element,
this.applicationContext
)
},
},
watch: {
defaultValueResolved: {
handler(newValue) {
this.inputValue = newValue
},
immediate: true,
},
'element.multiple'() {
this.setFormData(this.defaultValueResolved)
this.setFormData(this.resolvedDefaultValue)
},
},
methods: {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,7 @@
import formElement from '@baserow/modules/builder/mixins/formElement'
import ABDateTimePicker from '@baserow/modules/builder/components/elements/baseComponents/ABDateTimePicker.vue'
import { DATE_FORMATS, TIME_FORMATS } from '@baserow/modules/builder/enums'
import {
ensureDateTime,
ensureDate,
ensureString,
} from '@baserow/modules/core/utils/validator'
import { ensureString } from '@baserow/modules/core/utils/validator'

export default {
name: 'DateTimePickerElement',
Expand All @@ -52,41 +48,10 @@ export default {
DATE_FORMATS() {
return DATE_FORMATS
},
resolvedDefaultValue() {
const resolvedFormula = this.resolveFormula(this.element.default_value)

if (!resolvedFormula) {
return null
}

try {
const result = this.element.include_time
? ensureDateTime(resolvedFormula)
: ensureDate(resolvedFormula)

if (result && !isNaN(result)) {
// We convert to an iso string here because date objects are not serialized
// properly during SSR
return result.toJSON()
} else {
return result
}
} catch (e) {
return null
}
},
resolvedLabel() {
return ensureString(this.resolveFormula(this.element.label))
},
},
watch: {
resolvedDefaultValue: {
handler(value) {
this.setFormData(value)
},
immediate: true,
},
},
methods: {
getErrorMessage() {
if (this.inputValue) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,17 +60,6 @@ export default {
localeLanguage() {
return this.$i18n.locale
},
resolvedDefaultValue() {
try {
const value = this.resolveFormula(this.element.default_value)

return this.isNumericField
? ensureNumeric(value, { allowNull: true })
: ensureString(value)
} catch {
return null
}
},
isNumericField() {
return this.element.validation_type === 'integer'
},
Expand All @@ -82,20 +71,16 @@ export default {
},
},
watch: {
resolvedDefaultValue: {
handler(value) {
this.inputValue = value
this.internalValue = this.toInternalValue(value)
inputValue: {
handler(newValue) {
// If the inputValue was updated (after a reset for instance) we want to update
// the internal value
if (this.fromInternalValue(this.internalValue) !== newValue) {
this.internalValue = this.toInternalValue(newValue)
}
},
immediate: true,
},
inputValue(newValue) {
// If the inputValue was updated (after a reset for instance) we want to update
// the internal value
if (this.fromInternalValue(this.internalValue) !== newValue) {
this.internalValue = this.toInternalValue(newValue)
}
},
},
methods: {
toInternalValue(value) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,15 +12,15 @@

<script>
import Rating from '@baserow/modules/database/components/Rating'
import formElement from '@baserow/modules/builder/mixins/formElement'
import element from '@baserow/modules/builder/mixins/element'
import { ensurePositiveInteger } from '@baserow/modules/core/utils/validator'

export default {
name: 'RatingElement',
components: {
Rating,
},
mixins: [formElement],
mixins: [element],
computed: {
resolvedValue() {
try {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,7 @@
<script>
import Rating from '@baserow/modules/database/components/Rating'
import formElement from '@baserow/modules/builder/mixins/formElement'
import {
ensurePositiveInteger,
ensureString,
} from '@baserow/modules/core/utils/validator'
import { ensureString } from '@baserow/modules/core/utils/validator'
import { useVuelidate } from '@vuelidate/core'
import { required } from '@vuelidate/validators'

Expand All @@ -35,13 +32,6 @@ export default {
return { v$: useVuelidate() }
},
computed: {
resolvedDefaultValue() {
try {
return ensurePositiveInteger(this.resolveFormula(this.element.value))
} catch {
return 0
}
},
labelResolved() {
return ensureString(this.resolveFormula(this.element.label))
},
Expand All @@ -53,14 +43,6 @@ export default {
}
},
},
watch: {
resolvedDefaultValue: {
handler(value) {
this.inputValue = value
},
immediate: true,
},
},
validations() {
return this.rules
},
Expand Down
Loading
Loading