Skip to content

Save preference

This operation is the library's only write entry point. It never inserts, updates, or deletes directly; instead it inspects the supplied text, treats blank content as a delete request, and otherwise chooses update versus insert by checking whether the scoped preference row already exists.

Field Value
Operation ID OP-PREF-003
Trigger Caller invokes PreferenceData.SavePreferences(appName, pageName, userId, preferenceText).
Inputs appName, pageName, userId, preferenceText
Outputs true after the delegated write path completes, or an exception if preprocessing/delegated execution fails
Primary components PreferenceData.SavePreferences, PreferenceData.DeletePref, PreferenceData.DoesPrefExist, PreferenceData.UpdatePref, PreferenceData.InsertPref
Entry point SAIF.Framework.Preferences\PreferenceData.cs

Steps

  1. Evaluate preferenceText.Trim() and pass the result to string.IsNullOrEmpty(...) to decide whether the caller supplied usable content (BR-002).
  2. On failure: if preferenceText is null, the immediate Trim() call throws NullReferenceException; this method does not guard that case locally.
  3. If the trimmed text is empty, dispatch to Delete preference row, which applies the scoped delete against USER_PREFERENCE using SQL-006 and the scope rules BR-001, BR-003.
  4. The delete path returns true even when no row matches the delete criteria.
  5. If the trimmed text is not empty, call Check preference existence to count rows in USER_PREFERENCE via SQL-007 under BR-001 and BR-003.
  6. If the helper returns true, continue to step 4.
  7. If the helper returns false, continue to step 5.
  8. When a scoped row already exists, call Update preference row, which updates USER_PREFERENCE through SQL-005 and enforces BR-001, BR-003, BR-004, and BR-005.
  9. Because the update SQL contains the no-op guard from BR-004, unchanged text can lead to zero rows updated while this operation still returns true.
  10. When no scoped row exists, call Insert preference row, which allocates identity with SQL-001, inserts the row with SQL-004, and enforces BR-001, BR-003, and BR-005 against USER_PREFERENCE.
  11. Return true to the caller after the selected delete/update/insert helper completes.
  12. On failure: exceptions raised by the delegated helper methods are not caught here and propagate to the caller.

Process flow

The following diagram visualizes this operation's control flow.

flowchart TD
    Start([Caller invokes SavePreferences]) --> Trim[Trim preferenceText]
    Trim --> Empty{Trimmed text empty?}
    Empty -->|Yes| Delete[Delete preference row]
    Empty -->|No| Exists[Check preference existence]
    Exists -->|Yes| Update[Update preference row]
    Exists -->|No| Insert[Insert preference row]
    Delete --> EndOk([Return true])
    Update --> EndOk
    Insert --> EndOk

Failure and edge-case behavior

  • preferenceText is null: Trim() throws before delete/update/insert routing begins.
  • Blank or whitespace-only text always routes to delete; this method never persists an empty PREFERENCE_TEXT value.
  • The return value is a plain true/exception signal — it does not distinguish between insert, update, delete, or a no-op update/delete outcome.

Sources

  • SAIF.Framework.Preferences\PreferenceData.cs