Mercurial > hg > ismi-richfaces
view src/main/java/de/mpiwg/itgroup/ismi/merge/ImportMerge.java @ 188:34ac2e1b323a
new Clean UI to find non-public digitalizations of public codices and make them public.
author | Robert Casties <casties@mpiwg-berlin.mpg.de> |
---|---|
date | Tue, 06 Nov 2018 20:05:49 +0100 |
parents | 15c26735fff7 |
children |
line wrap: on
line source
package de.mpiwg.itgroup.ismi.merge; import java.io.File; import java.io.FileInputStream; import java.io.InputStreamReader; import java.io.Reader; import java.io.Serializable; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import javax.faces.event.ActionEvent; import javax.faces.model.SelectItem; import org.apache.commons.lang.StringUtils; import org.apache.log4j.Logger; import org.mpi.openmind.repository.bo.Attribute; import org.mpi.openmind.repository.bo.Entity; import org.mpi.openmind.repository.bo.Node; import org.mpi.openmind.repository.bo.Relation; import org.mpi.openmind.repository.utils.CsvNodeListReader; import org.richfaces.event.FileUploadEvent; import org.richfaces.model.UploadedFile; import de.mpiwg.itgroup.ismi.entry.beans.AbstractISMIBean; public class ImportMerge extends AbstractISMIBean implements Serializable { private static Logger logger = Logger.getLogger(ImportMerge.class); private static final long serialVersionUID = 1L; private String importFilename = "/var/tmp/ismi-import.csv"; private String importFileMsg = null; private List<Node> importNodeList; private int importNodeIdx; private int importNodeListLength = 0; private Node importNode; private String importNodeMsg; public static String FIRST_VALUE = "old value"; public static String SECOND_VALUE = "new value"; public static String IGNORE = "ignore"; public static String TAKE = "take"; private boolean showAttributeMapping = false; private boolean showSrcRelationMapping = false; private boolean showTarRelationMapping = false; private boolean entitiesLoaded = false; private Map<String, String> firstAttMap = new HashMap<String, String>(); private Map<String, String> secondAttMap = new HashMap<String, String>(); private Entity firstEntity; private Entity secondEntity; private String firstId; private String secondId; private Entity entResult; private List<Attribute> resultAtts; private List<Relation> resultSrcRels; private List<Relation> resultTarRels; private List<String> attLabels; private Map<String, String> selectedAtts; Map<Long, String> selectedFirstSrcRelations; Map<Long, String> selectedSecondSrcRelations; Map<Long, String> selectedFirstTarRelations; Map<Long, String> selectedSecondTarRelations; public ImportMerge() { } public void uploadListener(FileUploadEvent event) throws Exception { UploadedFile item = event.getUploadedFile(); importFilename = item.getName(); reset(); try { Reader importReader = new InputStreamReader(item.getInputStream(), "UTF-8"); importNodeList = CsvNodeListReader.readCsv(importReader); this.importNodeListLength = importNodeList.size(); this.importFileMsg = "File "+ importFilename + " contains " + importNodeListLength + " Nodes"; this.importNodeIdx = 0; loadImportNode(); } catch (Exception e) { addErrorMsg("The import file could no be loaded."); addErrorMsg("Error: "+e); } } /** * Action that loads the import file and parses it into the Nodes list. * * @param event */ public void loadImportFile(ActionEvent event) { reset(); try { File importFile = new File(this.importFilename); if (!importFile.canRead()) { this.importFileMsg = "File missing!"; return; } Reader importReader = new InputStreamReader(new FileInputStream(importFile), "UTF-8"); importNodeList = CsvNodeListReader.readCsv(importReader); this.importNodeListLength = importNodeList.size(); this.importFileMsg = importNodeListLength + " Nodes"; this.importNodeIdx = 0; loadImportNode(); } catch (Exception e) { addErrorMsg("The import file could no be loaded."); addErrorMsg("Error: "+e); } } /** * Load the current Node from the import list. * * @param event */ public void loadImportNode() { reset(); try { importNode = importNodeList.get(importNodeIdx); importNodeMsg = null; firstEntity = null; secondEntity = null; if (importNode.getNodeType().equals("ATTRIBUTE")) { /* * Attribute */ Attribute att = (Attribute) importNode; String attName = att.getName(); if (attName == null) { importNodeMsg = "Attribute has no name!"; return; } Long source_id = att.getSourceId(); if (source_id == null) { importNodeMsg = "Attribute has no source_id to attach to!"; return; } else { Entity systemEnt = getWrapper().getEntityById(source_id); if (systemEnt != null) { if (systemEnt.isLightweight()) { systemEnt = getWrapper().getEntityContent(systemEnt); } Attribute systemAtt = systemEnt.getAttributeByName(attName); if ((systemAtt != null) && (systemAtt.getOwnValue().equals(att.getOwnValue()))) { importNodeMsg = "Same attribute exists already!"; return; } // create new Entity with this Attribute Entity newEnt = (Entity) systemEnt.clone(); newEnt.addAttribute(att); this.secondEntity = newEnt; // compare with old version this.firstEntity = systemEnt; } else { importNodeMsg = "Entity for Attribute does not exist!"; return; } } } else if (importNode.getNodeType().equals("ENTITY")) { /* * Entity */ Entity ent = (Entity) importNode; Long id = ent.getId(); if (id == null) { // new Entity this.secondEntity = ent; // what to use to compare? this.firstEntity = new Entity(); this.firstEntity.setLightweight(false); } else { // entity exists Entity systemEnt = getWrapper().getEntityById(id); if (systemEnt != null) { if (systemEnt.isLightweight()) { systemEnt = getWrapper().getEntityContent(systemEnt); } importNodeMsg = "Entity exists (but may be different)."; // TODO: does it make sense to check for equality? this.secondEntity = ent; // compare with old version this.firstEntity = systemEnt; } else { importNodeMsg = "Entity does not exist!"; // TODO: try to undelete? this.firstEntity = new Entity(); this.firstEntity.setLightweight(false); this.secondEntity = ent; } } } else if (importNode.getNodeType().equals("RELATION")) { /* * Relation */ Relation rel = (Relation) importNode; String relName = rel.getObjectClass(); if (relName == null) { importNodeMsg = "Relation has no name!"; return; } Long source_id = rel.getSourceId(); Long target_id = rel.getTargetId(); if (source_id == null) { // no source id importNodeMsg = "Relation has no source_id!"; return; } else if (target_id == null) { // no target id importNodeMsg = "Relation has no target_id!"; return; } else { // get source and target Entities Entity sourceEnt = getWrapper().getEntityById(source_id); Entity targetEnt = getWrapper().getEntityById(target_id); if (sourceEnt == null) { importNodeMsg = "Relation source does not exist!"; } else if (targetEnt == null) { importNodeMsg = "Relation target does not exist!"; } else { if (sourceEnt.isLightweight()) { sourceEnt = getWrapper().getEntityContent(sourceEnt); } // get existing Relation Relation systemRel = sourceEnt.getSourceRelation(relName, target_id); if ((systemRel != null) && (systemRel.getObjectClass().equals(rel.getObjectClass()))) { // TODO: also check Relation attributes importNodeMsg = "Same Relation exists already!"; return; } // create new Entity with this Relation Entity newEnt = new Entity(); newEnt.setLightweight(false); newEnt.addSourceRelation(rel); this.secondEntity = newEnt; // compare with old version this.firstEntity = sourceEnt; } } } } catch (Exception e) { addErrorMsg("The import Node could no be loaded."); addErrorMsg("Error: "+e); } } public void skipCurrentNode(ActionEvent event) { importNodeIdx += 1; if (importNodeIdx >= importNodeList.size()) { importNodeIdx = importNodeList.size() - 1; } if (importNodeIdx < 0) { importNodeIdx = 0; } loadImportNode(); } public void skipToPrevNode(ActionEvent event) { importNodeIdx -= 1; if (importNodeIdx >= importNodeList.size()) { importNodeIdx = importNodeList.size() - 1; } if (importNodeIdx < 0) { importNodeIdx = 0; } loadImportNode(); } public void loadFirstEntity(ActionEvent event) { reset(); try { if (firstEntity != null && secondEntity != null) { // create list of differences deployDifferences(); } else { if (importNodeMsg != null) { addErrorMsg(importNodeMsg); } } } catch (Exception e) { addErrorMsg("The first entity could no be loaded."); } } @Override public void reset() { this.attLabels = new ArrayList<String>(); this.selectedAtts = new HashMap<String, String>(); this.selectedFirstSrcRelations = new HashMap<Long, String>(); this.selectedSecondSrcRelations = new HashMap<Long, String>(); this.selectedFirstTarRelations = new HashMap<Long, String>(); this.selectedSecondTarRelations = new HashMap<Long, String>(); this.entResult = null; this.entitiesLoaded = false; this.showAttributeMapping = false; this.showSrcRelationMapping = false; this.showTarRelationMapping = false; } /** * Create list of differences in attributes and relations for display. */ private void deployDifferences() { this.showAttributeMapping = true; this.showSrcRelationMapping = true; this.showTarRelationMapping = true; this.entitiesLoaded = true; if (this.firstEntity != null && this.secondEntity != null) { /* if (firstEntity.isLightweight()) { this.firstEntity = getWrapper().getEntityContent(this.firstEntity); } if (secondEntity.isLightweight()) { this.secondEntity = getWrapper().getEntityContent(this.secondEntity); } this.firstEntity = (Entity) firstEntity.clone(); this.secondEntity = (Entity) secondEntity.clone(); */ /* * attributes */ this.attLabels = new ArrayList<String>(); this.selectedAtts = new HashMap<String, String>(); this.firstAttMap = new HashMap<String, String>(); this.secondAttMap = new HashMap<String, String>(); for (Attribute att : this.firstEntity.getAttributes()) { firstAttMap.put(att.getName(), att.getValue()); if (!attLabels.contains(att.getName())) { attLabels.add(att.getName()); selectedAtts.put(att.getName(), SECOND_VALUE); } } for (Attribute att : this.secondEntity.getAttributes()) { secondAttMap.put(att.getName(), att.getValue()); if (!attLabels.contains(att.getName())) { attLabels.add(att.getName()); selectedAtts.put(att.getName(), SECOND_VALUE); } } /* * source relations */ this.selectedFirstSrcRelations = new HashMap<Long, String>(); this.selectedSecondSrcRelations = new HashMap<Long, String>(); for (Relation rel : this.firstEntity.getSourceRelations()) { rel.setTarget(getWrapper().getEntityById(rel.getTargetId())); selectedFirstSrcRelations.put(rel.getId(), TAKE); } for (Relation rel : this.secondEntity.getSourceRelations()) { rel.setTarget(getWrapper().getEntityById(rel.getTargetId())); if (rel.getTarget() != null) { selectedSecondSrcRelations.put(rel.getId(), TAKE); } else { logger.error("source relation to merge has nonexistent target: "+rel); selectedSecondSrcRelations.put(rel.getId(), IGNORE); } } /* * target relations */ this.selectedFirstTarRelations = new HashMap<Long, String>(); this.selectedSecondTarRelations = new HashMap<Long, String>(); for (Relation rel : this.firstEntity.getTargetRelations()) { rel.setSource(getWrapper().getEntityById(rel.getSourceId())); selectedFirstTarRelations.put(rel.getId(), TAKE); } for (Relation rel : this.secondEntity.getTargetRelations()) { rel.setSource(getWrapper().getEntityById(rel.getSourceId())); if (rel.getSource() != null) { selectedSecondTarRelations.put(rel.getId(), TAKE); } else { logger.error("target relation to merge has nonexistent source: " + rel); selectedSecondTarRelations.put(rel.getId(), IGNORE); } } } } /** * Preview merged Entity as text. * * @param event */ public void preview(ActionEvent event) { this.generateResultEntity(); } /** * Execute Merge action from UI. */ public void listenerExecuteMerge() { this.executeMerge(); getAppBean().getSimpleSearchCache().setMapDirty(true); } /** * Merge Entities. * * firstEntity is current one. secondEntity is imported. */ private void executeMerge() { logger.info("Starting merge import " + firstEntity.getObjectClass() + " [" + getUserName() + "]" + "[firstEntity=" + firstEntity.getId() + ", secondEntity=" + secondEntity.getId() + "]"); try { this.generateResultEntity(); if (this.entResult != null) { // print to log this.printMergeInfo(entResult); // save the new Entity this.getWrapper().saveEntity(this.entResult, getSessionUser().getEmail() + "_merge", null); // update generated ownvalues this.updateRelatedOW(this.entResult, getSessionUser().getEmail() + "_merge"); logger.info("Merge import successful " + firstEntity.getObjectClass() + " [" + getUserName() + "]" + "[firstEntity=" + firstEntity.getId() + ", secondEntity=" + secondEntity.getId() + ", generatedEntity=" + entResult.getId() + "]"); this.firstEntity = null; this.secondEntity = null; addGeneralMsg("The imported entity was merged successfully"); addGeneralMsg("The new entity has the id " + this.entResult.getId()); this.reset(); } } catch (Exception e) { printInternalError(e); logger.error("[" + getUserName() + "] " + e.getMessage(), e); } } private void printMergeInfo(Entity ent) { StringBuilder sb = new StringBuilder("\n\n"); sb.append("-----------------------------------------\n"); sb.append("Merging result [" + getUserName() + "]\n"); sb.append(ent.toString() + "\n"); sb.append("Attributes:\n"); for (Attribute att : ent.getAttributes()) { sb.append("\t" + att.toString() + "\n"); } sb.append("Src Relations:\n"); for (Relation src : ent.getSourceRelations()) { sb.append("\t" + src.toString() + "\n"); } sb.append("Tar Relations:\n"); for (Relation tar : ent.getTargetRelations()) { sb.append("\t" + tar.toString() + "\n"); } sb.append("-----------------------------------------\n"); logger.info(sb.toString()); } /** * Generate new Entity taking selected Attributes and Relations from both Entities. * * Uses id from firstEntity, creating a new version of this entity. */ private void generateResultEntity() { // create new Entity this.entResult = new Entity(); this.entResult.setLightweight(false); // use id from firstEntity Long newId = this.firstEntity.getId(); if (newId == null) { // Entity is new -- try imported id newId = secondEntity.getId(); } this.entResult.setId(newId); // use object_class from firstEntity String oc = this.firstEntity.getObjectClass(); if (oc == null) { // Entity is new -- try imported object_class oc = secondEntity.getObjectClass(); } this.entResult.setObjectClass(oc); /* * generating attributes */ try { for (String attName : this.selectedAtts.keySet()) { String selected = this.selectedAtts.get(attName); String value = ""; if (selected.equals(FIRST_VALUE)) { value = (firstEntity.getAttributeByName(attName) == null) ? "" : firstEntity.getAttributeByName(attName).getOwnValue(); } else if (selected.equals(SECOND_VALUE)) { value = (secondEntity.getAttributeByName(attName) == null) ? "" : secondEntity.getAttributeByName(attName).getOwnValue(); } this.entResult.addAttribute(new Attribute(attName, "text", value)); } } catch (Exception e) { logger.error(e); addErrorMsg("Please inform support of this exception: " + e.getMessage()); } /* * generating source relations */ for (Relation rel : firstEntity.getSourceRelations()) { String selectedValue = this.selectedFirstSrcRelations.get(rel.getId()); if (StringUtils.isNotEmpty(selectedValue) && selectedValue.equals(TAKE)) { if (!this.entResult.containsSourceRelation(rel.getOwnValue(), rel.getTargetId())) { this.entResult.addSourceRelation(generateSrcRelation(rel)); } } } for (Relation rel : secondEntity.getSourceRelations()) { String selectedValue = this.selectedSecondSrcRelations.get(rel.getId()); if (StringUtils.isNotEmpty(selectedValue) && selectedValue.equals(TAKE)) { if (!this.entResult.containsSourceRelation(rel.getOwnValue(), rel.getTargetId())) { this.entResult.addSourceRelation(generateSrcRelation(rel)); } } } /* * generating target relations */ for (Relation rel : firstEntity.getTargetRelations()) { String selectedValue = this.selectedFirstTarRelations.get(rel.getId()); if (StringUtils.isNotEmpty(selectedValue) && selectedValue.equals(TAKE)) { // ensuring that there is no two equals relations. if (!this.entResult.containsTargetRelation(rel.getOwnValue(), rel.getSourceId())) { this.entResult.addTargetRelation(generateTarRelation(rel)); } } } for (Relation rel : secondEntity.getTargetRelations()) { String selectedValue = this.selectedSecondTarRelations.get(rel.getId()); if (StringUtils.isNotEmpty(selectedValue) && selectedValue.equals(TAKE)) { if (!this.entResult.containsTargetRelation(rel.getOwnValue(), rel.getSourceId())) { this.entResult.addTargetRelation(generateTarRelation(rel)); } } } } private Relation generateSrcRelation(Relation rel) { Relation newRel = new Relation(); newRel.setOwnValue(rel.getOwnValue()); newRel.setTarget(getWrapper().getEntityById(rel.getTargetId())); return newRel; } private Relation generateTarRelation(Relation rel) { Relation newRel = new Relation(); newRel.setOwnValue(rel.getOwnValue()); newRel.setSource(getWrapper().getEntityById(rel.getSourceId())); return newRel; } public List<SelectItem> getAttSelectItems() { List<SelectItem> items = new ArrayList<SelectItem>(); items.add(new SelectItem(FIRST_VALUE)); items.add(new SelectItem(SECOND_VALUE)); items.add(new SelectItem(IGNORE)); return items; } public List<SelectItem> getRelSelectItems() { List<SelectItem> items = new ArrayList<SelectItem>(); items.add(new SelectItem(TAKE)); items.add(new SelectItem(IGNORE)); return items; } public void actionShowTarRelationMapping(ActionEvent event) { this.showTarRelationMapping = true; } public void actionHideTarRelationMapping(ActionEvent event) { this.showTarRelationMapping = false; } public void actionShowSrcRelationMapping(ActionEvent event) { this.showSrcRelationMapping = true; } public void actionHideSrcRelationMapping(ActionEvent event) { this.showSrcRelationMapping = false; } public void actionShowAttributeMapping(ActionEvent event) { this.showAttributeMapping = true; } public void actionHideAttributeMapping(ActionEvent event) { this.showAttributeMapping = false; } public Entity getEntResult() { return entResult; } public void setEntResult(Entity entResult) { this.entResult = entResult; } public List<Attribute> getResultAtts() { return resultAtts; } public void setResultAtts(List<Attribute> resultAtts) { this.resultAtts = resultAtts; } public List<Relation> getResultSrcRels() { return resultSrcRels; } public void setResultSrcRels(List<Relation> resultSrcRels) { this.resultSrcRels = resultSrcRels; } public List<Relation> getResultTarRels() { return resultTarRels; } public void setResultTarRels(List<Relation> resultTarRels) { this.resultTarRels = resultTarRels; } public Entity getFirstEntity() { return firstEntity; } public void setFirstEntity(Entity firstEntity) { this.firstEntity = firstEntity; } public Entity getSecondEntity() { return secondEntity; } public void setSecondEntity(Entity secondEntity) { this.secondEntity = secondEntity; } public String getFirstId() { return firstId; } public void setFirstId(String firstId) { this.firstId = firstId; } public String getSecondId() { return secondId; } public void setSecondId(String secondId) { this.secondId = secondId; } public List<String> getAttLabels() { return attLabels; } public void setAttLabels(List<String> attLabels) { this.attLabels = attLabels; } public Map<String, String> getFirstAttMap() { return firstAttMap; } public void setFirstAttMap(Map<String, String> firstAttMap) { this.firstAttMap = firstAttMap; } public Map<String, String> getSecondAttMap() { return secondAttMap; } public void setSecondAttMap(Map<String, String> secondAttMap) { this.secondAttMap = secondAttMap; } public Map<String, String> getSelectedAtts() { return selectedAtts; } public void setSelectedAtts(Map<String, String> selectedAtts) { this.selectedAtts = selectedAtts; } public boolean isShowAttributeMapping() { return showAttributeMapping; } public void setShowAttributeMapping(boolean showAttributeMapping) { this.showAttributeMapping = showAttributeMapping; } public boolean isEntitiesLoaded() { return entitiesLoaded; } public void setEntitiesLoaded(boolean entitiesLoaded) { this.entitiesLoaded = entitiesLoaded; } public Map<Long, String> getSelectedFirstSrcRelations() { return selectedFirstSrcRelations; } public void setSelectedFirstSrcRelations(Map<Long, String> selectedFirstSrcRelations) { this.selectedFirstSrcRelations = selectedFirstSrcRelations; } public Map<Long, String> getSelectedSecondSrcRelations() { return selectedSecondSrcRelations; } public void setSelectedSecondSrcRelations(Map<Long, String> selectedSecondSrcRelations) { this.selectedSecondSrcRelations = selectedSecondSrcRelations; } public boolean isShowSrcRelationMapping() { return showSrcRelationMapping; } public void setShowSrcRelationMapping(boolean showSrcRelationMapping) { this.showSrcRelationMapping = showSrcRelationMapping; } public boolean isShowTarRelationMapping() { return showTarRelationMapping; } public void setShowTarRelationMapping(boolean showTarRelationMapping) { this.showTarRelationMapping = showTarRelationMapping; } public Map<Long, String> getSelectedFirstTarRelations() { return selectedFirstTarRelations; } public void setSelectedFirstTarRelations(Map<Long, String> selectedFirstTarRelations) { this.selectedFirstTarRelations = selectedFirstTarRelations; } public Map<Long, String> getSelectedSecondTarRelations() { return selectedSecondTarRelations; } public void setSelectedSecondTarRelations(Map<Long, String> selectedSecondTarRelations) { this.selectedSecondTarRelations = selectedSecondTarRelations; } /** * @return the importFilename */ public String getImportFilename() { return importFilename; } /** * @param importFilename * the importFilename to set */ public void setImportFilename(String importFilename) { this.importFilename = importFilename; } /** * @return the importFileMsg */ public String getImportFileMsg() { return importFileMsg; } /** * @param importFileMsg * the importFileMsg to set */ public void setImportFileMsg(String importFileMsg) { this.importFileMsg = importFileMsg; } /** * @return the importNode */ public Node getImportNode() { return importNode; } public String getImportNodeAsText() { String s = ""; try { String nt = importNode.getNodeType(); if (nt.equals("ATTRIBUTE")) { Attribute att = (Attribute) importNode; s = "ATTRIBUTE " + att.getName() + " [" + att.getSourceObjectClass() + " " + att.getSourceId() + "] = " + att.getOwnValue(); } else if (nt.equals("ENTITY")) { Entity ent = (Entity) importNode; s = "ENTITY " + ent.getObjectClass() + " [" + ent.getId() + "] : " + ent.getOwnValue(); } else if (nt.equals("RELATION")) { Relation rel = (Relation) importNode; s = "RELATION " + rel.getObjectClass() + " [" + rel.getId() + "] : " + "source=[" + rel.getSourceObjectClass() + " " + rel.getSourceId() + "] " + "target=[" + rel.getTargetObjectClass() + " " + rel.getTargetId() + "]"; } else { s = importNode.toString(); } } catch (Exception e) { logger.error(e); } return s; } /** * @param importNode the importNode to set */ public void setImportNode(Node importNode) { this.importNode = importNode; } /** * @return the importNodeList */ public List<Node> getImportNodeList() { return importNodeList; } /** * @param importNodeList the importNodeList to set */ public void setImportNodeList(List<Node> importNodeList) { this.importNodeList = importNodeList; } /** * @return the importNodeListLength */ public int getImportNodeListLength() { return importNodeListLength; } /** * @return the importNodeIdx */ public int getImportNodeIdx() { return importNodeIdx; } /** * @param importNodeIdx the importNodeIdx to set */ public void setImportNodeIdx(int importNodeIdx) { this.importNodeIdx = importNodeIdx; } /** * @return the importNodeMsg */ public String getImportNodeMsg() { return importNodeMsg; } /** * @param importNodeMsg the importNodeMsg to set */ public void setImportNodeMsg(String importNodeMsg) { this.importNodeMsg = importNodeMsg; } }