package foundation.dao; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; import org.json.JSONObject; import foundation.dao.version.PackageChange; import foundation.data.entity.Entity; import foundation.data.entity.EntityNode; import foundation.data.entity.EntitySet; import foundation.data.entity.EntityTree; import foundation.data.entity.LineOperator; import foundation.data.object.DataObject; import foundation.data.object.IParamProvider; import foundation.handler.IMessageReporter; import foundation.json.IJSONProvider; import foundation.json.IJSONWriter; import foundation.json.JArrayReader; import foundation.json.JObjectReader; import foundation.json.JSONBuilder; import foundation.json.JSONReader; import foundation.json.JType; import foundation.translator.ValueType; import foundation.util.ContentBuilder; import foundation.util.ID; import foundation.util.Util; import foundation.variant.provider.DataEvent; public class PackageItem implements IJSONProvider { protected static Logger logger; protected DataPackage parent; protected PackageItem master; protected PackageItem owner; protected PackageItemMeta meta; protected String lineId; protected DataCells dataCells; static { logger = LogManager.getLogger(PackageItem.class); } public PackageItem(DataPackage parent, PackageItemMeta meta) { this.parent = parent; this.meta = meta; this.dataCells = new DataCells(); } public PackageItem(DataObject dataObject) { meta = new PackageItemMeta(); meta.load(dataObject); this.dataCells = new DataCells(); } public void loadOneDataFromJSON(JObjectReader packageReader, DataSource dataSource) throws Exception { String name = getName(); JType valueType = packageReader.getType(name); //1. 如果JSON中是Object,加载Entity if (JType.Object == valueType) { JObjectReader itemReader = packageReader.getReader(name, JType.Object); loadEntityFromJSON(itemReader, dataSource); return; } //1. 如果JSON中是Array,加载EntitySet if (JType.Array == valueType) { JArrayReader itemReader = packageReader.getReader(name, JType.Array); loadEntitySetFromJSON(itemReader, dataSource); return; } } public Entity createDefaultOneData() throws Exception { DataObject dataObject = meta.getDataObject(); //1. 创建Entity, 添加默认值 Entity entity = dataObject.createBrowseEntity(true); dataObject.setEntityDefaultValues(DataEvent.New, entity); entity.setId(ID.newValue()); //2. 如果不是Master,设置ParentID if (PackageItemType.Master != getType()) { String masterId = master.getId(); entity.set(meta.getParentField(), masterId); } //3. 加载数据并返回 dataCells.load(DataSource.New, entity); return entity; } public void cloneDataTo(PackageItem target, DataSource... dataSource) throws Exception { for (DataSource source: dataSource) { Object data = dataCells.getData(source); if (data == null) { continue; } DataObject dataObject = meta.getDataObject(); //1. 如果是 Entity 就 clone 一条 if (data instanceof Entity) { Entity entity = dataObject.cloneEntity((Entity)data); target.dataCells.setData(entity, DataSource.New); return; } //2. 如果是 EntitySet 就 clone 多条 if (data instanceof EntitySet) { EntitySet entitySet = dataObject.cloneEntitySet((EntitySet)data); target.dataCells.setData(entitySet, DataSource.New); return; } } } public void loadBatchDataFromDB(Filter filter, Page page, OrderBy orderBy) throws Exception { DataObject dataObject = meta.getDataObject(); //1. 如果没有OrderBy,使用DataPackage配置中的默认OrderBy if (orderBy == null || orderBy.isEmpty()) { orderBy = dataObject.getDefaultOrderBy(); } //2. 加载EntitySet EntitySet entitySet = dataObject.getBrowseEntitySet(filter, page, orderBy); dataCells.load(DataSource.DB, entitySet); } public void loadTreeDataFromDB(Filter filter, OrderBy customOrderBy) throws Exception { DataObject dataObject = meta.getDataObject(); //1. Order By OrderBy orderBy = new OrderBy("parent_id"); if (customOrderBy == null || customOrderBy.isEmpty()) { customOrderBy = dataObject.getDefaultOrderBy(); } orderBy.addAll(customOrderBy); //2.1 如果没有过滤条件,加载包含所有数据的EntityTree if (filter == null || filter.isEmpty()) { EntityTree tree = dataObject.getBrowseEntityTree(filter, orderBy); dataCells.load(DataSource.DB, tree); return; } //2.2 如果有过滤条件,加载包含所有数据的EntityTree,然后进行过滤 EntitySet entitySet = dataObject.getTableEntitySet(filter); EntityTree tree = dataObject.getBrowseEntityTree(orderBy); tree.setSelectActive(true); for (Entity entity: entitySet) { Entity selected = tree.getEntity("id", entity.getId()); ((EntityNode)selected).setSelected(); } dataCells.load(DataSource.DB, tree); return; } public void loadOneDataFromDB() throws Exception { loadOneDataFromDB(null); } public boolean loadOneDataFromDB(Filter filter) throws Exception { DataObject dataObject = meta.getDataObject(); PackageItemType type = meta.getType(); //1. 在页面原有filter的基础上,增加过滤条件,如果是 master用id,如果不是master用parentID String fieldName = (PackageItemType.Master == getType()) ? "id" : meta.getParentField(); String masterId = master.getId(); if (Util.isEmpty(masterId) && (filter == null || filter.isEmpty())) { logger.error("id or filter is null, dataPackage skip load"); return false; } if (filter == null) { filter = new Filter(); } if (!Util.isEmpty(masterId)) { fieldName = dataObject.getTableName() + "." + fieldName; filter.add(fieldName, masterId); } //2. 从数据库中加载Entity if (type.isEntity()) { Entity entity = dataObject.getBrowseEntity(filter); if (entity != null) { lineId = entity.getId(); } dataCells.load(DataSource.DB, entity); return entity != null; } //3. 从数据库中加载EntitySet if (type.isEntitySet()) { EntitySet entityset = dataObject.getBrowseEntitySet(filter); dataCells.load(DataSource.DB, entityset); return !entityset.isEmpty(); } return false; } public int saveOneDataToDB(DataSource dataSource) throws Exception { return saveOneDataToDB(dataSource, null, null); } public int saveOneDataToDB(DataSource dataSource, IParamProvider paramProvider, IMessageReporter reporter) throws Exception { DataObject dataObject = meta.getDataObject(); //1. 如果是Entity,就单条保存 if (isEntity(dataSource)) { Entity entity = getEntity(dataSource); dataObject.saveEntity(entity, paramProvider, reporter); if (Util.isEmpty(lineId)) { lineId = entity.getId(); } return 1; } //2. 如果是EntitySet,就多条保存 int result = 0; if (isEntitySet(dataSource)) { EntitySet entitySet = getEntitySet(dataSource); //2.1 判断明细中哪些记录需要删除 deleteEntitys(dataObject, entitySet); for (Entity entity: entitySet) { dataObject.saveEntity(entity, paramProvider, reporter); result++; } } return result; } //将不在 EntitySet 中的记录删除掉 private void deleteEntitys(DataObject dataObject, EntitySet entitySet) throws Exception { String parentId = master.getId(); if (Util.isEmpty(parentId)) { return; } //1. 根据 parent.id 删除不在entitySet中的数据 Filter filter = new Filter(); filter.add(meta.getParentField(), parentId); ContentBuilder builder = new ContentBuilder(", "); boolean empty = true; for (Entity entity : entitySet) { String id = entity.getString("id"); if (Util.isEmpty(id)) { continue; } builder.append(Util.quotedStr(id)); empty = false; } if (entitySet != null && !entitySet.isEmpty()) { filter.add("id", " not in ", "(" + builder.toString() + ")"); } //2. 如果都是没有 ID 的数据(都是需要插入的数据),就直接退出 if (empty) { return; } //3. 删除数据 dataObject.deleteEntitySet(filter); } public void saveOneDataToString(DataSource dataSource, JSONBuilder result) { if(isEmpty(dataSource)) { return; } //1. 如果是Entity,就单条保存 if (isEntity(dataSource)) { Entity entity = getEntity(dataSource); result.beginObject(getName()); entity.writeJSONBody(result); result.endObject(); return; } //2. 如果是EntitySet,就多条保存 if (isEntitySet(dataSource)) { EntitySet entitySet = getEntitySet(dataSource); result.beginArray(getName()); for (Entity entity: entitySet) { if (Util.isEmpty(entity.getId())) { entity.set("id", ID.newValue()); } result.beginObject(); entity.writeJSONBody(result); result.endObject(); } result.endArray(); } } public void deleteOneDataFromDB() throws Exception { DataObject dataObject = meta.getDataObject(); String fieldName = (PackageItemType.Master == getType()) ? "id" : meta.getParentField(); String masterId = master.getId(); Filter filter = new Filter(fieldName, masterId); dataObject.deleteEntity(filter); } public void compare(PackageChange changes, DataSource oneSource, DataSource anotherSource) throws Exception { if (oneSource == anotherSource) { return; } if (oneSource == null || anotherSource == null) { return; } //1. 如果是Entity,就单条保存 if (isEntity(oneSource)) { Entity one = getEntity(oneSource); Entity another = getEntity(anotherSource); changes.compareEntity(getName(), one, another); return; } //2. 如果是EntitySet,就多条保存 if (isEntitySet(oneSource)) { EntitySet one = getEntitySet(oneSource); EntitySet another = getEntitySet(anotherSource); changes.compareEntitySet(getName(), one, another); } } protected Entity loadEntityFromJSON(JObjectReader itemReader, DataSource dataSource) throws Exception { if (itemReader == null) { return null; } //1. 创建空记录 DataObject dataObject = meta.getDataObject(); Entity entity = dataObject.createEmptyBrowseEntity(); //2. 从JSON读取数据 doLoadEntityFromJSON(itemReader, entity); if (entity.isEmpty()) { return null; } //3. 如果ID为空,设置ID if (entity.isEmptyValue("id")) { String dataId = ID.newValue(); entity.set("id", dataId); } //4. 设置ParentID if (PackageItemType.Master != getType()) { String masterId = master.getId(), parentField = meta.getParentField(); if (entity.isEmptyValue(parentField)) { entity.set(parentField, masterId); } } //5. 设置行ID和data lineId = entity.getId(); dataCells.load(dataSource, entity); return entity; } protected void loadEntitySetFromJSON(JSONReader arrayReader, DataSource dataSource) throws Exception { DataObject dataObject = meta.getDataObject(); String masterField = meta.getParentField(); String masterId = master.getId(); EntitySet entitySet = dataObject.createBrowseEntitySet(); for (JSONReader detailReader: arrayReader) { Entity entity = entitySet.newEntity(); doLoadEntityFromJSON(detailReader, entity); if (entity.isEmpty()) { continue; } if (entity.isEmptyValue(masterField)) { entity.set(masterField, masterId); } entitySet.append(entity); } dataCells.load(dataSource, entitySet); } protected void doLoadEntityFromJSON(JSONReader objectReader, Entity entity) { //1. load operator LineOperator operator = LineOperator.parse(objectReader.getString(LineOperator.Code)); entity.setOperator(operator); //2. load field value for (JSONReader item: objectReader) { String name = item.getName(); Object value = item.getValue(null); if (!entity.contains(name) || (value == null)) { continue; } if (JSONObject.NULL == value) { entity.set(name, ValueType.Null); continue; } value = Util.decodeValue(value); entity.set(name, value); } } public String getId() { return lineId; } public void setId(String id) throws Exception { lineId = id; } public String getName() { return meta.getName(); } public String getFullName() { String result = parent.getName() + "." + meta.getName(); return result; } public PackageItemType getType() { return meta.getType(); } public PackageItemMeta getMeta() { return meta; } public Object getData(DataSource... dataSource) { return dataCells.getData(dataSource); } public Entity getEntity(DataSource... dataSource) { return dataCells.getEntity(dataSource); } public EntitySet getEntitySet(DataSource... dataSource) { return dataCells.getEntitySet(dataSource); } public String getValueString(String fieldName) { return getValueString(fieldName, DataSource.DB); } public String getValueString(String fieldName, DataSource... dataSource) { Entity entity = getEntity(dataSource); return entity.getString(fieldName); } public void setMaster(PackageItem master) { this.master = master; } public DataObject getDataObject() { return meta.getDataObject(); } public boolean isTree() { return meta.isTree(); } public boolean isEntitySet(DataSource... dataSource) { return dataCells.isEntitySet(dataSource); } public boolean isEntity(DataSource... dataSource) { return dataCells.isEntity(dataSource); } public boolean isEmpty(DataSource... dataSource) { return dataCells.isEmpty(dataSource); } public String getParentField() { return meta.getParentField(); } public boolean isLasyLoad() { return meta.isLasyLoad(); } public void setResultData(DataSource dataSource) { dataCells.setResult(dataSource); } public Page getPage() { return null; } @Override public void writeJSON(IJSONWriter writer) { writer.beginObject(getName()); writeJSONBody(writer); writer.endObject(); } public void writeJSONBody(IJSONWriter writer) { writer.write("lasyLoad", meta.isLasyLoad()); } @Override public String toString() { return parent.getName() + "." + meta.getName(); } }