Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Eclipse Projects » Eclipse 4 » Inject values into fields when class instantiated in my code(Dependency Injection question)
Inject values into fields when class instantiated in my code [message #1752661] Wed, 25 January 2017 21:34 Go to next message
Ken Keefe is currently offline Ken KeefeFriend
Messages: 23
Registered: April 2012
Junior Member
I'm trying to figure out how to correctly inject values into a handler when it is created in my own custom code. Here is the handler code:

public class OpenProjectComponentHandler {
	
	@Inject
	private MApplication application;
	
	@Inject
	private EModelService modelService;

	@Execute
	public Object execute(@Named(IServiceConstants.ACTIVE_SELECTION) ISelection sel) {
		/* Code that uses modelService and application here */
		return null;
	}

	@CanExecute
	public boolean canExecute() {
		return true;
	}
}


Now, when a menu item click triggers the call to this handler, application and modelService are injected as I'd expect. But, I also want to call this handler from other custom code like this:

OpenProjectComponentHandler handle = new OpenProjectComponentHandler();
			handle.execute(new StructuredSelection(o));


When I call the handler using my own code, the fields have nothing injected into them.
Re: Inject values into fields when class instantiated in my code [message #1752669 is a reply to message #1752661] Wed, 25 January 2017 21:50 Go to previous messageGo to next message
Erdal Karaca is currently offline Erdal KaracaFriend
Messages: 839
Registered: July 2009
Senior Member
That is possible using

IEclipseContext context = ...;
handler = ContextInjectionFactory.make(OpenProjectComponentHandler.class, eclipseContext);
ContextInjectionFactory.invoke(handler, Execute.class, eclipseContext);


But, I think, it would be better to extract the executed logic into a utility method that you can call outside DI and just delegat to within DI.

Ken Keefe wrote on Wed, 25 January 2017 22:34
I'm trying to figure out how to correctly inject values into a handler when it is created in my own custom code. Here is the handler code:

public class OpenProjectComponentHandler {
	
	@Inject
	private MApplication application;
	
	@Inject
	private EModelService modelService;

	@Execute
	public Object execute(@Named(IServiceConstants.ACTIVE_SELECTION) ISelection sel) {
		/* Code that uses modelService and application here */
		return null;
	}

	@CanExecute
	public boolean canExecute() {
		return true;
	}
}


Now, when a menu item click triggers the call to this handler, application and modelService are injected as I'd expect. But, I also want to call this handler from other custom code like this:

OpenProjectComponentHandler handle = new OpenProjectComponentHandler();
			handle.execute(new StructuredSelection(o));


When I call the handler using my own code, the fields have nothing injected into them.

Re: Inject values into fields when class instantiated in my code [message #1752672 is a reply to message #1752661] Wed, 25 January 2017 21:56 Go to previous messageGo to next message
Ken Keefe is currently offline Ken KeefeFriend
Messages: 23
Registered: April 2012
Junior Member
Well, the good people on the freenode irc solved this for me.

OpenProjectComponentHandler handle = ContextInjectionFactory.make(OpenProjectComponentHandler.class, context);
handle.execute(new StructuredSelection(o));


And, the context variable in that code fragment was injected in the class that this code is contained in. I don't know if I'll ever need to make a call like this from an object that was not created by the context injection factory.
Re: Inject values into fields when class instantiated in my code [message #1752673 is a reply to message #1752661] Wed, 25 January 2017 21:57 Go to previous message
Patrik Suzzi is currently offline Patrik SuzziFriend
Messages: 86
Registered: June 2010
Location: Imola, Italy
Member

I generally avoid field injection, because I can not easily predict the values of the injected fields.

I tend to use injected constructors and injected methods in general, as I find more predictable the way I can obtain values injecting parameters.

In the code snippet below, you can see how I transformed your initial code snippet in a way that is easier to use and less prone to errors. In particular, note that:

1. I injected the needed parameters in the @Execute method. So doing, Eclipse injects the actual instances for "IEclipseContext ", "EModelService" and "MApplication" each time the method is called.

2. I added another method where @Optional @Named(IServiceConstants.ACTIVE_SELECTION) is injected. This means that this method is automagically executed each time the ACTIVE_SELECTION changes.

public class OpenProjectComponentHandler {
	
	private MApplication application;
	
	private EModelService modelService;
	
	private StructuredSelection selection;

	@Execute
	public Object execute(IEclipseContext context, EModelService modelService, MApplication application) {
		// you can keep references to the injected objects
		this.application = application;
		this.modelService = modelService;
		// execute code using modelService application and context
		return null;
	}

	@CanExecute
	public boolean canExecute() {
		return true;
	}

	@Inject
	@Optional
	public void executeOnSelection(
					@Optional @Named(IServiceConstants.ACTIVE_SELECTION) StructuredSelection selection) {
		// you can keep reference to the injected object
		this.selection = selection;
		// here you execute your code when the selection changes

	}
	
}


In case you need more information, please read about dependency injection in Eclipse 4, and about the difference between field injection and parameter injection.
- as an example: http://eclipsesource.com/blogs/tutorials/eclipse-4-e4-tutorial-part-4-dependency-injection-basics/

Also, you can check for one of the many tutorials available on the web.

Kind Regards,

Ing. Patrik Suzzi
Consultant Software Engineer,
Eclipse Platform Committer
https://about.me/psuzzi

[Updated on: Thu, 26 January 2017 22:55]

Report message to a moderator

Previous Topic:Dynamic toolbar contributions
Next Topic:Contributed MenuItems don't get translated sometimes
Goto Forum:
  


Current Time: Wed Nov 22 02:23:55 GMT 2017

Powered by FUDForum. Page generated in 0.01595 seconds
.:: Contact :: Home ::.

Powered by: FUDforum 3.0.2.
Copyright ©2001-2010 FUDforum Bulletin Board Software