Jetty + Jersey 2 + Swagger programmatic configuration without web.xml

4,436 views
Skip to first unread message

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 12:06:22 PM4/15/14
to swagger-sw...@googlegroups.com
Hi all,

I'm trying to configure Swagger in an embedded application that exposes a REST API with jersey 2 and jetty without using web.xml file and I have some problems with the Swagger configuration. I'm using these versions of the different technologies:

jetty v9.1.3
jax-rs -> jersey v.2.5
swagger v1.3.4

The main steps for configuring the servlets for jetty look like this:

Server server = new Server();
...
final ServletContextHandler restApi = setupRestApiContextHandler(serviceConfig);
final ServletContextHandler swagger = setupSwaggerContextHandler(serviceConfig.getServerPort());

ContextHandlerCollection contextHandlers = new ContextHandlerCollection();
contextHandlers.setHandlers(new Handler[] { restApi, swagger });
server.setHandler(contextHandlers);
...
server.start();

The setup for both my restful resources and swagger is as follows:

    private static ServletContextHandler setupRestApiContextHandler(ContentServiceConfiguration serviceConfig) {
        ResourceConfig resourceConfig = new ResourceConfig();
        resourceConfig.register(new FacadeBinder(serviceConfig));
        resourceConfig.register(JacksonFeature.class);
        resourceConfig.packages("my.package.containg.resources", "com.wordnik.swagger.jaxrs.listing");

        ServletContainer servletContainer = new ServletContainer(resourceConfig);

        ServletHolder jerseyServletHolder = new ServletHolder(servletContainer);
        jerseyServletHolder.setInitOrder(1);
        jerseyServletHolder.setInitParameter("jersey.config.server.tracing", "ALL");

        final ServletContextHandler jerseyContextHandler = new ServletContextHandler();
        jerseyContextHandler.setSessionHandler(new SessionHandler());
        jerseyContextHandler.setContextPath("/v1");
        jerseyContextHandler.addServlet(jerseyServletHolder, "/*");
        return jerseyContextHandler;
    }

    private static ServletContextHandler setupSwaggerContextHandler() {
        // Configure Swagger-core
        final ServletHolder swaggerServletHolder = new ServletHolder(new JerseyJaxrsConfig());
        swaggerServletHolder.setName("JerseyJaxrsConfig");
        swaggerServletHolder.setInitParameter("api.version", "1.0.0");
        swaggerServletHolder.setInitParameter("swagger.api.basepath", "http://localhost:4080/api");
        swaggerServletHolder.setInitOrder(2);

        final ServletContextHandler swaggerContextHandler = new ServletContextHandler();
        swaggerContextHandler.setSessionHandler(new SessionHandler());
        // Bind Swagger-core to the url HOST/api-docs
        swaggerContextHandler.setContextPath("/api-docs");
        swaggerContextHandler.addServlet(swaggerServletHolder, "/*");

        return swaggerContextHandler;
    }

