Skip to content

Create a menu item

Creates a new menu item, illustrating the create pattern shared by every maintenance object in this library (clsMenuPage, clsMenuSecurity, clsMenuSecurityUser, clsMenuFavorite, clsApplicationCode, clsMenuCategoryCode), including the cascading save of the item's child security groups.

Field Value
Operation ID OP-MENU-06
Trigger Administration code calls clsMenuItem.NewMenuItem(dpi) then Save()
Inputs Item properties supplied by the caller; DataPortalInfo.UserID
Outputs New MENU_ITEM row and a populated sequence number
Primary components clsMenuItem (create + insert); the same pattern applies to every maintenance object in this library
Entry point SAIF.Business.Menu/clsMenuItem.vb

Steps

  1. NewMenuItem calls DataAccessLayer.CreateObject(New Criteria(dpi)).
  2. BeforeCreate issues a Scalar request with CreateSQL = SELECT MENU_ITEM_SEQ.NEXTVAL FROM DUAL (SQL-002). (BR-MENU-014)
  3. AfterCreate stores the returned sequence into both the object and the criteria, stamps UpdateDate = Now and UpdateUser from DataPortalInfo.UserID.Trim.ToUpper, then MarkNew + MarkClean. (BR-MENU-015, BR-MENU-016)
  4. The caller sets properties; each setter compares old and new values and calls MarkDirty only on an actual change. (BR-MENU-017)
  5. Save → SaveMe: if the object itself is dirty, call MyBase.SaveChild() when it is a child, else MyBase.Save(). (BR-MENU-018)
  6. If not dirty: no database work occurs.
  7. BeforeInsert issues a NonQuery with InsertSQL (SQL-008) and parameters MenuItemSeqNum, MenuPageSeqNum, MenuCategoryCode (5), VisibleFlag (1, from IsVisible.ToY_N_String), PageOrder, ToolTip (1000), UserId (30). UPDATE_DATE is set to SYSDATE in SQL, not passed. (BR-MENU-016, BR-MENU-019; table MENU_ITEM)
  8. AfterInsert requires exactly one affected row; otherwise it adds error message InsertError = "Insert Failed". On success it calls MarkOld. (BR-MENU-020)
  9. On failure (rows affected ≠ 1): the object records the InsertError error message instead of throwing.
  10. After the parent save succeeds, if SecurityGroups.IsDirty the child clsMenuSecurityCollection is saved with SaveChildObject (SQL-010, table MENU_SECURITY). (BR-MENU-021)

Process flow

flowchart TD
    Start([NewMenuItem]) --> Seq[BeforeCreate: fetch MENU_ITEM_SEQ.NEXTVAL]
    Seq --> Stamp[AfterCreate: stamp UpdateDate/UpdateUser, MarkClean]
    Stamp --> SetProps[Caller sets properties, MarkDirty on change]
    SetProps --> Dirty{Object dirty?}
    Dirty -->|No| Skip([Save is a no-op])
    Dirty -->|Yes| Insert[BeforeInsert: INSERT MENU_ITEM row]
    Insert --> RowCheck{Exactly one row affected?}
    RowCheck -->|No| Fail([AfterInsert: add InsertError])
    RowCheck -->|Yes| MarkOld[AfterInsert: MarkOld]
    MarkOld --> SecDirty{SecurityGroups dirty?}
    SecDirty -->|Yes| SaveChild([SaveChildObject: insert MENU_SECURITY rows])
    SecDirty -->|No| Done([Create complete])
    SaveChild --> Done

Failure and edge-case behavior

  • Insert affects zero or more than one row: AfterInsert adds InsertError = "Insert Failed" instead of throwing.
  • Object is not dirty when Save is called: no database work occurs.

Sources

  • SAIF.Business.Menu/clsMenuItem.vb
  • SAIF.Business.Menu/clsMenuSecurityCollection.vb