diff --git a/docs/io.sarl.docs.markdown/src/main/documentation/gettingstarted/RunSARLAgentJava.md b/docs/io.sarl.docs.markdown/src/main/documentation/gettingstarted/RunSARLAgentJava.md index af00b5e4f2..49fe8bf3c3 100644 --- a/docs/io.sarl.docs.markdown/src/main/documentation/gettingstarted/RunSARLAgentJava.md +++ b/docs/io.sarl.docs.markdown/src/main/documentation/gettingstarted/RunSARLAgentJava.md @@ -21,7 +21,7 @@ application classpath. The SARL API defines a SRE bootstrap as: - [:ShowType:]([:bootstrap]$io.sarl.core.SREBootstrap$) + [:ShowType:]([:bootstrap]$io.sarl.bootstrap.SREBootstrap$) A run-time environment, such as [Janus](http://www.janusproject.io) must provide a service implementing this bootstrap interface. @@ -37,7 +37,7 @@ In the following Java code, the [:sre:] utility type is used for retrieving the [:Success:] package io.sarl.docs.bootstrap - import io.sarl.core.SRE + import io.sarl.bootstrap.SRE class MyProgram { static def main(arguments : String*) { @@ -61,7 +61,7 @@ It is the role of the SARL run-time environment to create this instance for you, [:Success:] package io.sarl.docs.bootstrap - import io.sarl.core.SRE + import io.sarl.bootstrap.SRE agent [:myagent](MyAgent) { } class MyProgram { diff --git a/docs/io.sarl.docs.markdown/src/main/documentation/tutorials/CreateSREWithTinyMAS.md b/docs/io.sarl.docs.markdown/src/main/documentation/tutorials/CreateSREWithTinyMAS.md index 5b86b94b1d..1fbd3f0291 100644 --- a/docs/io.sarl.docs.markdown/src/main/documentation/tutorials/CreateSREWithTinyMAS.md +++ b/docs/io.sarl.docs.markdown/src/main/documentation/tutorials/CreateSREWithTinyMAS.md @@ -3216,7 +3216,7 @@ programmatically without having a specific SRE library into the *compilation cla The [:bootstrapname:] service provides the following functions: - [:ShowType:]([:bootstrapqname]{io.sarl.core.[:bootstrapname]$SREBootstrap$}) + [:ShowType:]([:bootstrapqname]{io.sarl.bootstrap.[:bootstrapname]$SREBootstrap$}) ### Configuration by hand diff --git a/main/apiplugins/io.sarl.core/src/io/sarl/core/bootstrap.sarl b/main/apiplugins/io.sarl.core/src/io/sarl/core/bootstrap.sarl deleted file mode 100644 index 5518c09dca..0000000000 --- a/main/apiplugins/io.sarl.core/src/io/sarl/core/bootstrap.sarl +++ /dev/null @@ -1,221 +0,0 @@ -/* - * $Id$ - * - * SARL is an general-purpose agent programming language. - * More details on http://www.sarl.io - * - * Copyright (C) 2014-2018 the original authors or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package io.sarl.core - -import java.lang.ref.SoftReference -import java.util.ServiceLoader -import java.util.UUID -import io.sarl.lang.core.Agent -import io.sarl.lang.core.AgentContext - -/** - * Represents an access point to the SARL run-time environment (SRE). - * This access point may be used for accessing the underlying SRE independently of its implementation. - * - *

Depending on the implementation of the SRE, an instance of this SRE access point could be injected. - * - * @author $Author: sgalland$ - * @version $FullVersion$ - * @mavengroupid $GroupId$ - * @mavenartifactid $ArtifactId$ - * @since 0.6 - */ -interface SREBootstrap { - - /** - * Start the SRE without an agent. - This function prepare the default context. - * - * @return the context that is created by the bootstrap. If {@code null} there is no context created. - * @since 0.7 - */ - def startWithoutAgent : AgentContext - - /** - * Launch the SRE and the first agent in the kernel. - * - *

The function {@link #getBootAgentIdentifier()} permits to retrieve the identifier of the launched agent. - * - * @param agentCls type of the first agent to launch. - * @param params parameters to pass to the agent as its initialization parameters. - * @return the identifier of the created agent. - * @throws Exception - if it is impossible to start the platform. - * @see #getBootAgentIdentifier() - */ - def startAgent(agentCls : Class, params : Object*) : UUID throws Exception - - /** - * Launch the SRE and the first agent in the kernel. - * - *

The function {@link #getBootAgentIdentifier()} permits to retrieve the identifier of the launched agent. - * - * @param nbAgents the number of agents to be launched. - * @param agentCls type of the first agent to launch. - * @param params parameters to pass to the agent as its initialization parameters. - * @return the identifiers of the created agents. - * @throws Exception - if it is impossible to start the platform. - * @see #getBootAgentIdentifier() - */ - def startAgent(nbAgents : int, agentCls : Class, params : Object*) : Iterable throws Exception - - /** - * Replies the identifier of the boot agent from the system's properties. The boot agent is launched with - * {@link #startAgent(int, Class, Object...)}. - * - * @return the identifier of the boot agent, or null if it is unknown. - * @see #startAgent(int, Class, Object...) - */ - def getBootAgentIdentifier : UUID - - /** Replies if the bootstrap could be used. - * - *

If the bootstrap cannot be used, it cannot launch agent. - * - * @return {@code true} if the bootstrap could be used. {@code false} if it cannot be used. - */ - def isActive : boolean { true } -} - -/** - * Represents an access point to the SARL run-time environment (SRE). - * This access point may be used for accessing the underlying SRE independently of its implementation. - * - *

Depending on the implementation of the SRE, an instance of this SRE access point could be injected. - * - *

For declaring a SRE bootstrap, the library that contains the contributing SRE must declared - * a specific service implementation of {@link SREBootstrap}. The declaration of this service must be - * done by creating a file into the folder {@code META-INF/services/io.sarl.lang.core.SREBootstrap}. - * This file contains a single line that is the fully qualified name of the {@link SREBootstrap}'s implementation. - * - * @author $Author: sgalland$ - * @version $FullVersion$ - * @mavengroupid $GroupId$ - * @mavenartifactid $ArtifactId$ - * @since 0.6 - * @see ServiceLoader - */ -final class SRE { - - static var currentSRE : SREBootstrap - - static var loader : SoftReference> - - private new { - } - - /** Reset the service loader for the SRE bootstrap. - */ - static def resetServiceLoader() : void { - synchronized (typeof(SRE)) { - loader = null - } - } - - /** Replies all the installed SRE into the classpath. - * - * @param onlyInstalledInJRE indicates if the services will be considered only into the libraries that are - * installed into the JRE. If {@code true}, only the libraries into the JRE will be considered and - * the application libraries will be ignored. If {@code false}, the application libraries will be - * considered as well. - * @return the installed SRE. - */ - static def getServiceLoader(onlyInstalledInJRE : boolean = false) : ServiceLoader { - synchronized (typeof(SRE)) { - var sl = if (loader === null) null else loader.get - if (sl === null) { - if (onlyInstalledInJRE) { - sl = ServiceLoader::loadInstalled(typeof(SREBootstrap)) - } else { - sl = ServiceLoader::load(typeof(SREBootstrap)) - } - loader = new SoftReference(sl) - } - return sl - } - } - - /** Change the current SRE. - * - * @param sre the current SRE. - */ - static def setBootstrap(sre : SREBootstrap) : void { - synchronized (typeof(SRE)) { - currentSRE = sre - } - } - - /** Find and reply the current SRE. - * - * @return the current SRE, never {@code null}. - * @throws IllegalStateException if a SRE cannot be found. - */ - static def getBootstrap : SREBootstrap { - synchronized (typeof(SRE)) { - if (currentSRE === null) { - val iterator = getServiceLoader.iterator - if (iterator.hasNext) { - currentSRE = iterator.next - } else { - currentSRE = new VoidSREBootstrap - } - } - return currentSRE - } - } - - /** - * Private API: not documented. - * - * @author $Author: sgalland$ - * @version $FullVersion$ - * @mavengroupid $GroupId$ - * @mavenartifactid $ArtifactId$ - * @since 0.6 - * @ExcludeFromApidoc - */ - private static class VoidSREBootstrap implements SREBootstrap { - - package new { - } - - override startWithoutAgent : AgentContext { - null - } - - override startAgent(agentCls : Class, params : Object*) : UUID { - throw new UnsupportedOperationException - } - - override startAgent(nbAgents : int, agentCls : Class, params : Object*) : Iterable { - throw new UnsupportedOperationException - } - - override getBootAgentIdentifier : UUID { - throw new UnsupportedOperationException - } - - override isActive : boolean { - false - } - - } - -} diff --git a/main/coreplugins/io.sarl.lang.core/META-INF/MANIFEST.MF b/main/coreplugins/io.sarl.lang.core/META-INF/MANIFEST.MF index be639e0472..da05383150 100644 --- a/main/coreplugins/io.sarl.lang.core/META-INF/MANIFEST.MF +++ b/main/coreplugins/io.sarl.lang.core/META-INF/MANIFEST.MF @@ -7,7 +7,8 @@ Bundle-RequiredExecutionEnvironment: JavaSE-1.8 Bundle-Vendor: %Bundle-Vendor Require-Bundle: org.eclipse.xtext.xbase.lib;bundle-version="2.13.0";visibility:=reexport, javax.inject;bundle-version="1.0.0" -Export-Package: io.sarl.lang, +Export-Package: io.sarl.bootstrap, + io.sarl.lang, io.sarl.lang.annotation, io.sarl.lang.core, io.sarl.lang.scoping.batch, diff --git a/main/coreplugins/io.sarl.lang.core/src/io/sarl/bootstrap/SRE.java b/main/coreplugins/io.sarl.lang.core/src/io/sarl/bootstrap/SRE.java new file mode 100644 index 0000000000..643e2feb73 --- /dev/null +++ b/main/coreplugins/io.sarl.lang.core/src/io/sarl/bootstrap/SRE.java @@ -0,0 +1,199 @@ +/* + * $Id$ + * + * SARL is an general-purpose agent programming language. + * More details on http://www.sarl.io + * + * Copyright (C) 2014-2018 the original authors or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package io.sarl.bootstrap; + +import java.lang.ref.SoftReference; +import java.util.Iterator; +import java.util.ServiceLoader; +import java.util.UUID; + +import org.eclipse.xtext.xbase.lib.Inline; +import org.eclipse.xtext.xbase.lib.Pure; + +import io.sarl.lang.core.Agent; +import io.sarl.lang.core.AgentContext; + +/** + * Represents an access point to the SARL run-time environment (SRE). + * This access point may be used for accessing the underlying SRE independently of its implementation. + * + *

Depending on the implementation of the SRE, an instance of this SRE access point could be injected. + * + *

For declaring a SRE bootstrap, the library that contains the contributing SRE must declared + * a specific service implementation of {@link SRE}. The declaration of this service must be + * done by creating a file into the folder {@code META-INF/services/io.sarl.lang.core.SREBootstrap}. + * This file contains a single line that is the fully qualified name of the {@link SRE}'s implementation. + * + * @author $Author: sgalland$ + * @version $FullVersion$ + * @mavengroupid $GroupId$ + * @mavenartifactid $ArtifactId$ + * @since 0.6 + * @see ServiceLoader + */ +public final class SRE { + + private static SREBootstrap currentSRE; + + private static SoftReference> loader; + + private SRE() { + // + } + + /** Reset the service loader for the SRE bootstrap. + */ + public static void resetServiceLoader() { + synchronized (SRE.class) { + loader = null; + } + } + + /** Replies all the installed SRE into the class path. + * + * @return the installed SRE. + */ + @Pure + @Inline("getServiceLoader(false)") + public static ServiceLoader getServiceLoader() { + return getServiceLoader(false); + } + + /** Replies all the installed SRE into the class path. + * + * @param onlyInstalledInJRE indicates if the services will be considered only into the libraries that are + * installed into the JRE. If {@code true}, only the libraries into the JRE will be considered and + * the application libraries will be ignored. If {@code false}, the application libraries will be + * considered as well. + * @return the installed SRE. + */ + @Pure + public static ServiceLoader getServiceLoader(boolean onlyInstalledInJRE) { + synchronized (SRE.class) { + ServiceLoader sl = loader == null ? null : loader.get(); + if (sl == null) { + if (onlyInstalledInJRE) { + sl = ServiceLoader.loadInstalled(SREBootstrap.class); + } else { + sl = ServiceLoader.load(SREBootstrap.class); + } + loader = new SoftReference<>(sl); + } + return sl; + } + } + + /** Change the current SRE. + * + * @param sre the current SRE. + */ + public static void setBootstrap(SREBootstrap sre) { + synchronized (SRE.class) { + currentSRE = sre; + } + } + + /** Launch the SRE from a declared bootstrap within the JRE services. + * This execution entry point does not provide advanced interface, e.g. command line options. + * + * @param args the command-line arguments. The first argument must be the qualified name of the agent to be launched. + * The other values are directly given to the launched agent as initialization parameter. + * @throws Exception in case of error. + * @since 0.7 + */ + @SuppressWarnings("unchecked") + public static void main(String[] args) throws Exception { + final Object[] params = new Object[args.length - 1]; + if (args.length > 1) { + System.arraycopy(args, 1, params, 0, params.length); + } + final Class type = (Class) Class.forName(args[0]); + getBootstrap().startAgent(type, params); + } + + /** Find and reply the current SRE. + * + * @return the current SRE, never {@code null}. + * @throws IllegalStateException if a SRE cannot be found. + */ + @Pure + public static SREBootstrap getBootstrap() { + synchronized (SRE.class) { + if (currentSRE == null) { + final Iterator iterator = getServiceLoader().iterator(); + if (iterator.hasNext()) { + currentSRE = iterator.next(); + } else { + currentSRE = new VoidSREBootstrap(); + } + } + return currentSRE; + } + } + + /** + * Private API: not documented. + * + * @author $Author: sgalland$ + * @version $FullVersion$ + * @mavengroupid $GroupId$ + * @mavenartifactid $ArtifactId$ + * @since 0.6 + * @ExcludeFromApidoc + */ + private static class VoidSREBootstrap implements SREBootstrap { + + /** + * Constructor. + */ + VoidSREBootstrap() { + // + } + + @Override + public AgentContext startWithoutAgent() { + return null; + } + + @Override + public UUID startAgent(Class agentCls, Object... params) { + throw new UnsupportedOperationException(); + } + + @Override + public Iterable startAgent(int nbAgents, Class agentCls, Object... params) { + throw new UnsupportedOperationException(); + } + + @Override + public UUID getBootAgentIdentifier() { + throw new UnsupportedOperationException(); + } + + @Override + public boolean isActive() { + return false; + } + + } + +} diff --git a/main/coreplugins/io.sarl.lang.core/src/io/sarl/bootstrap/SREBootstrap.java b/main/coreplugins/io.sarl.lang.core/src/io/sarl/bootstrap/SREBootstrap.java new file mode 100644 index 0000000000..fd5253bc1d --- /dev/null +++ b/main/coreplugins/io.sarl.lang.core/src/io/sarl/bootstrap/SREBootstrap.java @@ -0,0 +1,98 @@ +/* + * $Id$ + * + * SARL is an general-purpose agent programming language. + * More details on http://www.sarl.io + * + * Copyright (C) 2014-2018 the original authors or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package io.sarl.bootstrap; + +import java.util.UUID; + +import io.sarl.lang.core.Agent; +import io.sarl.lang.core.AgentContext; + +/** + * Represents an access point to the SARL run-time environment (SRE). + * This access point may be used for accessing the underlying SRE independently of its implementation. + * + *

Depending on the implementation of the SRE, an instance of this SRE access point could be injected. + * + * @author $Author: sgalland$ + * @version $FullVersion$ + * @mavengroupid $GroupId$ + * @mavenartifactid $ArtifactId$ + * @since 0.6 + */ +public interface SREBootstrap { + + /** + * Start the SRE without an agent. + This function prepare the default context. + * + * @return the context that is created by the bootstrap. If {@code null} there is no context created. + * @since 0.7 + */ + AgentContext startWithoutAgent(); + + /** + * Launch the SRE and the first agent in the kernel. + * + *

The function {@link #getBootAgentIdentifier()} permits to retrieve the identifier of the launched agent. + * + * @param agentCls type of the first agent to launch. + * @param params parameters to pass to the agent as its initialization parameters. + * @return the identifier of the created agent. + * @throws Exception - if it is impossible to start the platform. + * @see #getBootAgentIdentifier() + */ + UUID startAgent(Class agentCls, Object... params) throws Exception; + + /** + * Launch the SRE and the first agent in the kernel. + * + *

The function {@link #getBootAgentIdentifier()} permits to retrieve the identifier of the launched agent. + * + * @param nbAgents the number of agents to be launched. + * @param agentCls type of the first agent to launch. + * @param params parameters to pass to the agent as its initialization parameters. + * @return the identifiers of the created agents. + * @throws Exception - if it is impossible to start the platform. + * @see #getBootAgentIdentifier() + */ + Iterable startAgent(int nbAgents, Class agentCls, Object... params) throws Exception; + + /** + * Replies the identifier of the boot agent from the system's properties. The boot agent is launched with + * {@link #startAgent(int, Class, Object...)}. + * + * @return the identifier of the boot agent, or null if it is unknown. + * @see #startAgent(int, Class, Object...) + */ + UUID getBootAgentIdentifier(); + + /** Replies if the bootstrap could be used. + * + *

If the bootstrap cannot be used, it cannot launch agent. + * + * @return {@code true} if the bootstrap could be used. {@code false} if it cannot be used. + */ + default boolean isActive() { + return true; + } + +} diff --git a/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/Boot.java b/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/Boot.java index 1bcfa592ae..e702902685 100644 --- a/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/Boot.java +++ b/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/Boot.java @@ -57,8 +57,8 @@ import io.janusproject.services.network.NetworkConfig; import io.janusproject.util.LoggerCreator; -import io.sarl.core.SRE; -import io.sarl.core.SREBootstrap; +import io.sarl.bootstrap.SRE; +import io.sarl.bootstrap.SREBootstrap; import io.sarl.lang.SARLVersion; import io.sarl.lang.core.Agent; diff --git a/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/Bootstrap.java b/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/Bootstrap.java index 55e404303f..7797f08ed3 100644 --- a/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/Bootstrap.java +++ b/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/Bootstrap.java @@ -27,7 +27,7 @@ import io.janusproject.kernel.Kernel; -import io.sarl.core.SREBootstrap; +import io.sarl.bootstrap.SREBootstrap; import io.sarl.lang.core.Agent; import io.sarl.lang.core.AgentContext; diff --git a/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/JanusConfig.java b/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/JanusConfig.java index a1279946b1..5bb1793688 100644 --- a/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/JanusConfig.java +++ b/sre/io.janusproject/io.janusproject.plugin/src/io/janusproject/JanusConfig.java @@ -30,6 +30,7 @@ * Constants for the Janus configuration. * * @author $Author: srodriguez$ + * @author $Author: sgalland$ * @version $FullVersion$ * @mavengroupid $GroupId$ * @mavenartifactid $ArtifactId$ diff --git a/tests/io.sarl.core.tests/src/test/resources/META-INF/services/io.sarl.core.SREBootstrap b/tests/io.sarl.core.tests/src/test/resources/META-INF/services/io.sarl.core.SREBootstrap deleted file mode 100644 index 65dcee6d69..0000000000 --- a/tests/io.sarl.core.tests/src/test/resources/META-INF/services/io.sarl.core.SREBootstrap +++ /dev/null @@ -1 +0,0 @@ -io.sarl.core.tests.SREBootstrapMock diff --git a/tests/io.sarl.core.tests/src/test/java/io/sarl/core/tests/SREBootstrapMock.java b/tests/io.sarl.lang.core.tests/src/test/java/io/sarl/bootstrap/tests/SREBootstrapMock.java similarity index 95% rename from tests/io.sarl.core.tests/src/test/java/io/sarl/core/tests/SREBootstrapMock.java rename to tests/io.sarl.lang.core.tests/src/test/java/io/sarl/bootstrap/tests/SREBootstrapMock.java index e225ed68cf..89d8602e93 100644 --- a/tests/io.sarl.core.tests/src/test/java/io/sarl/core/tests/SREBootstrapMock.java +++ b/tests/io.sarl.lang.core.tests/src/test/java/io/sarl/bootstrap/tests/SREBootstrapMock.java @@ -18,11 +18,11 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package io.sarl.core.tests; +package io.sarl.bootstrap.tests; import java.util.UUID; -import io.sarl.core.SREBootstrap; +import io.sarl.bootstrap.SREBootstrap; import io.sarl.lang.core.Agent; import io.sarl.lang.core.AgentContext; diff --git a/tests/io.sarl.core.tests/src/test/java/io/sarl/core/tests/SRETest.java b/tests/io.sarl.lang.core.tests/src/test/java/io/sarl/bootstrap/tests/SRETest.java similarity index 96% rename from tests/io.sarl.core.tests/src/test/java/io/sarl/core/tests/SRETest.java rename to tests/io.sarl.lang.core.tests/src/test/java/io/sarl/bootstrap/tests/SRETest.java index 6ce0b8d7fb..ab140c5645 100644 --- a/tests/io.sarl.core.tests/src/test/java/io/sarl/core/tests/SRETest.java +++ b/tests/io.sarl.lang.core.tests/src/test/java/io/sarl/bootstrap/tests/SRETest.java @@ -18,7 +18,7 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package io.sarl.core.tests; +package io.sarl.bootstrap.tests; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotNull; @@ -33,8 +33,8 @@ import org.junit.Before; import org.junit.Test; -import io.sarl.core.SRE; -import io.sarl.core.SREBootstrap; +import io.sarl.bootstrap.SRE; +import io.sarl.bootstrap.SREBootstrap; import io.sarl.lang.core.Agent; import io.sarl.tests.api.AbstractSarlTest; diff --git a/tests/io.sarl.lang.core.tests/src/test/resources/META-INF/services/io.sarl.bootstrap.SREBootstrap b/tests/io.sarl.lang.core.tests/src/test/resources/META-INF/services/io.sarl.bootstrap.SREBootstrap new file mode 100644 index 0000000000..3835cac5d0 --- /dev/null +++ b/tests/io.sarl.lang.core.tests/src/test/resources/META-INF/services/io.sarl.bootstrap.SREBootstrap @@ -0,0 +1 @@ +io.sarl.bootstrap.tests.SREBootstrapMock