When I start jetty, I can access the resources of my app under "/v1" and I can make HTTP requests (e.g. GET http://localhost:4080/v1/myResource1.
However, I can't access the Swagger documentation under "/api-docs" (e.g. curl http://localhost:4080/api-docs returns an empty response.) As far as I've read, I should retrieve something like this:
{"apiVersion":"1.0.0","swaggerVersion":"1.2","apis":[{"path":"/myResource1","description":"bla, bla}],"info":{"title":"My RESTful API","description":"My RESTful resources"}}
I've also tried to access http://localhost:4080/api & http://localhost:4080/api/api-docs but I get a 404 not found message.

I tried to follow and adapt the examples for jersey 2 and jaxrs in github trying different ways of configuring swagger without any success (e.g. trying to deploy another servlet with the Bootstrap configuration that appears in those examples, trying to use the BeanConfig that I found in other examples...)

What am I doing wrong? Could you please provide/point to an example/guidelines on how to configure programmatically Swagger without web.xml and get the servlet providing the API documentation through a browser up and running? Any help on this would be appreciated!

Thanks in advance, 

Francisco

Ron

unread,
Apr 15, 2014, 1:05:38 PM4/15/14
to swagger-sw...@googlegroups.com
Francisco,

I believe the simplest solution to initialize Swagger without a web.xml is to add the following Filter class to your code -

@WebListener
public class SwaggerInitializer implements ServletContextListener {

    public void contextInitialized(ServletContextEvent servletContextEvent) {
        BeanConfig beanConfig = new BeanConfig();
        beanConfig.setVersion( "1.0.2" );
        beanConfig.setResourcePackage( "com.company.swagger.domain.rest" ); // replace with your packages
        beanConfig.setBasePath( "http://localhost:8080/myApp/resources/" );
        beanConfig.setDescription( "My RESTful resources" );
        beanConfig.setTitle( "My RESTful API" );
        beanConfig.setScan( true );
    }

    public void contextDestroyed(ServletContextEvent servletContextEvent) {
    }
   
}

Can you please try it and let me know if it works?
Make sure to change the values of the configuration to your requirements (and remove the code you previously added to try and configure swagger).


--
You received this message because you are subscribed to the Google Groups "Swagger" group.
To unsubscribe from this group and stop receiving emails from it, send an email to swagger-swaggers...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 2:15:04 PM4/15/14
to swagger-sw...@googlegroups.com
Thanks for your quick response Ron!

I already tried that also. I defined the servlet context listener as you said:

@WebListener
public class SwaggerInitializer implements ServletContextListener {

    private static final String RESOURCES_PKG = "com.myapp.jaxrs.resource";

    public void contextInitialized(ServletContextEvent servletContextEvent) {
        BeanConfig beanConfig = new BeanConfig();
        beanConfig.setVersion("1.0.2");
        beanConfig.setResourcePackage(CONTENT_RESOURCES_PKG); // replace with your packages
        beanConfig.setBasePath("http://localhost:4080/api");
        beanConfig.setDescription("My RESTful resources");
        beanConfig.setTitle("My RESTful API");
        beanConfig.setScan(true);
    }

    public void contextDestroyed(ServletContextEvent servletContextEvent) {
    }

}

and then I tried to add it to the servlet context of the servlet context handler of my rest api (I removed the other context handler I had before for Swagger):

...
        final ServletContextHandler restApi = setupRestApiContextHandler(serviceConfig);
        restApi.getServletContext().addListener(new SwaggerInitializer());

        ContextHandlerCollection contextHandlers = new ContextHandlerCollection();
        contextHandlers.setHandlers(new Handler[] { restApi }); // Put required handlers in here

        server.setHandler(contextHandlers);
...

However, I get this exception:

Caused by: java.lang.IllegalStateException
at org.eclipse.jetty.servlet.ServletContextHandler$Context.addListener(ServletContextHandler.java:1291)
at com.yahoo.edentity.content.jetty.component.ContentServiceComponent.initJettyServer(ContentServiceComponent.java:108)
at com.yahoo.edentity.content.jetty.component.ContentServiceComponent.<init>(ContentServiceComponent.java:68)
at com.yahoo.edentity.content.jetty.ContentService.initJettyBasedRestApi(ContentService.java:77)
at com.yahoo.edentity.content.jetty.ContentService.main(ContentService.java:60)
... 6 more

Am I adding the SwaggerInitializer listener in the right place?

Thanks again!

Francisco
To unsubscribe from this group and stop receiving emails from it, send an email to swagger-swaggersocket+unsub...@googlegroups.com.

Ron

unread,
Apr 15, 2014, 2:20:04 PM4/15/14
to swagger-sw...@googlegroups.com
You shouldn't need to explicitly add the listener, the @WebListener annotation should be enough. Can you try it? 


To unsubscribe from this group and stop receiving emails from it, send an email to swagger-swaggers...@googlegroups.com.

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 3:37:24 PM4/15/14
to swagger-sw...@googlegroups.com
Hi Ron,

I've removed the .addListener() call and I've checked the output with curl http://localhost:4080/api but nothing happens. I've added a log message in the SwaggerInitializer but it does not appear, so I guess that the wiring for injecting the @WebListener is not working.

Francisco
To unsubscribe from this group and stop receiving emails from it, send an email to swagger-swaggersocket+unsubscri...@googlegroups.com.

For more options, visit https://groups.google.com/d/optout.

tony tam

unread,
Apr 15, 2014, 3:40:53 PM4/15/14
to swagger-sw...@googlegroups.com
It looks like you're binding to /v1 in your context path.  If that's true, swagger should be available on /v1/api-docs

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 3:48:54 PM4/15/14
to swagger-sw...@googlegroups.com
Thanks Tony,

Now I get the following response with curl http://localhost:4080/v1/api-docs

{"apiVersion":"0.0","swaggerVersion":"1.2"}

tony tam

unread,
Apr 15, 2014, 3:52:10 PM4/15/14
to swagger-sw...@googlegroups.com
Great, we're closer.  Now it appears your swagger scanner is not picking up the classes.  What you need to do is configure a scanner like Ron said:

// in your setupSwaggerContextHandler()
BeanConfig beanConfig = new BeanConfig();
beanConfig.setVersion( "1.0.2" );
beanConfig.setResourcePackage( "com.company.swagger.domain.rest" ); // replace with your packages
beanConfig.setBasePath( "http://localhost:8080/myApp/resources/" );
beanConfig.setDescription( "My RESTful resources" );
beanConfig.setTitle( "My RESTful API" );
beanConfig.setScan( true );

This tells swagger to scan your package "com.company.swagger.domain.rest" (replace with your package) for APIs.  It will pick up any apis annotated with @Api annotations and you'll see them in the api-docs resource listing.

Give that a spin and post back

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 4:57:54 PM4/15/14
to swagger-sw...@googlegroups.com
Hi again Tony,

This is the code I have now, just to summarize:

...
        final ServletContextHandler restApi = setupRestApiContextHandler(serviceConfig); // Same as described in the original mail
        setupSwaggerContextHandler();

        ContextHandlerCollection contextHandlers = new ContextHandlerCollection();
        contextHandlers.setHandlers(new Handler[] { restApi });
        server.setHandler(contextHandlers);
...

    private static void setupSwaggerContextHandler() {
        BeanConfig beanConfig = new BeanConfig();
        beanConfig.setVersion("1.0.2");
        beanConfig.setResourcePackage(CONTENT_RESOURCES_PKG); // Is "com.myapp.jaxrs.resource"
        beanConfig.setBasePath("http://localhost:4080/api");
        beanConfig.setDescription("My RESTful resources");
        beanConfig.setTitle("My RESTful API");
        beanConfig.setScan(true);
        logger.info("Swagger initialized...");
    }

After adding the initialization with the BeanConfig by calling setupSwaggerContextHandler(), the output when I curl http://localhost:4080/v1/api-docs is a HTTP Code 500 :-(

Thanks again,

Francisco

tony tam

unread,
Apr 15, 2014, 5:00:26 PM4/15/14
to swagger-sw...@googlegroups.com
Can you share a stack trace?

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 5:06:58 PM4/15/14
to swagger-sw...@googlegroups.com
Opsss sorry, forgot to paste it:

WARNING:
javax.servlet.ServletException: org.glassfish.jersey.server.ContainerException: java.lang.NoSuchMethodError: com.google.common.cache.CacheBuilder.maximumSize(I)Lcom/google/common/cache/CacheBuilder;
at org.glassfish.jersey.servlet.WebComponent.service(WebComponent.java:392)
at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:382)
at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:345)
at org.glassfish.jersey.servlet.ServletContainer.service(ServletContainer.java:220)
at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:711)
at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:552)
at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:219)
at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1112)
at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:479)
at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandler.java:183)
at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1046)
at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:141)
at org.eclipse.jetty.server.handler.ContextHandlerCollection.handle(ContextHandlerCollection.java:199)
at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:97)
at org.eclipse.jetty.server.Server.handle(Server.java:462)
at org.eclipse.jetty.server.HttpChannel.handle(HttpChannel.java:281)
at org.eclipse.jetty.server.HttpConnection.onFillable(HttpConnection.java:232)
at org.eclipse.jetty.io.AbstractConnection$1.run(AbstractConnection.java:505)
at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:607)
at org.eclipse.jetty.util.thread.QueuedThreadPool$3.run(QueuedThreadPool.java:536)
at java.lang.Thread.run(Thread.java:724)
Caused by: org.glassfish.jersey.server.ContainerException: java.lang.NoSuchMethodError: com.google.common.cache.CacheBuilder.maximumSize(I)Lcom/google/common/cache/CacheBuilder;
at org.glassfish.jersey.servlet.internal.ResponseWriter.rethrow(ResponseWriter.java:249)
at org.glassfish.jersey.servlet.internal.ResponseWriter.failure(ResponseWriter.java:231)
at org.glassfish.jersey.server.ServerRuntime$Responder.process(ServerRuntime.java:436)
at org.glassfish.jersey.server.ServerRuntime$1.run(ServerRuntime.java:265)
at org.glassfish.jersey.internal.Errors$1.call(Errors.java:271)
at org.glassfish.jersey.internal.Errors$1.call(Errors.java:267)
at org.glassfish.jersey.internal.Errors.process(Errors.java:315)
at org.glassfish.jersey.internal.Errors.process(Errors.java:297)
at org.glassfish.jersey.internal.Errors.process(Errors.java:267)
at org.glassfish.jersey.process.internal.RequestScope.runInScope(RequestScope.java:318)
at org.glassfish.jersey.server.ServerRuntime.process(ServerRuntime.java:236)
at org.glassfish.jersey.server.ApplicationHandler.handle(ApplicationHandler.java:1010)
at org.glassfish.jersey.servlet.WebComponent.service(WebComponent.java:373)
... 20 more
Caused by: java.lang.NoSuchMethodError: com.google.common.cache.CacheBuilder.maximumSize(I)Lcom/google/common/cache/CacheBuilder;
at org.reflections.adapters.JavassistAdapter.<init>(JavassistAdapter.java:28)
at org.reflections.util.ConfigurationBuilder.<init>(ConfigurationBuilder.java:41)
at com.wordnik.swagger.jaxrs.config.BeanConfig.classesFromContext(BeanConfig.scala:58)
at com.wordnik.swagger.jaxrs.listing.ApiListingCache$$anonfun$listing$1$$anonfun$apply$1$$anonfun$apply$2.apply(ApiListing.scala:42)
at com.wordnik.swagger.jaxrs.listing.ApiListingCache$$anonfun$listing$1$$anonfun$apply$1$$anonfun$apply$2.apply(ApiListing.scala:40)
at scala.Option.map(Option.scala:145)
at com.wordnik.swagger.jaxrs.listing.ApiListingCache$$anonfun$listing$1$$anonfun$apply$1.apply(ApiListing.scala:40)
at com.wordnik.swagger.jaxrs.listing.ApiListingCache$$anonfun$listing$1$$anonfun$apply$1.apply(ApiListing.scala:39)
at scala.Option.map(Option.scala:145)
at com.wordnik.swagger.jaxrs.listing.ApiListingCache$$anonfun$listing$1.apply(ApiListing.scala:39)
at com.wordnik.swagger.jaxrs.listing.ApiListingCache$$anonfun$listing$1.apply(ApiListing.scala:37)
at scala.Option.orElse(Option.scala:257)
at com.wordnik.swagger.jaxrs.listing.ApiListingCache$.listing(ApiListing.scala:37)
at com.wordnik.swagger.jaxrs.listing.ApiListingResource.resourceListing(ApiListing.scala:85)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at org.glassfish.jersey.server.model.internal.ResourceMethodInvocationHandlerFactory$1.invoke(ResourceMethodInvocationHandlerFactory.java:81)
at org.glassfish.jersey.server.model.internal.AbstractJavaResourceMethodDispatcher$1.run(AbstractJavaResourceMethodDispatcher.java:151)
at org.glassfish.jersey.server.model.internal.AbstractJavaResourceMethodDispatcher.invoke(AbstractJavaResourceMethodDispatcher.java:171)
at org.glassfish.jersey.server.model.internal.JavaResourceMethodDispatcherProvider$ResponseOutInvoker.doDispatch(JavaResourceMethodDispatcherProvider.java:152)
at org.glassfish.jersey.server.model.internal.AbstractJavaResourceMethodDispatcher.dispatch(AbstractJavaResourceMethodDispatcher.java:104)
at org.glassfish.jersey.server.model.ResourceMethodInvoker.invoke(ResourceMethodInvoker.java:402)
at org.glassfish.jersey.server.model.ResourceMethodInvoker.apply(ResourceMethodInvoker.java:349)
at org.glassfish.jersey.server.model.ResourceMethodInvoker.apply(ResourceMethodInvoker.java:106)
at org.glassfish.jersey.server.ServerRuntime$1.run(ServerRuntime.java:259)
... 29 more

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 6:06:42 PM4/15/14
to swagger-sw...@googlegroups.com
I've double-checked and upgraded guava in my project from 14.0.1 to 16.0.1 but still the same error. The CacheBuilder seems to be since 10.0

