/******************************************************************************* * Copyright (c) 2007, 2010 Association for Decentralized Information Management * in Industry THTH ry. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * VTT Technical Research Centre of Finland - initial API and implementation *******************************************************************************/ package org.simantics.modeling.services; import java.util.Collections; import java.util.List; import java.util.Set; import org.simantics.databoard.Bindings; import org.simantics.databoard.util.URIStringUtils; import org.simantics.db.ReadGraph; import org.simantics.db.Resource; import org.simantics.db.common.primitiverequest.PossibleRelatedValueImplied2; import org.simantics.db.common.procedure.adapter.TransientCacheListener; import org.simantics.db.common.utils.NameUtils; import org.simantics.db.exception.DatabaseException; import org.simantics.layer0.Layer0; import org.simantics.operation.Layer0X; import org.simantics.project.IProject; import org.simantics.structural.stubs.StructuralResource2; /** * @author Tuukka Lehtonen */ public final class ComponentNamingUtil { private final static boolean DEBUG = false; public static final String validateInstanceName(ReadGraph graph, IProject project, Resource configurationRoot, Resource composite, Resource componentType, String proposition, boolean acceptProposition) throws DatabaseException, NamingException { if (DEBUG) { System.out.println("validateInstanceName(project=" + project + ", configurationRoot=" + configurationRoot + ", composite=" + composite + ", componentType=" + componentType + ", proposition=" + proposition + ")"); System.out.println(" INVOKED FROM: " + new Exception().getStackTrace()[1].toString()); } ComponentNamingStrategy strategy = findNamingStrategy(graph, project, composite); if (strategy != null) { proposition = strategy.validateInstanceName(graph, configurationRoot, composite, componentType, proposition, acceptProposition); } // As a fallback method, try to deduce the name based on type properties. if (proposition == null) { proposition = fallbackNameGeneration(graph, composite, componentType); } return proposition; } public static final String validateInstanceName(ReadGraph graph, IProject project, Resource configurationRoot, Resource component, String proposition, boolean acceptProposition) throws DatabaseException, NamingException { Layer0 L0 = Layer0.getInstance(graph); Resource composite = graph.getPossibleObject(component, L0.PartOf); ComponentNamingStrategy strategy = findNamingStrategy(graph, project, composite); if (strategy != null) { return strategy.validateInstanceName(graph, configurationRoot, component, proposition, acceptProposition); } else { return null; } } public static final String findFreshInstanceName(ReadGraph graph, IProject project, Resource configurationRoot, Resource composite, Resource componentType) throws DatabaseException, NamingException { String proposition = null; if (DEBUG) { System.out.println("findFreshInstanceName(project=" + project + ", configurationRoot=" + configurationRoot + ", composite=" + composite + ", componentType=" + componentType + ")"); System.out.println(" INVOKED FROM: " + new Exception().getStackTrace()[1].toString()); } ComponentNamingStrategy strategy = findNamingStrategy(graph, project, composite); if (strategy != null) { proposition = strategy.findFreshInstanceName(graph, configurationRoot, composite, componentType); } // As a fallback method, try to deduce the name based on type properties. if (proposition == null) { proposition = fallbackNameGeneration(graph, composite, componentType); } return proposition; } public static final String findFreshEscapedInstanceName(ReadGraph graph, IProject project, Resource configurationRoot, Resource composite, Resource componentType) throws DatabaseException, NamingException { if (DEBUG) { System.out.println("findFreshEscapedInstanceName(project=" + project + ", configurationRoot=" + configurationRoot + ", composite=" + composite + ", componentType=" + componentType + ")"); new Exception("trace").printStackTrace(); } String proposition = findFreshInstanceName(graph, project, configurationRoot, composite, componentType); proposition = URIStringUtils.escape(proposition); return proposition; } /** * @param graph * @param project * @param configurationRoot * @param composite * @param componentType * @param externallyReserved * @return * @throws DatabaseException * @throws NamingException */ public static final String validateInstanceName( ReadGraph graph, IProject project, Resource configurationRoot, Resource composite, Resource componentType, Set externallyReserved) throws DatabaseException, NamingException { if (DEBUG) { System.out.println("validateInstanceName(project=" + project + ", configurationRoot=" + configurationRoot + ", composite=" + composite + ", componentType=" + componentType + ")"); System.out.println(" INVOKED FROM: " + new Exception().getStackTrace()[1].toString()); } ComponentNamingStrategy strategy = findNamingStrategy(graph, project, composite); if (strategy == null) throw new NamingException("No naming strategy available, project=" + project + ", composite=" + composite + ", componentType=" + componentType); String proposition = ComponentNamingUtil.generateProposition(graph, composite, componentType); List validated = strategy.validateInstanceNames(graph, configurationRoot, Collections.singletonList(proposition), true, externallyReserved); proposition = validated.get(0); return proposition; } /** * @param graph * @param project * @param configurationRoot * @param propositions * @param externallyReserved * @return * @throws DatabaseException * @throws NamingException */ public static final List validateInstanceNames( ReadGraph graph, IProject project, Resource configurationRoot, List propositions, boolean acceptProposition, Set externallyReserved) throws DatabaseException, NamingException { ComponentNamingStrategy strategy = findNamingStrategy(graph, project, configurationRoot); if (strategy == null) throw new NamingException("No naming strategy available, project=" + project); return strategy.validateInstanceNames(graph, configurationRoot, propositions, acceptProposition, externallyReserved); } /** * This is a fallback name generation method that deduces propositions * container-locally based on component type prefixes or names. * * @param graph * @param composite * @param componentType * @return * @throws DatabaseException */ private static String fallbackNameGeneration(ReadGraph graph, Resource container, Resource componentType) throws DatabaseException { return NameUtils.findFreshName(graph, generateProposition(graph, container, componentType), container); } public static String generateProposition(ReadGraph graph, String containerGeneratedNamePrefix, Resource componentType) throws DatabaseException { Layer0X L0X = Layer0X.getInstance(graph); StringBuilder proposition = new StringBuilder(); if (containerGeneratedNamePrefix != null) proposition.append(containerGeneratedNamePrefix); String componentPrefix = graph.getPossibleRelatedValue(componentType, L0X.HasGeneratedNamePrefix, Bindings.STRING); if (componentPrefix == null) { Layer0 L0 = Layer0.getInstance(graph); componentPrefix = graph.getPossibleRelatedValue(componentType, L0.HasName); if (componentPrefix == null) componentPrefix = "Entity"; } proposition.append(componentPrefix); return proposition.toString(); } public static String generateProposition(ReadGraph graph, Resource container, Resource componentType) throws DatabaseException { Layer0X L0X = Layer0X.getInstance(graph); String containerPrefix = graph.getPossibleRelatedValue(container, L0X.HasGeneratedNamePrefix, Bindings.STRING); return generateProposition(graph, containerPrefix != null ? containerPrefix : "", componentType); } public static final ComponentNamingStrategy findNamingStrategy(ReadGraph graph, IProject project, Resource composite) throws DatabaseException { // Primarily, use naming function from composite ComponentNamingStrategy strategy = graph.syncRequest( new PossibleRelatedValueImplied2(composite, StructuralResource2.getInstance(graph).Composite_namingFunction), TransientCacheListener.instance()); if (strategy == null && project != null) { // If not available, try to find ComponentNamingStrategy for project strategy = project.getHint(ComponentNamingStrategy.PROJECT_KEY); } return strategy; } }