matteobaccan/owner

Make object creation dependency injection friendly

KamBha opened this issue · 5 comments

Problem: We use Guice to help wire up our dependencies. While the approach of creating a Converter (for example) from a default constructor or a method on a class is powerful, it would be nice to have Guice instantiate the object directly.

I imagine something that allows you register a class with the ConfigFactory that looks like this:-


public interface ObjectInstantiator {
    <T> T createObject(Class<T> inClassToInstantiate, 
                                   DependencyAnnotations inDependencyAnnotation);
}

DependencyAnnotations would be a new annotation which would allow users to specify annotations used to qualify the instance. For example, Spring's @qualifier or Guice's @nAmed.

Hi.

I don't use guice so I don't know how to integrate it. Also I don't want to introduce external dependencies in OWNER; there is a sub-project called owner-extras that can accept that if you want to contribute your integration code for guice, I will consider merging it.

I have notice of people using owner with spring and guice, and I did it before for spring-ioc, I had no issue with that.

If you want to discuss future development in Owner please join https://t.me/ownerapi
Also consider donating if you find owner useful for your business: https://github.com/lviggiano/owner#donate

Thank you.

Sorry, I wasn’t clear. I agree that we should not make any injection library a dependency in OWNER. The above was more an example of our problem. The solution I had in mind was instead to provide a framework for integrating such frameworks easily.

Basically, from what I can tell, owner has a number of places where it creates objects (eg tokenisers and converters). And a number of strategies to do so. However, there is currently no way of having these objects created by a dependency framework.

The basic idea of this change is to provide a mechanism for doing so by allowing owner to take a custom strategy class for overriding the code responsible for creating objects via the default constructor.

What would be the benefits and tradeoffs?

I know, this is an old conversation, but it confusied me, because I don't see any problem with DI integration already.

e.g. example with Dagger2 :

@Module
class OwnerModule {

	@Provides
	static MySuperLoaderForOwner provideMySuperLoaderForOwner(...) {
		return new MySuperLoaderforOwner(...);
	}

	@Provides 
	@Singleton
	static org.aeonbits.owner.Factory provideOwnerFactory(MySuperLoaderForOwner mySuperLoaderforOwner) {
		org.aeonbits.owner.Factory factory = org.aeonbits.owner.ConfigFactory.newInstance();
		factory.registerLoader(mySuperLoaderforOwner);
		return factory;
	}

	@Provides 
	static MySeperConfig provideMySeperConfig(org.aeonbits.owner.Factory factory) {
		return factory.create(MySeperConfig.class);
	}
}

You can already implement an OWNER-loader that can load anything from any source (e.g. JSON from database). The loader is a simple java class, so you can easily integrate it with your DI framework to get the necessary object instances from the DI (e.g. JDBC DataSource, JOOQ DSLContext, JPA EntityManagerFactory or whatever you need). Easy.