tony tam

unread,
Apr 15, 2014, 6:13:07 PM4/15/14
to swagger-sw...@googlegroups.com
My guess is we have conflicting versions of Reflections libraries.  Can you please see what version is being evicted?  This could be due to the upgrade to 0.9.9-RC1 in the 1.3.4 swagger library.

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 6:54:37 PM4/15/14
to swagger-sw...@googlegroups.com
Thanks Tony! I also had a dependency on reflections set to 0.9.6. I've updated to 0.9.9-RC1 and now I get the right version when doing the curl on /v1/api-docs:

{"apiVersion":"1.0.2","swaggerVersion":"1.2","apis":[{"path":"/myResource1","description":"Bla, bla"}],"info":{"title":"My RESTful API","description":"My RESTful resources"}}

So one more step achieved :-) Now, how can I get the API through the web browser?

Thanks again!

tony tam

unread,
Apr 15, 2014, 7:05:03 PM4/15/14
to swagger-sw...@googlegroups.com
Great news!  Clone this project:


put your url (http://{host}/v1/api-docs) in the text-edit box and hit explore.

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 7:37:13 PM4/15/14
to swagger-sw...@googlegroups.com
I accessed the http://localhost:4080/v1/api-docs URL from the Swagger UI text box and I observe this in the Jetty output:

INFO: Jetty Content Service started
Apr 16, 2014 1:34:10 AM org.reflections.Reflections scan
INFO: Reflections took 62 ms to scan 1 urls, producing 29 keys and 99 values

However, the web page shows this message:

"Can't read from server. It may not have the appropriate access-control-origin settings." :-(

tony tam

unread,
Apr 15, 2014, 7:50:57 PM4/15/14
to swagger-sw...@googlegroups.com
I suggest opening up a network debug tool in firefox or chrome and seeing what URL it's trying to call.  It also could be that your server is running on 127.0.0.1 and this is truly a CORS issue.  Can you look for network errors in the tool and post back?

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 8:07:57 PM4/15/14
to swagger-sw...@googlegroups.com
This is the URL I got with Chrome in the Network tab of dev tools:

  1. Request URL:
    1.  Request Headers CAUTION: Provisional headers are shown.
    2. Origin:
      null
    3. User-Agent:
      Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_2) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/33.0.1750.152 Safari/537.36

What's the beanConfig.setBasePath("http://localhost:4080/api"); for? Could be related to this? I've also tried to access http://localhost:4080/api/v1/api-docs but I got the same result.

tony tam

unread,
Apr 15, 2014, 8:20:49 PM4/15/14
to swagger-sw...@googlegroups.com
the basePath configured in the code is for invoking the API, not reading the swagger JSON, which is what makes it interactive.

Can you jump on irc.freenode.net #swagger so we can do this more quickly?  I think you need to give a little more info.
Thanks again!
For more options, visit <a
...

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 8:29:54 PM4/15/14
to swagger-sw...@googlegroups.com
Sorry Tony but I need to go to sleep. It's 2 a.m. here. Can we continue tomorrow?
Thanks again!

Francisco
</fon
...

tony tam

unread,
Apr 15, 2014, 8:30:36 PM4/15/14
to swagger-sw...@googlegroups.com
of course!
...

Francisco Pérez-Sorrosal

unread,
Apr 15, 2014, 8:37:57 PM4/15/14
to swagger-sw...@googlegroups.com
Thanks again Tony! See you tomorrow!
...

Francisco Pérez-Sorrosal

unread,
Apr 16, 2014, 10:53:25 AM4/16/14
to swagger-sw...@googlegroups.com
Hi again Tony,

Summary: Yesterday I was running my application in my localmachine, I tried to exercise the API doc from the same machine using the Swagger UI, and I couldn't retrieve the nice API presentation in my browser. You pointed out that could be something related to CORS, but it was strange because the app was in the same machine.

Today:

First I tried to deploy the application in a different server in another domain, and it didn't work. Same behaviour as in the local machine.

Then I tried to add jetty's CrossOriginFilter filter to the ServletContextHandler of my application exposing the API, but it didn't work neither being the app deployed locally or remotely. So then I tried with your ApiOriginFilter and now when deploying the app remotely it works and I can see the beautiful API, but it doesn't work if I deploy it in my local machine. Any idea about why it doesn't work locally? I can jump to the irc when you have time. Thanks again!

Francisco,

P.S.

This is the code I've added to make it work remotely:

private static ServletContextHandler setupRestApiContextHandler(ContentServiceConfiguration serviceConfig) {
...
        final ServletContextHandler jerseyContextHandler = new ServletContextHandler();
        jerseyContextHandler.setSessionHandler(new SessionHandler());
        jerseyContextHandler.setContextPath("/" + REST_API_VERSION);
        jerseyContextHandler.addServlet(jerseyServletHolder, "/*");
        // logger.info("Adding CORS filter");  <- The jersey CrossOrigin filter didn't work when I tried
        // jerseyContextHandler.addFilter(CrossOriginFilter.class, "/*", EnumSet.of(DispatcherType.REQUEST));
        logger.info("Adding API Origin filter");
        jerseyContextHandler.addFilter(ApiOriginFilter.class, "/*", EnumSet.allOf(DispatcherType.class));

        return jerseyContextHandler;
}

Thanks again!

Ron

unread,
Apr 16, 2014, 10:55:47 AM4/16/14
to swagger-sw...@googlegroups.com
Regarding CORS, if I'm not mistaken it's not enough that they run on the same machine, they also need to run on the same web server. If you pack Swagger-UI with your war and deploy it as part of your application, it would have worked without the filter.


--
You received this message because you are subscribed to the Google Groups "Swagger" group.
To unsubscribe from this group and stop receiving emails from it, send an email to swagger-swaggers...@googlegroups.com.

Francisco Pérez-Sorrosal

unread,
Apr 16, 2014, 11:03:03 AM4/16/14
to swagger-sw...@googlegroups.com
Thanks Ron,

The thing is that is a standalone application with embedded Jetty and I create the servlets programmatically, so I don't have any packaging mechanism :(
...

Mingkui Liu

unread,
Dec 29, 2014, 5:29:22 PM12/29/14
to swagger-sw...@googlegroups.com
Hi guys, did you finally solve the problem?
Do you have some example code on github?
I tried the same thing with you do, but failed at the @WebListener step.
Could you kindly send me some code or link?
Thanks very much.
...

Ron

unread,
Dec 30, 2014, 7:06:53 AM12/30/14
to swagger-sw...@googlegroups.com
Can you share what you currently have in terms of code, and what you've tried doing which doesn't work and we'll go from there?

--
Reply all
Reply to author
Forward
0 new messages