Camel context properties from DB - spring

Right now, I bootstrap Camel using Spring. Using Spring, I can point my Camel contexts to their respective properties files which are then injected at boot time. My issues is that I now want to move my properties from a file to a database, yet still be able to use the property placeholders as I was before. What's the best way to go about doing this?
I've noticed that there's a PropertiesResolver interface that I could implement, but I wouldn't know how to tell Camel about my implementation. Camel's documentation is very lacking in this area.
I also wouldn't be opposed to having Spring get the properties from the database for me, although I don't see that happening.

The PropertiesResolver was designed to help Camel to locate the properties files from OSGi bundle or normal class path.
If you want to setup your owner PropertiesResolver, you can try to use org.apache.camel.spring.spi.BridgePropertyPlaceholderConfigurer.
You can inject your customer implementation of PropertiesResolver there.

I thought I'd update this with what I found to work. This probably isn't the best method way to do it, but it works and I didn't have to modify the Camel source code. Basically, I converted all of my classes from inheriting from RouteBuilder to inherit from GJKRouteBuilder (which inherits from RouteBuilder). Then in there, I did this:
public class GJKRouteBuilder extends RouteBuilder {
#Override
protected void checkInitialized() throws Exception {
//Get properties from CamelContext using getContext()
//Lookup properties from DB based on CamelContext
//Get the properties component from the context (or create one)
//call setOverrideProperties() on properties component
super.checkInitialized();
}
}
Again, probably not the best method, but it works. Now, any route that inherits from GJKRouteBuilder and has the proper values wired up through Spring will have the properties injected into the properties component as if they were coming right from a properties file.

Related

spring data - get beans in a custom default repository implementation

Im trying to upgrade my project from spring-boot-1.4.3.RELEASE to spring-boot-1.5.9.RELEASE.
In the 1.4.3.RELEASE the way I have used my custom implementation of repositories is as follow:
Made an interface MyCustomRepositroy that extends JpaRepository
Had a class MyCustomRepositoryImpl that implements MyCustomRepositroy and SimpleJpaRepository. In that class I have changed the behavior of
the of save, find and delete methods, because I needed a
ceratin behavior for entitys of certain type (lets say that I need a
custom save for all entitys that implements Special interface)
I made a MyCustomJpaRepositoryFactoryBean that extends JpaRepositoryFactoryBean. In that factory, I've overridden createRepositoryFactory and gave it my MyRepositoryFactory implementation.
In MyRepositoryFactory implementation I've overridden the getTargetRepository, and getRepositoryBaseClass.In these methods, I check if the entity is of type Special, and if so, I return MyCustomRepositoryImpl, otherwise I return SimpleJpaRepository.
Also, I can get the beanFactory in my MyCustomRepositoryImpl class because I call my own constructor of MyCustomRepositoryImpl that has also a beanFactory parameter via getTargetRepositoryViaReflection.
Now, with the new version (that uses spring-data-commons-1.13.9.RELEASE), I cannot override the Factory class, and hence can't decide for each entitiy which implementation to give, and have no way to get the beanFactory.
Is there any way I can get what I want?
Sorry for the mess, but I cannot post my code here.
P.S - my project is a spring based library, so I can't do anything to the entitys because my clients declare them, all I know that some entitys implement the Special interface and some don't
I am trying to figure out what happened in 1.5.9.RELEASE, but in the meantime, just as a fyi - 1.5.6.RELEASE works ok.
I am having the same issue when trying to update from 1.5.6.RELEASE to 1.5.9.RELEASE

Spring in a JavaFX application - how to property handle controller as dependency?

I have a JavaFX application that uses spring boot, exactly as described in this blog post:
http://www.greggbolinger.com/let-spring-be-your-javafx-controller-factory/
I am using the FXML loader overriding the controller factory to use spring.
The problem is that Spring loads the controller class marked as #Component on application start or later if marked with #Lazy, but keeps the bean in memory.
If I open a Stage, modify the data, close the stage and open it again, the data is still there (because the controller was kept by spring). It also gets in the way if I open two of the same Stage (window). It shares the same controller, so if I modify one, the other modifies too, and this is not the desired behavior.
How to I properly handle JavaFX controllers with spring?
Thanks!
Mark the controller as having prototype scope, so that a new instance is created on each request:
#Component
#Scope(BeanDefinition.SCOPE_PROTOTYPE)
public class Controller {
// ...
}

Explicitly declaring service gateway in Java configuration

