Some Eclipse Foundation services are deprecated, or will be soon. Please ensure you've read this important communication.

Bug 347198

Summary: Support URI syntax to auto select port...e.g. ecftcp://localhost:0/server
Product: [RT] ECF Reporter: Alex Blewitt <alex.blewitt>
Component: ecf.serverAssignee: ecf.core-inbox <ecf.core-inbox>
Status: NEW --- QA Contact:
Severity: enhancement    
Priority: P3 CC: bugs.eclipse.org, slewis
Version: unspecified   
Target Milestone: ---   
Hardware: All   
OS: All   
Whiteboard:

Description Alex Blewitt CLA 2011-05-25 13:30:28 EDT
Build Identifier: Eclipse 3.6.2

The generic ECF server picks a specific port, which prevents running multiple clients/services easily on the same machine. However, it is possible to specify a 'don't care' port to the ServerSocket when created by using 0 as a port number.

Unfortunately the server string is used as-is for other purposes (e.g. remote service discovery) so you end up with a reference to ecftcp://localhost:0, which of course can't be connected to.

The URL should instead replace the port value (if it is :0 anyway) with serverSocket.getLocalPort(), which will be the one chosen.

new ServerSocket(80).getLocalPort() == 80
new ServerSocket(0).getLocalPort() == 12345?

Reproducible: Always

Steps to Reproduce:
Run one of the ECF examples with the following:

-containerType ecf.generic.server -containerId ecftcp://localhost:0/server

As you can see from the logs, the server is created. However, when publishing you see the same URL being used:

serviceReference={org.eclipse.ecf.examples.remoteservices.hello.IHello}={org.eclipse.ecf.containerFactoryArgs=ecftcp://localhost:0/server,...}
Comment 1 Scott Lewis CLA 2011-05-25 13:47:29 EDT
The generic server creation/instantiation can/will automatically select an available port...if the following system property is set to 'true':

org.eclipse.ecf.provider.generic.port.fallback

e.g.

eclipse -vmargs -Dorg.eclipse.ecf.provider.generic.port.fallback=true

This assumes, however, that the org.eclipse.ecf.containerFactoryArgs is not set at all.  If it is set to something (as in the examples), then the port specified is what is used.  

In addition/with this bug, it may be a good idea for this bug to simply add support for ecftcp://localhost:0/server...i.e. to do the same thing as the port.fallback (select an available port).
Comment 2 Markus Kuppe CLA 2011-05-25 13:50:19 EDT
Would org.eclipse.ecf.provider.generic.TCPServerSOContainer.DEFAULT_FALLBACK_PORT  do the job too?
Comment 3 Alex Blewitt CLA 2011-05-26 05:53:49 EDT
I think it's useful to be able to select the server type but not be constrained by the port. For example, you can't run two of the 'hello hosts' in the examples because they'll share the same port registry. And given that the launch arguments are used to select the container type (which I'm guessing sets the port under the covers) then you can't run it twice.

Ideally you could run:

ecftcp://localhost

and then have it assume :0 and use any available port (e.g effectively using the fallback parameter set to true). However, you'd still need to be able to adjust the ID such that it advertises the actual port used.
Comment 4 Scott Lewis CLA 2011-05-26 13:02:50 EDT
(In reply to comment #3)
> I think it's useful to be able to select the server type but not be constrained
> by the port. For example, you can't run two of the 'hello hosts' in the
> examples because they'll share the same port registry. And given that the
> launch arguments are used to select the container type (which I'm guessing sets
> the port under the covers) then you can't run it twice.

You can determine the container type without setting the port (i.e. using the system property to have the port autoset itself).  The way to do this is to set a standard OSGi remote services property:

props.put("service.exported.configs","ecf.generic.server");

for the remote service registration and *not* set the containerFactoryArgs service property.

The "service.exported.configs" is one of the OSGi remote service standard properties, that define the type/provider for remote service export.  We associate it with an ECF container type.

The examples don't use this...only because parts of them predate the OSGi spec.

One other thing:  For extensibility, the ECF impl of RSA defines a service called org.eclipse.ecf.osgi.services.remoteserviceadmin.IHostContainerSelector...which during the RSA.exportService call is responsible for *selecting or creating* the host container that is used to export a remote service.  If you need to, it's easy to register your own impl of IHostContainerSelector (extending HostContainerSelector and/or AbstractHostContainerSelector) to modify the runtime behavior of the ECF container selection/creation.  Just registering your own implementation will override the default one (which is in class HostContainerSelector).

Anyway...all this is meant to allow people to customize the runtime behavior of the ECF container selection (and/or creation/initialization)...so that they can have full control over that process.  It's not required or expected that people will need to use it for the use case you describe in this bug, but I just wanted to make it's availability known to you.

> 
> Ideally you could run:
> 
> ecftcp://localhost
> 
> and then have it assume :0 and use any available port (e.g effectively using
> the fallback parameter set to true). However, you'd still need to be able to
> adjust the ID such that it advertises the actual port used.

I don't disagree with you that it might be useful to allow/support (e.g.)

ecftcp://localhost:0/server

to also auto select the port...and perhaps other autoselect as well (e.g. autoselect the hostname also).  If that's what this bug should turn into then I'm all for that...although it might be good to change this bug an enhancement.  I'll let you decide whether that's what you want this bug to turn into...or open another bug.

For your information Al...the code that creates the generic server container instance...and therefore interprets the String passed in is in this class:

org.eclipse.ecf.provider.generic.GenericContainerInstantiator.createInstance
Comment 5 Scott Lewis CLA 2011-08-09 00:25:46 EDT
As suggested in comment 4, turning this into an enhancement and changing bug title appropriately.