Developer Kit · Templates
State-Bag in einem Textfeld
Hey zusammen! 👋
Ich habe kürzlich immer mehr mit sogenannten StateFields gearbeitet und wollte das Konzept mal teilen – vielleicht hilft es euch auch weiter.
Das Problem: Für jeden Filter, Tab oder ausgewählten Datensatz braucht man normalerweise ein eigenes Ninox-Feld. Bei komplexeren UIs hat man schnell 5–10 Helper-Felder im Schema, nur für UI-Zustände.
Die Lösung: Ein JSON-Feld als „State-Bag" Ein einziges Textfeld speichert ein JSON-Objekt mit beliebig vielen Keys. Navigation, Filter, ausgewählte IDs – alles in einem Feld.
---
1. Feld und Rohdaten auslesen
let stateField := fieldId(Nr, "helper_uiState");
let stateRaw := if current.helper_uiState then
parseJSON(text(current.helper_uiState))
else
{}
end;
2. Einzelne Werte extrahieren (mit Default-Werten)
let activeTab := if item(stateRaw, "activeTab") then
text(item(stateRaw, "activeTab"))
else
"uebersicht"
end;
let statusFilter := if item(stateRaw, "statusFilter") then text(item(stateRaw, "statusFilter")) else "alle" end;
let selectedRecordId := if item(stateRaw, "selectedId") then text(item(stateRaw, "selectedId")) else "" end;</code></pre>
3. Werte schreiben — empfohlen: dataBag auf der Action
Partielles Patchen ohne manuelles setItem in der Formel — der Action Performer übernimmt Read → Patch → Write:
{
type: "update",
recordId: Nr,
fieldId: stateField,
dataBag: {
base: helper_uiState,
patch: { activeTab: "details" }
}
}
Ausführlich: <a href="../patterns/data-bag-actions.md"><code>data-bag-actions</code></a> — gilt für alle Widgets mit actions (Button, Layout, Table, Drawing, …).
Alternative (manuell): Topf lesen → setItem → formatJSON als value:
let uiData := parseJSON(
if current.helper_uiState then
text(current.helper_uiState)
else
"{}"
end);
setItem(uiData, "activeTab", "details");
Dann als Action:
{
type: "update",
recordId: Nr,
field: stateField,
value: formatJSON(uiData)
}
4. Mehrere Keys gleichzeitig setzen (z.B. Zurück-Button)
Mit dataBag mehrere Keys in einem Patch:
dataBag: {
base: helper_uiState,
patch: { selectedId: "", statusFilter: "alle" }
}
Oder manuell:
let uiDataReset := parseJSON(text(current.helper_uiState));
setItem(uiDataReset, "selectedId", "");
setItem(uiDataReset, "statusFilter", "alle");
--- value: formatJSON(uiDataReset) in der Action ---;
---
Genutzte Ninox-Funktionen: - parseJSON() / formatJSON() – JSON ↔ Objekt (Plain-JSON im Textfeld) - setItem(obj, "key", value) – Key setzen - item(obj, "key") – Wert auslesen
Legacy: Ältere Projekte nutzen manchmal urlEncode/urlDecode um JSON in Actions zu schreiben. Für neue Apps: dataBag + Plain-JSON — siehe <a href="../patterns/data-bag-actions.md#legacy-urlencoded"><code>data-bag-actions</code></a>.
Vorteile: - Ein Feld statt vieler – Filter, Tabs, ausgewählte IDs in einem Feld - Einfach erweiterbar – neuer Key = kein neues Feld im Schema - Übersichtlich – alle Keys an einer Stelle dokumentieren - Weniger Wartung – weniger Felder im Formular
Tipp: Keys am besten im Code dokumentieren:
--- State-Keys: activeTab (uebersicht|details), statusFilter (alle|offen|erledigt), selectedId ---;
Viel Spaß damit! 🚀