Services: A Rumination on Introducing a New Role into the Ember Programming Model

As linked to in the pdxb.us example, the actual implementation of this feature builds heavily on top of existing features. All said and done, I imagine it would be implemented in under 100 lines of code. Just moving the view infrastructure from Metamorph to HTMLbars will probably be an order of magnitude reduction compared to that.

2 Likes

I like the idea of defining a role for Services. I can see some good use-cases where I could use this in some applications I’ve built.

I am wondering if are there cases where services could depend on each other. So like in @tomdale’s example, but instead of a NearbyTweets controller we might have a more general Twitter service which in turn uses the Geolocation service. This example is a bit off, but you get the idea.

@tomdale when I see the word “services” I can’t help but thinking about the services menu concept in OS X. Is this concept analogous?

Services are features exported by your application for the benefit of other applications. Services let you share the resources and capabilities of your application with other applications in the system.

I think it we substituted the word applications with the word controllers we might have an approximation of what services are about in an ember context.

@tomdale I’d really like to see an architecture overview such as this but fleshed out more appear in the ofifcial ember docs. It really needs it.

Good clarification! This would make sense in our app too.

We’ve got something similar (albeit not named ‘services’) wrapping the W3C Geo API and device APIs (e.g. the push notification permissions API on iPhone).

I’m interested in how this fits into the world of (ES6) modules.

I like that Ember manages the Route and Controller instances automagically. The application, routes and controllers are all somewhat tightly coupled to one another, and this approach allows me to declare how my application works, rather than taking a more imperative approach.

A “service” seems like it could (should?) exist independently of the application. Given that, maybe the best advice would be to wrap the service up as a module that can be imported wherever it’s needed. The module loader already handles dependency management for loosely-coupled modules, so maybe it makes sense to just use that.

I’m not sure how this maps to “globals”-style Ember apps. Perhaps the best advice there is to tack service-providing objects onto the app namespace or the app controller.

(I apologize if I’m missing the point here, in that all of this “how” may be irrelevant in deciding whether there should be some class of objects in Ember called Services.)

1 Like

As a though-experiment, I forked @tomdale’s pdxb.us app and made the geolocation service into a stand-alone module.

https://github.com/nonsensery/pdxb.us/commit/5ea51219476c64d955f402741944a5c4d604cf11

This works in this instance, because the geolocation service doesn’t have any dependencies on other parts of the system, and it’s stateless. But how would you accomplish something like Ember Data’s store, where it needs to both maintain a cache and lookup models the user has defined?

Hey, so what’s the status on this? Can we play it with right now? I do like the idea of some sort of service object.

1 Like

I submitted a PR, but after discussion in that thread, the proposed API has changed and I have not yet updated the PR to reflect that. If you’d like to tackle it, feel free to fork the PR and update it with the new API.

Yes! I played around with extracting the model from pdxb.us into a module. That worked out OK (I actually really like the idea of an isolated, stand-alone data model), but pdxb.us doesn’t use Ember-Data…

I also experimented with an Ember-Data-based model. In doing so, I realized that it wouldn’t work because the Ember framework needs access to the model so that it can, for instance, automatically resolve URL segments into model objects (e.g., /books/:book_id).

I learned a lot from this thought experiment, and my feeling now is that there may be a fundamental difference between a loosely-coupled service like a geolocator or a roll-your-own model, and an integrated service like an Ember-Data-based model.

Being relatively noob I agree. Understand DI and Ember’s container is a bit foggy for me right now but this proposal is extremely straight forward and easily implemented.

I really like this proposal. With respect to injection, it is yet another case where declarative mixin/injection makes sense which could then be controlled/configured externally. Would be awful to maintain on a per instance basis directly in the code IMO. Just doesn’t scale, too easy to make mistakes.

See my Declarative Mixer RFC https://github.com/emberjs/rfcs/pull/7

A similar approach could be used for declarative authorization rules on routes, etc. etc. So many use cases really! The notion of Aspects were introduced in Java for the same reason. Many concerns are horizontal and best controlled externally to the code, much like CSS for layout.

I like this proposal because having a solid DI is vital. Will Ember support any form of scopes or contexts in the DI container, for example like Symfony does? I found it very useful when working on a large Symfony application.