Hi.
For the "hundred of implementations" problem, You can use custom scopes to
select on runtime the binding that should be used. Final code may look like
this:
public class LogicThatUseTheSelectedService {
@Inject
private Provider<Service> selectedServiceProvider;
@AnnotationToBindServiceSelection
public void makeTheWork(){
Service selectedService = selectedServiceProvider.get();
....
}
}
To make it work, You need to:
-- Make a custom scope that will have a reference to the binded service in
runtime (a ThreadLocal<Service>)
-- make a aspect for the annotation @AnnotationToBindServiceSelection that
will find and setup the desired service (on base of the current runtime
context) in the custom scope.
A very similar example is provided in my post "Controlled Scope"
http://softwaremathmodel.blogspot.com/2012/05/controlled-scope.html
The difference is that the calls "controller.setupBusinessContext.." and
"controller.clearBusinessContext()" in the method "businessOperation" will
be extracted to the annotation aspect. Your final implementation of
BusinessContextController will be:
public interface BusinessContextControl {
void setupBusinessContext(Service selectedService);
void clearBusinessContext();
}
If you need any more details, just let me know.
Pawel Cesar Sanjuan Szklarz.
On Thu, Feb 27, 2014 at 7:22 AM, Stephan Classen <[email protected]> wrote:
> Question1 - 10+ implementations:
> If you have lots of implementation or you have a plugin like architecture
> where new implementations may be added after your main component has
> already been released then my proposed solution would not scale. If you are
> in such a situation have a look at multibinders:
> http://code.google.com/p/google-guice/wiki/Multibindings
> But if you are sure you will only have a very limited number of
> implementations and no new ones will be added after release day I would go
> with an approach similar to my proposal. Simply because I feel it is easier
> readable and most important it is testable without having to create an
> injector.
>
> Question2 - should it implement Provider<T>:
> I deliberately did not implement the provider interface. And if you would
> try to add it to my code you would get a compiler error.
> I prefer to pass the required data to make the decision which
> implementation to choose to the method getServiceFor(...).
> The provider interface on the other hand has only a no-arg method get().
> If you would want to implement the provider interface you would have to
> inject all required information to make the decision into your
> implementation. This may lead to more complex code when the decision is
> based on a user action or similar information which is not available
> beforehand.
> I agree that in a guice based implementation the usage of the word
> provider in a class name may not be well suited if the class does not
> implement the provider interface.
> You could call the class OrganizationServiceFactory or
> OrganizationServiceLocator to avoid confusion.
>
>
>
> On 02/26/2014 03:35 PM, sreenivasu puppala wrote:
>
> I agree with you JP , it would be very difficult to accomodate if there
> are hundred implementations , Please post me if you find any solution, iam
> in need of the code urgently :-)
>
>
> Thanks SCL, i have question
>
> I guess OrganizationServiceProvider should implement Provider in the below
> code?
>
> On Wednesday, February 26, 2014 11:38:57 AM UTC, Juan Pablo Vergara
> Villarraga wrote:
>>
>> I understand the solution from scl as a container for all the possible
>> implementations of the dependency to be injected. It looks like a practical
>> solution when there are few implementations. Would it be an elegant
>> solution if we have a hundred implementations or so?
>>
>> Im currently coding a solution for this problem as well. If I find a
>> different solution I'll post it :)
>>
>> JP
>>
>> El martes, 25 de febrero de 2014 03:06:34 UTC-5, scl escribió:
>>>
>>> public class OrganizationServiceProvider {
>>>
>>> private final OrganizationServiceImpl orgService;
>>> private final OrgDeatilsServiceImpl orgDetailService;
>>>
>>> @Inject
>>> OrganizationServiceProvider(final OrganizationServiceImpl
>>> orgService, final OrgDeatilsServiceImpl orgDetailService) {
>>> this.orgService = orgService;
>>> this.orgDetailService = orgDetailService;
>>> }
>>>
>>> public OrganizationService getServiceFor(/* you must pass the the
>>> necessary input to decide which impl to choose */) {
>>> // your code goes here. it must return either orgService or
>>> orgDetailService
>>> }
>>> }
>>>
>>> public class OrganizationsResource {
>>>
>>> private final OrganizationServiceProvider osProvider;
>>>
>>> @Inject
>>> OrganizationsResource(final OrganizationServiceProvider osProvider)
>>> {
>>> this.osProvider = osProvider;
>>> }
>>>
>>> // more code...
>>> }
>>>
>>> There is no special binding in the Guice module necessary since all
>>> injections go to concrete classes.
>>> Of course it would be nice to introduce an interface for
>>> OrganizationServiceProvider and have an OrganizationServiceProviderImpl.
>>>
>>> In this case you would need to bind the impl to the interface.
>>>
>> --
> You received this message because you are subscribed to the Google Groups
> "google-guice" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to [email protected].
> To post to this group, send email to [email protected].
> Visit this group at http://groups.google.com/group/google-guice.
> For more options, visit https://groups.google.com/groups/opt_out.
>
>
> --
> You received this message because you are subscribed to the Google Groups
> "google-guice" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to [email protected].
> To post to this group, send email to [email protected].
> Visit this group at http://groups.google.com/group/google-guice.
> For more options, visit https://groups.google.com/groups/opt_out.
>
--
You received this message because you are subscribed to the Google Groups
"google-guice" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To post to this group, send email to [email protected].
Visit this group at http://groups.google.com/group/google-guice.
For more options, visit https://groups.google.com/groups/opt_out.