websocket-spec
  1. websocket-spec
  2. WEBSOCKET_SPEC-98

Consider a property bag on EndpointConfiguration instead of subclassing for shared application state

    Details

    • Type: New Feature New Feature
    • Status: Resolved
    • Priority: Major Major
    • Resolution: Fixed
    • Affects Version/s: None
    • Fix Version/s: None
    • Labels:
      None

      Description

      As a simpler way to allow all instances of an endpoint to share some global state, use a property bag (EndpointConfiguration.get/setProperty(..)) instead of having to subclass EndpointConfiguration to do it. Avoids an extra developer class for the case where you just have object you want to share, rather than some other initialization code.

        Activity

        Hide
        dannycoward added a comment -

        We still need to be able to allow developer to attach arbitrary execution code to endpoint configs, but for sharing use data, the new config apis have included this.

        Show
        dannycoward added a comment - We still need to be able to allow developer to attach arbitrary execution code to endpoint configs, but for sharing use data, the new config apis have included this.
        Hide
        Pavel Bucek added a comment - - edited

        I'm using DefaultClientEndpointConfiguration class from tyrus (implements ClientEndpointConfiguration), which provides simple impl for all ClientEndpointConfiguration class; things would be even more messy if I wouldn't do that).

        Current state:

            public static void current() throws URISyntaxException, DeploymentException {
        
                MyClientEndpointConfiguration cec = new MyClientEndpointConfiguration();
                cec.getProperties().put("MyKey", "MyValue");
        
                final WebSocketContainer client = ClientManager.createClient();
                client.connectToServer(MyEndpointCurrent.class, cec, new URI("ws://myUri"));
            }
        
            public static class MyEndpointCurrent extends Endpoint {
                @Override
                public void onOpen(Session session, EndpointConfiguration config) {
                    if (config instanceof MyClientEndpointConfiguration) {
                        MyClientEndpointConfiguration cec = (MyClientEndpointConfiguration) config;
        
                        // voilà!
                        final Object myProperty = cec.getProperties().get("MyKey");
                    }
                }
            }
        
            public static class MyClientEndpointConfiguration extends DefaultClientEndpointConfiguration implements ClientEndpointConfiguration {
                private final Map<String, Object> properties = new HashMap<String, Object>();
        
                public MyClientEndpointConfiguration() {
                    super(Collections.<Encoder>emptyList(), Collections.<Decoder>emptyList(), Collections.<String>emptyList(), Collections.<Extension>emptyList());
                }
        
                public Map<String, Object> getProperties() {
                    return properties;
                }
            }

        What might be more convenient for users:

            public static void wanna() throws URISyntaxException, DeploymentException {
        
                ClientEndpointConfiguration cec = new DefaultClientEndpointConfiguration.Builder().property("MyKey", "MyValue").build();
        
                final WebSocketContainer client = ClientManager.createClient();
                client.connectToServer(MyEndpointWanna.class, cec, new URI("ws://myUri"));
            }
        
            public static class MyEndpointWanna extends Endpoint {
                @Override
                public void onOpen(Session session, EndpointConfiguration config) {
        
                    // voilà!
                    final Object myProperty = config.getProperties().get("MyKey");
                }
            }

        Last but not least - there is no way how can I utilize this in annotated endpoint case; this might be considered as another issue (please let me know, I can file it):

            public static void annotated() {
                MyClientEndpointConfiguration cec = new MyClientEndpointConfiguration();
                cec.getProperties().put("MyKey", "MyValue");
        
                final WebSocketContainer client = ClientManager.createClient();
                
                // ?? where should I put my ClientEndpointConfiguration instance?
                client.connectToServer(MyEndpoint.class, new URI("ws://myUri"));
            }
            
            @WebSocketClient
            public static class MyEndpoint {
                
                @WebSocketOpen
                public void onOpen(Session session, EndpointConfiguration config) {
                    // ???
                }
            }
        Show
        Pavel Bucek added a comment - - edited I'm using DefaultClientEndpointConfiguration class from tyrus (implements ClientEndpointConfiguration), which provides simple impl for all ClientEndpointConfiguration class; things would be even more messy if I wouldn't do that). Current state: public static void current() throws URISyntaxException, DeploymentException { MyClientEndpointConfiguration cec = new MyClientEndpointConfiguration(); cec.getProperties().put( "MyKey" , "MyValue" ); final WebSocketContainer client = ClientManager.createClient(); client.connectToServer(MyEndpointCurrent.class, cec, new URI( "ws: //myUri" )); } public static class MyEndpointCurrent extends Endpoint { @Override public void onOpen(Session session, EndpointConfiguration config) { if (config instanceof MyClientEndpointConfiguration) { MyClientEndpointConfiguration cec = (MyClientEndpointConfiguration) config; // voilà! final Object myProperty = cec.getProperties().get( "MyKey" ); } } } public static class MyClientEndpointConfiguration extends DefaultClientEndpointConfiguration implements ClientEndpointConfiguration { private final Map< String , Object > properties = new HashMap< String , Object >(); public MyClientEndpointConfiguration() { super (Collections.<Encoder>emptyList(), Collections.<Decoder>emptyList(), Collections.< String >emptyList(), Collections.<Extension>emptyList()); } public Map< String , Object > getProperties() { return properties; } } What might be more convenient for users: public static void wanna() throws URISyntaxException, DeploymentException { ClientEndpointConfiguration cec = new DefaultClientEndpointConfiguration.Builder().property( "MyKey" , "MyValue" ).build(); final WebSocketContainer client = ClientManager.createClient(); client.connectToServer(MyEndpointWanna.class, cec, new URI( "ws: //myUri" )); } public static class MyEndpointWanna extends Endpoint { @Override public void onOpen(Session session, EndpointConfiguration config) { // voilà! final Object myProperty = config.getProperties().get( "MyKey" ); } } Last but not least - there is no way how can I utilize this in annotated endpoint case; this might be considered as another issue (please let me know, I can file it): public static void annotated() { MyClientEndpointConfiguration cec = new MyClientEndpointConfiguration(); cec.getProperties().put( "MyKey" , "MyValue" ); final WebSocketContainer client = ClientManager.createClient(); // ?? where should I put my ClientEndpointConfiguration instance? client.connectToServer(MyEndpoint.class, new URI( "ws: //myUri" )); } @WebSocketClient public static class MyEndpoint { @WebSocketOpen public void onOpen(Session session, EndpointConfiguration config) { // ??? } }

          People

          • Assignee:
            dannycoward
            Reporter:
            dannycoward
          • Votes:
            0 Vote for this issue
            Watchers:
            0 Start watching this issue

            Dates

            • Due:
              Created:
              Updated:
              Resolved: