Vibe.d rest & web service?
Is it possible to have some urls routed to serve content and some to receive JSON in the same class? Basically I want: shared static this() { auto router = new URLRouter; auto a = new MyInterface; router.registerWebInterface(new MyInterface); //?? selective combination router.registerRestInterface(new MyInterface); //?? auto settings = new HTTPServerSettings; settings.port = 8080; settings.bindAddresses = ["::1","127.0.0.1"]; listenHTTP(settings, router); } class MyInterface { SomeData[] items; // Get void index() { render!("index.dt"); } // Get void getPage() { render!("page.dt", items); } // REST -> receive d as JSON. void postGiveMeData(SomeData d) { synchronized { items ~= d; } } }
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 17:04:13 UTC, Nicholas Wilson wrote: Is it possible to have some urls routed to serve content and some to receive JSON in the same class? This seems unlikely to me, the function signature doesn't provide a way to distinguish between REST and not. I'm also not sure it is necessary, you can certainly have multiple class which provide REST and Web endpoints. You can even dynamically build routes within a route.
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 17:57:09 UTC, Jesse Phillips wrote: On Wednesday, 7 February 2018 at 17:04:13 UTC, Nicholas Wilson wrote: Is it possible to have some urls routed to serve content and some to receive JSON in the same class? This seems unlikely to me, the function signature doesn't provide a way to distinguish between REST and not. I'm also not sure it is necessary, you can certainly have multiple class which provide REST and Web endpoints. You can even dynamically build routes within a route. Hmm, this might be one of the few use cases for nested classes. But is would still require some routing trickery.
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 17:04:13 UTC, Nicholas Wilson wrote: Is it possible to have some urls routed to serve content and some to receive JSON in the same class? Basically I want: shared static this() { auto router = new URLRouter; auto a = new MyInterface; router.registerWebInterface(new MyInterface); //?? selective combination router.registerRestInterface(new MyInterface); //?? auto settings = new HTTPServerSettings; settings.port = 8080; settings.bindAddresses = ["::1","127.0.0.1"]; listenHTTP(settings, router); } class MyInterface { SomeData[] items; // Get void index() { render!("index.dt"); } // Get void getPage() { render!("page.dt", items); } // REST -> receive d as JSON. void postGiveMeData(SomeData d) { synchronized { items ~= d; } } } How about using the normal Vibe.d Web Service? An example from my WIP project vibe-by-example project: https://github.com/wilzbach/vibe-d-by-example/blob/master/web/service.d I also have a fork of vibe.web.web that adds additional convenience features to Vibe.d: https://github.com/teamhackback/hb-web (I have been struggling to get most of them merged upstream - https://github.com/vibe-d/vibe.d/pulls/wilzbach)
Re: Vibe.d rest & web service?
On 2/7/18 12:04 PM, Nicholas Wilson wrote: Is it possible to have some urls routed to serve content and some to receive JSON in the same class? Basically I want: shared static this() { auto router = new URLRouter; auto a = new MyInterface; router.registerWebInterface(new MyInterface); //?? selective combination router.registerRestInterface(new MyInterface); //?? auto settings = new HTTPServerSettings; settings.port = 8080; settings.bindAddresses = ["::1","127.0.0.1"]; listenHTTP(settings, router); } class MyInterface { SomeData[] items; // Get void index() { render!("index.dt"); } // Get void getPage() { render!("page.dt", items); } // REST -> receive d as JSON. void postGiveMeData(SomeData d) { synchronized { items ~= d; } } } Yes you can, but it's not pretty. interface MyInterface { void postGiveMeData(SomeData d); } class MyInterfaceImpl : MyInterface { void postGiveMeData(SomeData d) { ... } void getPage() { ... } void index() { ... } } auto myI = new MyInterfaceImpl; router.registerRestInterface(myI); router.get("/route/to/getPage", &myI.getPage); router.get("/route/to/index", &myI.index); This worked for me, but note that my "non-rest" function was static, so I didn't need to worry about instances. I'm not sure if the above works exactly right for you. However, I would recommend actually not doing this for your purpose. My case was different -- I still wanted routes that were REST routes, but I wanted to control the result streaming (the vibe.d return value doesn't work with ranges, so I would have had to construct essentially my entire database in an array so I could return it). In your case, I think you are better off using 2 classes, and one shared data storage area. -Steve
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 18:38:15 UTC, Seb wrote: How about using the normal Vibe.d Web Service? Stupid question: whats the difference? An example from my WIP project vibe-by-example project: https://github.com/wilzbach/vibe-d-by-example/blob/master/web/service.d I also have a fork of vibe.web.web that adds additional convenience features to Vibe.d: https://github.com/teamhackback/hb-web (I have been struggling to get most of them merged upstream - https://github.com/vibe-d/vibe.d/pulls/wilzbach)
Re: Vibe.d rest & web service?
On 2018-02-07 18:04, Nicholas Wilson wrote: Is it possible to have some urls routed to serve content and some to receive JSON in the same class? Basically I want: shared static this() { auto router = new URLRouter; auto a = new MyInterface; router.registerWebInterface(new MyInterface); //?? selective combination router.registerRestInterface(new MyInterface); //?? auto settings = new HTTPServerSettings; settings.port = 8080; settings.bindAddresses = ["::1","127.0.0.1"]; listenHTTP(settings, router); } class MyInterface { SomeData[] items; // Get void index() { render!("index.dt"); } // Get void getPage() { render!("page.dt", items); } // REST -> receive d as JSON. void postGiveMeData(SomeData d) { synchronized { items ~= d; } } } Have you tried this? -- /Jacob Carlborg
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 19:50:31 UTC, Jacob Carlborg wrote: Have you tried this? No. But apart from the fact that I forgot to make the class inherit from an interface to that the rest interface would actually compile, the web interface is routed before the rest interface and so the rest interface would never be reached since the methods are all the same and the REST's are shadowed by the web's .
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 20:23:10 UTC, Nicholas Wilson wrote: On Wednesday, 7 February 2018 at 19:50:31 UTC, Jacob Carlborg wrote: Have you tried this? No. But apart from the fact that I forgot to make the class inherit from an interface to that the rest interface would actually compile, the web interface is routed before the rest interface and so the rest interface would never be reached since the methods are all the same and the REST's are shadowed by the web's . Makes me wonder whether or not vibe does honor the http request Accept headers? e.g.: application/json or application/javascript or text/html etc.
Re: Vibe.d rest & web service?
On Thursday, 8 February 2018 at 10:51:39 UTC, Arjan wrote: On Wednesday, 7 February 2018 at 20:23:10 UTC, Nicholas Wilson wrote: On Wednesday, 7 February 2018 at 19:50:31 UTC, Jacob Carlborg wrote: Have you tried this? No. But apart from the fact that I forgot to make the class inherit from an interface to that the rest interface would actually compile, the web interface is routed before the rest interface and so the rest interface would never be reached since the methods are all the same and the REST's are shadowed by the web's . Makes me wonder whether or not vibe does honor the http request Accept headers? e.g.: application/json or application/javascript or text/html etc. Hmm, I hadn't considered the Accept Headers.
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 18:47:05 UTC, Steven Schveighoffer wrote: Yes you can, but it's not pretty. interface MyInterface { void postGiveMeData(SomeData d); } class MyInterfaceImpl : MyInterface { void postGiveMeData(SomeData d) { ... } void getPage() { ... } void index() { ... } } auto myI = new MyInterfaceImpl; router.registerRestInterface(myI); router.get("/route/to/getPage", &myI.getPage); router.get("/route/to/index", &myI.index); This worked for me, but note that my "non-rest" function was static, so I didn't need to worry about instances. I'm not sure if the above works exactly right for you. However, I would recommend actually not doing this for your purpose. My case was different -- I still wanted routes that were REST routes, but I wanted to control the result streaming (the vibe.d return value doesn't work with ranges, so I would have had to construct essentially my entire database in an array so I could return it). In your case, I think you are better off using 2 classes, and one shared data storage area. -Steve Thanks! (Some how I missed your post).