sclass HCRUD_Concepts extends HCRUD_Data { Concepts cc = db_mainConcepts(); Class cClass; new L> onCreateOrUpdate; MapSO filters; // fields to filter by/add to new objects *(Class *cClass) {} S itemName() { ret humanizeShortName(cClass); } //LS fields() { ret conceptFields(cClass); } L list() { ret lambdaMap itemToMapForList(defaultSort(asList(listConcepts()))); } Cl listConcepts() { ret conceptsWhere(cc, cClass, mapToParams(filters)); } L defaultSort(L l) { ret l; } MapSO emptyObject() { A c = unlisted(cClass); print("fieldOrder", getFieldOrder(c)); ret printStruct("emptyObject", itemToMap(c)); } MapSO itemToMap(A c) { if (c == null) null; ret putKeysFirst(getFieldOrder(c), conceptToMap_gen_withNullValues(c)); } MapSO itemToMapForList(A c) { if (c == null) null; MapSO map = itemToMap(c); massageItemMapForList(c, map); ret map; } // overridable void massageItemMapForList(A c, MapSO map) { } MapSO getObject(O id) { ret itemToMap(getConcept(cc, cClass, toLong(id))); } O createObject(SS map) { A c = cnew(cc, cClass); cset(c, mapToParams(filters)); cSmartSet(c, mapToParams(map)); pcallFAll(onCreateOrUpdate, c); ret c.id; } S updateObject(O id, SS map) { A c = getConcept(cc, cClass, toLong(id)); if (c == null) ret "Object " + id + " not found"; cSmartSet(c, mapToParams(map)); pcallFAll(onCreateOrUpdate, c); ret "Object " + id + " updated"; } S deleteObject(O id) { A c = getConcept(cc, cClass, toLong(id)); if (c == null) ret "Object not found"; deleteConcept(c); ret "Object deleted"; } HCRUD_Concepts addFilter(S field, O value) { filters = orderedMapPutOrCreate(filters, field, value); this; } Renderer getRenderer(S field) { Class type = fieldType(cClass, field); if (eq(type, bool.class)) ret new CheckBox(); if (eq(type, Concept.Ref.class)) { Class c = getTypeArgumentAsClass(genericFieldType(cClass, field)); ret new ComboBox(map(cc.list(c), val -> shorten(val.id + ": " + val))); } ret super.getRenderer(field); } }