I have an application using Spring Integration where I have multiple handlers (strategies) for some service gateway methods, and I want the deployment launcher to be able to select which specific handlers are loaded. Since component scanning will pick up all of the handlers indiscriminately, I prefer to explicitly declare JavaConfig #Beans for them.
This works fine for the service objects themselves, but I can't find a way to load the service interface itself in Java without #IntegrationComponentScan. My current workaround is to include a "one-liner" XML file with an <int-gateway> tag and #ImportResource it, but I'd really prefer a more direct solution.
Is there any straightforward way in JavaConfig to tell Spring Integration to create a proxy service interface for a specific class?
GatewayProxyFactoryBean is for you.
This class is used to populate bean definition from <int:gateway> tag and from MessagingGateway annotation.
So, you can do like this:
#Bean
public GatewayProxyFactoryBean myGateway() {
GatewayProxyFactoryBean factoryBean = new GatewayProxyFactoryBean(YourServiceInterface.class);
factoryBean.setDefaultRequestChannel(gatewayRequestChannel());
return factoryBean;
}

Is it possible to use Spring without a configuration file?

In my unit tests I want to configure Spring in code (API, Annotations) so they will not depend on bean configuration files.
Can this be done?
For example:
Class Dependency {}
Class A
{
#AutoWired
Dependency d;
}
When testing A, I want to be able to create an instance of it with the Dependency member resolved, without having to use configuration files.
Thank you!
In short, yes, you can start a spring application context with any of the implementations of org.springframework.context.support.AbstractApplicationContext. Namely, if you don't want to load the definitions from an XML file, you can use the org.springframework.context.support.StaticApplicationContext or org.springframework.context.support.GenericApplicationContext to start the context.
With the context instantiated, you can start creating beans with the BeanFactory, either the oen default to the selected context or a custom one, that suits your needs.
In practice, it's lot more work than that. It's easier if you just use plain XML configuration, but it can be done.
You can use the Java configuration instead of the XML configuration.
You can use the AnnotationConfigApplicationContext to create application context programatically without bean configuration files.

A bunch of questions on Spring 3 framework

Here are the questions resulted from reading the Spring Reference, please help.
(1) Do I ever need manual creation of ApplicationContext? Do I ever need second instance of AplicationContext?
(2) We have the following config instructions:
<context:annotation-config/>
<context:component-scan base-package=".."/>
<mvc:annotation-driven/>
Do these instructions duplicate theirselfs? In which cases yes, in which no?
(3) I am a bit stuck with all that ways Spring introduces to convert from string to object: PropertyEditor, Conversions, Formatting..
Here is a simple use case:
I have a Spring MVC controller that processes some POST request. That request is a result of filling some form. The form is a web representation of some entity.
So, given a the user submits a new Project form. In that form exist a date field and a manager's name field to be selected from the list of existing managers. The entered date should be converted to Date property of Project object, and manager's name - to Manager property, created or located by this name (i.e. I want to inject Manager into his Project). What should I use in this case? Property editors, formatters, something else?
(4) Generally, may I say that all the #interface classes that are found on classpath can be used by Spring as annotations?
In other words, how can I know which annotations can be used in my project? All that can be found in my classpath, or I need to register them somehow?
(5) I tried to use spring aop without aspectj.jar: just created an Aspect and addred XML definition for this aspect (without any annotations). As a result it throws "class not found Exception: org/aspectj/weaver/BCException".
So looks like I cannot use Spring AOP without aspectJ library?
(1) Do I ever need manual creation of ApplicationContext? Do I ever need second instance of AplicationContext?
Spring is typically usd in two environments - in web development and in desktop applications/standalone servers. In the former case the ApplicationContext is created automatically via ContextLoaderListener defined in web.xml or WebContextInitializer in Servlet 3.0 container.
In the latter case (standalone application) you are responsible for creating and destroying the application context.
(2) We have the following config instructions:
<context:component-scan base-package=".."/> provides all the functionality of <context:annotation-config/> plus (surprise!) component scanning. <mvc:annotation-driven/> is completely independent and it recognizes spring-mvc annotations like #Controller.
[...]The entered date should be converted to Date property of Project object[...]
Register custom editor within #Controller:
#Controller
public class FooController {
#InitBinder
public void binder(WebDataBinder binder) {
binder.registerCustomEditor(Date.class, new PropertyEditorSupport() {
public void setAsText(String value) {
try {
setValue(new SimpleDateFormat("yy-MM-dd HH:mm:ss").parse(value));
} catch (ParseException e) {
setValue(null);
}
}
});
}
}
[...]how can I know which annotations can be used in my project?[...]
I found this awesome annotations support sheet some time ago (I am not an author). It will tell you which annotations are enabled when.
All that can be found in my classpath
#Inject is enabled if it is found on the CLASSPATH, other annotations need to be enabled manually, see above.
So looks like I cannot use Spring AOP without aspectJ library?
You can use Spring without CGLIB if you only use interface proxies (i.e. you only apply aspects on classes implementing at least one interface). Otherwise you need CGLIB to dynamically create subclasses.

Resources