diff --git a/packages/builder/src/pages/builder/app/[application]/design/[screenId]/_components/AppPanel.svelte b/packages/builder/src/pages/builder/app/[application]/design/[screenId]/_components/AppPanel.svelte
index b04cd8b956..98a3f129a2 100644
--- a/packages/builder/src/pages/builder/app/[application]/design/[screenId]/_components/AppPanel.svelte
+++ b/packages/builder/src/pages/builder/app/[application]/design/[screenId]/_components/AppPanel.svelte
@@ -1,8 +1,13 @@
@@ -15,6 +20,10 @@
{#if $appStore.clientFeatures.devicePreview}
{/if}
+
+
{}}
+ >Errors ({$screenComponentErrorList.length})
diff --git a/packages/builder/src/stores/builder/index.js b/packages/builder/src/stores/builder/index.js
index c6dc631e5c..5856a394e0 100644
--- a/packages/builder/src/stores/builder/index.js
+++ b/packages/builder/src/stores/builder/index.js
@@ -20,6 +20,7 @@ import {
screenComponents,
screenComponentErrors,
findComponentsBySettingsType,
+ screenComponentErrorList,
} from "./screenComponent"
// Backend
@@ -75,6 +76,7 @@ export {
screenComponents,
screenComponentErrors,
findComponentsBySettingsType,
+ screenComponentErrorList,
}
export const reset = () => {
diff --git a/packages/builder/src/stores/builder/screenComponent.ts b/packages/builder/src/stores/builder/screenComponent.ts
index 62bc97cc27..0ee64501f0 100644
--- a/packages/builder/src/stores/builder/screenComponent.ts
+++ b/packages/builder/src/stores/builder/screenComponent.ts
@@ -115,6 +115,7 @@ function getInvalidDatasources(
const friendlyTypeName = friendlyNameByType[type] ?? type
result[component._id!] = [
{
+ componentId: component._id!,
key: setting.key,
message: `The ${friendlyTypeName} named "${label}" could not be found`,
errorType: "setting",
@@ -174,6 +175,7 @@ function getMissingRequiredSettings(
if (missingRequiredSettings?.length) {
result[component._id!] = missingRequiredSettings.map((s: any) => ({
+ componentId: component._id!,
key: s.key,
message: `Add the ${s.label} setting to start using your component`,
errorType: "setting",
@@ -214,6 +216,7 @@ function getMissingAncestors(
result[component._id!] = missingAncestors.map(ancestor => {
const ancestorDefinition = definitions[`${BudibasePrefix}${ancestor}`]
return {
+ componentId: component._id!,
message: `${pluralise(definition.name)} need to be inside a
${ancestorDefinition.name}`,
errorType: "ancestor-setting",
@@ -270,6 +273,17 @@ export function findComponentsBySettingsType(
return result
}
+export const screenComponentErrorList = derived(
+ [screenComponentErrors],
+ ([$screenComponentErrors]): UIComponentError[] => {
+ if (!featureFlag.isEnabled("CHECK_COMPONENT_SETTINGS_ERRORS")) {
+ return []
+ }
+
+ return Object.values($screenComponentErrors).flatMap(errors => errors)
+ }
+)
+
export const screenComponents = derived(
[selectedScreen],
([$selectedScreen]) => {
diff --git a/packages/types/src/ui/components/errors.ts b/packages/types/src/ui/components/errors.ts
index 9725ed8a33..58c36c7248 100644
--- a/packages/types/src/ui/components/errors.ts
+++ b/packages/types/src/ui/components/errors.ts
@@ -1,4 +1,5 @@
interface BaseUIComponentError {
+ componentId: string
message: string
}