package org.openlca.app.cloud.ui.diff;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.openlca.app.cloud.CloudUtil;
import org.openlca.app.cloud.index.DiffIndex;
import org.openlca.app.cloud.ui.diff.DiffResult.DiffResponse;
import org.openlca.cloud.model.data.Dataset;
import org.openlca.core.database.CategoryDao;
import org.openlca.core.database.IDatabase;
import org.openlca.core.model.Category;
import org.openlca.core.model.ModelType;
public class DiffNodeBuilder {
private final Map<String, DiffNode> nodes = new HashMap<>();
private final Map<String, DiffResult> diffs = new HashMap<>();
private final CategoryDao categoryDao;
private final DiffIndex index;
private final String database;
public DiffNodeBuilder(IDatabase database, DiffIndex index) {
this.categoryDao = new CategoryDao(database);
this.index = index;
this.database = database.getName();
}
public DiffNode build(List<DiffResult> diffs) {
if (!init(diffs))
return null;
DiffNode root = new DiffNode(null, database);
nodes.put("", root);
for (DiffResult result : this.diffs.values())
build(result);
return root;
}
private boolean init(List<DiffResult> diffs) {
for (DiffResult result : diffs)
this.diffs.put(result.getDataset().refId, result);
nodes.clear();
return this.diffs.size() != 0;
}
private void build(DiffResult result) {
if (nodes.containsKey(result.getDataset().refId))
return;
if (!result.getDataset().type.isCategorized())
return;
if (result.getType() == DiffResponse.NONE)
return;
DiffNode parent = getOrCreateParentNode(result.getDataset());
DiffNode node = new DiffNode(parent, result);
parent.children.add(node);
nodes.put(result.getDataset().refId, node);
}
private DiffNode getOrCreateParentNode(Dataset dataset) {
String parentId = dataset.categoryRefId;
ModelType categoryType = dataset.type;
if (categoryType == ModelType.CATEGORY)
categoryType = dataset.categoryType;
if (parentId == null)
return getOrCreateModelTypeNode(categoryType);
DiffNode categoryNode = nodes.get(parentId);
if (categoryNode != null)
return categoryNode;
DiffResult result = diffs.get(parentId);
if (result != null)
return createNodeFromDiff(result);
Category category = categoryDao.getForRefId(parentId);
return createNodeFromCategory(category);
}
private DiffNode createNodeFromCategory(Category category) {
DiffNode parent = getOrCreateParentNode(CloudUtil.toDataset(category));
DiffResult result = new DiffResult(index.get(category.getRefId()));
DiffNode node = new DiffNode(parent, result);
parent.children.add(node);
nodes.put(category.getRefId(), node);
return node;
}
private DiffNode createNodeFromDiff(DiffResult result) {
DiffNode parent = getOrCreateParentNode(result.getDataset());
DiffNode node = new DiffNode(parent, result);
parent.children.add(node);
nodes.put(result.getDataset().refId, node);
return node;
}
private DiffNode getOrCreateModelTypeNode(ModelType type) {
DiffNode typeNode = nodes.get(type.name());
if (typeNode != null)
return typeNode;
DiffNode root = nodes.get("");
typeNode = new DiffNode(root, type);
root.children.add(typeNode);
nodes.put(type.name(), typeNode);
return typeNode;
}
}