Search code examples
javaspringspring-bootjavafx

JavaFX + Spring boot implementation


Getting acknowledged with "Spring boot + JavaFX" coop.

Was hoping to get answers for such questions:

  1. In the examples through out the web I've found only cases of "@SpringBootApplication" set to the "... extends Application" and by this overriding the "init()" method. But is there a way to have the initial annotation in another place and mark the "Application" bean as a component, thus starting it manually?

I'm not that good with 'JavaFX' yet, and I've tried to start that bean by calling the 'Application.start(UIClass.class)' and got no spring functionality(I get the idea that this doesn't start the object bean, but initiates it separately).

  1. How to properly initiate a spring app from even the 'extends Application'? The examples I've found suggest to override the 'init()' and place the 'ApplicationContext' there. This works, but didn't manage to use the autowiring and similar stuff(and I did verify that the bindings work and have the appropriate naming).

In a similar thread (Spring Boot Main and JavaFX) I've found a solution to use the:

ApplicationContext ctx = SpringApplication.run(Root.class); 
ctx.getAutowireCapableBeanFactory().autowireBean(this);

but I have the feeling that this is more of a workaround and I've made a mistake somewhere.

Thanks in advance.


Solution

  • In general, I'd make a case for arguing that if you are accessing the Application instance from another part of the application, you probably need to refactor your application. The role of the Application is just to manage application lifecycle, so accessing that object from elsewhere is a sign that you are likely violating design principles somewhere (single responsibility, at a minimum).

    That said, there are some corner cases. I have one application where I needed to access the HostServices in a controller, and that is only generally available via the Application instance. In that case I used a similar solution/workaround to the one you propose in order to programmatically register the HostServices as a "Spring-managed" bean.

    The bottom line here is that you have two toolkits/frameworks that are responsible for creating and managing object lifecycle to some degree. (JavaFX is more of a toolkit than a framework, and doesn't do much object lifecycle management, but it does some.) Any time you are in that situation and you want one framework to be aware of an object created and managed by the other framework, you need to do some programmatic wiring between the two frameworks. This is one example, because the Application instance is created for you by JavaFX, so if you want Spring to be aware of it, you have to explicitly tell Spring about it.

    So in summary, properly structuring your application will minimize the need for the kinds of workaround you suggest, but there are cases where it might be necessary. There's generally no way to configure one framework to support objects created by another framework unless there is explicit support for the second framework in the first.