I'm writing an application with Spring MVC which I'd like to be configurable with properties files. I looked into Spring's util namespace and found this:
<util:properties id="MyProperties" location="propertiesPath" />
with this, I can annotate my classes field simply with
#Value("myProperty")
and have the property simply injected. So, it's very simple to read your properties. But when you have to save them, it's not as intuitive.
I've stumbled upon quite a few questions on how to do it properly and I think this represents best what I want to say: Updating a properties file injected by Spring to include a last run timestamp.
My question is: why it's so difficult to save properties in Spring? Am I doing it the wrong way? At this point I am even wondering if saving properties this way is a good practice or if I should use a database.
From Oracle I can read:
The Properties class represents a persistent set of properties. The Properties can be saved to a stream or loaded from a stream.
But Spring seems to make easier only one of them. Please enlighten me.
Thank you.
Spring is largely involved in creating the static, unchanging, structure of your application, and not really involved in transaction processing or business-logic. Often it defines how transactions are to be processed, but it isn't usually involved in the processing itself. We often talk about the separation of the domain model and the architecture -- spring is about architecture.
Writing something out to a store of some kind, say properties to a disk file, is transactional logic (even if you don't need an explicit transaction to do it). It would be one of the end-user features of your system, not part of the architecture -- it would be a feature (even if the end user, in this case, is a sys-admin). Spring has little support for this type of behaviour -- just as it has little support for storing information regarding dynamic changes to the application context.
Using properties like this supposed it read-only. If you need some managing with it, you should better write you custom service with pure java properties handling http://www.mkyong.com/java/java-properties-file-examples/
Related
Background : I don't want to hardcode properties in a java constant file, coz every time I want to change to one of the property_value, I have to build and deploy the entire code again. I don't even want to keep them in application.yaml/application.properties file, coz my properties are huge in numbers(100s). So, I have decided to maintain properties in a properties table in oracle DB.
I can think of two approaches :
Read the property value as and when required by firing a sql query.
Load all/part of the properties at the time of starting application and have global point of access by caching them.
As I need few of the properties in the beginning itself, I want to go with approach number 2.
I wanted to go for singleton bean, but this requires me to know all of the keys(property_names) in the beginning itself, and makes the singleton look ugly having 100s of member variables. Here I was planning to fire query by using pre-construct function of spring bean. The main problem here is the bean requires to be changed every time I add/delete properties from the properties table.
Another approach I could think of was to go with a Map<String,String> as both the property_name and property_value columns of my table are of VARCHAR type. But the question is how can I get global point of access to this map ?
Any better approaches much appreciated!
Many thanks in advance
If you deploy your app on web server you can take advantage of it. Many of web server supports changing configuration on the fly (using web console) such as JBoss EAP.
The other idea is to build your own properties lib. Create a function which read the data. I'd prefer using NoSQL database than RDBMS because of lightweight, great performance and scale very well. I wouldn't use caching unless it persisted somewhere and good on availability.
I've heard about Spring Cloud Config to externalize configuration but i never deep dive into it.
Some of us uses Apache Commons Configuration that support properties reload. Take a look at this thread.
What is the best procedure for storing configuration data?
I have several classes that require some configuration data that is only needed in their class.
Should I load all this data from a configuration file or should I hardcode it into the classes?
Many thanks in advance
To address your question:
Should I load all this data from a configuration file or should I hardcode it into the classes?
Basically if you hard code some value into the class, you don't intend to change that value in different environments. Each such a change would require re-compilation of the project.
For example if you have a constant for PI=3.14 it doesn't make sense to use different values for different environments.
Alternatively if you go with configuration files, the update of such a file that can be supplied with a deployment script is much easier.
An example of this can be a host/port of the database. Development might use one host, production might use another.
So you should decide what works for you best.
This is common for all types of applications (not only spring boot driven).
Now its true that in spring boot you can create a configuration file (properties or yaml) and place it into the artifact (by putting it into src/resources/ or src/resources/config).
For some situations its good enough, for others you might use another way of configuration.
I don't refer managing secrets here, this is a more advanced stuff, but in general you won't want to manage things like passwords neither in the source code (hard coded) nor in the configuration file.
I'm new to Spring and DI in general. But from what I have read, DI affords you the ability to swap out implementations very easily using frameworks like Spring. I can understand value there when it comes to XML bean configuration because code doesn't need to be changed at all for accomplishing switchable implementations. But if we're using annotations like #Autowired or #Qualifier...we would need to change the code. So why do we want to use annotations over XML-based configuration?
This was actually a topic of lively conversation around the time that Spring 3.0 came out in 2009 and JavaConfig was added to the core system base.
In theory, being able to externalize application setup is a great thing. However, it turns out that in practice there are two distinct groups of setup choices: the application shape or dependency graph, and particular values like API keys, database connection strings, and so on that vary between environment but usually don't change the way that the beans are wired.
Experience has shown that the dependency graph, which is essentially what you'd express in XML, is almost never changed without also making changes to the accompanying implementation code anyway, so there is very little real-world benefit to defining the graph in XML. On the other hand, writing #Bean methods in Java means that it's a lot easier to test configuration when needed, the compiler can ensure type safety, and decision logic (such as conditionals) are simpler to implement.
Furthermore, the availability of annotations means that it's possible to extend the domain-specific language for configuration fairly easily in Java--just create a new annotation and its accompanying processor (such as #ConditionalOnProperty); Spring Boot itself is an extreme example of the flexibility of this model. In XML, on the other hand, injecting new tags or attributes into a schema is a lot more of a hassle.
There are times when XML may still be the better choice (I've particularly gone with it for writing out Spring Integration pipelines, which can be easier to read in XML than in the Java DSL), but the real-world benefits turned out not to be all that valuable in most cases, and the safety and flexibility of configuration as code has won out.
This is not must, you have to choices to use Annotations or XML its up to you but Annotations is easy to use, faster and more readable than configurations, and when you use it you will find all the information in a single file, but it also have disadvantages.
Annotations preferable
Use Annotations in anything that is stable and defines the core
structure of the application. Anything that would need a code change
is okay to sit as an annotation.
I recommended you to read the following links for more info :
xml-configuration-versus-annotation-based-configuration
spring-framework-xml-vs-annotations
I haven't been able to find any good examples, or a direction to go for this. But essentially I want to be able to create a configurable object to object mapping interface. I don't want to hardcode the fields that should be mapped to one another, but rather give users an interface to be able to say fieldA from objectA maps to fieldB from objectB.
These configuration settings can be persisted in SQL, or an XML file, doesn't really matter to me. This is a Spring Boot application.
I was using Orika for the mapping currently, but I don't know how to make it configurable. Am I on the right track, or does it not have that capability? Would a CustomMapper be what I need to do? Looking for some good examples, or the right direction.
You can give Dozer a try. It provides full automation of mapping process and allows handling of complicated mapping cases. Usually, all this flexibility comes at a price of reduced performance, but is maybe good enough in your case.
Mappings are usually set using XML files. In later versions, Dozer also supports mappings via API and via Annotations. Check their website for more info. Dozer also has a Spring framework integration.
When I look at Java frameworks like Hibernate, JPA, or Spring, I usually have the possibility to make my configuration via an xml-file or put annotations directly in my classes.
I am cosistently asking myself what way should I go.
When I use annotations, I have the class and its configuration together but with an xml I get a bigger picture of my system because I can see all class-configurations.
Annotations also get compiled in some way I guess and it should be quicker than parsing the xml, but on the other hand, if I want to change my configuration I have to recompile it instead of just changing the xml file (which might become even more handy for production environments on customer side).
So, when looking at my points, I tend to go the xml-way. But when looking at forums or tutorials usually annotations are used.
What are your pros and cons?
A good rule of thumb: anything you can see yourself wanting to change without a full redeploy (e.g. tweaking performance parameters) should really go in something "soft-configurable" such as an XML file. Anything which is never realistically going to change - or only in the sort of situation where you'll be having to change the code anyway - can reasonably be in an annotation.
Ignore any ideas of performance differences between annotations and XML - unless your configuration is absolutely massive the difference will be insignificant.
Concentrate on flexibility and readability.
If you're writing an API, then a word of warning: Annotations can leak out into your public interface which can be unbelievably infuriating.
I'm currently working with APIs where the API vendor has peppered his implementation with Spring MBean annotations, which suddenly means I have a dependency upon the Spring libraries, despite the possibility I might not need to use Spring at all :(
(Of course, if your API was an extension to Spring itself, this might be a valid assumption.)
I think the decision comes down to 'lifecycle', and impedance mismatch between lifecycles.
Lifecycle: Every piece of data, whether its source code, a database row, a compiled class, an object, has a lifecycle associated with it. When does it come into existence and when is it garbage collected?
Suppose I put Hibernate annotations on a Java class. Seems like a reasonable idea, especially if I am creating a new database from scratch and am confident that only this one application will ever connect to it - the lifecycles of my classes, the database schema and the ORM mapping are naturally in sync.
Now suppose I want to use that same class in an API and give it to some third party to consume. The Hibernate annotations leak into my API. This happens because the lifecycle of that class and the database are not the same thing. So we end up using mapping tools to translate between layers of beans in a system.
I try to think about lifecycles and that annotations that can cause lifecycle mismatches should be avoided. Some annotations are relatively harmless in this respect, and some are a hidden danger.
Examples of bad annotations: ORM mapping, database configuration, hard coded config for items that may vary between deployment environments, validations that may vary depending on context.
Examples of harmless annotations: REST endpoint definitions, JSON/XML serialization, validations that always apply.