From fc7e3dc61a2ac8de32914af331c1144e4fa843e6 Mon Sep 17 00:00:00 2001 From: Kristóf Marussy Date: Sat, 19 Aug 2023 03:00:23 +0200 Subject: refactor: remove unused VIATRA code We don't need Eclipse platform support, table-based scopes, and EMF support. --- .../tools/refinery/viatra/runtime/IExtensions.java | 24 - .../viatra/runtime/ViatraQueryRuntimePlugin.java | 32 - .../runtime/api/AdvancedViatraQueryEngine.java | 163 ++-- .../runtime/api/IModelConnectorTypeEnum.java | 18 - .../viatra/runtime/api/IQuerySpecification.java | 37 +- .../viatra/runtime/api/IRunOnceQueryEngine.java | 68 -- .../viatra/runtime/api/LazyLoadingQueryGroup.java | 64 -- .../viatra/runtime/api/PackageBasedQueryGroup.java | 133 ---- .../viatra/runtime/api/ViatraQueryEngine.java | 2 - .../runtime/api/ViatraQueryEngineManager.java | 77 +- .../runtime/api/impl/BaseGeneratedEMFPQuery.java | 110 --- .../impl/BaseGeneratedEMFQuerySpecification.java | 40 - ...tedEMFQuerySpecificationWithGenericMatcher.java | 58 -- .../viatra/runtime/api/impl/BasePatternMatch.java | 40 +- .../runtime/api/impl/RunOnceQueryEngine.java | 140 ---- .../runtime/api/scope/IIndexingErrorListener.java | 8 +- .../runtime/emf/DynamicEMFQueryRuntimeContext.java | 47 -- .../viatra/runtime/emf/EMFBaseIndexWrapper.java | 160 ---- .../viatra/runtime/emf/EMFEngineContext.java | 110 --- .../viatra/runtime/emf/EMFQueryMetaContext.java | 405 ---------- .../viatra/runtime/emf/EMFQueryRuntimeContext.java | 839 --------------------- .../refinery/viatra/runtime/emf/EMFScope.java | 199 ----- .../emf/helper/ViatraQueryRuntimeHelper.java | 161 ---- .../viatra/runtime/emf/types/BaseEMFTypeKey.java | 34 - .../runtime/emf/types/EClassExactInstancesKey.java | 51 -- .../emf/types/EClassTransitiveInstancesKey.java | 47 -- .../EClassUnscopedTransitiveInstancesKey.java | 46 -- .../runtime/emf/types/EDataTypeInSlotsKey.java | 48 -- .../emf/types/EStructuralFeatureInstancesKey.java | 48 -- .../runtime/extensibility/IQueryGroupProvider.java | 40 - .../extensibility/IQuerySpecificationProvider.java | 36 - .../extensibility/PQueryExtensionFactory.java | 33 - .../extensibility/SingletonExtensionFactory.java | 62 -- .../extensibility/SingletonQueryGroupProvider.java | 46 -- .../SingletonQuerySpecificationProvider.java | 42 -- .../extensibility/ViatraQueryRuntimeConstants.java | 27 - .../ExtensionBasedSurrogateQueryLoader.java | 148 ---- .../ExtensionBasedSystemDefaultBackendLoader.java | 60 -- .../internal/apiimpl/ViatraQueryEngineImpl.java | 15 +- .../ExtensionBasedQuerySpecificationLoader.java | 303 -------- .../runtime/registry/IConnectorListener.java | 40 - .../runtime/registry/IDefaultRegistryView.java | 37 - .../registry/IQuerySpecificationRegistry.java | 74 -- .../IQuerySpecificationRegistryChangeListener.java | 35 - .../registry/IQuerySpecificationRegistryEntry.java | 48 -- .../runtime/registry/IRegistrySourceConnector.java | 50 -- .../viatra/runtime/registry/IRegistryView.java | 72 -- .../runtime/registry/IRegistryViewFactory.java | 34 - .../runtime/registry/IRegistryViewFilter.java | 33 - .../registry/QuerySpecificationRegistry.java | 112 --- .../connector/AbstractRegistrySourceConnector.java | 81 -- .../QueryGroupProviderSourceConnector.java | 80 -- .../connector/SpecificationMapSourceConnector.java | 147 ---- .../registry/data/QuerySpecificationStore.java | 38 - .../runtime/registry/data/RegistryEntryImpl.java | 81 -- .../runtime/registry/data/RegistrySourceImpl.java | 73 -- .../registry/impl/FilteringRegistryView.java | 43 -- .../runtime/registry/impl/GlobalRegistryView.java | 65 -- .../impl/QuerySpecificationRegistryImpl.java | 177 ----- .../registry/impl/RegistryChangeMultiplexer.java | 58 -- .../registry/view/AbstractRegistryView.java | 150 ---- .../viatra/runtime/tabular/EcoreIndexHost.java | 166 ---- .../runtime/tabular/TabularEngineContext.java | 107 --- .../viatra/runtime/tabular/TabularIndexHost.java | 145 ---- 64 files changed, 145 insertions(+), 5822 deletions(-) delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/IExtensions.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/ViatraQueryRuntimePlugin.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IModelConnectorTypeEnum.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IRunOnceQueryEngine.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/LazyLoadingQueryGroup.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/PackageBasedQueryGroup.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFPQuery.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFQuerySpecification.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFQuerySpecificationWithGenericMatcher.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/RunOnceQueryEngine.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/DynamicEMFQueryRuntimeContext.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFBaseIndexWrapper.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFEngineContext.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFQueryMetaContext.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFQueryRuntimeContext.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFScope.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/helper/ViatraQueryRuntimeHelper.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/BaseEMFTypeKey.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassExactInstancesKey.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassTransitiveInstancesKey.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassUnscopedTransitiveInstancesKey.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EDataTypeInSlotsKey.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EStructuralFeatureInstancesKey.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/IQueryGroupProvider.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/IQuerySpecificationProvider.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/PQueryExtensionFactory.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonExtensionFactory.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonQueryGroupProvider.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonQuerySpecificationProvider.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/ViatraQueryRuntimeConstants.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/ExtensionBasedSurrogateQueryLoader.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/ExtensionBasedSystemDefaultBackendLoader.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/ExtensionBasedQuerySpecificationLoader.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IConnectorListener.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IDefaultRegistryView.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistry.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistryChangeListener.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistryEntry.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistrySourceConnector.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryView.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryViewFactory.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryViewFilter.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/QuerySpecificationRegistry.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/AbstractRegistrySourceConnector.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/QueryGroupProviderSourceConnector.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/SpecificationMapSourceConnector.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/QuerySpecificationStore.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/RegistryEntryImpl.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/RegistrySourceImpl.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/FilteringRegistryView.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/GlobalRegistryView.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/QuerySpecificationRegistryImpl.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/RegistryChangeMultiplexer.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/view/AbstractRegistryView.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/EcoreIndexHost.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/TabularEngineContext.java delete mode 100644 subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/TabularIndexHost.java (limited to 'subprojects/viatra-runtime/src/main') diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/IExtensions.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/IExtensions.java deleted file mode 100644 index d5e0d51f..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/IExtensions.java +++ /dev/null @@ -1,24 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2004-2010 Gabor Bergmann, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ - -package tools.refinery.viatra.runtime; - -/** - * Interface for storing string constants related to VIATRA Query's extension points. - * - * @author Istvan Rath - * - */ -public interface IExtensions { - - public static final String QUERY_SPECIFICATION_EXTENSION_POINT_ID = ViatraQueryRuntimePlugin.PLUGIN_ID + ".queryspecification"; - - public static final String INJECTOREXTENSIONID = ViatraQueryRuntimePlugin.PLUGIN_ID + ".injectorprovider"; - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/ViatraQueryRuntimePlugin.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/ViatraQueryRuntimePlugin.java deleted file mode 100644 index 5fbcdad0..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/ViatraQueryRuntimePlugin.java +++ /dev/null @@ -1,32 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2004-2010 Gabor Bergmann and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime; - -import org.eclipse.core.runtime.Plugin; -import tools.refinery.viatra.runtime.internal.ExtensionBasedSurrogateQueryLoader; -import tools.refinery.viatra.runtime.internal.ExtensionBasedSystemDefaultBackendLoader; -import tools.refinery.viatra.runtime.registry.ExtensionBasedQuerySpecificationLoader; -import org.osgi.framework.BundleContext; - -/** - * The activator class controls the plug-in life cycle - */ -public class ViatraQueryRuntimePlugin extends Plugin { - - public static final String PLUGIN_ID = "tools.refinery.viatra.runtime"; - - @Override - public void start(BundleContext context) throws Exception { - super.start(context); - ExtensionBasedSurrogateQueryLoader.instance().loadKnownSurrogateQueriesIntoRegistry(); - ExtensionBasedQuerySpecificationLoader.getInstance().loadRegisteredQuerySpecificationsIntoRegistry(); - ExtensionBasedSystemDefaultBackendLoader.instance().loadKnownBackends(); - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/AdvancedViatraQueryEngine.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/AdvancedViatraQueryEngine.java index 21e7dfa3..32a3430d 100644 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/AdvancedViatraQueryEngine.java +++ b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/AdvancedViatraQueryEngine.java @@ -3,32 +3,27 @@ * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v. 2.0 which is available at * http://www.eclipse.org/legal/epl-v20.html. - * + * * SPDX-License-Identifier: EPL-2.0 *******************************************************************************/ package tools.refinery.viatra.runtime.api; -import java.lang.reflect.InvocationTargetException; -import java.util.concurrent.Callable; - import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.emf.EMFScope; import tools.refinery.viatra.runtime.internal.apiimpl.ViatraQueryEngineImpl; import tools.refinery.viatra.runtime.matchers.ViatraQueryRuntimeException; -import tools.refinery.viatra.runtime.matchers.backend.IMatcherCapability; -import tools.refinery.viatra.runtime.matchers.backend.IQueryBackend; -import tools.refinery.viatra.runtime.matchers.backend.IQueryBackendFactory; -import tools.refinery.viatra.runtime.matchers.backend.IQueryResultProvider; -import tools.refinery.viatra.runtime.matchers.backend.QueryEvaluationHint; +import tools.refinery.viatra.runtime.matchers.backend.*; + +import java.lang.reflect.InvocationTargetException; +import java.util.concurrent.Callable; /** * Advanced interface to a VIATRA incremental evaluation engine. - * + * *

* You can create a new, private, unmanaged {@link AdvancedViatraQueryEngine} instance using * {@link #createUnmanagedEngine(QueryScope)}. Additionally, you can access the advanced interface on any * {@link ViatraQueryEngine} by {@link AdvancedViatraQueryEngine#from(ViatraQueryEngine)}. - * + * *

* While the default interface {@link ViatraQueryEngine}, is suitable for most users, this advanced interface provides more * control over the engine. The most important added functionality is the following: @@ -45,29 +40,29 @@ import tools.refinery.viatra.runtime.matchers.backend.QueryEvaluationHint; * register a callback using {@link #addLifecycleListener(ViatraQueryEngineLifecycleListener)} to learn when another client * has called the destructive methods {@link #dispose()} or {@link #wipe()}. * - * + * * @author Bergmann Gabor * @noextend This class is not intended to be subclassed by clients. */ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { - + /** * Creates a new unmanaged VIATRA Query engine to evaluate queries over a given scope specified by an {@link QueryScope}. - * - *

Repeated invocations will return different instances, so other clients are unable to independently access - * and influence the returned engine. Note that unmanaged engines do not benefit from some performance improvements - * that stem from sharing incrementally maintained indices and caches between multiple clients using the same managed + * + *

Repeated invocations will return different instances, so other clients are unable to independently access + * and influence the returned engine. Note that unmanaged engines do not benefit from some performance improvements + * that stem from sharing incrementally maintained indices and caches between multiple clients using the same managed * engine instance. - * + * *

* Client is responsible for the lifecycle of the returned engine, hence the usage of the advanced interface * {@link AdvancedViatraQueryEngine}. - * + * *

* The match set of any patterns will be incrementally refreshed upon updates from this scope. - * - * @param scope - * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. + * + * @param scope + * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. * Provide e.g. a {@link EMFScope} for evaluating queries on an EMF model. * @return the advanced interface to a newly created unmanaged engine * @since 0.9 @@ -75,24 +70,24 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { public static AdvancedViatraQueryEngine createUnmanagedEngine(QueryScope scope) { return new ViatraQueryEngineImpl(null, scope); } - + /** * Creates a new unmanaged VIATRA Query engine to evaluate queries over a given scope specified by an {@link QueryScope}. - * - *

Repeated invocations will return different instances, so other clients are unable to independently access - * and influence the returned engine. Note that unmanaged engines do not benefit from some performance improvements - * that stem from sharing incrementally maintained indices and caches between multiple clients using the same managed + * + *

Repeated invocations will return different instances, so other clients are unable to independently access + * and influence the returned engine. Note that unmanaged engines do not benefit from some performance improvements + * that stem from sharing incrementally maintained indices and caches between multiple clients using the same managed * engine instance. - * + * *

* Client is responsible for the lifecycle of the returned engine, hence the usage of the advanced interface * {@link AdvancedViatraQueryEngine}. - * + * *

* The match set of any patterns will be incrementally refreshed upon updates from this scope. - * - * @param scope - * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. + * + * @param scope + * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. * Provide e.g. a {@link EMFScope} for evaluating queries on an EMF model. * @return the advanced interface to a newly created unmanaged engine * @since 1.4 @@ -103,11 +98,11 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { /** * Provides access to a given existing engine through the advanced interface. - * + * *

* Caveat: if the referenced engine is managed (i.e. created via {@link ViatraQueryEngine#on(QueryScope)}), the advanced * methods {@link #dispose()} and {@link #wipe()} will not be allowed. - * + * * @param engine * the engine to access using the advanced interface * @return a reference to the same engine conforming to the advanced interface @@ -118,7 +113,7 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { /** * Add an engine lifecycle listener to this engine instance. - * + * * @param listener * the {@link ViatraQueryEngineLifecycleListener} that should listen to lifecycle events from this engine */ @@ -126,7 +121,7 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { /** * Remove an existing lifecycle listener from this engine instance. - * + * * @param listener * the {@link ViatraQueryEngineLifecycleListener} that should not listen to lifecycle events from this * engine anymore @@ -136,7 +131,7 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { /** * Add an model update event listener to this engine instance (that fires its callbacks according to its * notification level). - * + * * @param listener * the {@link ViatraQueryModelUpdateListener} that should listen to model update events from this engine. */ @@ -144,7 +139,7 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { /** * Remove an existing model update event listener to this engine instance. - * + * * @param listener * the {@link ViatraQueryModelUpdateListener} that should not listen to model update events from this engine * anymore @@ -153,20 +148,20 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { /** * Registers low-level callbacks for match appearance and disappearance on this pattern matcher. - * + * *

* Caution: This is a low-level callback that is invoked when the pattern matcher is not necessarily in a * consistent state yet. Importantly, no model modification permitted during the callback. Most users should use the * databinding support ({@link org.eclipse.viatra.addon.databinding.runtime.api.ViatraObservables ViatraObservables}) or the event-driven API * ({@link org.eclipse.viatra.transformation.evm.api.EventDrivenVM EventDrivenVM}) instead. - * + * *

* Performance note: expected to be much more efficient than polling at {@link #addCallbackAfterUpdates(Runnable)}, * but prone to "signal hazards", e.g. spurious match appearances that will disappear immediately afterwards. - * + * *

* The callback can be unregistered via {@link #removeCallbackOnMatchUpdate(IMatchUpdateListener)}. - * + * * @param fireNow * if true, appearCallback will be immediately invoked on all current matches as a one-time effect. See * also {@link ViatraQueryMatcher#forEachMatch(IMatchProcessor)}. @@ -180,7 +175,7 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { /** * Remove an existing match update event listener to this engine instance. - * + * * @param matcher * the {@link ViatraQueryMatcher} for which this listener should not be active anymore * @param listener @@ -189,15 +184,15 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { public abstract void removeMatchUpdateListener(ViatraQueryMatcher matcher, IMatchUpdateListener listener); - + /** - * Access a pattern matcher based on a {@link IQuerySpecification}, overriding some of the default query evaluation hints. - * Multiple calls may return the same matcher depending on the actual evaluation hints. - * - *

It is guaranteed that this method will always return a matcher instance which is functionally compatible - * with the requested functionality (see {@link IMatcherCapability}). + * Access a pattern matcher based on a {@link IQuerySpecification}, overriding some of the default query evaluation hints. + * Multiple calls may return the same matcher depending on the actual evaluation hints. + * + *

It is guaranteed that this method will always return a matcher instance which is functionally compatible + * with the requested functionality (see {@link IMatcherCapability}). * Otherwise, the query evaluator is free to ignore any hints. - * + * *

For stateful query backends (Rete), hints may be effective only the first time a matcher is created. * @param querySpecification a {@link IQuerySpecification} that describes a VIATRA query * @return a pattern matcher corresponding to the specification @@ -206,20 +201,20 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { * @since 0.9 */ public abstract > Matcher getMatcher( - IQuerySpecification querySpecification, + IQuerySpecification querySpecification, QueryEvaluationHint optionalEvaluationHints); /** - * Initializes matchers for a group of patterns as one step (optionally overriding some of the default query evaluation hints). + * Initializes matchers for a group of patterns as one step (optionally overriding some of the default query evaluation hints). * If some of the pattern matchers are already * constructed in the engine, no task is performed for them. - * + * *

* This preparation step has the advantage that it prepares pattern matchers for an arbitrary number of patterns in a - * single-pass traversal of the model. - * This is typically more efficient than traversing the model each time an individual pattern matcher is initialized on demand. + * single-pass traversal of the model. + * This is typically more efficient than traversing the model each time an individual pattern matcher is initialized on demand. * The performance benefit only manifests itself if the engine is not in wildcard mode. - * + * * @param queryGroup a {@link IQueryGroup} identifying a set of VIATRA queries * @param optionalEvaluationHints additional / overriding options on query evaluation; passing null means default options associated with each query * @throws ViatraQueryRuntimeException @@ -227,23 +222,23 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { * @since 0.9 */ public abstract void prepareGroup(IQueryGroup queryGroup, QueryEvaluationHint optionalEvaluationHints); - + /** * Indicates whether the engine is managed, i.e. the default engine assigned to the given scope root by * {@link ViatraQueryEngine#on(QueryScope)}. - * + * *

* If the engine is managed, there may be other clients using it, as all calls to * {@link ViatraQueryEngine#on(QueryScope)} return the same managed engine instance for a given scope root. Therefore the * destructive methods {@link #wipe()} and {@link #dispose()} are not allowed. - * + * *

* On the other hand, if the engine is unmanaged (i.e. a private instance created using * {@link #createUnmanagedEngine(QueryScope)}), then {@link #wipe()} and {@link #dispose()} can be called. If you * explicitly share a private, unmanaged engine between multiple sites, register a callback using * {@link #addLifecycleListener(ViatraQueryEngineLifecycleListener)} to learn when another client has called these * destructive methods. - * + * * @return true if the engine is managed, and therefore potentially shared with other clients querying the same EMF * model */ @@ -252,11 +247,11 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { /** * Indicates whether the engine is in a tainted, inconsistent state due to some internal errors. If true, results * are no longer reliable; engine should be disposed. - * + * *

* The engine is in a tainted state if any of its internal processes report back a fatal error. The * {@link ViatraQueryEngineLifecycleListener} interface provides a callback method for entering the tainted state. - * + * * @return the tainted state */ public abstract boolean isTainted(); @@ -265,7 +260,7 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { * Discards any pattern matcher caches and forgets known patterns. The base index built directly on the underlying * EMF model, however, is kept in memory to allow reuse when new pattern matchers are built. Use this method if you * have e.g. new versions of the same patterns, to be matched on the same model. - * + * *

* Matcher objects will continue to return stale results. If no references are retained to the matchers, they can * eventually be GC'ed. @@ -275,7 +270,7 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { * If you explicitly share a private, unmanaged engine between multiple sites, register a callback using * {@link #addLifecycleListener(ViatraQueryEngineLifecycleListener)} to learn when another client has called this * destructive method. - * + * * @throws UnsupportedOperationException * if engine is managed */ @@ -295,12 +290,12 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { * If you explicitly share a private, unmanaged engine between multiple sites, register a callback using * {@link #addLifecycleListener(ViatraQueryEngineLifecycleListener)} to learn when another client has called this * destructive method. - * + * * @throws UnsupportedOperationException * if engine is managed */ public abstract void dispose(); - + /** * Provides access to the selected query backend component of the VIATRA Query engine. * @noreference for internal use only @@ -316,45 +311,45 @@ public abstract class AdvancedViatraQueryEngine extends ViatraQueryEngine { * @since 1.4 */ public abstract > Matcher getExistingMatcher(IQuerySpecification querySpecification, QueryEvaluationHint optionalOverrideHints); - + /** * Returns the immutable {@link ViatraQueryEngineOptions} of the engine. - * + * * @return the engine options * @since 1.4 */ public abstract ViatraQueryEngineOptions getEngineOptions(); - + /** * Return the underlying result provider for the given matcher. - * + * * @beta This method may change in future versions * @since 1.4 * @noreference This method is considered internal API */ public abstract IQueryResultProvider getResultProviderOfMatcher(ViatraQueryMatcher matcher); - + /** - * The given callable will be executed, and all update propagation in stateful query backends + * The given callable will be executed, and all update propagation in stateful query backends * will be delayed until the execution is done. Within the callback, these backends will provide stale results. - * - *

It is optional for a {@link IQueryBackend} to support the delaying of update propagation; stateless backends will display up-to-date results. - * In this case, the given callable shall be executed, and the update propagation shall happen just like in non-delayed execution. - * - *

Example: in the Rete network, no messages will be propagated until the given callable is executed. - * After the execution of the callable, all accumulated messages will be delivered. - * + * + *

It is optional for a {@link IQueryBackend} to support the delaying of update propagation; stateless backends will display up-to-date results. + * In this case, the given callable shall be executed, and the update propagation shall happen just like in non-delayed execution. + * + *

Example: in the Rete network, no messages will be propagated until the given callable is executed. + * After the execution of the callable, all accumulated messages will be delivered. + * *

The purpose of this method is that stateful query backends may save work when multiple model modifications are performed within the callback that partially cancel each other out. - * + * * @param callable the callable to be executed * @return the result of the callable * @since 1.6 */ public abstract V delayUpdatePropagation(Callable callable) throws InvocationTargetException; - + /** - * Returns true if the update propagation in this engine is currently delayed, false otherwise. - * + * Returns true if the update propagation in this engine is currently delayed, false otherwise. + * * @see {@link #delayUpdatePropagation(Callable)} * @since 1.6 */ diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IModelConnectorTypeEnum.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IModelConnectorTypeEnum.java deleted file mode 100644 index e672a6e2..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IModelConnectorTypeEnum.java +++ /dev/null @@ -1,18 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2012, Andras Okros, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.api; - -/** - * This enum represents the possible notifier types which a model input should provide for the ui. - */ -public enum IModelConnectorTypeEnum { - - RESOURCESET, RESOURCE; - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IQuerySpecification.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IQuerySpecification.java index 9b84b031..326d2202 100644 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IQuerySpecification.java +++ b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IQuerySpecification.java @@ -3,14 +3,13 @@ * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v. 2.0 which is available at * http://www.eclipse.org/legal/epl-v20.html. - * + * * SPDX-License-Identifier: EPL-2.0 *******************************************************************************/ package tools.refinery.viatra.runtime.api; import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.emf.EMFScope; import tools.refinery.viatra.runtime.matchers.ViatraQueryRuntimeException; import tools.refinery.viatra.runtime.matchers.psystem.queries.PQuery; import tools.refinery.viatra.runtime.matchers.psystem.queries.PQueryHeader; @@ -18,8 +17,8 @@ import tools.refinery.viatra.runtime.matchers.psystem.queries.PQueryHeader; /** * API interface for a VIATRA query specification. Each query is associated with a pattern. Methods instantiate a matcher * of the pattern with various parameters. - * - *

As of 0.9.0, some internal details (mostly relevant for query evaluator backends) have been moved to {@link #getInternalQueryRepresentation()}. + * + *

As of 0.9.0, some internal details (mostly relevant for query evaluator backends) have been moved to {@link #getInternalQueryRepresentation()}. * * @author Bergmann Gábor * @@ -39,49 +38,49 @@ public interface IQuerySpecificationThe returned match will be immutable. Use {@link #newEmptyMatch()} to obtain a mutable match object. - * + * * @param parameters * the fixed value of pattern parameters, or null if not bound. * @return the (partial) match object. */ public abstract IPatternMatch newMatch(Object... parameters); - + /** * The query is formulated over this kind of modeling platform. * E.g. for queries over EMF models, the {@link EMFScope} class is returned. */ public Class getPreferredScopeClass(); - + /** - * Returns the definition of the query in a format intended for consumption by the query evaluator. + * Returns the definition of the query in a format intended for consumption by the query evaluator. * @return the internal representation of the query. */ public PQuery getInternalQueryRepresentation(); - + /** * Creates a new uninitialized matcher, which is not functional until an engine initializes it. Clients * should not call this method, it is used by the {@link ViatraQueryEngine} instance to instantiate matchers. - * @throws ViatraQueryRuntimeException + * @throws ViatraQueryRuntimeException * @noreference This method is not intended to be referenced by clients. * @since 1.4 */ public Matcher instantiate(); - + } diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IRunOnceQueryEngine.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IRunOnceQueryEngine.java deleted file mode 100644 index b625980b..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/IRunOnceQueryEngine.java +++ /dev/null @@ -1,68 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2013, Abel Hegedus, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.api; - -import java.util.Collection; - -import org.eclipse.emf.common.notify.Notifier; -import tools.refinery.viatra.runtime.base.api.BaseIndexOptions; -import tools.refinery.viatra.runtime.base.api.NavigationHelper; - -/** - * A run-once query engine is used to get matches for queries without incremental support. - * Users can create a query engine with a given {@link Notifier} as scope and use a query specification - * to retrieve the current match set with this scope (see {@link #getAllMatches}). - * - * @author Abel Hegedus - * - */ -public interface IRunOnceQueryEngine { - - /** - * Returns the set of all matches for the given query in the scope of the engine. - * - * @param querySpecification the query that is evaluated - * @return matches represented as a Match object. - */ - Collection getAllMatches( - final IQuerySpecification> querySpecification); - - /** - * @return the scope of pattern matching, i.e. the root of the EMF model tree that this engine is attached to. - */ - Notifier getScope(); - - /** - * The base index options specifies how the base index is built, including wildcard mode (defaults to false) and - * dynamic EMF mode (defaults to false). See {@link NavigationHelper} for the explanation of wildcard mode and - * dynamic EMF mode. - * - *

The returned options can be modified in order to affect subsequent calls of {@link #getAllMatches}. - * - * @return the base index options used by the engine. - */ - BaseIndexOptions getBaseIndexOptions(); - - /** - * When set to true, the run-once query engine will not dispose it's engine and will resample the values of derived - * features before returning matches if the model changed since the last call. - * - * If the values of derived features may change without any model modification, call {@link #resampleOnNextCall()} - * before subsequent calls of {@link #getAllMatches}. - * - * @param automaticResampling - */ - void setAutomaticResampling(boolean automaticResampling); - - /** - * If automatic resampling is enabled and the value of derived features may change without model modifications, - * calling this method will make sure that re-sampling will occur before returning match results. - */ - void resampleOnNextCall(); -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/LazyLoadingQueryGroup.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/LazyLoadingQueryGroup.java deleted file mode 100644 index 6ae44b7c..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/LazyLoadingQueryGroup.java +++ /dev/null @@ -1,64 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Zoltan Ujhelyi, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.api; - -import java.util.Collections; -import java.util.Objects; -import java.util.Set; -import java.util.function.Supplier; -import java.util.stream.Collectors; - -import tools.refinery.viatra.runtime.api.impl.BaseQueryGroup; -import tools.refinery.viatra.runtime.matchers.util.Preconditions; -import tools.refinery.viatra.runtime.util.ViatraQueryLoggingUtil; - -/** - * Initializes a query group from a set of query providers. The query providers are not executed until the queries - * themselves are asked in the {@link #getSpecifications()} method. - * - * @author Zoltan Ujhelyi - * @since 1.3 - * - */ -public class LazyLoadingQueryGroup extends BaseQueryGroup { - - private final Set>> providers; - private Set> specifications = null; - - /** - * @param providers a non-null set to initialize the group - */ - public LazyLoadingQueryGroup(Set>> providers) { - Preconditions.checkArgument(providers != null, "The set of providers must not be null"); - this.providers = providers; - } - - /** - * @param providers a non-null set to initialize the group - */ - public static IQueryGroup of(Set>> querySpecifications) { - return new LazyLoadingQueryGroup(querySpecifications); - } - - @Override - public Set> getSpecifications() { - if (specifications == null) { - try { - specifications = providers.stream().filter(Objects::nonNull).map(Supplier::get).filter(Objects::nonNull).collect(Collectors.toSet()); - } catch (Exception e) { - // TODO maybe store in issue list and provide better error reporting in general - String errorMessage = "Exception occurred while accessing query specification from provider: " + e.getMessage(); - ViatraQueryLoggingUtil.getLogger(getClass()).error(errorMessage); - return Collections.emptySet(); - } - } - return specifications; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/PackageBasedQueryGroup.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/PackageBasedQueryGroup.java deleted file mode 100644 index 252bb7fd..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/PackageBasedQueryGroup.java +++ /dev/null @@ -1,133 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2012, Abel Hegedus, Mark Czotter, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.api; - -import java.util.Collections; -import java.util.HashSet; -import java.util.Set; - -import tools.refinery.viatra.runtime.api.impl.BaseQueryGroup; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistry; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryEntry; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryChangeListener; -import tools.refinery.viatra.runtime.registry.IRegistryView; -import tools.refinery.viatra.runtime.registry.IRegistryViewFilter; -import tools.refinery.viatra.runtime.registry.QuerySpecificationRegistry; - -/** - * Package based {@link BaseQueryGroup} implementation. It handles patterns as a group within the same package. - * - * @author Abel Hegedus, Mark Czotter - * - */ -public class PackageBasedQueryGroup extends BaseQueryGroup { - - private final Set> querySpecifications = new HashSet<>(); - private final String packageName; - private final boolean includeSubPackages; - private IRegistryView view; - - /** - * Creates a query group with specifications of a given package from the {@link QuerySpecificationRegistry}. Only - * query specifications with the exact package fully qualified name are included. - * - * @param packageName - * that contains the specifications - */ - public PackageBasedQueryGroup(String packageName) { - this(packageName, false); - } - - /** - * Creates a query group with specifications of a given package from the {@link QuerySpecificationRegistry}. - * - * @param packageName - * that contain the specifications - * @param includeSubPackages - * if true all query specifications with package names starting with the given package are included - */ - public PackageBasedQueryGroup(String packageName, boolean includeSubPackages) { - super(); - this.packageName = packageName; - this.includeSubPackages = includeSubPackages; - IQuerySpecificationRegistry registry = QuerySpecificationRegistry.getInstance(); - view = registry.createView(new PackageNameBasedViewFilter()); - for (IQuerySpecificationRegistryEntry entry : view.getEntries()) { - this.querySpecifications.add(entry.get()); - } - SpecificationSetUpdater listener = new SpecificationSetUpdater(); - view.addViewListener(listener); - } - - @Override - public Set> getSpecifications() { - return Collections.unmodifiableSet(new HashSet<>(querySpecifications)); - } - - public String getPackageName() { - return packageName; - } - - public boolean isIncludeSubPackages() { - return includeSubPackages; - } - - /** - * Refreshes the pattern group from the query specification registry based on the parameters used during the - * initialization. - */ - public void refresh() { - // do nothing, view is automatically refreshed - } - - /** - * Listener to update the specification set - * - * @author Abel Hegedus - * - */ - private final class SpecificationSetUpdater implements IQuerySpecificationRegistryChangeListener { - @Override - public void entryAdded(IQuerySpecificationRegistryEntry entry) { - querySpecifications.add(entry.get()); - } - - @Override - public void entryRemoved(IQuerySpecificationRegistryEntry entry) { - querySpecifications.remove(entry.get()); - } - } - - /** - * Registry view filter that checks FQNs against the given package name. - * - * @author Abel Hegedus - * - */ - private final class PackageNameBasedViewFilter implements IRegistryViewFilter { - @Override - public boolean isEntryRelevant(IQuerySpecificationRegistryEntry entry) { - String fqn = entry.getFullyQualifiedName(); - if (packageName.length() + 1 < fqn.length()) { - if (includeSubPackages) { - if (fqn.startsWith(packageName + '.')) { - return true; - } - } else { - String name = fqn.substring(fqn.lastIndexOf('.') + 1, fqn.length()); - if (fqn.equals(packageName + '.' + name)) { - return true; - } - } - } - return false; - } - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/ViatraQueryEngine.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/ViatraQueryEngine.java index fd8ff848..ebae57a7 100644 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/ViatraQueryEngine.java +++ b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/ViatraQueryEngine.java @@ -12,8 +12,6 @@ package tools.refinery.viatra.runtime.api; import org.eclipse.emf.common.notify.Notifier; import tools.refinery.viatra.runtime.api.scope.IBaseIndex; import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.base.api.BaseIndexOptions; -import tools.refinery.viatra.runtime.emf.EMFScope; import tools.refinery.viatra.runtime.matchers.ViatraQueryRuntimeException; import java.util.Set; diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/ViatraQueryEngineManager.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/ViatraQueryEngineManager.java index ca709b02..4a256aea 100644 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/ViatraQueryEngineManager.java +++ b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/ViatraQueryEngineManager.java @@ -3,47 +3,42 @@ * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v. 2.0 which is available at * http://www.eclipse.org/legal/epl-v20.html. - * + * * SPDX-License-Identifier: EPL-2.0 *******************************************************************************/ package tools.refinery.viatra.runtime.api; -import static tools.refinery.viatra.runtime.matchers.util.Preconditions.checkArgument; - -import java.lang.ref.WeakReference; -import java.util.Collections; -import java.util.HashSet; -import java.util.Map; -import java.util.Set; -import java.util.WeakHashMap; - import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.emf.EMFScope; import tools.refinery.viatra.runtime.internal.apiimpl.ViatraQueryEngineImpl; import tools.refinery.viatra.runtime.util.ViatraQueryLoggingUtil; +import java.lang.ref.WeakReference; +import java.util.*; + +import static tools.refinery.viatra.runtime.matchers.util.Preconditions.checkArgument; + /** * Global registry of active VIATRA Query Engines. - * + * *

* Manages an {@link ViatraQueryEngine} for each model (more precisely scope), that is created on demand. Managed engines are shared between * clients querying the same model. - * + * *

* It is also possible to create private, unmanaged engines that are not shared between clients. - * + * *

* Only weak references are retained on the managed engines. So if there are no other references to the matchers or the * engine, they can eventually be GC'ed, and they won't block the model from being GC'ed either. - * - * + * + * * @author Bergmann Gabor - * + * */ public class ViatraQueryEngineManager { private static ViatraQueryEngineManager instance = new ViatraQueryEngineManager(); - + /** * @return the singleton instance @@ -68,32 +63,32 @@ public class ViatraQueryEngineManager { } /** - * Creates a managed VIATRA Query Engine at a given scope (e.g. an EMF Resource or ResourceSet, as in {@link EMFScope}) - * or retrieves an already existing one. Repeated invocations for a single model root will return the same engine. + * Creates a managed VIATRA Query Engine at a given scope (e.g. an EMF Resource or ResourceSet, as in {@link EMFScope}) + * or retrieves an already existing one. Repeated invocations for a single model root will return the same engine. * Consequently, the engine will be reused between different clients querying the same model, providing performance benefits. - * + * *

* The match set of any patterns will be incrementally refreshed upon updates from this scope. - * - * @param scope - * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. + * + * @param scope + * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. * Provide e.g. a {@link EMFScope} for evaluating queries on an EMF model. * @return a new or previously existing engine */ public ViatraQueryEngine getQueryEngine(QueryScope scope) { return getQueryEngine(scope, ViatraQueryEngineOptions.getDefault()); } - + /** - * Creates a managed VIATRA Query Engine at a given scope (e.g. an EMF Resource or ResourceSet, as in {@link EMFScope}) - * or retrieves an already existing one. Repeated invocations for a single model root will return the same engine. + * Creates a managed VIATRA Query Engine at a given scope (e.g. an EMF Resource or ResourceSet, as in {@link EMFScope}) + * or retrieves an already existing one. Repeated invocations for a single model root will return the same engine. * Consequently, the engine will be reused between different clients querying the same model, providing performance benefits. - * + * *

* The match set of any patterns will be incrementally refreshed upon updates from this scope. - * - * @param scope - * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. + * + * @param scope + * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. * Provide e.g. a {@link EMFScope} for evaluating queries on an EMF model. * @return a new or previously existing engine * @since 1.4 @@ -110,9 +105,9 @@ public class ViatraQueryEngineManager { /** * Retrieves an already existing managed VIATRA Query Engine. - * - * @param scope - * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. + * + * @param scope + * the scope of query evaluation; the definition of the set of model elements that this engine is operates on. * Provide e.g. a {@link EMFScope} for evaluating queries on an EMF model. * @return a previously existing engine, or null if no engine is active for the given EMF model root */ @@ -122,7 +117,7 @@ public class ViatraQueryEngineManager { /** * Collects all {@link ViatraQueryEngine} instances that still exist. - * + * * @return set of engines if there is any, otherwise EMTPY_SET */ public Set getExistingQueryEngines(){ @@ -139,14 +134,14 @@ public class ViatraQueryEngineManager { } return existingEngines; } - + private final Set initializationListeners; - + /** * Registers a listener for new engine initialization. - * + * *

For removal, use {@link #removeQueryEngineInitializationListener} - * + * * @param listener the listener to register */ public void addQueryEngineInitializationListener(ViatraQueryEngineInitializationListener listener) { @@ -156,7 +151,7 @@ public class ViatraQueryEngineManager { /** * Removes a registered listener added with {@link #addQueryEngineInitializationListener} - * + * * @param listener */ public void removeQueryEngineInitializationListener(ViatraQueryEngineInitializationListener listener) { @@ -166,7 +161,7 @@ public class ViatraQueryEngineManager { /** * Notifies listeners that a new engine has been initialized. - * + * * @param engine the initialized engine */ protected void notifyInitializationListeners(AdvancedViatraQueryEngine engine) { diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFPQuery.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFPQuery.java deleted file mode 100644 index c1fb0622..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFPQuery.java +++ /dev/null @@ -1,110 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.api.impl; - -import org.eclipse.emf.ecore.EClass; -import org.eclipse.emf.ecore.EClassifier; -import org.eclipse.emf.ecore.EEnum; -import org.eclipse.emf.ecore.EEnumLiteral; -import org.eclipse.emf.ecore.EPackage; -import org.eclipse.emf.ecore.EStructuralFeature; -import tools.refinery.viatra.runtime.exception.ViatraQueryException; -import tools.refinery.viatra.runtime.matchers.psystem.queries.BasePQuery; -import tools.refinery.viatra.runtime.matchers.psystem.queries.PVisibility; -import tools.refinery.viatra.runtime.matchers.psystem.queries.QueryInitializationException; - -/** - * Common superclass for EMF-based generated PQueries. - * @author Bergmann Gabor - * - */ -public abstract class BaseGeneratedEMFPQuery extends BasePQuery { - - public BaseGeneratedEMFPQuery() { - this(PVisibility.PUBLIC); - } - - /** - * @since 2.0 - */ - public BaseGeneratedEMFPQuery(PVisibility visibility) { - super(visibility); - } - - protected QueryInitializationException processDependencyException(ViatraQueryException ex) { - if (ex.getCause() instanceof QueryInitializationException) - return (QueryInitializationException) ex.getCause(); - return new QueryInitializationException( - "Failed to initialize external dependencies of query specification - see 'caused by' for details.", - null, "Problem with query dependencies.", this, ex); - } - - protected EClassifier getClassifierLiteral(String packageUri, String classifierName) { - EPackage ePackage = EPackage.Registry.INSTANCE.getEPackage(packageUri); - if (ePackage == null) - throw new QueryInitializationException( - "Query refers to EPackage {1} not found in EPackage Registry.", - new String[]{packageUri}, - "Query refers to missing EPackage.", this); - EClassifier literal = ePackage.getEClassifier(classifierName); - if (literal == null) - throw new QueryInitializationException( - "Query refers to classifier {1} not found in EPackage {2}.", - new String[]{classifierName, packageUri}, - "Query refers to missing type in EPackage.", this); - return literal; - } - - /** - * For parameter type retrieval only. - * - *

If parameter type declaration is erroneous, we still get a working parameter list (without the type declaration); - * the exception will be thrown again later when the body is processed. - */ - protected EClassifier getClassifierLiteralSafe(String packageURI, String classifierName) { - try { - return getClassifierLiteral(packageURI, classifierName); - } catch (QueryInitializationException e) { - return null; - } - } - - protected EStructuralFeature getFeatureLiteral(String packageUri, String className, String featureName) { - EClassifier container = getClassifierLiteral(packageUri, className); - if (! (container instanceof EClass)) - throw new QueryInitializationException( - "Query refers to EClass {1} in EPackage {2} which turned out not be an EClass.", - new String[]{className, packageUri}, - "Query refers to missing EClass.", this); - EStructuralFeature feature = ((EClass)container).getEStructuralFeature(featureName); - if (feature == null) - throw new QueryInitializationException( - "Query refers to feature {1} not found in EClass {2}.", - new String[]{featureName, className}, - "Query refers to missing feature.", this); - return feature; - } - - protected EEnumLiteral getEnumLiteral(String packageUri, String enumName, String literalName) { - EClassifier enumContainer = getClassifierLiteral(packageUri, enumName); - if (! (enumContainer instanceof EEnum)) - throw new QueryInitializationException( - "Query refers to EEnum {1} in EPackage {2} which turned out not be an EEnum.", - new String[]{enumName, packageUri}, - "Query refers to missing enumeration type.", this); - EEnumLiteral literal = ((EEnum)enumContainer).getEEnumLiteral(literalName); - if (literal == null) - throw new QueryInitializationException( - "Query refers to enumeration literal {1} not found in EEnum {2}.", - new String[]{literalName, enumName}, - "Query refers to missing enumeration literal.", this); - return literal; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFQuerySpecification.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFQuerySpecification.java deleted file mode 100644 index 9956983d..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFQuerySpecification.java +++ /dev/null @@ -1,40 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2004-2010 Gabor Bergmann and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ - -package tools.refinery.viatra.runtime.api.impl; - -import tools.refinery.viatra.runtime.api.IPatternMatch; -import tools.refinery.viatra.runtime.api.ViatraQueryMatcher; -import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.emf.EMFScope; -import tools.refinery.viatra.runtime.matchers.psystem.queries.PQuery; - -/** - * Provides common functionality of pattern-specific generated query specifications over the EMF scope. - * - * @author Bergmann Gábor - * @author Mark Czotter - */ -public abstract class BaseGeneratedEMFQuerySpecification> extends - BaseQuerySpecification { - - - /** - * Instantiates query specification for the given internal query representation. - */ - public BaseGeneratedEMFQuerySpecification(PQuery wrappedPQuery) { - super(wrappedPQuery); - } - - @Override - public Class getPreferredScopeClass() { - return EMFScope.class; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFQuerySpecificationWithGenericMatcher.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFQuerySpecificationWithGenericMatcher.java deleted file mode 100644 index 949dd112..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BaseGeneratedEMFQuerySpecificationWithGenericMatcher.java +++ /dev/null @@ -1,58 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2017, Zoltan Ujhelyi, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.api.impl; - -import tools.refinery.viatra.runtime.api.GenericPatternMatch; -import tools.refinery.viatra.runtime.api.GenericPatternMatcher; -import tools.refinery.viatra.runtime.api.GenericQuerySpecification; -import tools.refinery.viatra.runtime.api.ViatraQueryEngine; -import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.emf.EMFScope; -import tools.refinery.viatra.runtime.matchers.psystem.queries.PQuery; - -/** - * Provides common functionality of pattern-specific generated query specifications for without generated - * pattern-specific match and matcher classes, including private patterns. - * - * @since 1.7 - * - */ -public abstract class BaseGeneratedEMFQuerySpecificationWithGenericMatcher - extends GenericQuerySpecification { - - public BaseGeneratedEMFQuerySpecificationWithGenericMatcher(PQuery wrappedPQuery) { - super(wrappedPQuery); - } - - @Override - public Class getPreferredScopeClass() { - return EMFScope.class; - } - - @Override - protected GenericPatternMatcher instantiate(final ViatraQueryEngine engine) { - return defaultInstantiate(engine); - } - - @Override - public GenericPatternMatcher instantiate() { - return new GenericPatternMatcher(this); - } - - @Override - public GenericPatternMatch newEmptyMatch() { - return GenericPatternMatch.newEmptyMatch(this); - } - - @Override - public GenericPatternMatch newMatch(final Object... parameters) { - return GenericPatternMatch.newMatch(this, parameters); - } - -} \ No newline at end of file diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BasePatternMatch.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BasePatternMatch.java index 7690daf6..182bb466 100644 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BasePatternMatch.java +++ b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/BasePatternMatch.java @@ -3,25 +3,23 @@ * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v. 2.0 which is available at * http://www.eclipse.org/legal/epl-v20.html. - * + * * SPDX-License-Identifier: EPL-2.0 *******************************************************************************/ package tools.refinery.viatra.runtime.api.impl; +import tools.refinery.viatra.runtime.api.IPatternMatch; + import java.util.Arrays; import java.util.Collections; import java.util.List; -import org.eclipse.emf.ecore.EObject; -import org.eclipse.emf.ecore.EStructuralFeature; -import tools.refinery.viatra.runtime.api.IPatternMatch; - /** * Base implementation of IPatternMatch. - * + * * @author Bergmann Gábor - * + * */ public abstract class BasePatternMatch implements IPatternMatch { @@ -29,36 +27,14 @@ public abstract class BasePatternMatch implements IPatternMatch { protected static List makeImmutableList(T... elements) { return Collections.unmodifiableList(Arrays.asList(elements)); } - + public static String prettyPrintValue(Object o) { if (o == null) { return "(null)"; } - String name = prettyPrintFeature(o, "name"); - if (name != null) { - return name; - } - /* - * if (o instanceof EObject) { EStructuralFeature feature = ((EObject)o).eClass().getEStructuralFeature("name"); - * if (feature != null) { Object name = ((EObject)o).eGet(feature); if (name != null) return name.toString(); } - * } - */ return o.toString(); } - public static String prettyPrintFeature(Object o, String featureName) { - if (o instanceof EObject) { - EStructuralFeature feature = ((EObject) o).eClass().getEStructuralFeature(featureName); - if (feature != null) { - Object value = ((EObject) o).eGet(feature); - if (value != null) { - return value.toString(); - } - } - } - return null; - } - // TODO performance can be improved here somewhat @Override @@ -83,7 +59,7 @@ public abstract class BasePatternMatch implements IPatternMatch { public String toString() { return "Match<" + patternName() + ">{" + prettyPrint() + "}"; } - + @Override public boolean isCompatibleWith(IPatternMatch other) { if(other == null) { @@ -102,7 +78,7 @@ public abstract class BasePatternMatch implements IPatternMatch { } return true; } - + @Override public String patternName() { return specification().getFullyQualifiedName(); diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/RunOnceQueryEngine.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/RunOnceQueryEngine.java deleted file mode 100644 index a97dea5d..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/impl/RunOnceQueryEngine.java +++ /dev/null @@ -1,140 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2013, Abel Hegedus, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.api.impl; - -import java.util.Collection; - -import org.eclipse.emf.common.notify.Notifier; -import tools.refinery.viatra.runtime.api.AdvancedViatraQueryEngine; -import tools.refinery.viatra.runtime.api.IPatternMatch; -import tools.refinery.viatra.runtime.api.IQuerySpecification; -import tools.refinery.viatra.runtime.api.IRunOnceQueryEngine; -import tools.refinery.viatra.runtime.api.ViatraQueryEngine; -import tools.refinery.viatra.runtime.api.ViatraQueryMatcher; -import tools.refinery.viatra.runtime.api.ViatraQueryModelUpdateListener; -import tools.refinery.viatra.runtime.base.api.BaseIndexOptions; -import tools.refinery.viatra.runtime.emf.EMFScope; - -/** - * Run-once query engines can be used to retrieve the current match set of query specifications - * in a given scope. The engine is initialized with a {@link Notifier} as scope and a base index options - * that specifically allows traversing derived features that are not well-behaving. - * - * @author Abel Hegedus - * - */ -public class RunOnceQueryEngine implements IRunOnceQueryEngine { - - /** - * If the model changes, we know that a resampling is required. - * - * @author Abel Hegedus - * - */ - private final class RunOnceSamplingModelUpdateListener implements ViatraQueryModelUpdateListener { - @Override - public void notifyChanged(ChangeLevel changeLevel) { - // any model change may require re-sampling - reSamplingNeeded = true; - } - - @Override - public ChangeLevel getLevel() { - return ChangeLevel.MODEL; - } - } - - /** - * Override the default base index options to allow traversing and indexing derived features - * that would be problematic in incremental evaluation. - * - * @author Abel Hegedus - * - */ - private static final class RunOnceBaseIndexOptions extends BaseIndexOptions { - - public RunOnceBaseIndexOptions() { - this.traverseOnlyWellBehavingDerivedFeatures = false; - } - - } - - /** - * The scope of the engine that is used when creating one-time {@link ViatraQueryEngine}s. - */ - private Notifier notifier; - /** - * The options that are used for initializing the {@link ViatraQueryEngine}. - */ - private RunOnceBaseIndexOptions baseIndexOptions; - private AdvancedViatraQueryEngine engine; - private boolean reSamplingNeeded = false; - protected boolean samplingMode = false; - private RunOnceSamplingModelUpdateListener modelUpdateListener; - - /** - * Creates a run-once query engine on the given notifier. - */ - public RunOnceQueryEngine(Notifier notifier) { - this.notifier = notifier; - this.baseIndexOptions = new RunOnceBaseIndexOptions(); - } - - @Override - public Collection getAllMatches( - IQuerySpecification> querySpecification) { - - if(samplingMode && reSamplingNeeded && engine != null) { - // engine exists from earlier, but may need resampling if model changed - engine.getBaseIndex().resampleDerivedFeatures(); - } else { - // create new engine if it doesn't exists - //TODO correct scope handling - engine = AdvancedViatraQueryEngine.createUnmanagedEngine(new EMFScope(notifier, baseIndexOptions)); - } - ViatraQueryMatcher matcher = engine.getMatcher(querySpecification); - Collection allMatches = matcher.getAllMatches(); - if(samplingMode) { - engine.addModelUpdateListener(modelUpdateListener); - } else { - engine.dispose(); - engine = null; - } - return allMatches; - } - - @Override - public BaseIndexOptions getBaseIndexOptions() { - return baseIndexOptions; - } - - @Override - public Notifier getScope() { - return notifier; - } - - @Override - public void setAutomaticResampling(boolean automaticResampling) { - samplingMode = automaticResampling; - if(automaticResampling) { - if (modelUpdateListener == null) { - modelUpdateListener = new RunOnceSamplingModelUpdateListener(); - } - } else if(engine != null) { - engine.dispose(); - engine = null; - } - } - - @Override - public void resampleOnNextCall() { - reSamplingNeeded = true; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/scope/IIndexingErrorListener.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/scope/IIndexingErrorListener.java index d144bba6..f61a5edb 100644 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/scope/IIndexingErrorListener.java +++ b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/api/scope/IIndexingErrorListener.java @@ -3,17 +3,15 @@ * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v. 2.0 which is available at * http://www.eclipse.org/legal/epl-v20.html. - * + * * SPDX-License-Identifier: EPL-2.0 *******************************************************************************/ package tools.refinery.viatra.runtime.api.scope; -import tools.refinery.viatra.runtime.base.api.NavigationHelper; - /** - * + * * This interface contains callbacks for various internal errors from the {@link NavigationHelper base index}. - * + * * @author Zoltan Ujhelyi * @since 0.9 * diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/DynamicEMFQueryRuntimeContext.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/DynamicEMFQueryRuntimeContext.java deleted file mode 100644 index a6da213e..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/DynamicEMFQueryRuntimeContext.java +++ /dev/null @@ -1,47 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf; - -import org.apache.log4j.Logger; -import tools.refinery.viatra.runtime.base.api.NavigationHelper; -import tools.refinery.viatra.runtime.matchers.tuple.Tuple; -import tools.refinery.viatra.runtime.matchers.tuple.Tuples; - -/** - * In dynamic EMF mode, we need to make sure that EEnum literal constants and values returned by eval() expressions - * are canonicalized in the same way as enum literals from the EMF model. - * - *

This canonicalization is a one-way mapping, so - * {@link #unwrapElement(Object)} and {@link #unwrapTuple(Object)} remain NOPs. - * - * @author Bergmann Gabor - * - */ -public class DynamicEMFQueryRuntimeContext extends EMFQueryRuntimeContext { - - public DynamicEMFQueryRuntimeContext(NavigationHelper baseIndex, Logger logger, EMFScope emfScope) { - super(baseIndex, logger, emfScope); - } - - @Override - public Object wrapElement(Object externalElement) { - return baseIndex.toCanonicalValueRepresentation(externalElement); - } - - @Override - public Tuple wrapTuple(Tuple externalElements) { - Object[] elements = externalElements.getElements(); - for (int i=0; i< elements.length; ++i) - elements[i] = wrapElement(elements[i]); - return Tuples.flatTupleOf(elements); - } - - - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFBaseIndexWrapper.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFBaseIndexWrapper.java deleted file mode 100644 index 433c5f72..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFBaseIndexWrapper.java +++ /dev/null @@ -1,160 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2014, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf; - -import java.lang.reflect.InvocationTargetException; -import java.util.HashMap; -import java.util.Map; -import java.util.concurrent.Callable; - -import org.eclipse.emf.common.notify.Notification; -import org.eclipse.emf.ecore.EObject; -import org.eclipse.emf.ecore.EStructuralFeature; -import tools.refinery.viatra.runtime.api.scope.IBaseIndex; -import tools.refinery.viatra.runtime.api.scope.IIndexingErrorListener; -import tools.refinery.viatra.runtime.api.scope.IInstanceObserver; -import tools.refinery.viatra.runtime.api.scope.ViatraBaseIndexChangeListener; -import tools.refinery.viatra.runtime.base.api.EMFBaseIndexChangeListener; -import tools.refinery.viatra.runtime.base.api.IEMFIndexingErrorListener; -import tools.refinery.viatra.runtime.base.api.LightweightEObjectObserver; -import tools.refinery.viatra.runtime.base.api.NavigationHelper; - -/** - * Wraps the EMF base index into the IBaseIndex interface. - * @author Bergmann Gabor - * - */ -public class EMFBaseIndexWrapper implements IBaseIndex { - - private final NavigationHelper navigationHelper; - /** - * @return the underlying index object - */ - public NavigationHelper getNavigationHelper() { - return navigationHelper; - } - - /** - * @param navigationHelper - */ - public EMFBaseIndexWrapper(NavigationHelper navigationHelper) { - this.navigationHelper = navigationHelper; - } - - @Override - public void resampleDerivedFeatures() { - navigationHelper.resampleDerivedFeatures(); - } - - - @Override - public V coalesceTraversals(Callable callable) throws InvocationTargetException { - return navigationHelper.coalesceTraversals(callable); - } - - Map indexErrorListeners = - new HashMap(); - @Override - public boolean addIndexingErrorListener(final IIndexingErrorListener listener) { - if (indexErrorListeners.containsKey(listener)) return false; - IEMFIndexingErrorListener emfListener = new IEMFIndexingErrorListener() { - @Override - public void fatal(String description, Throwable t) { - listener.fatal(description, t); - } - @Override - public void error(String description, Throwable t) { - listener.error(description, t); - } - }; - indexErrorListeners.put(listener, emfListener); - return navigationHelper.addIndexingErrorListener(emfListener); - } - @Override - public boolean removeIndexingErrorListener(IIndexingErrorListener listener) { - if (!indexErrorListeners.containsKey(listener)) return false; - return navigationHelper.removeIndexingErrorListener(indexErrorListeners.remove(listener)); - } - - - Map indexChangeListeners = - new HashMap(); - @Override - public void addBaseIndexChangeListener(final ViatraBaseIndexChangeListener listener) { - EMFBaseIndexChangeListener emfListener = new EMFBaseIndexChangeListener() { - @Override - public boolean onlyOnIndexChange() { - return listener.onlyOnIndexChange(); - } - - @Override - public void notifyChanged(boolean indexChanged) { - listener.notifyChanged(indexChanged); - } - }; - indexChangeListeners.put(listener, emfListener); - navigationHelper.addBaseIndexChangeListener(emfListener); - } - @Override - public void removeBaseIndexChangeListener(ViatraBaseIndexChangeListener listener) { - final EMFBaseIndexChangeListener cListener = indexChangeListeners.remove(listener); - if (cListener != null) - navigationHelper.removeBaseIndexChangeListener(cListener); - } - - Map instanceObservers = - new HashMap(); - @Override - public boolean addInstanceObserver(final IInstanceObserver observer, - Object observedObject) { - if (observedObject instanceof EObject) { - EObjectObserver emfObserver = instanceObservers.computeIfAbsent(observer, EObjectObserver::new); - boolean success = - navigationHelper.addLightweightEObjectObserver(emfObserver, (EObject) observedObject); - if (success) emfObserver.usageCount++; - return success; - } else return false; - } - @Override - public boolean removeInstanceObserver(IInstanceObserver observer, - Object observedObject) { - if (observedObject instanceof EObject) { - EObjectObserver emfObserver = instanceObservers.get(observer); - if (emfObserver == null) - return false; - boolean success = - navigationHelper.removeLightweightEObjectObserver(emfObserver, (EObject)observedObject); - if (success) - if (0 == --emfObserver.usageCount) - instanceObservers.remove(observer); - return success; - } else return false; - } - private static class EObjectObserver implements LightweightEObjectObserver { - /** - * - */ - private final IInstanceObserver observer; - int usageCount = 0; - - /** - * @param observer - */ - private EObjectObserver(IInstanceObserver observer) { - this.observer = observer; - } - - @Override - public void notifyFeatureChanged(EObject host, - EStructuralFeature feature, Notification notification) { - observer.notifyBinaryChanged(host, feature); - } - } - -} \ No newline at end of file diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFEngineContext.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFEngineContext.java deleted file mode 100644 index 5fe9e23a..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFEngineContext.java +++ /dev/null @@ -1,110 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2014, Bergmann Gabor, Denes Harmath, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf; - -import org.apache.log4j.Logger; -import org.eclipse.emf.common.notify.Notifier; -import tools.refinery.viatra.runtime.api.ViatraQueryEngine; -import tools.refinery.viatra.runtime.api.scope.IBaseIndex; -import tools.refinery.viatra.runtime.api.scope.IEngineContext; -import tools.refinery.viatra.runtime.api.scope.IIndexingErrorListener; -import tools.refinery.viatra.runtime.base.api.ViatraBaseFactory; -import tools.refinery.viatra.runtime.base.api.NavigationHelper; -import tools.refinery.viatra.runtime.matchers.ViatraQueryRuntimeException; -import tools.refinery.viatra.runtime.matchers.context.IQueryRuntimeContext; - -/** - * Implements an engine context on EMF models. - * @author Bergmann Gabor - * - */ -class EMFEngineContext implements IEngineContext { - - private final EMFScope emfScope; - ViatraQueryEngine engine; - Logger logger; - NavigationHelper navHelper; - IBaseIndex baseIndex; - IIndexingErrorListener taintListener; - private EMFQueryRuntimeContext runtimeContext; - - public EMFEngineContext(EMFScope emfScope, ViatraQueryEngine engine, IIndexingErrorListener taintListener, Logger logger) { - this.emfScope = emfScope; - this.engine = engine; - this.logger = logger; - this.taintListener = taintListener; - } - - /** - * @throws ViatraQueryRuntimeException thrown if the navigation helper cannot be initialized - */ - public NavigationHelper getNavHelper() { - return getNavHelper(true); - } - - private NavigationHelper getNavHelper(boolean ensureInitialized) { - if (navHelper == null) { - // sync to avoid crazy compiler reordering which would matter if derived features use VIATRA and call this - // reentrantly - synchronized (this) { - navHelper = ViatraBaseFactory.getInstance().createNavigationHelper(null, this.emfScope.getOptions(), - logger); - getBaseIndex().addIndexingErrorListener(taintListener); - } - - if (ensureInitialized) { - ensureIndexLoaded(); - } - - } - return navHelper; - } - - private void ensureIndexLoaded() { - for (Notifier scopeRoot : this.emfScope.getScopeRoots()) { - navHelper.addRoot(scopeRoot); - } - } - - @Override - public IQueryRuntimeContext getQueryRuntimeContext() { - NavigationHelper nh = getNavHelper(false); - if (runtimeContext == null) { - runtimeContext = - emfScope.getOptions().isDynamicEMFMode() ? - new DynamicEMFQueryRuntimeContext(nh, logger, emfScope) : - new EMFQueryRuntimeContext(nh, logger, emfScope); - - ensureIndexLoaded(); - } - - return runtimeContext; - } - - @Override - public void dispose() { - if (runtimeContext != null) runtimeContext.dispose(); - if (navHelper != null) navHelper.dispose(); - - this.baseIndex = null; - this.engine = null; - this.logger = null; - this.navHelper = null; - } - - - @Override - public IBaseIndex getBaseIndex() { - if (baseIndex == null) { - final NavigationHelper navigationHelper = getNavHelper(); - baseIndex = new EMFBaseIndexWrapper(navigationHelper); - } - return baseIndex; - } -} \ No newline at end of file diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFQueryMetaContext.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFQueryMetaContext.java deleted file mode 100644 index c316d308..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFQueryMetaContext.java +++ /dev/null @@ -1,405 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf; - -import java.util.Arrays; -import java.util.Collection; -import java.util.Collections; -import java.util.Comparator; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Map; -import java.util.Set; - -import org.eclipse.emf.common.util.EList; -import org.eclipse.emf.ecore.EAttribute; -import org.eclipse.emf.ecore.EClass; -import org.eclipse.emf.ecore.EClassifier; -import org.eclipse.emf.ecore.EDataType; -import org.eclipse.emf.ecore.EObject; -import org.eclipse.emf.ecore.EReference; -import org.eclipse.emf.ecore.EStructuralFeature; -import org.eclipse.emf.ecore.EcorePackage; -import tools.refinery.viatra.runtime.emf.types.BaseEMFTypeKey; -import tools.refinery.viatra.runtime.emf.types.EClassTransitiveInstancesKey; -import tools.refinery.viatra.runtime.emf.types.EClassUnscopedTransitiveInstancesKey; -import tools.refinery.viatra.runtime.emf.types.EDataTypeInSlotsKey; -import tools.refinery.viatra.runtime.emf.types.EStructuralFeatureInstancesKey; -import tools.refinery.viatra.runtime.matchers.context.AbstractQueryMetaContext; -import tools.refinery.viatra.runtime.matchers.context.IInputKey; -import tools.refinery.viatra.runtime.matchers.context.InputKeyImplication; -import tools.refinery.viatra.runtime.matchers.context.common.JavaTransitiveInstancesKey; - -/** - * The meta context information for EMF scopes. - * - *

The runtime context may specialize answers with a given scope. - * In a static context, a conservative default version ({@link #DEFAULT}) can be used instead. - * - *

TODO generics? - * @author Bergmann Gabor - * - */ -public final class EMFQueryMetaContext extends AbstractQueryMetaContext { - - /** - * Default static instance that only makes conservative assumptions that are valid for any {@link EMFScope} (but not if objects are used). - * @since 1.6 - */ - public static final EMFQueryMetaContext DEFAULT = new EMFQueryMetaContext(false, true, UnscopedTypeSupport.EMIT_ALWAYS); - - /** - * Default static instance that only makes conservative assumptions that are valid for any scope, even with surrogate objects. - * Unscoped types are used for inference, but not emitted as replacement candidates, as they cannot be checked at runtime. - * @since 2.1 - */ - public static final EMFQueryMetaContext DEFAULT_SURROGATE = new EMFQueryMetaContext(false, true, UnscopedTypeSupport.EMIT_EXCEPT_AS_WEAKENED_REPLACEMENT); - - - private static final EClass EOBJECT_CLASS = - EcorePackage.eINSTANCE.getEObject(); - private static final EClassTransitiveInstancesKey EOBJECT_SCOPED_KEY = - new EClassTransitiveInstancesKey(EOBJECT_CLASS); - private static final EClassUnscopedTransitiveInstancesKey EOBJECT_UNSCOPED_KEY = - new EClassUnscopedTransitiveInstancesKey(EOBJECT_CLASS); - - private boolean assumeNonDangling; - private boolean subResourceScopeSplit; - private UnscopedTypeSupport emitUnscopedEClassTypes; - - private enum UnscopedTypeSupport { - EMIT_ALWAYS, - EMIT_EXCEPT_AS_WEAKENED_REPLACEMENT, - EMIT_NEVER - } - - - /** - * Instantiates a specialized meta information that is aware of scope-specific details. - * Note that this API is not stable and thus non-public. - * - * @param assumeNonDangling assumes that all cross-references are non-dangling (do not lead out of scope), no matter what - * @param subResourceScopeSplit the scope granularity may be finer than resource-level, i.e. proxy-non-resolving references can lead out of scope - * @param emitUnscopedEClassTypes if requested, the metacontext will suppress unscoped input keys; this is recommended if surrogates are used instead of EObjects - */ - EMFQueryMetaContext(boolean assumeNonDangling, boolean subResourceScopeSplit, UnscopedTypeSupport emitUnscopedEClassTypes) { - this.assumeNonDangling = assumeNonDangling; - this.subResourceScopeSplit = subResourceScopeSplit; - this.emitUnscopedEClassTypes = emitUnscopedEClassTypes; - } - - /** - * Instantiates a specialized meta information that is aware of scope-specific details. - * @since 2.1 - */ - public EMFQueryMetaContext(EMFScope scope) { - this(scope.getOptions().isDanglingFreeAssumption(), - scope.getScopeRoots().size()==1 && scope.getScopeRoots().iterator().next() instanceof EObject, - UnscopedTypeSupport.EMIT_ALWAYS); - } - - - @Override - public boolean isEnumerable(IInputKey key) { - ensureValidKey(key); - return key.isEnumerable(); -// if (key instanceof JavaTransitiveInstancesKey) -// return false; -// else -// return true; - } - - @Override - public boolean canLeadOutOfScope(IInputKey key) { - ensureValidKey(key); - if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - if (feature instanceof EReference){ - return canLeadOutOfScope((EReference) feature); - } - } - return false; - } - - /** - * Tells whether the given reference may lead out of scope. - * @since 2.1 - */ - public boolean canLeadOutOfScope(EReference reference) { - // Is it possible that this edge is dangling, i.e. its target lies outside of the scope? - // Unless non-dangling is globally assumed, - // proxy-resolving references (incl. containment) might point to proxies and are thus considered unsafe. - // Additionally, if the scope is sub-resource (containment subtree of object), - // all non-containment edges are also unsafe. - // Note that in case of cross-resource containment, - // the scope includes the contained object even if it is in a foreign resource. - return (!assumeNonDangling) - && (reference.isResolveProxies() || (subResourceScopeSplit && !reference.isContainment())); - } - - @Override - public boolean isStateless(IInputKey key) { - ensureValidKey(key); - return key instanceof JavaTransitiveInstancesKey || key instanceof EClassUnscopedTransitiveInstancesKey; - } - - @Override - public Map, Set> getFunctionalDependencies(IInputKey key) { - ensureValidKey(key); - if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - final Map, Set> result = - new HashMap, Set>(); - if (isFeatureMultiplicityToOne(feature)) - result.put(Collections.singleton(0), Collections.singleton(1)); - if (isFeatureMultiplicityOneTo(feature)) - result.put(Collections.singleton(1), Collections.singleton(0)); - return result; - } else { - return Collections.emptyMap(); - } - } - - /** - * @since 2.1 - */ - public EClassTransitiveInstancesKey getSourceTypeKey(EStructuralFeatureInstancesKey key) { - return new EClassTransitiveInstancesKey(key.getEmfKey().getEContainingClass()); - } - /** - * @since 2.1 - */ - public IInputKey getTargetTypeKey(EStructuralFeatureInstancesKey key) { - EStructuralFeature feature = key.getEmfKey(); - if (feature instanceof EAttribute) { - return new EDataTypeInSlotsKey(((EAttribute) feature).getEAttributeType()); - } else if (feature instanceof EReference) { - EClass eReferenceType = ((EReference) feature).getEReferenceType(); - if (canLeadOutOfScope(key)) { - return new EClassUnscopedTransitiveInstancesKey(eReferenceType); - } else { - return new EClassTransitiveInstancesKey(eReferenceType); - } - } else throw new IllegalArgumentException(); - } - - @Override - public Collection getImplications(IInputKey implyingKey) { - ensureValidKey(implyingKey); - Collection result = new HashSet(); - - if (implyingKey instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) implyingKey).getEmfKey(); - - // direct eSuperClasses - EList directSuperTypes = eClass.getESuperTypes(); - if (!directSuperTypes.isEmpty()) { - for (EClass superType : directSuperTypes) { - final EClassTransitiveInstancesKey implied = new EClassTransitiveInstancesKey(superType); - result.add(new InputKeyImplication(implyingKey, implied, Arrays.asList(0))); - } - } else { - if (!EOBJECT_SCOPED_KEY.equals(implyingKey)) { - result.add(new InputKeyImplication(implyingKey, EOBJECT_SCOPED_KEY, Arrays.asList(0))); - } - } - // implies unscoped - if (UnscopedTypeSupport.EMIT_NEVER != emitUnscopedEClassTypes) - result.add(new InputKeyImplication(implyingKey, - new EClassUnscopedTransitiveInstancesKey(eClass), - Arrays.asList(0))); - } else if (implyingKey instanceof EClassUnscopedTransitiveInstancesKey) { - EClass eClass = ((EClassUnscopedTransitiveInstancesKey) implyingKey).getEmfKey(); - - // direct eSuperClasses - EList directSuperTypes = eClass.getESuperTypes(); - if (!directSuperTypes.isEmpty()) { - for (EClass superType : directSuperTypes) { - final EClassUnscopedTransitiveInstancesKey implied = new EClassUnscopedTransitiveInstancesKey( - superType); - result.add(new InputKeyImplication(implyingKey, implied, Arrays.asList(0))); - } - } else { - if (!EOBJECT_UNSCOPED_KEY.equals(implyingKey)) { - result.add(new InputKeyImplication(implyingKey, EOBJECT_UNSCOPED_KEY, Arrays.asList(0))); - } - } - - } else if (implyingKey instanceof JavaTransitiveInstancesKey) { - Class instanceClass = ((JavaTransitiveInstancesKey) implyingKey).getInstanceClass(); - if (instanceClass != null) { // resolution successful - // direct Java superClass - Class superclass = instanceClass.getSuperclass(); - if (superclass != null) { - JavaTransitiveInstancesKey impliedSuper = new JavaTransitiveInstancesKey(superclass); - result.add(new InputKeyImplication(implyingKey, impliedSuper, Arrays.asList(0))); - } - - // direct Java superInterfaces - for (Class superInterface : instanceClass.getInterfaces()) { - if (superInterface != null) { - JavaTransitiveInstancesKey impliedInterface = new JavaTransitiveInstancesKey(superInterface); - result.add(new InputKeyImplication(implyingKey, impliedInterface, Arrays.asList(0))); - } - } - } - - } else if (implyingKey instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) implyingKey).getEmfKey(); - - // source and target type - final EClass sourceType = featureSourceType(feature); - final EClassTransitiveInstancesKey impliedSource = new EClassTransitiveInstancesKey(sourceType); - final EClassifier targetType = featureTargetType(feature); - final IInputKey impliedTarget; - if (feature instanceof EReference) { - EReference reference = (EReference) feature; - - if (!canLeadOutOfScope(reference)) { - impliedTarget = new EClassTransitiveInstancesKey((EClass) targetType); - } else { - impliedTarget = (UnscopedTypeSupport.EMIT_NEVER != emitUnscopedEClassTypes) ? - new EClassUnscopedTransitiveInstancesKey((EClass) targetType) - : null; - } - } else { // EDatatype - impliedTarget = new EDataTypeInSlotsKey((EDataType) targetType); - } - - result.add(new InputKeyImplication(implyingKey, impliedSource, Arrays.asList(0))); - if (impliedTarget != null) - result.add(new InputKeyImplication(implyingKey, impliedTarget, Arrays.asList(1))); - - // opposite - EReference opposite = featureOpposite(feature); - if (opposite != null && !canLeadOutOfScope((EReference) feature)) { - EStructuralFeatureInstancesKey impliedOpposite = new EStructuralFeatureInstancesKey(opposite); - result.add(new InputKeyImplication(implyingKey, impliedOpposite, Arrays.asList(1, 0))); - } - - // containment - // TODO - } else if (implyingKey instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) implyingKey).getEmfKey(); - - // instance class of datatype - // TODO this can have a generation gap! (could be some dynamic EMF impl or whatever) - Class instanceClass = dataType.getInstanceClass(); - if (instanceClass != null) { - JavaTransitiveInstancesKey implied = new JavaTransitiveInstancesKey(instanceClass); - result.add(new InputKeyImplication(implyingKey, implied, Arrays.asList(0))); - } - } else { - illegalInputKey(implyingKey); - } - - return result; - } - - @Override - public Map> getConditionalImplications(IInputKey implyingKey) { - ensureValidKey(implyingKey); - if (implyingKey instanceof EClassUnscopedTransitiveInstancesKey) { - EClass emfKey = ((EClassUnscopedTransitiveInstancesKey) implyingKey).getEmfKey(); - - Map> result = new HashMap<>(); - result.put( - new InputKeyImplication(implyingKey, EOBJECT_SCOPED_KEY, Arrays.asList(0)), - new HashSet<>(Arrays.asList(new InputKeyImplication(implyingKey, new EClassTransitiveInstancesKey(emfKey), Arrays.asList(0)))) - ); - return result; - } else return super.getConditionalImplications(implyingKey); - } - - @Override - public Collection getWeakenedAlternatives(IInputKey implyingKey) { - ensureValidKey(implyingKey); - if (UnscopedTypeSupport.EMIT_ALWAYS == emitUnscopedEClassTypes && implyingKey instanceof EClassTransitiveInstancesKey) { - EClass emfKey = ((EClassTransitiveInstancesKey) implyingKey).getEmfKey(); - - Collection result = new HashSet(); - result.add( - // in some cases, filtering by the the unscoped key may be sufficient - new InputKeyImplication(implyingKey, new EClassUnscopedTransitiveInstancesKey(emfKey), Arrays.asList(0)) - ); - return result; - } else return super.getWeakenedAlternatives(implyingKey); - } - - public void ensureValidKey(IInputKey key) { - if (! (key instanceof BaseEMFTypeKey) && ! (key instanceof JavaTransitiveInstancesKey)) - illegalInputKey(key); - } - - public void illegalInputKey(IInputKey key) { - throw new IllegalArgumentException("The input key " + key + " is not a valid EMF input key."); - } - - public boolean isFeatureMultiplicityToOne(EStructuralFeature feature) { - return !feature.isMany(); - } - - public boolean isFeatureMultiplicityOneTo(EStructuralFeature typeObject) { - if (typeObject instanceof EReference) { - final EReference feature = (EReference)typeObject; - final EReference eOpposite = feature.getEOpposite(); - return feature.isContainment() || (eOpposite != null && !eOpposite.isMany()); - } else return false; - } - - public EClass featureSourceType(EStructuralFeature feature) { - return feature.getEContainingClass(); - } - public EClassifier featureTargetType(EStructuralFeature typeObject) { - if (typeObject instanceof EAttribute) { - EAttribute attribute = (EAttribute) typeObject; - return attribute.getEAttributeType(); - } else if (typeObject instanceof EReference) { - EReference reference = (EReference) typeObject; - return reference.getEReferenceType(); - } else - throw new IllegalArgumentException("typeObject has invalid type " + typeObject.getClass().getName()); - } - public EReference featureOpposite(EStructuralFeature typeObject) { - if (typeObject instanceof EReference) { - EReference reference = (EReference) typeObject; - return reference.getEOpposite(); - } else return null; - } - - @Override - public Comparator getSuggestedEliminationOrdering() { - return SUGGESTED_ELIMINATION_ORDERING; - } - - private static final Comparator SUGGESTED_ELIMINATION_ORDERING = new Comparator() { - @Override - public int compare(IInputKey o1, IInputKey o2) { - if (o1 instanceof EClassTransitiveInstancesKey && o2 instanceof EClassTransitiveInstancesKey) { - // common EClass types with many instances should be eliminated before rare types - return getRarity((EClassTransitiveInstancesKey)o1) - getRarity((EClassTransitiveInstancesKey)o2); - } else { - return getKeyTypeEliminationSequence(o1) - getKeyTypeEliminationSequence(o2); - } - } - - // The more supertypes there are, the more specialized the type - // the more specialized the type, the rarer instances are expected to be found - private int getRarity(EClassTransitiveInstancesKey key) { - return key.getEmfKey().getEAllSuperTypes().size() + (EOBJECT_SCOPED_KEY.equals(key) ? 0 : 1); - } - - // Scoped EClass transitive instance keys are attempted to be eliminated before all else - // so that e.g. their unscoped version can eliminate them is variable is known to be scoped - private int getKeyTypeEliminationSequence(IInputKey o1) { - return (o1 instanceof EClassTransitiveInstancesKey) ? -1 : 0; - } - }; - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFQueryRuntimeContext.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFQueryRuntimeContext.java deleted file mode 100644 index 7809cd24..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFQueryRuntimeContext.java +++ /dev/null @@ -1,839 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf; - -import java.lang.reflect.InvocationTargetException; -import java.util.Collection; -import java.util.Collections; -import java.util.EnumSet; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Map; -import java.util.Optional; -import java.util.Set; -import java.util.concurrent.Callable; -import java.util.function.Function; -import java.util.stream.Collectors; - -import org.apache.log4j.Logger; -import org.eclipse.emf.ecore.EClass; -import org.eclipse.emf.ecore.EDataType; -import org.eclipse.emf.ecore.EObject; -import org.eclipse.emf.ecore.EStructuralFeature; -import tools.refinery.viatra.runtime.base.api.DataTypeListener; -import tools.refinery.viatra.runtime.base.api.FeatureListener; -import tools.refinery.viatra.runtime.base.api.IndexingLevel; -import tools.refinery.viatra.runtime.base.api.InstanceListener; -import tools.refinery.viatra.runtime.base.api.NavigationHelper; -import tools.refinery.viatra.runtime.emf.types.EClassTransitiveInstancesKey; -import tools.refinery.viatra.runtime.emf.types.EClassUnscopedTransitiveInstancesKey; -import tools.refinery.viatra.runtime.emf.types.EDataTypeInSlotsKey; -import tools.refinery.viatra.runtime.emf.types.EStructuralFeatureInstancesKey; -import tools.refinery.viatra.runtime.matchers.context.AbstractQueryRuntimeContext; -import tools.refinery.viatra.runtime.matchers.context.IInputKey; -import tools.refinery.viatra.runtime.matchers.context.IQueryMetaContext; -import tools.refinery.viatra.runtime.matchers.context.IQueryRuntimeContextListener; -import tools.refinery.viatra.runtime.matchers.context.IndexingService; -import tools.refinery.viatra.runtime.matchers.context.common.JavaTransitiveInstancesKey; -import tools.refinery.viatra.runtime.matchers.tuple.ITuple; -import tools.refinery.viatra.runtime.matchers.tuple.Tuple; -import tools.refinery.viatra.runtime.matchers.tuple.TupleMask; -import tools.refinery.viatra.runtime.matchers.tuple.Tuples; -import tools.refinery.viatra.runtime.matchers.util.Accuracy; - -/** - * The EMF-based runtime query context, backed by an IQBase NavigationHelper. - * - * @author Bergmann Gabor - * - *

TODO: {@link #ensureIndexed(EClass)} may be inefficient if supertype already cached. - * @since 1.4 - */ -public class EMFQueryRuntimeContext extends AbstractQueryRuntimeContext { - protected final NavigationHelper baseIndex; - //private BaseIndexListener listener; - - protected final Map> indexedClasses = new HashMap<>(); - protected final Map> indexedDataTypes = new HashMap<>(); - protected final Map> indexedFeatures = new HashMap<>(); - - protected final EMFQueryMetaContext metaContext; - - protected Logger logger; - - private EMFScope emfScope; - - public EMFQueryRuntimeContext(NavigationHelper baseIndex, Logger logger, EMFScope emfScope) { - this.baseIndex = baseIndex; - this.logger = logger; - this.metaContext = new EMFQueryMetaContext(emfScope); - this.emfScope = emfScope; - } - - public EMFScope getEmfScope() { - return emfScope; - } - - /** - * Utility method to add an indexing service to a given key. Returns true if the requested service was - * not present before this call. - * @param map - * @param key - * @param service - * @return - */ - private static boolean addIndexingService(Map> map, K key, IndexingService service){ - EnumSet current = map.get(key); - if (current == null){ - current = EnumSet.of(service); - map.put(key, current); - return true; - }else{ - return current.add(service); - } - } - - public void dispose() { - //baseIndex.removeFeatureListener(indexedFeatures, listener); - indexedFeatures.clear(); - //baseIndex.removeInstanceListener(indexedClasses, listener); - indexedClasses.clear(); - //baseIndex.removeDataTypeListener(indexedDataTypes, listener); - indexedDataTypes.clear(); - - // No need to remove listeners, as NavHelper will be disposed imminently. - } - - @Override - public V coalesceTraversals(Callable callable) throws InvocationTargetException { - return baseIndex.coalesceTraversals(callable); - } - - @Override - public boolean isCoalescing() { - return baseIndex.isCoalescing(); - } - - @Override - public IQueryMetaContext getMetaContext() { - return metaContext; - } - - @Override - public void ensureIndexed(IInputKey key, IndexingService service) { - ensureEnumerableKey(key); - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - ensureIndexed(eClass, service); - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - ensureIndexed(dataType, service); - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - ensureIndexed(feature, service); - } else { - illegalInputKey(key); - } - } - - /** - * Retrieve the current registered indexing services for the given key. May not return null, - * returns an empty set if no indexing is registered. - * - * @since 1.4 - */ - protected EnumSet getCurrentIndexingServiceFor(IInputKey key){ - ensureEnumerableKey(key); - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - EnumSet is = indexedClasses.get(eClass); - return is == null ? EnumSet.noneOf(IndexingService.class) : is; - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - EnumSet is = indexedDataTypes.get(dataType); - return is == null ? EnumSet.noneOf(IndexingService.class) : is; - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - EnumSet is = indexedFeatures.get(feature); - return is == null ? EnumSet.noneOf(IndexingService.class) : is; - } else { - illegalInputKey(key); - return EnumSet.noneOf(IndexingService.class); - } - } - - @Override - public boolean isIndexed(IInputKey key, IndexingService service) { - return getCurrentIndexingServiceFor(key).contains(service); - } - - @Override - public boolean containsTuple(IInputKey key, ITuple seed) { - ensureValidKey(key); - if (key instanceof JavaTransitiveInstancesKey) { - Class instanceClass = forceGetWrapperInstanceClass((JavaTransitiveInstancesKey) key); - return instanceClass != null && instanceClass.isInstance(seed.get(0)); - } else if (key instanceof EClassUnscopedTransitiveInstancesKey) { - EClass emfKey = ((EClassUnscopedTransitiveInstancesKey) key).getEmfKey(); - Object candidateInstance = seed.get(0); - return candidateInstance instanceof EObject - && baseIndex.isInstanceOfUnscoped((EObject) candidateInstance, emfKey); - } else { - ensureIndexed(key, IndexingService.INSTANCES); - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - // instance check not enough to satisfy scoping, must lookup from index - Object candidateInstance = seed.get(0); - return candidateInstance instanceof EObject - && baseIndex.isInstanceOfScoped((EObject) candidateInstance, eClass); - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - return baseIndex.isInstanceOfDatatype(seed.get(0), dataType); - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - Object sourceCandidate = seed.get(0); - return sourceCandidate instanceof EObject - && baseIndex.isFeatureInstance((EObject) sourceCandidate, seed.get(1), feature); - } else { - illegalInputKey(key); - return false; - } - } - } - - private Class forceGetWrapperInstanceClass(JavaTransitiveInstancesKey key) { - Class instanceClass; - try { - instanceClass = key.forceGetWrapperInstanceClass(); - } catch (ClassNotFoundException e) { - logger.error("Could not load instance class for type constraint " + key.getWrappedKey(), e); - instanceClass = null; - } - return instanceClass; - } - - @Override - public Iterable enumerateTuples(IInputKey key, TupleMask seedMask, ITuple seed) { - ensureIndexed(key, IndexingService.INSTANCES); - final Collection result = new HashSet(); - - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - - if (seedMask.indices.length == 0) { // unseeded - return baseIndex.getAllInstances(eClass).stream().map(wrapUnary).collect(Collectors.toSet()); - } else { // fully seeded - Object seedInstance = seedMask.getValue(seed, 0); - if (containsTuple(key, seed)) - result.add(Tuples.staticArityFlatTupleOf(seedInstance)); - } - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - - if (seedMask.indices.length == 0) { // unseeded - return baseIndex.getDataTypeInstances(dataType).stream().map(wrapUnary).collect(Collectors.toSet()); - } else { // fully seeded - Object seedInstance = seedMask.getValue(seed, 0); - if (containsTuple(key, seed)) - result.add(Tuples.staticArityFlatTupleOf(seedInstance)); - } - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - - boolean isSourceBound = false; - int sourceIndex = -1; - boolean isTargetBound = false; - int targetIndex = -1; - for (int i = 0; i < seedMask.getSize(); i++) { - int index = seedMask.indices[i]; - if (index == 0) { - isSourceBound = true; - sourceIndex = i; - } else if (index == 1) { - isTargetBound = true; - targetIndex = i; - } - } - - if (!isSourceBound && isTargetBound) { - final Object seedTarget = seed.get(targetIndex); - final Set results = baseIndex.findByFeatureValue(seedTarget, feature); - return results.stream().map(obj -> Tuples.staticArityFlatTupleOf(obj, seedTarget)).collect(Collectors.toSet()); - } else if (isSourceBound && isTargetBound) { // fully seeded - final Object seedSource = seed.get(sourceIndex); - final Object seedTarget = seed.get(targetIndex); - if (containsTuple(key, seed)) - result.add(Tuples.staticArityFlatTupleOf(seedSource, seedTarget)); - } else if (!isSourceBound && !isTargetBound) { // fully unseeded - baseIndex.processAllFeatureInstances(feature, (source, target) -> result.add(Tuples.staticArityFlatTupleOf(source, target))); - } else if (isSourceBound && !isTargetBound) { - final Object seedSource = seed.get(sourceIndex); - final Set results = baseIndex.getFeatureTargets((EObject) seedSource, feature); - return results.stream().map(obj -> Tuples.staticArityFlatTupleOf(seedSource, obj)).collect(Collectors.toSet()); - } - } else { - illegalInputKey(key); - } - - - return result; - } - - private static Function wrapUnary = Tuples::staticArityFlatTupleOf; - - @Override - public Iterable enumerateValues(IInputKey key, TupleMask seedMask, ITuple seed) { - ensureIndexed(key, IndexingService.INSTANCES); - - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - - if (seedMask.indices.length == 0) { // unseeded - return baseIndex.getAllInstances(eClass); - } else { - // must be unseeded, this is enumerateValues after all! - illegalEnumerateValues(seed.toImmutable()); - } - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - - if (seedMask.indices.length == 0) { // unseeded - return baseIndex.getDataTypeInstances(dataType); - } else { - // must be unseeded, this is enumerateValues after all! - illegalEnumerateValues(seed.toImmutable()); - } - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - - boolean isSourceBound = false; - int sourceIndex = -1; - boolean isTargetBound = false; - int targetIndex = -1; - for (int i = 0; i < seedMask.getSize(); i++) { - int index = seedMask.indices[i]; - if (index == 0) { - isSourceBound = true; - sourceIndex = i; - } else if (index == 1) { - isTargetBound = true; - targetIndex = i; - } - } - - if (!isSourceBound && isTargetBound) { - Object seedTarget = seed.get(targetIndex); - return baseIndex.findByFeatureValue(seedTarget, feature); - } else if (isSourceBound && !isTargetBound) { - Object seedSource = seed.get(sourceIndex); - return baseIndex.getFeatureTargets((EObject) seedSource, feature); - } else { - // must be singly unseeded, this is enumerateValues after all! - illegalEnumerateValues(seed.toImmutable()); - } - } else { - illegalInputKey(key); - } - return null; - } - - @Override - public int countTuples(IInputKey key, TupleMask seedMask, ITuple seed) { - ensureIndexed(key, IndexingService.STATISTICS); - - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - - if (seedMask.indices.length == 0) { // unseeded - return baseIndex.countAllInstances(eClass); - } else { // fully seeded - return (containsTuple(key, seed)) ? 1 : 0; - } - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - - if (seedMask.indices.length == 0) { // unseeded - return baseIndex.countDataTypeInstances(dataType); - } else { // fully seeded - return (containsTuple(key, seed)) ? 1 : 0; - } - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - - boolean isSourceBound = false; - int sourceIndex = -1; - boolean isTargetBound = false; - int targetIndex = -1; - for (int i = 0; i < seedMask.getSize(); i++) { - int index = seedMask.indices[i]; - if (index == 0) { - isSourceBound = true; - sourceIndex = i; - } else if (index == 1) { - isTargetBound = true; - targetIndex = i; - } - } - - if (!isSourceBound && isTargetBound) { - final Object seedTarget = seed.get(targetIndex); - return baseIndex.findByFeatureValue(seedTarget, feature).size(); - } else if (isSourceBound && isTargetBound) { // fully seeded - return (containsTuple(key, seed)) ? 1 : 0; - } else if (!isSourceBound && !isTargetBound) { // fully unseeded - return baseIndex.countFeatures(feature); - } else if (isSourceBound && !isTargetBound) { - final Object seedSource = seed.get(sourceIndex); - return baseIndex.countFeatureTargets((EObject) seedSource, feature); - } - } else { - illegalInputKey(key); - } - return 0; - } - - - /** - * @since 2.1 - */ - @Override - public Optional estimateCardinality(IInputKey key, TupleMask groupMask, Accuracy requiredAccuracy) { - - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - - if (isIndexed(key, IndexingService.STATISTICS)) { // exact answer known - if (groupMask.indices.length == 0) { // empty projection - return (0 != baseIndex.countAllInstances(eClass)) ? Optional.of(1L) : Optional.of(0L); - } else { // unprojected - return Optional.of((long)baseIndex.countAllInstances(eClass)); - } - } else return Optional.empty(); // TODO use known supertype counts as upper, subtypes as lower bounds - - } else if (key instanceof EClassUnscopedTransitiveInstancesKey) { - EClass eClass = ((EClassUnscopedTransitiveInstancesKey) key).getEmfKey(); - - // can give only lower bound based on the scoped key - if (Accuracy.BEST_LOWER_BOUND.atLeastAsPreciseAs(requiredAccuracy)) { - return estimateCardinality(new EClassTransitiveInstancesKey(eClass), groupMask, requiredAccuracy); - } else return Optional.empty(); - - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - - if (isIndexed(key, IndexingService.STATISTICS)) { - if (groupMask.indices.length == 0) { // empty projection - return (0 != baseIndex.countDataTypeInstances(dataType)) ? Optional.of(1L) : Optional.of(0L); - } else { // unprojected - return Optional.of((long)baseIndex.countDataTypeInstances(dataType)); - } - } else return Optional.empty(); - - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeatureInstancesKey featureKey = (EStructuralFeatureInstancesKey) key; - EStructuralFeature feature = featureKey.getEmfKey(); - - - boolean isSourceSelected = false; - boolean isTargetSelected = false; - for (int i = 0; i < groupMask.getSize(); i++) { - int index = groupMask.indices[i]; - if (index == 0) { - isSourceSelected = true; - } else if (index == 1) { - isTargetSelected = true; - } - } - - Optional sourceTypeUpperEstimate = - estimateCardinality(metaContext.getSourceTypeKey(featureKey), - TupleMask.identity(1), Accuracy.BEST_UPPER_BOUND); - Optional targetTypeUpperEstimate = - estimateCardinality(metaContext.getTargetTypeKey(featureKey), - TupleMask.identity(1), Accuracy.BEST_UPPER_BOUND); - - if (!isSourceSelected && !isTargetSelected) { // empty projection - if (isIndexed(key, IndexingService.STATISTICS)) { // we have exact node counts - return (0 == baseIndex.countFeatures(feature)) ? Optional.of(0L) : Optional.of(1L); - } else { // we can still say 0 in a few cases - if (0 == sourceTypeUpperEstimate.orElse(-1L)) - return Optional.of(0L); - - if (0 == targetTypeUpperEstimate.orElse(-1L)) - return Optional.of(0L); - - return Optional.empty(); - } - - } else if (isSourceSelected && !isTargetSelected) { // count sources - if (isIndexed(key, IndexingService.INSTANCES)) { // we have instances, therefore feature end counts - return Optional.of((long)(baseIndex.getHoldersOfFeature(feature).size())); - } else if (metaContext.isFeatureMultiplicityToOne(feature) && - isIndexed(key, IndexingService.STATISTICS)) { // count of edges = count of sources due to func. dep. - return Optional.of((long)(baseIndex.countFeatures(feature))); - } else if (Accuracy.BEST_UPPER_BOUND.atLeastAsPreciseAs(requiredAccuracy)) { - // upper bound by source type - Optional estimate = sourceTypeUpperEstimate; - // total edge counts are another upper bound (even if instances are unindexed) - if (isIndexed(key, IndexingService.STATISTICS)) { - estimate = Optional.of(Math.min( - baseIndex.countFeatures(feature), - estimate.orElse(Long.MAX_VALUE))); - } - return estimate; - } else return Optional.empty(); - - } else if (!isSourceSelected /*&& isTargetSelected*/) { // count targets - if (isIndexed(key, IndexingService.INSTANCES)) { // we have instances, therefore feature end counts - return Optional.of((long)(baseIndex.getValuesOfFeature(feature).size())); - } else if (metaContext.isFeatureMultiplicityOneTo(feature) && - isIndexed(key, IndexingService.STATISTICS)) { // count of edges = count of targets due to func. dep. - return Optional.of((long)(baseIndex.countFeatures(feature))); - } else if (Accuracy.BEST_UPPER_BOUND.atLeastAsPreciseAs(requiredAccuracy)) { // upper bound by target type - // upper bound by target type - Optional estimate = targetTypeUpperEstimate; - // total edge counts are another upper bound (even if instances are unindexed) - if (isIndexed(key, IndexingService.STATISTICS)) { - estimate = Optional.of(Math.min( - baseIndex.countFeatures(feature), - estimate.orElse(Long.MAX_VALUE))); - } - return estimate; - } else return Optional.empty(); - - } else { // (isSourceSelected && isTargetSelected) // count edges - if (isIndexed(key, IndexingService.STATISTICS)) { // we have exact edge counts - return Optional.of((long)baseIndex.countFeatures(feature)); - } else if (Accuracy.BEST_UPPER_BOUND.atLeastAsPreciseAs(requiredAccuracy)) { // overestimates may still be available - Optional estimate = // trivial upper bound: product of source & target type sizes (if available) - (sourceTypeUpperEstimate.isPresent() && targetTypeUpperEstimate.isPresent()) ? - Optional.of( - ((long)sourceTypeUpperEstimate.get()) * targetTypeUpperEstimate.get() - ) : Optional.empty(); - - if (metaContext.isFeatureMultiplicityToOne(feature) && sourceTypeUpperEstimate.isPresent()) { - // upper bounded by source type due to func. dep. - estimate = Optional.of(Math.min( - sourceTypeUpperEstimate.get(), - estimate.orElse(Long.MAX_VALUE))); - } - if (metaContext.isFeatureMultiplicityOneTo(feature) && targetTypeUpperEstimate.isPresent()) { - // upper bounded by target type due to func. dep. - estimate = Optional.of(Math.min( - targetTypeUpperEstimate.get(), - estimate.orElse(Long.MAX_VALUE))); - } - - return estimate; - } else return Optional.empty(); - } - - } else { - return Optional.empty(); - } - } - - /** - * @since 2.1 - */ - @Override - public Optional estimateAverageBucketSize(IInputKey key, TupleMask groupMask, Accuracy requiredAccuracy) { - // smart handling of special cases - if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeatureInstancesKey featureKey = (EStructuralFeatureInstancesKey) key; - EStructuralFeature feature = featureKey.getEmfKey(); - - // special treatment for edge navigation - if (1 == groupMask.getSize()) { - if (0 == groupMask.indices[0] && metaContext.isFeatureMultiplicityToOne(feature)) { // count targets per source - return Optional.of(1.0); - } else if (1 == groupMask.indices[0] && metaContext.isFeatureMultiplicityOneTo(feature)) { // count sources per target - return Optional.of(1.0); - } - } - } - - // keep the default behaviour - return super.estimateAverageBucketSize(key, groupMask, requiredAccuracy); - } - - - public void ensureEnumerableKey(IInputKey key) { - ensureValidKey(key); - if (! metaContext.isEnumerable(key)) - throw new IllegalArgumentException("Key is not enumerable: " + key); - - } - - public void ensureValidKey(IInputKey key) { - metaContext.ensureValidKey(key); - } - public void illegalInputKey(IInputKey key) { - metaContext.illegalInputKey(key); - } - public void illegalEnumerateValues(Tuple seed) { - throw new IllegalArgumentException("Must have exactly one unseeded element in enumerateValues() invocation, received instead: " + seed); - } - - /** - * @since 1.4 - */ - public void ensureIndexed(EClass eClass, IndexingService service) { - if (addIndexingService(indexedClasses, eClass, service)) { - final Set newClasses = Collections.singleton(eClass); - IndexingLevel level = IndexingLevel.toLevel(service); - if (!baseIndex.getIndexingLevel(eClass).providesLevel(level)) { - baseIndex.registerEClasses(newClasses, level); - } - //baseIndex.addInstanceListener(newClasses, listener); - } - } - - /** - * @since 1.4 - */ - public void ensureIndexed(EDataType eDataType, IndexingService service) { - if (addIndexingService(indexedDataTypes, eDataType, service)) { - final Set newDataTypes = Collections.singleton(eDataType); - IndexingLevel level = IndexingLevel.toLevel(service); - if (!baseIndex.getIndexingLevel(eDataType).providesLevel(level)) { - baseIndex.registerEDataTypes(newDataTypes, level); - } - //baseIndex.addDataTypeListener(newDataTypes, listener); - } - } - - /** - * @since 1.4 - */ - public void ensureIndexed(EStructuralFeature feature, IndexingService service) { - if (addIndexingService(indexedFeatures, feature, service)) { - final Set newFeatures = Collections.singleton(feature); - IndexingLevel level = IndexingLevel.toLevel(service); - if (!baseIndex.getIndexingLevel(feature).providesLevel(level)) { - baseIndex.registerEStructuralFeatures(newFeatures, level); - } - //baseIndex.addFeatureListener(newFeatures, listener); - } - } - - - - // UPDATE HANDLING SECTION - - /** - * Abstract internal listener wrapper for a {@link IQueryRuntimeContextListener}. - * Due to the overridden equals/hashCode(), it is safe to create a new instance for the same listener. - * - * @author Bergmann Gabor - */ - private abstract static class ListenerAdapter { - IQueryRuntimeContextListener listener; - Tuple seed; - /** - * @param listener - * @param seed must be non-null - */ - public ListenerAdapter(IQueryRuntimeContextListener listener, Object... seed) { - this.listener = listener; - this.seed = Tuples.flatTupleOf(seed); - } - - @Override - public int hashCode() { - final int prime = 31; - int result = 1; - result = prime * result - + ((listener == null) ? 0 : listener.hashCode()); - result = prime * result + ((seed == null) ? 0 : seed.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) - return true; - if (obj == null) - return false; - if (!(obj.getClass().equals(this.getClass()))) - return false; - ListenerAdapter other = (ListenerAdapter) obj; - if (listener == null) { - if (other.listener != null) - return false; - } else if (!listener.equals(other.listener)) - return false; - if (seed == null) { - if (other.seed != null) - return false; - } else if (!seed.equals(other.seed)) - return false; - return true; - } - - - @Override - public String toString() { - return "Wrapped#" + listener; - } - - - } - private static class EClassTransitiveInstancesAdapter extends ListenerAdapter implements InstanceListener { - private Object seedInstance; - public EClassTransitiveInstancesAdapter(IQueryRuntimeContextListener listener, Object seedInstance) { - super(listener, seedInstance); - this.seedInstance = seedInstance; - } - @Override - public void instanceInserted(EClass clazz, EObject instance) { - if (seedInstance != null && !seedInstance.equals(instance)) return; - listener.update(new EClassTransitiveInstancesKey(clazz), - Tuples.staticArityFlatTupleOf(instance), true); - } - @Override - public void instanceDeleted(EClass clazz, EObject instance) { - if (seedInstance != null && !seedInstance.equals(instance)) return; - listener.update(new EClassTransitiveInstancesKey(clazz), - Tuples.staticArityFlatTupleOf(instance), false); - } - } - private static class EDataTypeInSlotsAdapter extends ListenerAdapter implements DataTypeListener { - private Object seedValue; - public EDataTypeInSlotsAdapter(IQueryRuntimeContextListener listener, Object seedValue) { - super(listener, seedValue); - this.seedValue = seedValue; - } - @Override - public void dataTypeInstanceInserted(EDataType type, Object instance, - boolean firstOccurrence) { - if (firstOccurrence) { - if (seedValue != null && !seedValue.equals(instance)) return; - listener.update(new EDataTypeInSlotsKey(type), - Tuples.staticArityFlatTupleOf(instance), true); - } - } - @Override - public void dataTypeInstanceDeleted(EDataType type, Object instance, - boolean lastOccurrence) { - if (lastOccurrence) { - if (seedValue != null && !seedValue.equals(instance)) return; - listener.update(new EDataTypeInSlotsKey(type), - Tuples.staticArityFlatTupleOf(instance), false); - } - } - } - private static class EStructuralFeatureInstancesKeyAdapter extends ListenerAdapter implements FeatureListener { - private Object seedHost; - private Object seedValue; - public EStructuralFeatureInstancesKeyAdapter(IQueryRuntimeContextListener listener, Object seedHost, Object seedValue) { - super(listener, seedHost, seedValue); - this.seedHost = seedHost; - this.seedValue = seedValue; - } - @Override - public void featureInserted(EObject host, EStructuralFeature feature, - Object value) { - if (seedHost != null && !seedHost.equals(host)) return; - if (seedValue != null && !seedValue.equals(value)) return; - listener.update(new EStructuralFeatureInstancesKey(feature), - Tuples.staticArityFlatTupleOf(host, value), true); - } - @Override - public void featureDeleted(EObject host, EStructuralFeature feature, - Object value) { - if (seedHost != null && !seedHost.equals(host)) return; - if (seedValue != null && !seedValue.equals(value)) return; - listener.update(new EStructuralFeatureInstancesKey(feature), - Tuples.staticArityFlatTupleOf(host, value), false); - } - } - - @Override - public void addUpdateListener(IInputKey key, Tuple seed /* TODO ignored */, IQueryRuntimeContextListener listener) { - // stateless, so NOP - if (key instanceof JavaTransitiveInstancesKey) return; - - ensureIndexed(key, IndexingService.INSTANCES); - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - baseIndex.addInstanceListener(Collections.singleton(eClass), - new EClassTransitiveInstancesAdapter(listener, seed.get(0))); - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - baseIndex.addDataTypeListener(Collections.singleton(dataType), - new EDataTypeInSlotsAdapter(listener, seed.get(0))); - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - baseIndex.addFeatureListener(Collections.singleton(feature), - new EStructuralFeatureInstancesKeyAdapter(listener, seed.get(0), seed.get(1))); - } else { - illegalInputKey(key); - } - } - @Override - public void removeUpdateListener(IInputKey key, Tuple seed, IQueryRuntimeContextListener listener) { - // stateless, so NOP - if (key instanceof JavaTransitiveInstancesKey) return; - - ensureIndexed(key, IndexingService.INSTANCES); - if (key instanceof EClassTransitiveInstancesKey) { - EClass eClass = ((EClassTransitiveInstancesKey) key).getEmfKey(); - baseIndex.removeInstanceListener(Collections.singleton(eClass), - new EClassTransitiveInstancesAdapter(listener, seed.get(0))); - } else if (key instanceof EDataTypeInSlotsKey) { - EDataType dataType = ((EDataTypeInSlotsKey) key).getEmfKey(); - baseIndex.removeDataTypeListener(Collections.singleton(dataType), - new EDataTypeInSlotsAdapter(listener, seed.get(0))); - } else if (key instanceof EStructuralFeatureInstancesKey) { - EStructuralFeature feature = ((EStructuralFeatureInstancesKey) key).getEmfKey(); - baseIndex.removeFeatureListener(Collections.singleton(feature), - new EStructuralFeatureInstancesKeyAdapter(listener, seed.get(0), seed.get(1))); - } else { - illegalInputKey(key); - } - } - - // TODO wrap / unwrap enum literals - // TODO use this in all other public methods (maybe wrap & delegate?) - - @Override - public Object unwrapElement(Object internalElement) { - return internalElement; - } - @Override - public Tuple unwrapTuple(Tuple internalElements) { - return internalElements; - } - @Override - public Object wrapElement(Object externalElement) { - return externalElement; - } - @Override - public Tuple wrapTuple(Tuple externalElements) { - return externalElements; - } - - /** - * @since 1.4 - */ - @Override - public void ensureWildcardIndexing(IndexingService service) { - baseIndex.setWildcardLevel(IndexingLevel.toLevel(service)); - } - - /** - * @since 1.4 - */ - @Override - public void executeAfterTraversal(Runnable runnable) throws InvocationTargetException { - baseIndex.executeAfterTraversal(runnable); - } -} - diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFScope.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFScope.java deleted file mode 100644 index dead9716..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/EMFScope.java +++ /dev/null @@ -1,199 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2014, Bergmann Gabor, Denes Harmath, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf; - -import java.util.Arrays; -import java.util.Collections; -import java.util.HashSet; -import java.util.Set; -import java.util.function.Predicate; -import java.util.stream.Collectors; - -import org.apache.log4j.Logger; -import org.eclipse.emf.common.notify.Notifier; -import org.eclipse.emf.common.util.URI; -import org.eclipse.emf.ecore.EObject; -import org.eclipse.emf.ecore.resource.Resource; -import org.eclipse.emf.ecore.resource.ResourceSet; -import tools.refinery.viatra.runtime.api.AdvancedViatraQueryEngine; -import tools.refinery.viatra.runtime.api.ViatraQueryEngine; -import tools.refinery.viatra.runtime.api.scope.IEngineContext; -import tools.refinery.viatra.runtime.api.scope.IIndexingErrorListener; -import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.base.api.BaseIndexOptions; -import tools.refinery.viatra.runtime.base.api.NavigationHelper; -import tools.refinery.viatra.runtime.exception.ViatraQueryException; - -/** - * An {@link QueryScope} consisting of EMF objects contained in multiple {@link ResourceSet}s, a single {@link ResourceSet}, {@link Resource} or a containment subtree below a given {@link EObject}. - * - *

The scope is characterized by a root and some options (see {@link BaseIndexOptions}) such as dynamic EMF mode, subtree filtering etc. - *

- * The scope of pattern matching will be the given EMF model root(s) and below (see FAQ for more precise definition). - * - *

Note on cross-resource containment: in case of {@link EObject} scopes, cross-resource containments will be considered part of the scope. - * The same goes for {@link ResourceSet} scopes, provided that the resource of the contained element is successfully loaded into the resource set. - * In case of a {@link Resource} scope, containments pointing out from the resource will be excluded from the scope. - * Thus the boundaries of {@link EObject} scopes conform to the notion of EMF logical containment, while {@link Resource} and {@link ResourceSet} scopes adhere to persistence boundaries. - * - * @author Bergmann Gabor - * - */ -public class EMFScope extends QueryScope { - - private Set scopeRoots; - private BaseIndexOptions options; - - /** - * Creates an EMF scope at the given root, with default options (recommended for most users). - * @param scopeRoot the root of the EMF scope - * @throws ViatraQueryRuntimeException- if scopeRoot is not an EMF ResourceSet, Resource or EObject - */ - public EMFScope(Notifier scopeRoot) { - this(Collections.singleton(scopeRoot), new BaseIndexOptions()); - } - - /** - * Creates an EMF scope at the given root, with customizable options. - *

Most users should consider {@link #EMFScope(Notifier)} instead. - * @param scopeRoot the root of the EMF scope - * @param options the base index building settings - * @throws ViatraQueryRuntimeException if scopeRoot is not an EMF ResourceSet, Resource or EObject - */ - public EMFScope(Notifier scopeRoot, BaseIndexOptions options) { - this(Collections.singleton(scopeRoot), options); - } - - /** - * Creates an EMF scope at the given roots, with default options (recommended for most users). - * @param scopeRoots the roots of the EMF scope, must be {@link ResourceSet}s - * @throws ViatraQueryRuntimeException if not all scopeRoots are {@link ResourceSet}s - */ - public EMFScope(Set scopeRoots) { - this(scopeRoots, new BaseIndexOptions()); - } - - /** - * Creates an EMF scope at the given roots, with customizable options. - *

Most users should consider {@link #EMFScope(Set)} instead. - * @param scopeRoots the roots of the EMF scope, must be {@link ResourceSet}s - * @param options the base index building settings - * @throws ViatraQueryRuntimeException if not all scopeRoots are {@link ResourceSet}s - */ - public EMFScope(Set scopeRoots, BaseIndexOptions options) { - super(); - if (scopeRoots.isEmpty()) { - throw new IllegalArgumentException("No scope roots given"); - } else if (scopeRoots.size() == 1) { - checkScopeRoots(scopeRoots, EObject.class::isInstance, Resource.class::isInstance, ResourceSet.class::isInstance); - } else { - checkScopeRoots(scopeRoots, ResourceSet.class::isInstance); - } - this.scopeRoots = new HashSet<>(scopeRoots); - this.options = options.copy(); - } - - @SafeVarargs - private final void checkScopeRoots(Set scopeRoots, Predicate... predicates) { - for (Notifier scopeRoot : scopeRoots) { - // Creating compound predicate that checks the various branches of disjunction together - Predicate compoundPredicate = Arrays.stream(predicates).collect(Collectors.reducing(a -> true, a -> a, (a, b) -> a.or(b))); - if (!compoundPredicate.test(scopeRoot)) - throw new ViatraQueryException(ViatraQueryException.INVALID_EMFROOT - + (scopeRoot == null ? "(null)" : scopeRoot.getClass().getName()), - ViatraQueryException.INVALID_EMFROOT_SHORT); - } - } - - /** - * @return the scope roots ({@link ResourceSet}s) containing the model - */ - public Set getScopeRoots() { - return scopeRoots; - } - - /** - * @return the options - */ - public BaseIndexOptions getOptions() { - return options.copy(); - } - - @Override - public int hashCode() { - final int prime = 31; - int result = 1; - result = prime * result + ((options == null) ? 0 : options.hashCode()); - result = prime * result - + ((scopeRoots == null) ? 0 : scopeRoots.hashCode()); - return result; - } - @Override - public boolean equals(Object obj) { - if (this == obj) - return true; - if (obj == null) - return false; - if (!(obj instanceof EMFScope)) - return false; - EMFScope other = (EMFScope) obj; - if (options == null) { - if (other.options != null) - return false; - } else if (!options.equals(other.options)) - return false; - if (scopeRoots == null) { - if (other.scopeRoots != null) - return false; - } else if (!scopeRoots.equals(other.scopeRoots)) - return false; - return true; - } - - - @Override - public String toString() { - return String.format("EMFScope(%s):%s", options, scopeRoots.stream().map(this::scopeRootString).collect(Collectors.joining(","))); - } - - private String scopeRootString(Notifier notifier) { - if (notifier instanceof Resource) { - Resource resource = (Resource) notifier; - return String.format("%s(%s)", resource.getClass(), resource.getURI()); - } else if (notifier instanceof ResourceSet) { - ResourceSet resourceSet = (ResourceSet) notifier; - return resourceSet.getResources().stream() - .map(Resource::getURI) - .map(URI::toString) - .collect(Collectors.joining(", ", resourceSet.getClass() + "(", ")")); - } else { - return notifier.toString(); - } - } - - @Override - protected IEngineContext createEngineContext(ViatraQueryEngine engine, IIndexingErrorListener errorListener, Logger logger) { - return new EMFEngineContext(this, engine, errorListener, logger); - } - - /** - * Provides access to the underlying EMF model index ({@link NavigationHelper}) from a VIATRA Query engine instantiated on an EMFScope - * - * @param engine an already existing VIATRA Query engine instantiated on an EMFScope - * @return the underlying EMF base index that indexes the contents of the EMF model - * @throws ViatraQueryRuntimeException if base index initialization fails - */ - public static NavigationHelper extractUnderlyingEMFIndex(ViatraQueryEngine engine) { - final QueryScope scope = engine.getScope(); - if (scope instanceof EMFScope) - return ((EMFBaseIndexWrapper)AdvancedViatraQueryEngine.from(engine).getBaseIndex()).getNavigationHelper(); - else throw new IllegalArgumentException("Cannot extract EMF base index from VIATRA Query engine instantiated on non-EMF scope " + scope); - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/helper/ViatraQueryRuntimeHelper.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/helper/ViatraQueryRuntimeHelper.java deleted file mode 100644 index 93ac97f2..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/helper/ViatraQueryRuntimeHelper.java +++ /dev/null @@ -1,161 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2014, Abel Hegedus, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf.helper; - -import java.util.function.Function; - -import org.eclipse.emf.ecore.EClassifier; -import org.eclipse.emf.ecore.EObject; -import org.eclipse.emf.ecore.EPackage; -import org.eclipse.emf.ecore.EStructuralFeature; -import tools.refinery.viatra.runtime.api.IPatternMatch; - -/** - * Helper functions for dealing with the EMF objects with VIATRA Queries. - * - * @author Abel Hegedus - * @since 0.9 - * - */ -public class ViatraQueryRuntimeHelper { - - private ViatraQueryRuntimeHelper() {/*Utility class constructor*/} - - private static final Function STRING_VALUE_TRANSFORMER = input -> (input == null) ? "(null)" : input.toString(); - - /** - * Gives a human-readable name of an EMF type. - */ - public static String prettyPrintEMFType(Object typeObject) { - if (typeObject == null) { - return "(null)"; - } else if (typeObject instanceof EClassifier) { - final EClassifier eClassifier = (EClassifier) typeObject; - final EPackage ePackage = eClassifier.getEPackage(); - final String nsURI = ePackage == null ? null : ePackage.getNsURI(); - final String typeName = eClassifier.getName(); - return "" + nsURI + "/" + typeName; - } else if (typeObject instanceof EStructuralFeature) { - final EStructuralFeature feature = (EStructuralFeature) typeObject; - return prettyPrintEMFType(feature.getEContainingClass()) + "." + feature.getName(); - } else - return typeObject.toString(); - } - - - /** - * Get the structural feature with the given name of the given object. - * - * @param o - * the object (must be an EObject) - * @param featureName - * the name of the feature - * @return the EStructuralFeature of the object or null if it can not be found - */ - public static EStructuralFeature getFeature(Object o, String featureName) { - if (o instanceof EObject) { - EStructuralFeature feature = ((EObject) o).eClass().getEStructuralFeature(featureName); - return feature; - } - return null; - } - - /** - * Returns the message for the given match using the given format. The format string can refer to the value of - * parameter A of the match with $A$ and even access features of A (if it's an EObject), e.g. $A.id$. - * - *

- * If the selected parameter does not exist, the string "[no such parameter]" is added - * - *

- * If no feature is defined, but A has a feature called "name", then its value is used. - * - *

- * If the selected feature does not exist, A.toString() is added. - * - *

- * If the selected feature is null, the string "null" is added. - * - * @param match - * cannot be null! - * @param messageFormat - * cannot be null! - */ - public static String getMessage(IPatternMatch match, String messageFormat) { - return getMessage(match, messageFormat, STRING_VALUE_TRANSFORMER); - } - - /** - * Returns the message for the given match using the given format while transforming values with the given function. - * The format string can refer to the value of parameter A of the match with $A$ and even access features of A (if - * it's an EObject), e.g. $A.id$. The function will be called to compute the final string representation of the - * values selected by the message format. - * - *

- * If the selected parameter does not exist, the string "[no such parameter]" is added - * - *

- * If no feature is defined, but A has a feature called "name", then its value is passed to the function. - * - *

- * If the selected feature does not exist, A is passed to the function. - * - *

- * If the selected feature is null, the string "null" is added. - * - * @param match - * cannot be null! - * @param messageFormat - * cannot be null! - * @param parameterValueTransformer - * cannot be null! - * @since 2.0 - */ - public static String getMessage(IPatternMatch match, String messageFormat, Function parameterValueTransformer) { - String[] tokens = messageFormat.split("\\$"); - StringBuilder newText = new StringBuilder(); - - for (int i = 0; i < tokens.length; i++) { - if (i % 2 == 0) { - newText.append(tokens[i]); - } else { - String[] objectTokens = tokens[i].split("\\."); - if (objectTokens.length > 0) { - Object o = null; - EStructuralFeature feature = null; - - if (objectTokens.length == 1) { - o = match.get(objectTokens[0]); - feature = getFeature(o, "name"); - } - if (objectTokens.length == 2) { - o = match.get(objectTokens[0]); - feature = getFeature(o, objectTokens[1]); - } - - if (o != null && feature != null) { - Object value = ((EObject) o).eGet(feature); - if (value != null) { - newText.append(parameterValueTransformer.apply(value)); - } else { - newText.append("null"); - } - } else if (o != null) { - newText.append(parameterValueTransformer.apply(o)); - } - } else { - newText.append("[no such parameter]"); - } - } - } - - return newText.toString(); - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/BaseEMFTypeKey.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/BaseEMFTypeKey.java deleted file mode 100644 index c5dfa966..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/BaseEMFTypeKey.java +++ /dev/null @@ -1,34 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf.types; - -import tools.refinery.viatra.runtime.matchers.context.common.BaseInputKeyWrapper; - -/** - * Base class for EMF Type keys. - * @author Bergmann Gabor - * - */ -public abstract class BaseEMFTypeKey extends BaseInputKeyWrapper { - - public BaseEMFTypeKey(EMFKey emfKey) { - super(emfKey); - } - - public EMFKey getEmfKey() { - return getWrappedKey(); - } - - @Override - public String toString() { - return this.getPrettyPrintableName(); - } - - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassExactInstancesKey.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassExactInstancesKey.java deleted file mode 100644 index dd10502d..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassExactInstancesKey.java +++ /dev/null @@ -1,51 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2018, Gabor Bergmann, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ - -package tools.refinery.viatra.runtime.emf.types; - -import org.eclipse.emf.ecore.EClass; -import tools.refinery.viatra.runtime.emf.EMFScope; -import tools.refinery.viatra.runtime.emf.helper.ViatraQueryRuntimeHelper; - -/** - * Instance tuples are of form (x), where x is an eObject instance of the given eClass, but not one of its subclasses, within the scope. - *

This input key has the strict semantics that instances must be within the scope. - * - * @noreference This class is not intended to be referenced by clients. Not currently supported by {@link EMFScope}, for internal use only at the time - * - * @author Bergmann Gabor - * @since 2.1 - */ -public class EClassExactInstancesKey extends BaseEMFTypeKey { - - public EClassExactInstancesKey(EClass emfKey) { - super(emfKey); - } - - @Override - public String getPrettyPrintableName() { - return "(scoped,exact) "+ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey); - } - - @Override - public String getStringID() { - return "eClass(scoped,exact)#"+ ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey); - } - - @Override - public int getArity() { - return 1; - } - - @Override - public boolean isEnumerable() { - return true; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassTransitiveInstancesKey.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassTransitiveInstancesKey.java deleted file mode 100644 index 4ca6b220..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassTransitiveInstancesKey.java +++ /dev/null @@ -1,47 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf.types; - -import org.eclipse.emf.ecore.EClass; -import tools.refinery.viatra.runtime.emf.EMFScope; -import tools.refinery.viatra.runtime.emf.helper.ViatraQueryRuntimeHelper; - -/** - * Instance tuples are of form (x), where x is an eObject instance of the given eClass or one of its subclasses within the scope. - *

As of version 1.6, this input key has the strict semantics that instances must be within the {@link EMFScope}. - * @author Bergmann Gabor - * - */ -public class EClassTransitiveInstancesKey extends BaseEMFTypeKey { - - public EClassTransitiveInstancesKey(EClass emfKey) { - super(emfKey); - } - - @Override - public String getPrettyPrintableName() { - return "(scoped) "+ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey); - } - - @Override - public String getStringID() { - return "eClass(scoped)#"+ ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey); - } - - @Override - public int getArity() { - return 1; - } - - @Override - public boolean isEnumerable() { - return true; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassUnscopedTransitiveInstancesKey.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassUnscopedTransitiveInstancesKey.java deleted file mode 100644 index 11c5b235..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EClassUnscopedTransitiveInstancesKey.java +++ /dev/null @@ -1,46 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2017, Gabor Bergmann, IncQueryLabs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf.types; - -import org.eclipse.emf.ecore.EClass; -import tools.refinery.viatra.runtime.emf.helper.ViatraQueryRuntimeHelper; - -/** - * Instance tuples are of form (x), where x is an eObject instance of the given eClass or one of its subclasses regardless whether it is within the scope. - * - * @author Bergmann Gabor - * @since 1.6 - */ -public class EClassUnscopedTransitiveInstancesKey extends BaseEMFTypeKey { - - public EClassUnscopedTransitiveInstancesKey(EClass emfKey) { - super(emfKey); - } - - @Override - public String getPrettyPrintableName() { - return "(unscoped) "+ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey); - } - - @Override - public String getStringID() { - return "eClass(unscoped)#"+ ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey); - } - - @Override - public int getArity() { - return 1; - } - - @Override - public boolean isEnumerable() { - return false; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EDataTypeInSlotsKey.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EDataTypeInSlotsKey.java deleted file mode 100644 index a1cc4863..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EDataTypeInSlotsKey.java +++ /dev/null @@ -1,48 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf.types; - -import org.eclipse.emf.ecore.EDataType; -import tools.refinery.viatra.runtime.emf.helper.ViatraQueryRuntimeHelper; - -/** - * Instance tuples are of form (x), where x is an instance of the given eDataType residing at an attribute slot of an eObject in the model. - * @author Bergmann Gabor - * - */ -public class EDataTypeInSlotsKey extends BaseEMFTypeKey { - - /** - * @param emfKey - */ - public EDataTypeInSlotsKey(EDataType emfKey) { - super(emfKey); - } - - @Override - public String getPrettyPrintableName() { - return "(Attribute Slot Values: " + ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey) + ")"; - } - - @Override - public String getStringID() { - return "slotValue#" + ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey); - } - - @Override - public int getArity() { - return 1; - } - - @Override - public boolean isEnumerable() { - return true; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EStructuralFeatureInstancesKey.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EStructuralFeatureInstancesKey.java deleted file mode 100644 index 357f5e7e..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/emf/types/EStructuralFeatureInstancesKey.java +++ /dev/null @@ -1,48 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Bergmann Gabor, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.emf.types; - -import org.eclipse.emf.ecore.EStructuralFeature; -import tools.refinery.viatra.runtime.emf.EMFScope; -import tools.refinery.viatra.runtime.emf.helper.ViatraQueryRuntimeHelper; - -/** - * Instance tuples are of form (x, y), where x is an eObject that has y as the value of the given feature (or one of the values in case of multi-valued). - * - *

As of version 1.6, this input key has the strict semantics that x must be within the {@link EMFScope}, scoping is not implied for y. - * @author Bergmann Gabor - * - */ -public class EStructuralFeatureInstancesKey extends BaseEMFTypeKey { - - public EStructuralFeatureInstancesKey(EStructuralFeature emfKey) { - super(emfKey); - } - - @Override - public String getPrettyPrintableName() { - return ViatraQueryRuntimeHelper.prettyPrintEMFType(wrappedKey); - } - - @Override - public String getStringID() { - return "feature#"+ getPrettyPrintableName(); - } - - @Override - public int getArity() { - return 2; - } - - @Override - public boolean isEnumerable() { - return true; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/IQueryGroupProvider.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/IQueryGroupProvider.java deleted file mode 100644 index 45594b5b..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/IQueryGroupProvider.java +++ /dev/null @@ -1,40 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.extensibility; - -import java.util.Set; - -import tools.refinery.viatra.runtime.api.IQueryGroup; -import tools.refinery.viatra.runtime.matchers.util.IProvider; - -/** - * Provider interface for {@link IQueryGroup} instances with added method for - * requesting the set of FQNs for the query specifications in the group. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IQueryGroupProvider extends IProvider { - - /** - * Note that the provider should load the query group class only if the FQNs can not be computed in other ways. - * - * @return the set of query specification FQNs in the group - */ - Set getQuerySpecificationFQNs(); - - /** - * Note that the provider should load the query group class only if the FQNs can not be computed in other ways. - * - * @return a set of providers for query specifications in the group - */ - Set getQuerySpecificationProviders(); - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/IQuerySpecificationProvider.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/IQuerySpecificationProvider.java deleted file mode 100644 index 3c9c235d..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/IQuerySpecificationProvider.java +++ /dev/null @@ -1,36 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.extensibility; - -import tools.refinery.viatra.runtime.api.IQuerySpecification; -import tools.refinery.viatra.runtime.matchers.util.IProvider; - -/** - * Provider interface for {@link IQuerySpecification} instances with added method for - * requesting the FQN for the query specification. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IQuerySpecificationProvider extends IProvider> { - - /** - * Note that the provider will usually not load the query specification class to return the FQN. - * - * @return the fully qualified name of the provided query specification - */ - String getFullyQualifiedName(); - - /** - * Returns the name of project providing the specification (or null if not calculable) - */ - String getSourceProjectName(); - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/PQueryExtensionFactory.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/PQueryExtensionFactory.java deleted file mode 100644 index 91e087d7..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/PQueryExtensionFactory.java +++ /dev/null @@ -1,33 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Zoltan Ujhelyi, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.extensibility; - -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Status; -import tools.refinery.viatra.runtime.api.IQuerySpecification; - -/** - * An extension factory to access PQuery instances from Query Specifications. - * - * @author Zoltan Ujhelyi - * - */ -public class PQueryExtensionFactory extends SingletonExtensionFactory { - - @Override - public Object create() throws CoreException { - final Object _spec = super.create(); - if (_spec instanceof IQuerySpecification) { - return ((IQuerySpecification) _spec).getInternalQueryRepresentation(); - } - throw new CoreException(new Status(IStatus.ERROR, getBundle().getSymbolicName(), "Cannot instantiate PQuery instance.")); - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonExtensionFactory.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonExtensionFactory.java deleted file mode 100644 index 29705968..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonExtensionFactory.java +++ /dev/null @@ -1,62 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2014, Zoltan Ujhelyi, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.extensibility; - -import java.lang.reflect.Method; - -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IConfigurationElement; -import org.eclipse.core.runtime.IExecutableExtension; -import org.eclipse.core.runtime.IExecutableExtensionFactory; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Platform; -import org.eclipse.core.runtime.Status; -import org.osgi.framework.Bundle; - -/** - * Factory to register a static singleton instance in an extension point. - * - * @author Zoltan Ujhelyi - * - */ -public class SingletonExtensionFactory implements IExecutableExtension, IExecutableExtensionFactory { - - private String clazzName; - private Bundle bundle; - - protected Bundle getBundle() { - return bundle; - } - - @Override - public Object create() throws CoreException { - try { - final Class clazz = bundle.loadClass(clazzName); - Method method = clazz.getMethod("instance"); - return method.invoke(null); - } catch (Exception e) { - throw new CoreException(new Status(IStatus.ERROR, bundle.getSymbolicName(), "Error loading group " - + clazzName, e)); - } - } - - @Override - public void setInitializationData(IConfigurationElement config, String propertyName, Object data) - throws CoreException { - String id = config.getContributor().getName(); - bundle = Platform.getBundle(id); - if (data instanceof String) { - clazzName = (String) data; - } else { - throw new CoreException(new Status(IStatus.ERROR, bundle.getSymbolicName(), - "Unsupported extension initialization data: " + data)); - } - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonQueryGroupProvider.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonQueryGroupProvider.java deleted file mode 100644 index 758b51dd..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonQueryGroupProvider.java +++ /dev/null @@ -1,46 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.extensibility; - -import java.util.Set; -import java.util.stream.Collectors; - -import tools.refinery.viatra.runtime.api.IQueryGroup; -import tools.refinery.viatra.runtime.api.IQuerySpecification; -import tools.refinery.viatra.runtime.matchers.util.SingletonInstanceProvider; - -/** - * Provider implementation for storing an existing query group instance. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public class SingletonQueryGroupProvider extends SingletonInstanceProvider implements IQueryGroupProvider { - - /** - * @param instance the instance to wrap - */ - public SingletonQueryGroupProvider(IQueryGroup instance) { - super(instance); - } - - @Override - public Set getQuerySpecificationFQNs() { - return get().getSpecifications().stream().map(IQuerySpecification::getFullyQualifiedName) - .collect(Collectors.toSet()); - } - - @Override - public Set getQuerySpecificationProviders() { - return get().getSpecifications().stream().map(SingletonQuerySpecificationProvider::new) - .collect(Collectors.toSet()); - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonQuerySpecificationProvider.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonQuerySpecificationProvider.java deleted file mode 100644 index f8f3a741..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/SingletonQuerySpecificationProvider.java +++ /dev/null @@ -1,42 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.extensibility; - -import tools.refinery.viatra.runtime.api.IQuerySpecification; -import tools.refinery.viatra.runtime.matchers.util.SingletonInstanceProvider; - -/** - * Provider implementation for storing an existing query specification instance. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public class SingletonQuerySpecificationProvider extends SingletonInstanceProvider> - implements IQuerySpecificationProvider { - - /** - * - * @param instance the instance to wrap - */ - public SingletonQuerySpecificationProvider(IQuerySpecification instance) { - super(instance); - } - - @Override - public String getFullyQualifiedName() { - return get().getFullyQualifiedName(); - } - - @Override - public String getSourceProjectName() { - return null; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/ViatraQueryRuntimeConstants.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/ViatraQueryRuntimeConstants.java deleted file mode 100644 index 9b0850e4..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/extensibility/ViatraQueryRuntimeConstants.java +++ /dev/null @@ -1,27 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Abel Hegedus, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.extensibility; - -/** - * Utility class for Viatra Query runtime constants, such as extension point identifiers. - * - * @author Abel Hegedus - * - */ -public final class ViatraQueryRuntimeConstants { - - private ViatraQueryRuntimeConstants() {/* Constructor hidden for utility class */} - - // Surrogate query extension - - public static final String SURROGATE_QUERY_EXTENSIONID = "tools.refinery.viatra.runtime.surrogatequeryemf"; - - - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/ExtensionBasedSurrogateQueryLoader.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/ExtensionBasedSurrogateQueryLoader.java deleted file mode 100644 index af7cdaf1..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/ExtensionBasedSurrogateQueryLoader.java +++ /dev/null @@ -1,148 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2015, Abel Hegedus, Zoltan Ujhelyi, Istvan Rath and Daniel Varro - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.internal; - -import static tools.refinery.viatra.runtime.matchers.util.Preconditions.checkState; - -import java.util.Arrays; -import java.util.Collection; -import java.util.HashMap; -import java.util.Map; -import java.util.Map.Entry; - -import org.apache.log4j.Logger; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IConfigurationElement; -import org.eclipse.core.runtime.Platform; -import org.eclipse.emf.ecore.EClass; -import org.eclipse.emf.ecore.EClassifier; -import org.eclipse.emf.ecore.EPackage; -import org.eclipse.emf.ecore.EStructuralFeature; -import tools.refinery.viatra.runtime.emf.types.EStructuralFeatureInstancesKey; -import tools.refinery.viatra.runtime.extensibility.ViatraQueryRuntimeConstants; -import tools.refinery.viatra.runtime.matchers.context.IInputKey; -import tools.refinery.viatra.runtime.matchers.context.surrogate.SurrogateQueryRegistry; -import tools.refinery.viatra.runtime.matchers.psystem.queries.PQuery; -import tools.refinery.viatra.runtime.matchers.util.IProvider; - -/** - * @author Abel Hegedus - * - */ -public class ExtensionBasedSurrogateQueryLoader { - - private static final String DUPLICATE_SURROGATE_QUERY = "Duplicate surrogate query definition %s for feature %s of EClass %s in package %s (FQN in map %s, contributing plug-ins %s, plug-in %s)"; - - private Map contributingPluginOfFeatureMap = new HashMap<>(); - private Map contributedSurrogateQueries; - - private static final ExtensionBasedSurrogateQueryLoader INSTANCE = new ExtensionBasedSurrogateQueryLoader(); - - /** - * A provider implementation for PQuery instances based on extension elements. It is expected that the getter will only - * @author Zoltan Ujhelyi - * - */ - private static final class PQueryProvider implements IProvider { - - private final IConfigurationElement element; - private PQuery query; - - public PQueryProvider(IConfigurationElement element) { - this.element = element; - this.query = null; - } - - @Override - public PQuery get() { - try { - if (query == null) { - query = (PQuery) element.createExecutableExtension("surrogate-query"); - } - return query; - } catch (CoreException e) { - throw new IllegalArgumentException("Error initializing surrogate query", e); - } - } - } - - public static ExtensionBasedSurrogateQueryLoader instance() { - return INSTANCE; - } - - public void loadKnownSurrogateQueriesIntoRegistry() { - Map knownSurrogateQueryFQNs = getSurrogateQueryProviders(); - for (Entry entry : knownSurrogateQueryFQNs.entrySet()) { - final IInputKey inputKey = new EStructuralFeatureInstancesKey(entry.getKey()); - SurrogateQueryRegistry.instance().registerSurrogateQueryForFeature(inputKey, entry.getValue()); - } - } - - private Map getSurrogateQueryProviders() { - if(contributedSurrogateQueries != null) { - return contributedSurrogateQueries; - } - contributedSurrogateQueries = new HashMap<>(); - if (Platform.isRunning()) { - for (IConfigurationElement e : Platform.getExtensionRegistry().getConfigurationElementsFor(ViatraQueryRuntimeConstants.SURROGATE_QUERY_EXTENSIONID)) { - if (e.isValid()) { - processExtension(e); - } - } - } - return contributedSurrogateQueries; - } - - private void processExtension(IConfigurationElement el) { - - try { - String packageUri = el.getAttribute("package-nsUri"); - String className = el.getAttribute("class-name"); - String featureName = el.getAttribute("feature-name"); - String queryFqn = el.getAttribute("query-fqn"); - if (queryFqn == null) { - queryFqn = ""; - } - PQueryProvider surrogateQueryProvider = new PQueryProvider(el); - - String contributorName = el.getContributor().getName(); - StringBuilder featureIdBuilder = new StringBuilder(); - checkState(packageUri != null, "Package NsURI cannot be null in extension"); - checkState(className != null, "Class name cannot be null in extension"); - checkState(featureName != null, "Feature name cannot be null in extension"); - - EPackage pckg = EPackage.Registry.INSTANCE.getEPackage(packageUri); - featureIdBuilder.append(packageUri); - checkState(pckg != null, "Package %s not found! (plug-in %s)", packageUri, contributorName); - - EClassifier clsr = pckg.getEClassifier(className); - featureIdBuilder.append("##").append(className); - checkState(clsr instanceof EClass, "EClassifier %s does not exist in package %s! (plug-in %s)", className, packageUri, contributorName); - - EClass cls = (EClass) clsr; - EStructuralFeature feature = cls.getEStructuralFeature(featureName); - featureIdBuilder.append("##").append(featureName); - checkState(feature != null, "Feature %s of EClass %s in package %s not found! (plug-in %s)", featureName, className, packageUri, contributorName); - - PQueryProvider fqnInMap = contributedSurrogateQueries.get(feature); - if(fqnInMap != null) { - String duplicateSurrogateFormatString = DUPLICATE_SURROGATE_QUERY; - Collection contributorPlugins = Arrays.asList(contributorName, contributingPluginOfFeatureMap.get(featureIdBuilder.toString())); - String duplicateSurrogateMessage = String.format(duplicateSurrogateFormatString, queryFqn, featureName, - className, packageUri, fqnInMap, contributorPlugins, contributorName); - throw new IllegalStateException(duplicateSurrogateMessage); - } - contributedSurrogateQueries.put(feature, surrogateQueryProvider); - contributingPluginOfFeatureMap.put(featureIdBuilder.toString(), contributorName); - } catch (Exception e) { - final Logger logger = Logger.getLogger(SurrogateQueryRegistry.class); - logger.error("Surrogate query registration failed", e); - } - } -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/ExtensionBasedSystemDefaultBackendLoader.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/ExtensionBasedSystemDefaultBackendLoader.java deleted file mode 100644 index 4339b70c..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/ExtensionBasedSystemDefaultBackendLoader.java +++ /dev/null @@ -1,60 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2018, Zoltan Ujhelyi, IncQuery Labs - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.internal; - -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IConfigurationElement; -import org.eclipse.core.runtime.Platform; -import tools.refinery.viatra.runtime.api.ViatraQueryEngineOptions; -import tools.refinery.viatra.runtime.matchers.backend.IQueryBackendFactory; -import tools.refinery.viatra.runtime.matchers.backend.IQueryBackendFactoryProvider; -import tools.refinery.viatra.runtime.util.ViatraQueryLoggingUtil; - -/** - * @since 2.0 - */ -public class ExtensionBasedSystemDefaultBackendLoader { - - private static final String EXTENSION_ID = "tools.refinery.viatra.runtime.querybackend"; - private static final ExtensionBasedSystemDefaultBackendLoader INSTANCE = new ExtensionBasedSystemDefaultBackendLoader(); - - public static ExtensionBasedSystemDefaultBackendLoader instance() { - return INSTANCE; - } - - public void loadKnownBackends() { - IQueryBackendFactory defaultBackend = null; - IQueryBackendFactory defaultCachingBackend = null; - IQueryBackendFactory defaultSearchBackend = null; - final IConfigurationElement[] config = Platform.getExtensionRegistry().getConfigurationElementsFor(EXTENSION_ID); - for (IConfigurationElement e : config) { - try { - IQueryBackendFactoryProvider provider = (IQueryBackendFactoryProvider) e - .createExecutableExtension("provider"); - if (provider.isSystemDefaultEngine()) { - defaultBackend = provider.getFactory(); - } - if (provider.isSystemDefaultCachingBackend()) { - defaultCachingBackend = provider.getFactory(); - } - if (provider.isSystemDefaultSearchBackend()) { - defaultSearchBackend = provider.getFactory(); - } - - } catch (CoreException ex) { - // In case errors try to continue with the next one - ViatraQueryLoggingUtil.getLogger(getClass()).error( - String.format("Error while initializing backend %s from plugin %s.", - e.getAttribute("backend"), e.getContributor().getName()), ex); - } - } - ViatraQueryEngineOptions.setSystemDefaultBackends(defaultBackend, defaultCachingBackend, defaultSearchBackend); - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/apiimpl/ViatraQueryEngineImpl.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/apiimpl/ViatraQueryEngineImpl.java index c2341273..a3a9d073 100644 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/apiimpl/ViatraQueryEngineImpl.java +++ b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/internal/apiimpl/ViatraQueryEngineImpl.java @@ -34,9 +34,6 @@ import tools.refinery.viatra.runtime.matchers.util.CollectionsFactory; import tools.refinery.viatra.runtime.matchers.util.CollectionsFactory.MemoryType; import tools.refinery.viatra.runtime.matchers.util.IMultiLookup; import tools.refinery.viatra.runtime.matchers.util.Preconditions; -import tools.refinery.viatra.runtime.registry.IDefaultRegistryView; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistry; -import tools.refinery.viatra.runtime.registry.QuerySpecificationRegistry; import tools.refinery.viatra.runtime.util.ViatraQueryLoggingUtil; import java.lang.ref.WeakReference; @@ -227,17 +224,7 @@ public final class ViatraQueryEngineImpl extends AdvancedViatraQueryEngine @Override public ViatraQueryMatcher getMatcher(String patternFQN) { - IQuerySpecificationRegistry registry = QuerySpecificationRegistry.getInstance(); - IDefaultRegistryView view = registry.getDefaultView(); - IQuerySpecification> querySpecification = view - .getEntry(patternFQN).get(); - if (querySpecification != null) { - return getMatcher(querySpecification); - } else { - throw new ViatraQueryException(String.format( - "No matcher could be constructed for the pattern with FQN %s; if the generated matcher class is not available, please access for the first time using getMatcher(IQuerySpecification)", - patternFQN), "No matcher could be constructed for given pattern FQN."); - } + throw new UnsupportedOperationException("Query specification registry is not available"); } @Override diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/ExtensionBasedQuerySpecificationLoader.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/ExtensionBasedQuerySpecificationLoader.java deleted file mode 100644 index 40bf3e67..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/ExtensionBasedQuerySpecificationLoader.java +++ /dev/null @@ -1,303 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -import java.util.HashMap; -import java.util.HashSet; -import java.util.Map; -import java.util.Objects; -import java.util.Set; - -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IConfigurationElement; -import org.eclipse.core.runtime.Platform; -import tools.refinery.viatra.runtime.IExtensions; -import tools.refinery.viatra.runtime.api.IQueryGroup; -import tools.refinery.viatra.runtime.api.IQuerySpecification; -import tools.refinery.viatra.runtime.extensibility.IQueryGroupProvider; -import tools.refinery.viatra.runtime.extensibility.IQuerySpecificationProvider; -import tools.refinery.viatra.runtime.matchers.util.CollectionsFactory; -import tools.refinery.viatra.runtime.matchers.util.CollectionsFactory.MemoryType; -import tools.refinery.viatra.runtime.matchers.util.IMemoryView; -import tools.refinery.viatra.runtime.matchers.util.IMultiLookup; -import tools.refinery.viatra.runtime.util.ViatraQueryLoggingUtil; - -/** - * Loader for the {@link QuerySpecificationRegistry} based on the query group extensions generated by the VIATRA Query - * builder. The loader has a single instance that processes the extensions on demand if the platform is running, caches - * the results and updates the {@link QuerySpecificationRegistry}. Note that the loader does not perform class loading - * on the query group if possible. - * - *

- * The class has a single instance accessible with {@link #getInstance()}. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public class ExtensionBasedQuerySpecificationLoader { - - public static final String CONNECTOR_ID = "tools.refinery.viatra.runtime.querygroup.extension.based.connector"; - - private static final String DUPLICATE_QUERY_GROUP_MESSAGE = "Duplicate query group identifier %s for plugin %s (already contributed by %s)"; - private static final ExtensionBasedQuerySpecificationLoader INSTANCE = new ExtensionBasedQuerySpecificationLoader(); - - private IMultiLookup contributingPluginOfGroupMap = - CollectionsFactory.createMultiLookup(Object.class, MemoryType.SETS, Object.class); - private Map contributedQueryGroups; - - private ExtensionBasedSourceConnector sourceConnector; - - - /** - * @return the single instance of the loader. - */ - public static ExtensionBasedQuerySpecificationLoader getInstance() { - return INSTANCE; - } - - /** - * Loads the query specifications that are registered through extension points into the - * {@link QuerySpecificationRegistry}. - */ - public void loadRegisteredQuerySpecificationsIntoRegistry() { - ((QuerySpecificationRegistry) QuerySpecificationRegistry.getInstance()).addDelayedSourceConnector(getSourceConnector()); - } - - /** - * Return a source connector that can be used to load query specifications contributed through - * extensions into a {@link IQuerySpecificationRegistry}. - * - * @return the source connector - */ - public IRegistrySourceConnector getSourceConnector() { - if (this.sourceConnector == null) { - this.sourceConnector = new ExtensionBasedSourceConnector(); - } - return sourceConnector; - } - - private Map getRegisteredQueryGroups() { - if(contributedQueryGroups != null) { - return contributedQueryGroups; - } - contributedQueryGroups = new HashMap<>(); - if (Platform.isRunning()) { - for (IConfigurationElement e : Platform.getExtensionRegistry().getConfigurationElementsFor(IExtensions.QUERY_SPECIFICATION_EXTENSION_POINT_ID)) { - if (e.isValid()) { - processExtension(e); - } - } - } - return contributedQueryGroups; - } - - private void processExtension(IConfigurationElement el) { - String id = null; - try { - String contributorName = el.getContributor().getName(); - id = el.getAttribute("id"); - if(id == null) { - throw new IllegalStateException(String.format("Query group extension identifier is required (plug-in: %s)!", contributorName)); - } - - QueryGroupProvider provider = new QueryGroupProvider(el); - - QueryGroupProvider queryGroupInMap = contributedQueryGroups.get(id); - if(queryGroupInMap != null) { - IMemoryView contributorPlugins = contributingPluginOfGroupMap.lookupOrEmpty(id); - throw new IllegalStateException(String.format(DUPLICATE_QUERY_GROUP_MESSAGE, id, contributorName, contributorPlugins.distinctValues())); - } - - contributedQueryGroups.put(id, provider); - contributingPluginOfGroupMap.addPair(id, contributorName); - } catch (Exception e) { - // If there are serious compilation errors in the file loaded by the query registry, an error is thrown - if (id == null) { - id = "undefined in plugin.xml"; - } - ViatraQueryLoggingUtil.getLogger(ExtensionBasedQuerySpecificationLoader.class).error( - "[ExtensionBasedQuerySpecificationLoader] Exception during query specification registry initialization when preparing group: " - + id + "! " + e.getMessage(), e); - } - } - - /** - * @author Abel Hegedus - * - */ - private final class ExtensionBasedSourceConnector implements IRegistrySourceConnector { - - private Set listeners; - - public ExtensionBasedSourceConnector() { - this.listeners = new HashSet<>(); - } - - @Override - public String getIdentifier() { - return ExtensionBasedQuerySpecificationLoader.CONNECTOR_ID; - } - - @Override - public void addListener(IConnectorListener listener) { - Objects.requireNonNull(listener, "Listener must not be null!"); - boolean added = listeners.add(listener); - if(added) { - for (QueryGroupProvider queryGroupProvider : getRegisteredQueryGroups().values()) { - for (IQuerySpecificationProvider specificationProvider : queryGroupProvider.getQuerySpecificationProviders()) { - listener.querySpecificationAdded(this, specificationProvider); - } - } - } - } - - @Override - public void removeListener(IConnectorListener listener) { - Objects.requireNonNull(listener, "Listener must not be null!"); - listeners.remove(listener); - } - - @Override - public boolean includeSpecificationsInDefaultViews() { - return true; - } - } - - /** - * Provider implementation that uses the group extension to load the query group on-demand. - * It also provides the set of query FQNs that are part of the group without class loading. - * Once loaded, the query group is cached for future use. - * - * @author Abel Hegedus - */ - private static final class QueryGroupProvider implements IQueryGroupProvider { - - private static final String DUPLICATE_FQN_MESSAGE = "Duplicate FQN %s in query group extension point (plug-in %s)"; - private final IConfigurationElement element; - private IQueryGroup queryGroup; - private Set querySpecificationFQNs; - private Map querySpecificationMap; - - public QueryGroupProvider(IConfigurationElement element) { - this.element = element; - this.queryGroup = null; - this.querySpecificationFQNs = null; - this.querySpecificationMap = null; - } - - @Override - public IQueryGroup get() { - try{ - if(queryGroup == null) { - queryGroup = (IQueryGroup) element.createExecutableExtension("group"); - } - return queryGroup; - } catch (CoreException e) { - throw new IllegalStateException(e.getMessage(), e); - } - } - - @Override - public Set getQuerySpecificationFQNs() { - if(querySpecificationFQNs == null) { - Set fqns = new HashSet<>(); - for (IConfigurationElement e : element.getChildren("query-specification")) { - if (e.isValid()) { - String fqn = e.getAttribute("fqn"); - boolean added = fqns.add(fqn); - if(!added) { - String contributorName = e.getContributor().getName(); - throw new IllegalArgumentException(String.format(DUPLICATE_FQN_MESSAGE,fqn, contributorName)); - } - } - } - if(fqns.isEmpty()) { - // we must load the class and get the specifications - IQueryGroup loadedQueryGroup = get(); - for (IQuerySpecification specification : loadedQueryGroup.getSpecifications()) { - String fullyQualifiedName = specification.getFullyQualifiedName(); - boolean added = fqns.add(fullyQualifiedName); - if(!added) { - String contributorName = element.getContributor().getName(); - throw new IllegalArgumentException(String.format(DUPLICATE_FQN_MESSAGE, fullyQualifiedName, contributorName)); - } - } - } - // we will never change the set after initialization - querySpecificationFQNs = new HashSet<>(fqns); - } - return querySpecificationFQNs; - } - - @Override - public Set getQuerySpecificationProviders() { - return new HashSet<>(getQuerySpecificationMap().values()); - } - - private Map getQuerySpecificationMap() { - if(querySpecificationMap == null){ - querySpecificationMap = new HashMap<>(); - Set fqns = getQuerySpecificationFQNs(); - for (String fqn : fqns) { - querySpecificationMap.put(fqn, new GroupBasedQuerySpecificationProvider(fqn, this)); - } - } - return querySpecificationMap; - } - - } - - /** - * Provider implementation that uses the query group extension to load a query specification by its FQN. Note that - * the FQN of the provided query specification is set with the constructor and can be requested without loading the - * class. Once loaded, the query specification is cached for future use. - * - * @author Abel Hegedus - * - */ - private static final class GroupBasedQuerySpecificationProvider implements IQuerySpecificationProvider { - - private String queryFQN; - private QueryGroupProvider queryGroupProvider; - private IQuerySpecification specification; - - public GroupBasedQuerySpecificationProvider(String queryFQN, QueryGroupProvider queryGroupProvider) { - this.queryFQN = queryFQN; - this.queryGroupProvider = queryGroupProvider; - this.specification = null; - } - - @Override - public IQuerySpecification get() { - if(specification == null) { - if(queryGroupProvider.getQuerySpecificationFQNs().contains(queryFQN)) { - for (IQuerySpecification spec : queryGroupProvider.get().getSpecifications()) { - if(spec.getFullyQualifiedName().equals(queryFQN)){ - this.specification = spec; - } - } - } else { - throw new IllegalStateException(String.format("Could not find query specifition %s in group (plug-in %s)", queryFQN, queryGroupProvider.element.getContributor().getName())); - } - } - return specification; - } - - @Override - public String getFullyQualifiedName() { - return queryFQN; - } - - @Override - public String getSourceProjectName() { - return queryGroupProvider.element.getContributor().getName(); - } - } -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IConnectorListener.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IConnectorListener.java deleted file mode 100644 index 318415cc..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IConnectorListener.java +++ /dev/null @@ -1,40 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -import tools.refinery.viatra.runtime.extensibility.IQuerySpecificationProvider; - -/** - * Connector listeners are used to receive notifications on addition and removal of query specifications. - * The connector itself is also passed in the methods to allow the usage of the same listener on multiple connectors. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IConnectorListener { - - /** - * Called when a new query specification is added to the given connector. - * The provider interface is used to avoid class loading as long as possible. - * - * @param connector that has a new specification - * @param specificationProvider that wraps the new specification - */ - void querySpecificationAdded(IRegistrySourceConnector connector, IQuerySpecificationProvider specificationProvider); - - /** - * Called when a query specification is removed from the given connector. - * The provider interface is used to avoid class loading as long as possible. - * - * @param connector that has a removed specification - * @param specificationProvider that wraps the removed specification - */ - void querySpecificationRemoved(IRegistrySourceConnector connector, IQuerySpecificationProvider specificationProvider); -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IDefaultRegistryView.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IDefaultRegistryView.java deleted file mode 100644 index 9e3e0394..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IDefaultRegistryView.java +++ /dev/null @@ -1,37 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -import java.util.NoSuchElementException; - -import tools.refinery.viatra.runtime.api.IQueryGroup; - -/** - * The default registry view ensures that the fully qualified name of entries are unique and provides an additional - * method for retrieving the query group of entries for easy initialization. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IDefaultRegistryView extends IRegistryView { - - /** - * @return a query group containing all query specifications - */ - IQueryGroup getQueryGroup(); - - /** - * @param fullyQualifiedName - * of the entry that is requested - * @return the entry with the given FQN - * @throws NoSuchElementException if there is no such entry in the default view - */ - IQuerySpecificationRegistryEntry getEntry(String fullyQualifiedName); -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistry.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistry.java deleted file mode 100644 index 97a17f0e..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistry.java +++ /dev/null @@ -1,74 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -/** - * The query specification registry is used to manage query specifications provided by multiple connectors which can - * dynamically add and remove specifications. Users can read the contents of the registry through views that are also - * dynamically updated when the registry is changed by the connectors. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IQuerySpecificationRegistry { - - /** - * Cannot register connectors with the same identifier twice. No change occurs if the identifier is already used. - * - * @param connector - * cannot be null - * @return false if a connector with the given identifier has already been added, true otherwise - */ - boolean addSource(IRegistrySourceConnector connector); - - /** - * Removes the connector if it was registered. No change occurs if the identifier of the connector was not used - * before. - * - * @param connector - * cannot be null - * @return false if a registered connector with the given identifier was not found, true if it was successfully - * removed - */ - boolean removeSource(IRegistrySourceConnector connector); - - /** - * Returns a default view instance that contains query specification entries that indicate their inclusion in - * default views. If there are entries with the same FQN, only the last added will be included in the view to avoid - * duplicate FQNs. - * - * @return the default view instance - */ - IDefaultRegistryView getDefaultView(); - - /** - * Creates a view which contains query specification entries that indicate their inclusion in default views. This - * view will also be incrementally updated on registry changes and accepts listeners to notify on changes. - * - * @return a new view instance - */ - IRegistryView createView(); - - /** - * Creates a view which contains registered query specifications that are considered relevant by the passed filter. - * This view will also be incrementally updated on registry changes and accepts listeners to notify on changes. - * - * @return a new filtered view instance - */ - IRegistryView createView(IRegistryViewFilter filter); - - /** - * Creates a view which is instantiated by the factory and is connected to the registry. This - * view will also be incrementally updated on registry changes and accepts listeners to notify on changes. - * - * @return a new view instance - */ - IRegistryView createView(IRegistryViewFactory factory); -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistryChangeListener.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistryChangeListener.java deleted file mode 100644 index defdd2ab..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistryChangeListener.java +++ /dev/null @@ -1,35 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -/** - * Listener interface for providing update notifications of views to users. It is used for propagating changes from the - * query specification registry to the views and from the views to users. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IQuerySpecificationRegistryChangeListener { - - /** - * Called when a new entry is added to the registry. - * - * @param entry that is added - */ - void entryAdded(IQuerySpecificationRegistryEntry entry); - - /** - * Called when an existing entry is removed from the registry. - * - * @param entry that is removed - */ - void entryRemoved(IQuerySpecificationRegistryEntry entry); - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistryEntry.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistryEntry.java deleted file mode 100644 index 5009d74b..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IQuerySpecificationRegistryEntry.java +++ /dev/null @@ -1,48 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -import tools.refinery.viatra.runtime.extensibility.IQuerySpecificationProvider; - -/** - * The query specification registry entry interface can return the identifier of the source that added it to the - * registry. It is provider based and can delay class loading of the wrapped {@link IQuerySpecification} until needed. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IQuerySpecificationRegistryEntry extends IQuerySpecificationProvider { - - /** - * @return the identifier of the registry source that contributed the specification - */ - String getSourceIdentifier(); - - /** - * Returns whether the query specification was provided by an identifiable project. - */ - boolean isFromProject(); - - /** - * Collects the name of the project that is registered this specification to the registry. - * If {@link #getSourceIdentifier()} is false, it returns null. - */ - String getSourceProjectName(); - - /** - * @return true if the entry should be included in default views (created without any filters) - */ - boolean includeInDefaultViews(); - - /** - * @return the wrapped {@link IQuerySpecificationProvider} or itself - */ - IQuerySpecificationProvider getProvider(); -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistrySourceConnector.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistrySourceConnector.java deleted file mode 100644 index 94c68d1b..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistrySourceConnector.java +++ /dev/null @@ -1,50 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -/** - * A registry source connector can provide query specifications to listeners (e.g. {@link IQuerySpecificationRegistry}). - * The connector interface does not support direct access to query specifications, instead it sends existing specifications - * to listeners on addition and sends notifications to listeners when a change occurs in the set of specifications. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IRegistrySourceConnector { - - /** - * The connector must return the same identifier every time it is invoked! - * - * @return unique identifier of the connector - */ - String getIdentifier(); - - /** - * - * @return true if the specifications of the connector should be included in default views - */ - boolean includeSpecificationsInDefaultViews(); - - /** - * Add a listener to get updates on changes in the query specifications available from the connector. When the - * listener is added, the connector is expected to call the listener with each existing query specification. - * - * @param listener that should be added - */ - void addListener(IConnectorListener listener); - - /** - * Removes an already registered listener and stops sending updates. The connector is not required to send any - * updates before returning from this method, but should not send any events after this method returns. - * - * @param listener that should be removed - */ - void removeListener(IConnectorListener listener); -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryView.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryView.java deleted file mode 100644 index acf49b76..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryView.java +++ /dev/null @@ -1,72 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -import java.util.Set; - -/** - * The registry view is the primary interface for users to interact with the query specifications in an - * {@link IQuerySpecificationRegistry}. Views are created using the createView methods of registry and their content is - * also dynamically updated by the registry. - * - * The view contains a set of {@link IQuerySpecificationRegistryEntry} objects that can be used to access the query - * specifications themselves through the get() method. - * - * Users can check the contents of the view and add listeners to get notifications on view changes (added or removed - * entries). - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IRegistryView extends IQuerySpecificationRegistryChangeListener { - - /** - * @return an immutable copy of all entries found in the view - */ - Iterable getEntries(); - - /** - * @return the set of FQNs for the query specifications in the view - */ - Set getQuerySpecificationFQNs(); - - /** - * @param fullyQualifiedName - * that is looked up in the view - * @return true if the view contains an entry with given FQN, false otherwise - */ - boolean hasQuerySpecificationFQN(String fullyQualifiedName); - - /** - * @param fullyQualifiedName - * of the entries that are requested - * @return the possible empty set of entries with the given FQN - */ - Set getEntries(String fullyQualifiedName); - - /** - * Adds a listener to the view that will be notified when an entry is added to or removed from the view. - * - * @param listener that is added - */ - void addViewListener(IQuerySpecificationRegistryChangeListener listener); - - /** - * Removes a listener that was previously added to the view. - * - * @param listener that is removed - */ - void removeViewListener(IQuerySpecificationRegistryChangeListener listener); - - /** - * @return the registry underlying the view - */ - IQuerySpecificationRegistry getRegistry(); -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryViewFactory.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryViewFactory.java deleted file mode 100644 index 990902d3..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryViewFactory.java +++ /dev/null @@ -1,34 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -/** - * This interface can be used to ask the registry to construct specific view instances. The factory is responsible for - * instantiating the view, but the registry is responsible for establishing the connection with the internal data store - * and to fill up the view with entries. Instances of the factory are intended to be passed to - * {@link IQuerySpecificationRegistry#createView(IRegistryViewFactory)} and only the view instance returned by that - * method can be considered initialized. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IRegistryViewFactory { - - /** - * Instantiate a new view object and store the reference to the registry. - * This method should only be called by an {@link IQuerySpecificationRegistry}. - * - * @param registry that will be connected to the view - * @return the new instance of the view - * @noreference This method is not intended to be referenced by clients. - */ - IRegistryView createView(IQuerySpecificationRegistry registry); - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryViewFilter.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryViewFilter.java deleted file mode 100644 index fa13327f..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/IRegistryViewFilter.java +++ /dev/null @@ -1,33 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -/** - * The registry view filter can control which entries are added and removed from an {@link IRegistryView}. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public interface IRegistryViewFilter { - - /** - * This method controls whether a registry entry is added to the view or not. The filtering is called before - * checking the uniqueness of fully qualified names, and relevant entries can overwrite existing entries with the - * same FQN. - * - * Note that filters should usually return the same value for the same entry on multiple invocations. - * - * @param entry - * that is checked - * @return true, if the entry is relevant for the view, false otherwise - */ - boolean isEntryRelevant(IQuerySpecificationRegistryEntry entry); - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/QuerySpecificationRegistry.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/QuerySpecificationRegistry.java deleted file mode 100644 index 139dde1c..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/QuerySpecificationRegistry.java +++ /dev/null @@ -1,112 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry; - -import java.util.HashSet; -import java.util.Iterator; -import java.util.Set; - -import tools.refinery.viatra.runtime.registry.impl.QuerySpecificationRegistryImpl; - -/** - * Registry for query specifications that can be accessed using fully qualified names through views. - * Additional query specifications can be added using {@link IRegistrySourceConnector}s. - * - *

- * When running as an OSGi plug-in, the generated query specifications registered through extensions are automatically loaded - * into the registry by the {@link ExtensionBasedQuerySpecificationLoader} class. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public class QuerySpecificationRegistry implements IQuerySpecificationRegistry { - - private static final QuerySpecificationRegistry INSTANCE = new QuerySpecificationRegistry(); - - /** - * @return the singleton query specification registry instance - */ - public static IQuerySpecificationRegistry getInstance() { - return INSTANCE; - } - - private final QuerySpecificationRegistryImpl internalRegistry; - /** - * Connectors that should not be immediately loaded into the registry. - */ - private final Set delayedConnectors; - - /** - * Hidden constructor for singleton instance - */ - protected QuerySpecificationRegistry() { - this.internalRegistry = new QuerySpecificationRegistryImpl(); - this.delayedConnectors = new HashSet<>(); - - } - - /** - * @return the internal registry after adding delayed source connectors - */ - protected IQuerySpecificationRegistry getInternalRegistry() { - if(!delayedConnectors.isEmpty()) { - final Iterator it = delayedConnectors.iterator(); - while (it.hasNext()) { - final IRegistrySourceConnector connector = it.next(); - internalRegistry.addSource(connector); - it.remove(); - } - } - return internalRegistry; - } - - /** - * When the registry adds itself as a listener to connectors, it must send all specification providers - * to the registry. However, when {@link ExtensionBasedQuerySpecificationLoader} is triggered during the - * activation of the plugin, the individual query specification classes cannot be loaded yet. To avoid this, - * the connector of the loader is delayed until needed. - * - * @param connector that should be delayed before adding to the registry - */ - protected void addDelayedSourceConnector(IRegistrySourceConnector connector) { - delayedConnectors.add(connector); - } - - @Override - public boolean addSource(IRegistrySourceConnector connector) { - return getInternalRegistry().addSource(connector); - } - - @Override - public boolean removeSource(IRegistrySourceConnector connector) { - return getInternalRegistry().removeSource(connector); - } - - @Override - public IDefaultRegistryView getDefaultView() { - return getInternalRegistry().getDefaultView(); - } - - @Override - public IRegistryView createView() { - return getInternalRegistry().createView(); - } - - @Override - public IRegistryView createView(IRegistryViewFilter filter) { - return getInternalRegistry().createView(filter); - } - - @Override - public IRegistryView createView(IRegistryViewFactory factory) { - return getInternalRegistry().createView(factory); - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/AbstractRegistrySourceConnector.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/AbstractRegistrySourceConnector.java deleted file mode 100644 index 0e2ef273..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/AbstractRegistrySourceConnector.java +++ /dev/null @@ -1,81 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.connector; - -import java.util.HashSet; -import java.util.Objects; -import java.util.Set; - -import tools.refinery.viatra.runtime.registry.IConnectorListener; -import tools.refinery.viatra.runtime.registry.IRegistrySourceConnector; - -/** - * Abstract registry source connector implementation that stores the identifier and listener set. - * - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public abstract class AbstractRegistrySourceConnector implements IRegistrySourceConnector { - - protected Set listeners; - private String identifier; - private boolean includeInDefaultViews; - - /** - * Creates an instance of the connector with the given identifier. The identifier should be unique if you want to - * add it to a registry as a source. - * - * @param identifier - * of the newly created connector - * @param includeInDefaultViews - * true if the specifications in the connector should be included in default views - */ - public AbstractRegistrySourceConnector(String identifier, boolean includeInDefaultViews) { - super(); - Objects.requireNonNull(identifier, "Identifier must not be null!"); - this.identifier = identifier; - this.includeInDefaultViews = includeInDefaultViews; - this.listeners = new HashSet<>(); - } - - @Override - public String getIdentifier() { - return identifier; - } - - @Override - public boolean includeSpecificationsInDefaultViews() { - return includeInDefaultViews; - } - - @Override - public void addListener(IConnectorListener listener) { - Objects.requireNonNull(listener, "Listener must not be null!"); - boolean added = listeners.add(listener); - if (added) { - sendQuerySpecificationsToListener(listener); - } - } - - @Override - public void removeListener(IConnectorListener listener) { - Objects.requireNonNull(listener, "Listener must not be null!"); - listeners.remove(listener); - } - - /** - * Subclasses should send add notifications for each specification in the connector to the given listener. - * - * @param listener that should receive the notifications - */ - protected abstract void sendQuerySpecificationsToListener(IConnectorListener listener); - -} \ No newline at end of file diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/QueryGroupProviderSourceConnector.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/QueryGroupProviderSourceConnector.java deleted file mode 100644 index e6f0adf0..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/QueryGroupProviderSourceConnector.java +++ /dev/null @@ -1,80 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.connector; - -import java.util.Objects; - -import tools.refinery.viatra.runtime.extensibility.IQueryGroupProvider; -import tools.refinery.viatra.runtime.extensibility.IQuerySpecificationProvider; -import tools.refinery.viatra.runtime.registry.IConnectorListener; - -/** - * Source connector implementation that uses a {@link IQueryGroupProvider} to provide a query specifications into the - * registry. The query group can be later updated which triggers the removal of all specifications of the old group and - * the addition of all specifications from the new group. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public class QueryGroupProviderSourceConnector extends AbstractRegistrySourceConnector { - - IQueryGroupProvider queryGroupProvider; - - /** - * Creates an instance of the connector with the given identifier and the query group provider. The identifier - * should be unique if you want to add it to a registry as a source. - * - * @param identifier - * of the newly created connector - * @param provider - * that contains the query specifications handled by the connector - * @param includeInDefaultViews - * true if the specifications in the connector should be included in default views - */ - public QueryGroupProviderSourceConnector(String identifier, IQueryGroupProvider provider, boolean includeInDefaultViews) { - super(identifier, includeInDefaultViews); - this.queryGroupProvider = provider; - } - - /** - * Update the query group of the connector, which triggers the removal of all specifications on the old group and - * addition of all specifications in the given group. - * - * @param queryGroupProvider - * the queryGroupProvider to set - * @param includeInDefaultViews - * true if the specifications in the connector should be included in default views - */ - public void setQueryGroupProvider(IQueryGroupProvider queryGroupProvider) { - Objects.requireNonNull(queryGroupProvider, "Query group provider must not be null!"); - IQueryGroupProvider oldProvider = this.queryGroupProvider; - - for (IQuerySpecificationProvider specificationProvider : oldProvider.getQuerySpecificationProviders()) { - for (IConnectorListener iConnectorListener : listeners) { - iConnectorListener.querySpecificationRemoved(this, specificationProvider); - } - } - for (IQuerySpecificationProvider specificationProvider : queryGroupProvider.getQuerySpecificationProviders()) { - for (IConnectorListener iConnectorListener : listeners) { - iConnectorListener.querySpecificationAdded(this, specificationProvider); - } - } - - this.queryGroupProvider = queryGroupProvider; - } - - @Override - protected void sendQuerySpecificationsToListener(IConnectorListener listener) { - for (IQuerySpecificationProvider specificationProvider : queryGroupProvider.getQuerySpecificationProviders()) { - listener.querySpecificationAdded(this, specificationProvider); - } - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/SpecificationMapSourceConnector.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/SpecificationMapSourceConnector.java deleted file mode 100644 index e5778950..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/connector/SpecificationMapSourceConnector.java +++ /dev/null @@ -1,147 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.connector; - -import java.util.Collections; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Map; -import java.util.NoSuchElementException; -import java.util.Objects; -import java.util.Set; - -import tools.refinery.viatra.runtime.extensibility.IQuerySpecificationProvider; -import tools.refinery.viatra.runtime.extensibility.SingletonQuerySpecificationProvider; -import tools.refinery.viatra.runtime.registry.IConnectorListener; - -/** - * A simple connector implementation that allows users to simply add and remove specifications. These changes are - * propagated to listeners (e.g. the registry). Note that duplicate FQNs are not allowed in a given connector. - * - * @author Abel Hegedus - * @since 1.3 - * - */ -public class SpecificationMapSourceConnector extends AbstractRegistrySourceConnector { - - private static final String DUPLICATE_MESSAGE = "Duplicate FQN %s cannot be added to connector"; - private Map specificationProviderMap; - - /** - * Creates an instance of the connector with the given identifier. The identifier should be unique if you want to - * add it to a registry as a source. - * - * @param identifier - * of the newly created connector - * @param includeInDefaultViews - * true if the specifications in the connector should be included in default views - */ - public SpecificationMapSourceConnector(String identifier, boolean includeInDefaultViews) { - super(identifier, includeInDefaultViews); - this.specificationProviderMap = new HashMap<>(); - } - - /** - * Creates an instance of the connector with the given identifier and fills it up with the given specification - * providers. The identifier should be unique if you want to add it to a registry as a source. - * - * @param identifier - * of the newly created connector - * @param specificationProviders - * the initial set of specifications in the connector - * @param includeInDefaultViews - * true if the specifications in the connector should be included in default views - */ - public SpecificationMapSourceConnector(String identifier, Set specificationProviders, boolean includeInDefaultViews) { - this(identifier, includeInDefaultViews); - for (IQuerySpecificationProvider provider : specificationProviders) { - addQuerySpecificationProvider(provider); - } - } - - /** - * Creates an instance of the connector with the given identifier and fills it up with the specification providers - * from the given {@link SpecificationMapSourceConnector}. The identifier should be unique if you want to add it to - * a registry as a source. - * - * @param identifier - * of the newly created connector - * @param connector - * that contains the specifications to copy into the new instance - * @param includeInDefaultViews - * true if the specifications in the connector should be included in default views - */ - public SpecificationMapSourceConnector(String identifier, SpecificationMapSourceConnector connector, boolean includeInDefaultViews) { - this(identifier, includeInDefaultViews); - this.specificationProviderMap.putAll(connector.specificationProviderMap); - } - - /** - * Adds a query specification to the connector. - * If you have an {@link IQuerySpecification} object, use {@link SingletonQuerySpecificationProvider}. - * - * @param provider to add to the connector - * @throws IllegalArgumentException if the connector already contains a specification with the same FQN - */ - public void addQuerySpecificationProvider(IQuerySpecificationProvider provider) { - Objects.requireNonNull(provider, "Provider must not be null!"); - String fullyQualifiedName = provider.getFullyQualifiedName(); - if (!specificationProviderMap.containsKey(fullyQualifiedName)) { - specificationProviderMap.put(fullyQualifiedName, provider); - for (IConnectorListener listener : listeners) { - listener.querySpecificationAdded(this, provider); - } - } else { - throw new IllegalArgumentException(String.format(DUPLICATE_MESSAGE, fullyQualifiedName)); - } - } - - /** - * Remove a specification that has been added with the given FQN. - * - * @param fullyQualifiedName - * @throws NoSuchElementException if the connector does not contain a specification with the given FQN - */ - public void removeQuerySpecificationProvider(String fullyQualifiedName) { - Objects.requireNonNull(fullyQualifiedName, "Fully qualified name must not be null!"); - IQuerySpecificationProvider provider = specificationProviderMap.remove(fullyQualifiedName); - if (provider == null) { - throw new NoSuchElementException( - String.format("Connector does not contain specification with FQN %s", fullyQualifiedName)); - } - for (IConnectorListener listener : listeners) { - listener.querySpecificationRemoved(this, provider); - } - } - - /** - * @return the immutable copy of the set of FQNs for the added query specifications - */ - public Set getQuerySpecificationFQNs() { - return Collections.unmodifiableSet(new HashSet<>(specificationProviderMap.keySet())); - } - - /** - * - * @param fullyQualifiedName that is checked - * @return true if a specification with the given FQN exists in the connector, false otherwise - */ - public boolean hasQuerySpecificationFQN(String fullyQualifiedName) { - Objects.requireNonNull(fullyQualifiedName, "FQN must not be null!"); - return specificationProviderMap.containsKey(fullyQualifiedName); - } - - @Override - protected void sendQuerySpecificationsToListener(IConnectorListener listener) { - for (IQuerySpecificationProvider provider : specificationProviderMap.values()) { - listener.querySpecificationAdded(this, provider); - } - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/QuerySpecificationStore.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/QuerySpecificationStore.java deleted file mode 100644 index 649527b6..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/QuerySpecificationStore.java +++ /dev/null @@ -1,38 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.data; - -import java.util.Map; -import java.util.TreeMap; - -/** - * Internal data storage object that represents a query specification registry with a set of sources driven by - * connectors. The sources must have unique identifiers. - * - * @author Abel Hegedus - * - */ -public class QuerySpecificationStore { - - private Map sources; - - /** - * Creates a new instance with an empty identifier to source map. - */ - public QuerySpecificationStore() { - this.sources = new TreeMap<>(); - } - - /** - * @return the live, modifiable identifier to source map - */ - public Map getSources() { - return sources; - } -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/RegistryEntryImpl.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/RegistryEntryImpl.java deleted file mode 100644 index 758885e2..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/RegistryEntryImpl.java +++ /dev/null @@ -1,81 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.data; - -import tools.refinery.viatra.runtime.api.IQuerySpecification; -import tools.refinery.viatra.runtime.extensibility.IQuerySpecificationProvider; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryEntry; - -/** - * Internal data storage object that represents a query specification entry. The entry contains an - * {@link IQuerySpecificationProvider} and has a reference to the source that contains it. - * - * @author Abel Hegedus - * - */ -public class RegistryEntryImpl implements IQuerySpecificationRegistryEntry { - - private IQuerySpecificationProvider provider; - private RegistrySourceImpl source; - - /** - * Creates a new instance with the given source and the given provider. - * - * @param source - * that contains the new entry - * @param provider - * that wraps the specification represented by the entry - */ - public RegistryEntryImpl(RegistrySourceImpl source, IQuerySpecificationProvider provider) { - this.source = source; - this.provider = provider; - } - - /** - * @return the source that contains this entry - */ - public RegistrySourceImpl getSource() { - return source; - } - - @Override - public String getSourceIdentifier() { - return source.getIdentifier(); - } - - @Override - public boolean includeInDefaultViews() { - return getSource().includeEntriesInDefaultViews(); - } - - @Override - public String getFullyQualifiedName() { - return provider.getFullyQualifiedName(); - } - - @Override - public IQuerySpecification get() { - return provider.get(); - } - - @Override - public IQuerySpecificationProvider getProvider() { - return provider; - } - - @Override - public boolean isFromProject() { - return provider.getSourceProjectName() != null; - } - - @Override - public String getSourceProjectName() { - return provider.getSourceProjectName(); - } -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/RegistrySourceImpl.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/RegistrySourceImpl.java deleted file mode 100644 index 83c3b920..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/data/RegistrySourceImpl.java +++ /dev/null @@ -1,73 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.data; - -import java.util.Map; -import java.util.TreeMap; - -/** - * Internal data storage object that represents a query specification source driven by a connector. The source must have - * unique identifier that is copied from the connector. The source uses a FQN to entry map to manage registry entries. - * - * @author Abel Hegedus - * - */ -public class RegistrySourceImpl { - - private String identifier; - private boolean includeInDefaultViews; - private QuerySpecificationStore querySpecificationStore; - private Map fqnToEntryMap; - - /** - * Creates a new source with the given identifier and an empty entry map. - * - * @param identifier - * for the source - * @param querySpecificationStore - * that contains this source - * @param includeInDefaultViews - * true if the entries of the source should be included in default views - */ - public RegistrySourceImpl(String identifier, QuerySpecificationStore querySpecificationStore, boolean includeInDefaultViews) { - this.identifier = identifier; - this.includeInDefaultViews = includeInDefaultViews; - this.querySpecificationStore = querySpecificationStore; - this.fqnToEntryMap = new TreeMap<>(); - } - - /** - * @return the identifier of the source - */ - public String getIdentifier() { - return identifier; - } - - /** - * @return true if the entries in the source should be included in default views - */ - public boolean includeEntriesInDefaultViews() { - return includeInDefaultViews; - } - - /** - * @return the store that contains the source - */ - public QuerySpecificationStore getStore() { - return querySpecificationStore; - } - - /** - * @return the live, modifiable FQN to entry map - */ - public Map getFqnToEntryMap() { - return fqnToEntryMap; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/FilteringRegistryView.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/FilteringRegistryView.java deleted file mode 100644 index 164a30d3..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/FilteringRegistryView.java +++ /dev/null @@ -1,43 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.impl; - -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistry; -import tools.refinery.viatra.runtime.registry.IRegistryViewFilter; -import tools.refinery.viatra.runtime.registry.view.AbstractRegistryView; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryEntry; - -/** - * Registry view implementation that uses a filter to delegate the decision on whether - * a given specification is relevant to the view. - * - * @author Abel Hegedus - * - */ -public class FilteringRegistryView extends AbstractRegistryView { - - private IRegistryViewFilter filter; - - /** - * Creates a new filtering view instance. - * - * @param registry that defines the view - * @param filter that is used for deciding relevancy - */ - public FilteringRegistryView(IQuerySpecificationRegistry registry, IRegistryViewFilter filter, boolean allowDuplicateFQNs) { - super(registry, allowDuplicateFQNs); - this.filter = filter; - } - - @Override - protected boolean isEntryRelevant(IQuerySpecificationRegistryEntry entry) { - return filter.isEntryRelevant(entry); - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/GlobalRegistryView.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/GlobalRegistryView.java deleted file mode 100644 index 75d730b6..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/GlobalRegistryView.java +++ /dev/null @@ -1,65 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.impl; - -import java.util.NoSuchElementException; -import java.util.Set; -import java.util.stream.Collectors; - -import tools.refinery.viatra.runtime.api.IQueryGroup; -import tools.refinery.viatra.runtime.api.LazyLoadingQueryGroup; -import tools.refinery.viatra.runtime.registry.IDefaultRegistryView; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistry; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryEntry; -import tools.refinery.viatra.runtime.registry.view.AbstractRegistryView; - -/** - * Registry view implementation that considers specifications relevant if they are included in default views. - * - * @author Abel Hegedus - * - */ -public class GlobalRegistryView extends AbstractRegistryView implements IDefaultRegistryView { - - /** - * Creates a new instance of the global view. - * - * @param registry that defines the view - */ - public GlobalRegistryView(IQuerySpecificationRegistry registry) { - super(registry, false); - } - - @Override - protected boolean isEntryRelevant(IQuerySpecificationRegistryEntry entry) { - return entry.includeInDefaultViews(); - } - - @Override - public IQueryGroup getQueryGroup() { - Set allQueries = - fqnToEntryMap.distinctValuesStream().collect(Collectors.toSet()); - IQueryGroup queryGroup = LazyLoadingQueryGroup.of(allQueries); - return queryGroup; - } - - @Override - public IQuerySpecificationRegistryEntry getEntry(String fullyQualifiedName) { - Set entries = getEntries(fullyQualifiedName); - if(entries.isEmpty()){ - throw new NoSuchElementException("Cannot find entry with FQN " + fullyQualifiedName); - } - if(entries.size() > 1) { - throw new IllegalStateException("Global view must never contain duplicated FQNs!"); - } - IQuerySpecificationRegistryEntry entry = entries.iterator().next(); - return entry; - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/QuerySpecificationRegistryImpl.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/QuerySpecificationRegistryImpl.java deleted file mode 100644 index 63306e93..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/QuerySpecificationRegistryImpl.java +++ /dev/null @@ -1,177 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.impl; - -import static tools.refinery.viatra.runtime.matchers.util.Preconditions.checkArgument; - -import java.util.Map; - -import org.apache.log4j.Logger; -import tools.refinery.viatra.runtime.extensibility.IQuerySpecificationProvider; -import tools.refinery.viatra.runtime.registry.IConnectorListener; -import tools.refinery.viatra.runtime.registry.IDefaultRegistryView; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistry; -import tools.refinery.viatra.runtime.registry.IRegistryView; -import tools.refinery.viatra.runtime.registry.IRegistryViewFactory; -import tools.refinery.viatra.runtime.registry.IRegistryViewFilter; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryChangeListener; -import tools.refinery.viatra.runtime.registry.IRegistrySourceConnector; -import tools.refinery.viatra.runtime.registry.data.QuerySpecificationStore; -import tools.refinery.viatra.runtime.registry.data.RegistryEntryImpl; -import tools.refinery.viatra.runtime.registry.data.RegistrySourceImpl; -import tools.refinery.viatra.runtime.util.ViatraQueryLoggingUtil; - -/** - * This is the default implementation of the {@link IQuerySpecificationRegistry} interface. - * It uses a {@link QuerySpecificationStore} to keep track of sources and entries. - * It uses a {@link RegistryChangeMultiplexer} to update all views and a single {@link IConnectorListener} - * to subscribe to sources added to the registry. - * - * @author Abel Hegedus - * - */ -public class QuerySpecificationRegistryImpl implements IQuerySpecificationRegistry { - - private static final String CONNECTOR_NULL_MSG = "Connector cannot be null"; - private final QuerySpecificationStore querySpecificationStore; - private final IConnectorListener connectorListener; - private final RegistryChangeMultiplexer multiplexer; - private final Logger logger; - private IDefaultRegistryView defaultView = null; - - /** - * Creates a new instance of the registry - */ - public QuerySpecificationRegistryImpl() { - this.querySpecificationStore = new QuerySpecificationStore(); - this.connectorListener = new RegistryUpdaterConnectorListener(); - this.multiplexer = new RegistryChangeMultiplexer(); - this.logger = ViatraQueryLoggingUtil.getLogger(IQuerySpecificationRegistry.class); - } - - @Override - public boolean addSource(IRegistrySourceConnector connector) { - checkArgument(connector != null, CONNECTOR_NULL_MSG); - String identifier = connector.getIdentifier(); - Map sources = querySpecificationStore.getSources(); - if(sources.containsKey(identifier)){ - return false; - } - RegistrySourceImpl source = new RegistrySourceImpl(identifier, querySpecificationStore, connector.includeSpecificationsInDefaultViews()); - sources.put(identifier, source); - connector.addListener(connectorListener); - logger.debug("Source added: " + source.getIdentifier()); - return true; - } - - @Override - public boolean removeSource(IRegistrySourceConnector connector) { - checkArgument(connector != null, CONNECTOR_NULL_MSG); - String identifier = connector.getIdentifier(); - Map sources = querySpecificationStore.getSources(); - if(!sources.containsKey(identifier)){ - return false; - } - connector.removeListener(connectorListener); - RegistrySourceImpl source = sources.remove(identifier); - for (RegistryEntryImpl entry : source.getFqnToEntryMap().values()) { - multiplexer.entryRemoved(entry); - } - logger.debug("Source removed: " + source.getIdentifier()); - return true; - } - - /** - * @return the internal store of the registry - */ - protected QuerySpecificationStore getStore() { - return querySpecificationStore; - } - - @Override - public IRegistryView createView() { - return createGlobalView(); - } - - private GlobalRegistryView createGlobalView() { - GlobalRegistryView registryView = new GlobalRegistryView(this); - initializeChangeListener(registryView); - return registryView; - } - - protected void initializeChangeListener(IQuerySpecificationRegistryChangeListener listener) { - // send existing entries to aspect - for (RegistrySourceImpl source : querySpecificationStore.getSources().values()) { - Map entryMap = source.getFqnToEntryMap(); - for (RegistryEntryImpl entry : entryMap.values()) { - listener.entryAdded(entry); - } - } - multiplexer.addListener(listener); - } - - @Override - public IRegistryView createView(IRegistryViewFilter filter) { - checkArgument(filter != null, "Filter cannot be null"); - FilteringRegistryView registryView = new FilteringRegistryView(this, filter, false); - initializeChangeListener(registryView); - return registryView; - } - - /** - * Internal connector listener implementation for updating internal store and propagating changes to views. - * - * @author Abel Hegedus - * - */ - private final class RegistryUpdaterConnectorListener implements IConnectorListener { - @Override - public void querySpecificationAdded(IRegistrySourceConnector connector, IQuerySpecificationProvider specification) { - String identifier = connector.getIdentifier(); - RegistrySourceImpl source = querySpecificationStore.getSources().get(identifier); - String fullyQualifiedName = specification.getFullyQualifiedName(); - RegistryEntryImpl registryEntry = new RegistryEntryImpl(source, specification); - RegistryEntryImpl oldEntry = source.getFqnToEntryMap().put(fullyQualifiedName, registryEntry); - if(oldEntry != null) { - logger.warn(String.format("Specification added with existing FQN %s in source %s", fullyQualifiedName, identifier)); - multiplexer.entryRemoved(oldEntry); - } - multiplexer.entryAdded(registryEntry); - - } - - @Override - public void querySpecificationRemoved(IRegistrySourceConnector connector, IQuerySpecificationProvider specification) { - String identifier = connector.getIdentifier(); - RegistrySourceImpl source = querySpecificationStore.getSources().get(identifier); - String fullyQualifiedName = specification.getFullyQualifiedName(); - RegistryEntryImpl registryEntry = source.getFqnToEntryMap().remove(fullyQualifiedName); - if(registryEntry != null) { - multiplexer.entryRemoved(registryEntry); - } - } - } - - @Override - public IDefaultRegistryView getDefaultView() { - if(this.defaultView == null){ - this.defaultView = createGlobalView(); - } - return this.defaultView; - } - - @Override - public IRegistryView createView(IRegistryViewFactory factory) { - IRegistryView registryView = factory.createView(this); - initializeChangeListener(registryView); - return registryView; - } - - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/RegistryChangeMultiplexer.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/RegistryChangeMultiplexer.java deleted file mode 100644 index 450f36b8..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/impl/RegistryChangeMultiplexer.java +++ /dev/null @@ -1,58 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.impl; - -import java.util.Collections; -import java.util.Set; -import java.util.WeakHashMap; - -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryChangeListener; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryEntry; - -/** - * Listener implementation that propagates all changes to a set of listeners. - * The listeners are stored with weak references to avoid a need for disposal. - * - * @author Abel Hegedus - * - */ -public class RegistryChangeMultiplexer implements IQuerySpecificationRegistryChangeListener { - - private Set listeners; - - /** - * Creates a new instance of the multiplexer. - */ - public RegistryChangeMultiplexer() { - this.listeners = Collections.newSetFromMap(new WeakHashMap()); - } - - /** - * Adds a weak reference on the listener to the multiplexer. The listener will receive all further notifications and - * does not have to be removed, since the multiplexer will not keep it in memory when it can be collected. - */ - public boolean addListener(IQuerySpecificationRegistryChangeListener listener) { - return listeners.add(listener); - } - - @Override - public void entryAdded(IQuerySpecificationRegistryEntry entry) { - for (IQuerySpecificationRegistryChangeListener listener : listeners) { - listener.entryAdded(entry); - } - } - - @Override - public void entryRemoved(IQuerySpecificationRegistryEntry entry) { - for (IQuerySpecificationRegistryChangeListener listener : listeners) { - listener.entryRemoved(entry); - } - } - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/view/AbstractRegistryView.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/view/AbstractRegistryView.java deleted file mode 100644 index 7b3c34ba..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/registry/view/AbstractRegistryView.java +++ /dev/null @@ -1,150 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2016, Abel Hegedus, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.registry.view; - -import java.util.Collections; -import java.util.HashSet; -import java.util.Set; -import java.util.stream.Collectors; - -import org.apache.log4j.Logger; -import tools.refinery.viatra.runtime.matchers.util.CollectionsFactory; -import tools.refinery.viatra.runtime.matchers.util.CollectionsFactory.MemoryType; -import tools.refinery.viatra.runtime.matchers.util.IMemoryView; -import tools.refinery.viatra.runtime.matchers.util.IMultiLookup; -import tools.refinery.viatra.runtime.matchers.util.Preconditions; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistry; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryChangeListener; -import tools.refinery.viatra.runtime.registry.IQuerySpecificationRegistryEntry; -import tools.refinery.viatra.runtime.registry.IRegistryView; -import tools.refinery.viatra.runtime.util.ViatraQueryLoggingUtil; - -/** - * An abstract {@link IRegistryView} implementation that stores the registry, the set of listeners added to the view and - * the FQN to entry map of the view itself. The only responsibility of subclasses is to decide whether an entry received - * as an addition or removal notification is relevant to the view. - * - * @author Abel Hegedus - * @since 1.3 - */ -public abstract class AbstractRegistryView implements IRegistryView { - - private static final String LISTENER_EXCEPTION_REMOVE = "Exception occurred while notifying view listener %s about entry removal"; - private static final String LISTENER_EXCEPTION_ADD = "Exception occurred while notifying view listener %s about entry addition"; - protected final IQuerySpecificationRegistry registry; - protected final IMultiLookup fqnToEntryMap; - protected final Set listeners; - protected final boolean allowDuplicateFQNs; - - /** - * This method is called both when an addition or removal notification is received from the registry. Subclasses can - * implement view filtering by returning false for those specifications that are not relevant for this view. - * - * @param entry - * that is added or removed in the registry - * @return true if the entry should be added to or removed from the view, false otherwise - */ - protected abstract boolean isEntryRelevant(IQuerySpecificationRegistryEntry entry); - - /** - * Creates a new view instance for the given registry. Note that views are created by the registry and the view - * update mechanisms are also set up by the registry. - * - * @param registry - */ - public AbstractRegistryView(IQuerySpecificationRegistry registry, boolean allowDuplicateFQNs) { - this.registry = registry; - this.allowDuplicateFQNs = allowDuplicateFQNs; - this.fqnToEntryMap = CollectionsFactory.createMultiLookup(Object.class, MemoryType.SETS, Object.class); - this.listeners = new HashSet<>(); - } - - @Override - public IQuerySpecificationRegistry getRegistry() { - return registry; - } - - @Override - public Iterable getEntries() { - return fqnToEntryMap.distinctValuesStream().collect(Collectors.toSet()); - } - - @Override - public Set getQuerySpecificationFQNs() { - return fqnToEntryMap.distinctKeysStream().collect(Collectors.toSet()); - } - - @Override - public boolean hasQuerySpecificationFQN(String fullyQualifiedName) { - Preconditions.checkArgument(fullyQualifiedName != null, "FQN must not be null!"); - return fqnToEntryMap.lookupExists(fullyQualifiedName); - } - - @Override - public Set getEntries(String fullyQualifiedName) { - Preconditions.checkArgument(fullyQualifiedName != null, "FQN must not be null!"); - IMemoryView entries = fqnToEntryMap.lookupOrEmpty(fullyQualifiedName); - return Collections.unmodifiableSet(entries.distinctValues()); - } - - @Override - public void addViewListener(IQuerySpecificationRegistryChangeListener listener) { - Preconditions.checkArgument(listener != null, "Null listener not supported"); - listeners.add(listener); - } - - @Override - public void removeViewListener(IQuerySpecificationRegistryChangeListener listener) { - Preconditions.checkArgument(listener != null, "Null listener not supported"); - listeners.remove(listener); - } - - @Override - public void entryAdded(IQuerySpecificationRegistryEntry entry) { - if (isEntryRelevant(entry)) { - String fullyQualifiedName = entry.getFullyQualifiedName(); - IMemoryView duplicates = fqnToEntryMap.lookup(fullyQualifiedName); - if(!allowDuplicateFQNs && duplicates != null) { - Set removed = new HashSet<>(duplicates.distinctValues()); - for (IQuerySpecificationRegistryEntry e : removed) { - fqnToEntryMap.removePair(fullyQualifiedName, e); - notifyListeners(e, false); - } - } - fqnToEntryMap.addPair(fullyQualifiedName, entry); - notifyListeners(entry, true); - } - } - - @Override - public void entryRemoved(IQuerySpecificationRegistryEntry entry) { - if (isEntryRelevant(entry)) { - String fullyQualifiedName = entry.getFullyQualifiedName(); - fqnToEntryMap.removePair(fullyQualifiedName, entry); - notifyListeners(entry, false); - } - } - - private void notifyListeners(IQuerySpecificationRegistryEntry entry, boolean addition) { - for (IQuerySpecificationRegistryChangeListener listener : listeners) { - try { - if(addition){ - listener.entryAdded(entry); - } else { - listener.entryRemoved(entry); - } - } catch (Exception ex) { - Logger logger = ViatraQueryLoggingUtil.getLogger(AbstractRegistryView.class); - String formatString = addition ? LISTENER_EXCEPTION_ADD : LISTENER_EXCEPTION_REMOVE; - logger.error(String.format(formatString, listener), ex); - } - } - } - -} \ No newline at end of file diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/EcoreIndexHost.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/EcoreIndexHost.java deleted file mode 100644 index e87a726a..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/EcoreIndexHost.java +++ /dev/null @@ -1,166 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2018, Gabor Bergmann, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ - -package tools.refinery.viatra.runtime.tabular; - -import java.util.Collections; -import java.util.Map; -import java.util.Map.Entry; -import java.util.Set; - -import org.eclipse.emf.ecore.EClass; -import org.eclipse.emf.ecore.EClassifier; -import org.eclipse.emf.ecore.EDataType; -import org.eclipse.emf.ecore.EPackage; -import org.eclipse.emf.ecore.EStructuralFeature; -import org.eclipse.emf.ecore.EcorePackage; -import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.emf.EMFQueryMetaContext; -import tools.refinery.viatra.runtime.emf.EMFScope; -import tools.refinery.viatra.runtime.emf.types.EClassExactInstancesKey; -import tools.refinery.viatra.runtime.emf.types.EClassTransitiveInstancesKey; -import tools.refinery.viatra.runtime.emf.types.EDataTypeInSlotsKey; -import tools.refinery.viatra.runtime.emf.types.EStructuralFeatureInstancesKey; -import tools.refinery.viatra.runtime.matchers.context.IInputKey; -import tools.refinery.viatra.runtime.matchers.scopes.IStorageBackend; -import tools.refinery.viatra.runtime.matchers.scopes.SimpleRuntimeContext; -import tools.refinery.viatra.runtime.matchers.scopes.tables.DisjointUnionTable; -import tools.refinery.viatra.runtime.matchers.scopes.tables.ITableWriterBinary; -import tools.refinery.viatra.runtime.matchers.scopes.tables.ITableWriterUnary; -import tools.refinery.viatra.runtime.matchers.util.CollectionsFactory; - -/** - * Simple EMF-specific demo tabular index host. - * - *

Usage:

    - *
  • First, instantiate index host with given Ecore metamodel packages - *
  • To emulate an EMF instance model, write arbitrary content into the tables using {@link #getTableDirectInstances(EClassifier)} and {@link #getTableFeatureSlots(EStructuralFeature)}. - *
  • Initialize and evaluate regular EMF-based Viatra queries on the scope provided by {@link #getScope()}, as you would on an {@link EMFScope}. - *
      - * - *

      - * EXPERIMENTAL. This class or interface has been added as - * part of a work in progress. There is no guarantee that this API will - * work or that it will remain the same. - * - * @author Gabor Bergmann - * @since 2.1 - */ -public class EcoreIndexHost extends TabularIndexHost { - - public EcoreIndexHost(IStorageBackend storage, EPackage... packages) { - super(storage, new SimpleRuntimeContext(EMFQueryMetaContext.DEFAULT_SURROGATE)); - - initTables(packages); - } - - @Override - protected boolean isQueryScopeEmulated(Class queryScopeClass) { - return EMFScope.class.equals(queryScopeClass); - } - - - private Map> tableDirectInstances = CollectionsFactory.createMap(); - private Map tableTransitiveInstances = CollectionsFactory.createMap(); - private Map> tableFeatures = CollectionsFactory.createMap(); - - private void initTables(EPackage[] packages) { - - // create instance tables first - for (EPackage ePackage : packages) { - for (EClassifier eClassifier : ePackage.getEClassifiers()) { - boolean unique; - IInputKey classifierKey; - if (eClassifier instanceof EClass) { - EClass eClass = (EClass) eClassifier; - - // create transitive instances table - IInputKey transitiveKey = new EClassTransitiveInstancesKey(eClass); - DisjointUnionTable transitiveTable = registerNewTable(new DisjointUnionTable(transitiveKey, runtimeContext)); - tableTransitiveInstances.put(eClass, transitiveTable); - - // process feature tables - for (EStructuralFeature feature : eClass.getEStructuralFeatures()) { - IInputKey featureKey = new EStructuralFeatureInstancesKey(feature); - ITableWriterBinary.Table featureTable = newBinaryInputTable(featureKey, feature.isUnique()); - tableFeatures.put(feature, featureTable); - } - - // direct instance table - unique = true; - classifierKey = new EClassExactInstancesKey(eClass); - } else { // datatype - unique = false; - classifierKey = new EDataTypeInSlotsKey((EDataType) eClassifier); - } - ITableWriterUnary.Table directTable = newUnaryInputTable(classifierKey, unique); - tableDirectInstances.put(eClassifier, directTable); - } - } - - // global implicit supertype EObject is always available as a transitive table - EClass eObjectClass = EcorePackage.eINSTANCE.getEObject(); - DisjointUnionTable eObjectAllInstancesTable = tableTransitiveInstances.get(eObjectClass); - if (eObjectAllInstancesTable == null) { // is it already added? - IInputKey transitiveKey = new EClassTransitiveInstancesKey(eObjectClass); - eObjectAllInstancesTable = registerNewTable(new DisjointUnionTable(transitiveKey, runtimeContext)); - tableTransitiveInstances.put(eObjectClass, eObjectAllInstancesTable); - - boolean unique = true; - IInputKey classifierKey = new EClassExactInstancesKey(eObjectClass); - ITableWriterUnary.Table directTable = newUnaryInputTable(classifierKey, unique); - tableDirectInstances.put(eObjectClass, directTable); - } - - // set up disjoint unoin tables - for (Entry entry : tableTransitiveInstances.entrySet()) { - EClass eClass = entry.getKey(); - ITableWriterUnary.Table directTable = tableDirectInstances.get(eClass); - - // the direct type itself is a child - entry.getValue().addChildTable(directTable); - - // connect supertypes - for (EClass superClass : eClass.getEAllSuperTypes()) { - DisjointUnionTable transitiveTable = tableTransitiveInstances.get(superClass); - if (transitiveTable == null) { - throw new IllegalStateException( - String.format("No index table found for EClass %s, supertype of %s", - superClass.getName(), eClass.getName()) - ); - } - transitiveTable.addChildTable(directTable); - } - // global implicit supertype - if (!eClass.equals(eObjectClass)) { - eObjectAllInstancesTable.addChildTable(directTable); - } - - } - - } - - public ITableWriterUnary.Table getTableDirectInstances(EClassifier classifier) { - return tableDirectInstances.get(classifier); - } - public ITableWriterBinary.Table getTableFeatureSlots(EStructuralFeature feature) { - return tableFeatures.get(feature); - } - - - - public Set>> getAllCurrentTablesDirectInstances() { - return Collections.unmodifiableSet(tableDirectInstances.entrySet()); - } - public Set>> getAllCurrentTablesFeatures() { - return Collections.unmodifiableSet(tableFeatures.entrySet()); - } - - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/TabularEngineContext.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/TabularEngineContext.java deleted file mode 100644 index ee33d3bc..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/TabularEngineContext.java +++ /dev/null @@ -1,107 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2018, Gabor Bergmann, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ - -package tools.refinery.viatra.runtime.tabular; - -import org.apache.log4j.Logger; -import tools.refinery.viatra.runtime.api.ViatraQueryEngine; -import tools.refinery.viatra.runtime.api.scope.*; -import tools.refinery.viatra.runtime.matchers.context.IQueryRuntimeContext; -import tools.refinery.viatra.runtime.matchers.util.CollectionsFactory; - -import java.lang.reflect.InvocationTargetException; -import java.util.List; -import java.util.concurrent.Callable; - -/** - * @author Gabor Bergmann - * - * @since 2.1 - */ -class TabularEngineContext implements IEngineContext, IBaseIndex { - - private TabularIndexHost indexHost; - private ViatraQueryEngine engine; - private Logger logger; - - private List errorListeners = CollectionsFactory.createObserverList(); - - public TabularEngineContext(TabularIndexHost server, ViatraQueryEngine engine, - IIndexingErrorListener errorListener, Logger logger) { - this.indexHost = server; - this.engine = engine; - this.logger = logger; - - this.addIndexingErrorListener(errorListener); - } - - @Override - public IBaseIndex getBaseIndex() { - return this; - } - - @Override - public void dispose() { - // NOP, server lifecycle not controlled by engine - } - - @Override - public IQueryRuntimeContext getQueryRuntimeContext() { - return indexHost.getRuntimeContext(); - } - - @Override - public V coalesceTraversals(Callable callable) throws InvocationTargetException { - try { - return callable.call(); - } catch (Exception e) { - throw new InvocationTargetException(e); - } - } - - @Override - public void addBaseIndexChangeListener(ViatraBaseIndexChangeListener listener) { - // TODO no notifications yet - } - - @Override - public void removeBaseIndexChangeListener(ViatraBaseIndexChangeListener listener) { - // TODO no notifications yet - } - - @Override - public boolean addInstanceObserver(IInstanceObserver observer, Object observedObject) { - // TODO no notifications yet - return true; - } - - @Override - public boolean removeInstanceObserver(IInstanceObserver observer, Object observedObject) { - // TODO no notifications yet - return true; - } - - @Override - public void resampleDerivedFeatures() { - throw new UnsupportedOperationException(); - } - - @Override - public boolean addIndexingErrorListener(IIndexingErrorListener listener) { - return errorListeners.add(listener); - } - - @Override - public boolean removeIndexingErrorListener(IIndexingErrorListener listener) { - return errorListeners.remove(listener); - } - - - -} diff --git a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/TabularIndexHost.java b/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/TabularIndexHost.java deleted file mode 100644 index 6f2a1f5f..00000000 --- a/subprojects/viatra-runtime/src/main/java/tools/refinery/viatra/runtime/tabular/TabularIndexHost.java +++ /dev/null @@ -1,145 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2010-2018, Gabor Bergmann, IncQuery Labs Ltd. - * This program and the accompanying materials are made available under the - * terms of the Eclipse Public License v. 2.0 which is available at - * http://www.eclipse.org/legal/epl-v20.html. - * - * SPDX-License-Identifier: EPL-2.0 - *******************************************************************************/ -package tools.refinery.viatra.runtime.tabular; - -import tools.refinery.viatra.runtime.api.ViatraQueryEngine; -import tools.refinery.viatra.runtime.api.scope.IEngineContext; -import tools.refinery.viatra.runtime.api.scope.IIndexingErrorListener; -import tools.refinery.viatra.runtime.api.scope.QueryScope; -import tools.refinery.viatra.runtime.matchers.context.IInputKey; -import tools.refinery.viatra.runtime.matchers.scopes.IStorageBackend; -import tools.refinery.viatra.runtime.matchers.scopes.TabularRuntimeContext; -import tools.refinery.viatra.runtime.matchers.scopes.tables.IIndexTable; -import tools.refinery.viatra.runtime.matchers.scopes.tables.ITableWriterBinary; -import tools.refinery.viatra.runtime.matchers.scopes.tables.ITableWriterUnary; - -/** - * Simple tabular index host. - * - * Unlike traditional Viatra instances initialized on a model, - * this index host can be initialized and then queried, - * while its queriable "contents" (base relations) can be separately written using table writer API. - * - *

      Deriving classes are responsible for setting up the tables of this index and providing the writer API to clients. - * For the former, use {@link #newUnaryInputTable(IInputKey, boolean)}, - * {@link #newBinaryInputTable(IInputKey, boolean)} to create input tables, - * or {@link #registerNewTable(IIndexTable)} to register manually created derived tables. - * Instantiate such tables with {@link #runtimeContext} as their table context. - * - * - *

      - * EXPERIMENTAL. This class or interface has been added as - * part of a work in progress. There is no guarantee that this API will - * work or that it will remain the same. - * - * @see EcoreIndexHost EcoreIndexHost for EMF-specific example usage. - * - * @author Gabor Bergmann - * @since 2.1 - */ -public abstract class TabularIndexHost { - - private final IStorageBackend storage; - protected final TabularRuntimeContext runtimeContext; - protected final TabularIndexScope scope = new TabularIndexScope(); - - public TabularIndexHost(IStorageBackend storage, TabularRuntimeContext runtimeContext) { - this.storage = storage; - this.runtimeContext = runtimeContext; - } - - - public TabularRuntimeContext getRuntimeContext() { - return runtimeContext; - } - - public TabularIndexScope getScope() { - return scope; - } - - /** - * @return true if this index host aims to serve queries that have a scope of the given type - */ - protected abstract boolean isQueryScopeEmulated(Class queryScopeClass); - - - - /** - * Marks the beginning of an update transaction. - * In transaction mode, index table updates may be temporarily delayed for better performance. - * Stateful query backends will not update their results during the index update transaction. (TODO actually achieve this) - */ - public void startUpdateTransaction() { - storage.startTransaction(); - } - /** - * Marks the end of an update transaction. - * Any updates to index tables that were delayed during the transaction must now be flushed. - * Afterwards, stateful query backends will update their results. (TODO actually achieve this) - */ - public void finishUpdateTransaction() { - storage.finishTransaction(); - } - - /** - * To be called by deriving class. Creates and registers a new unary input table. - */ - protected ITableWriterUnary.Table newUnaryInputTable(IInputKey key, boolean unique) { - return registerNewTable(storage.createUnaryTable(key, runtimeContext, unique)); - } - /** - * To be called by deriving class. Creates and registers a new binary input table. - */ - protected ITableWriterBinary.Table newBinaryInputTable(IInputKey key, boolean unique) { - return registerNewTable(storage.createBinaryTable(key, runtimeContext, unique)); - } - /** - * To be called by deriving class. Registers the given freshly created table and also returns it for convenience. - */ - protected Table registerNewTable(Table newTable) { - runtimeContext.registerIndexTable(newTable); - return newTable; - } - - - /** - * A scope describing queries evaluated against tzhis index host. - * @author Gabor Bergmann - * - */ - public class TabularIndexScope extends QueryScope { - - public TabularIndexHost getIndexHost() { - return TabularIndexHost.this; - } - - @Override - public int hashCode() { - return getIndexHost().hashCode(); - } - - @Override - public boolean equals(Object obj) { - if (obj instanceof TabularIndexScope) - return getIndexHost().equals(((TabularIndexScope) obj).getIndexHost()); - return false; - } - - @Override - public boolean isCompatibleWithQueryScope(Class queryScopeClass) { - return isQueryScopeEmulated(queryScopeClass) || super.isCompatibleWithQueryScope(queryScopeClass); - } - - @Override - protected IEngineContext createEngineContext(ViatraQueryEngine engine, IIndexingErrorListener errorListener, org.apache.log4j.Logger logger) { - return new TabularEngineContext(getIndexHost(), engine, errorListener, logger); - } - - } -} -- cgit v1.2.3-54-g00ecf