What should be the strategy to migrate configuration files to new version? - java

I understand this is question is completely implementation dependent, but would like to know the general strategy used to migrate the configuration files.
We have a product that reads some configurations from properties/XML files. Some default values are configured in the properties file. Customer can change the properties as per his needs. Now suppose we change/add some properties in the file and customer migrates to newer version. How should we merge the customer specific configuration with newly added/updated properties? One way is to write a utility to merge the files, but dont want to do it for every release.
Thanks in advance

We have a configuration inheritance schema. Within development we have:
BaseSetup <- Setup <- DevelopmentSetup <-- StagingSystemSetup
|- DeveloperMikeSetup
|- DeveloperSusySetup
So the demonstration server runs with the setup StagingSystemSetup which inherits from the general DevelopmentSetup, etc. Also each developer has its own configuration/setup, which is also checked in. This means everybody can change its configuration as needed, without interfering others.
On production/customer just the setup is used without specialication, but that is the setup provided by the customer, which inherits from the basic setup.
If we introduce and enable a new feature we only need to modify the base setup. Ideally, forced setup changes by the customer should not happen.

I'd say it's all documentation. I won't bother with a migration tool. You surely have documentation of your software. Include the configuration changes in that documentation. It's the responsibility of your customer to read the change log and apply those configuration changes. If a missing new configuration is essential and has no reasonable default value the error message should clearly point the customer to the missing configuration. OTH if the missing configuration has a default value a warning in the log might be helpful.

Related

How to use log4j2 in the web application WITHOUT log4j-web.jar

I want to put the configuration file of the log4j2 (v2.17.0) outside of the war file. Therefore, I can change the logging configuration without redeploying the war file. The log4j2-web.jar provides mechanism to configure the configuration file outside of the war file along with other features.
Unfortunately, I am not allowed to use the log4j-web.jar file in web application.
According to the log4j2 FAQ, it is not recommended to use LoggerContext to load configuration file because it is not part of the public API.
Question:
Is there any valid way to use log4j2 in the web application without log4j-web.jar file?
Question: Is there any valid way to use log4j2 in the web application without log4j-web.jar file?
There are two potential ways that you could dynamically update the logging configs without using log4j2-web.jar .
Ignore the FAQ's recommendation1 and use LoggerContext.reload to reload the configuration.
It is possible that the Log4j2 team could change something in a future version so that this approach no longer works. But this is unlikely (IMO) ... and you can deal with that problem if / when it happens.
Use Log4j2's automatic reconfiguration mechanism. Basically, you tell Log4j2 to regularly check the config file to see if it has changed.
However ...
If I was you, I would want to understand why you are "not allowed" to use "log4j-web.jar". Is it for security reasons? If it is, you may need to talk to the security people so that you fully understand the security reasons.
Q: Why?
A: Because you appear to be wanting to duplicate some of the functionality of "log4j-web.jar". It may be that it is the functionality you are trying to duplicate that is the root of your security team's concerns. And if that is the case, then implementing the functionality by hand (i.e. without using "log4j-web.jar") could potentially be worse ... from a security perspective!
So ... find out! This is NOT a case where "asking for forgiveness rather than for permission" is a sound strategy.
1 - Actually, I don't read this as a "recommendation". Rather, I read it as a "warning of potential consequences". If they really thought that using LoggerContext.reload this was a bad idea, I think they would have used more explicit language.

What is the point of creating external configuration file in spring boot?

I am new to spring. But here a concept is confusing me and am also not getting a clear answer. I am not sure what is the point of creating an external configuration file? Like, what is the point of application.properties ? We can also use the features via code right? Also, if we make a change to the configuration file then we also have to rerun the application right? Then what is the point of doing such a thing?
Thanks in advance.
The point of application.properties is to be able to change some properties without re-compiling your code. So in big companies no QA phase, delivery needed
You just change some properties, restart the application and ready to go.
The application.properties or application.yml file contains the environment variables. This is quite similar with constants in your application. The importance of externalizing it is to minimize updating the source code when some configuration changes.
Example: Your app's database migrated to another server.
You can just update your application.properties file instead of opening your DBConfig.java.
Another benefit is if your team is using Spring Cloud Config Server where your app connects and fetches the testing/staging/production configurations. This means that your configurations are not tightly coupled into your app's source code.
Whereas if you do it directly into your source code, then every time there's a change in the configuration (be it database connection, connection to other services, etc) you'll have to update your code then rebuild and deploy.

How to create spring configuration the easy way

Is there any way to create the spring configuration more easily? I mean if I want to create a spring+hibernate project then there should be some wizard which asks location of the DAO file, Service file, Controller and then the wizard will automatically create all these classes with required annotations. In this way we will not forget to type any annotations or need to keep track of so many classes. Besides there could be some dialog which would allow to input the value of different configuration parameters such as connection URL, user name, etc so that I don't have to type and misspell any configuration parameter name. For instance, instead of having to type "hibernate.dialect" there could be a drop down list from where we can select the all available dialects. I am not sure whether this kind of tool or plugin exists. I think it would make things super fast to deploy because much time is wasted for fixing configuration issues even for experienced developer.
Please let me know whether any such tool exists.
Thanks
You can use Spring initializer in order to generate the skeleton for your project, with the relevant spring dependencies.
Aside from that, you can try looking for some maven archetypes that might meet your needs (look here)

Is it possible to add custom metadata to .class files?

We have used liquibase at our company for a while, and we've had a continuous integration environment set up for the database migrations that would break a job when a patch had an error.
An interesting "feature" of that CI environment is that the breakage had a "likely culprit", because all patches need to have an "author", and the error message shows the author name.
If you don't know what liquibase is, that's ok, its not the point.
The point is: having a person name attached to a error is really good to the software development proccess: problems get addressed way faster.
So I was thinking: Is that possible for Java stacktraces?
Could we possibly had a stacktrace with peoples names along with line numbers like the one below?
java.lang.NullPointerException
at org.hibernate.tuple.AbstractEntityTuplizer.createProxy(AbstractEntityTuplizer.java:372:john)
at org.hibernate.persister.entity.AbstractEntityPersister.createProxy(AbstractEntityPersister.java:3121:mike)
at org.hibernate.event.def.DefaultLoadEventListener.createProxyIfNecessary(DefaultLoadEventListener.java:232:bob)
at org.hibernate.event.def.DefaultLoadEventListener.proxyOrLoad(DefaultLoadEventListener.java:173:bob)
at org.hibernate.event.def.DefaultLoadEventListener.onLoad(DefaultLoadEventListener.java:87:bob)
at org.hibernate.impl.SessionImpl.fireLoad(SessionImpl.java:862:john)
That kind of information would have to be pulled out from a SCM system (like performing "svn blame" for each source file).
Now, forget about trashing the compilation time for a minute: Would that be even possible?
To add metadata to class files like that?
In principle you can add custom information to .class files (there's and attribute section where you can add stuff). You will have to write your own compiler/compiler extension to do so. There is no way to add something to your source code that then will show up in the class file.
You will also have major problems in practice:
The way stack-traces a built/printed is not aware of anything you add to the class file. So if you want this stuff printed like you show above, you have to hack some core JDK classes.
How much detail do you want? The last person who committed any change to a given file? That's not precise enough in practice, unless files are owned by a single developer.
Adding "last-committed-by" information at a finer granularity, say per method, or even worse, per line will quickly bloat your class file (and class files are limited in size to 64K)
As a side note, whether or not blaming people for bugs helps getting bugs fixed faster strongly depends on the culture of the development organization. Make sure you work in one where this helps before you spend a lot of time developing something like this.
Normally such feature can be implemented on top of the version control system. You need to know revision of your file in your version control system, then you can call blame/annotate command to get information on who has changed each individual line. You don't need to store this info into the class file, as long as you can identify revision of each class you deploy (e.g. you only deploy certain tag or label).
If you don't want to go into the version control when investigating stack trace, you could store line annotation info into the class file, e.g. using class post processor during your build that can add a custom annotation at the class level (this is relatively trivial to implement using ASM). Then logger that prints stack trace could read this annotation at runtime, similarly to showing jar versions.
One way to add add custom information to your class files using annotations in the source code. I don't know how you would put that information reliably in the stack trace, but you could create a tool to retrieve it.
As #theglauber correctly pointed out , you can use annotations to add custom metadata. Althougth i am not really sure you if you cant retrieve that information from your database implementing beans and decorating your custom exceptions manager.

Is it possible to check that class exists while editing Spring XML files?

I use Spring with long xml files for beans.
Is it possible at edit time to check if the names of the classes are correct and all references exist?
Try using STS, customized eclipse IDE with plugins, from Springsource. It have even auto-completion, error-checking features for writing spring's configuration(bean.xml) files.
UPDATE
For further details & features: Features of STS
As others have mentioned, this is the responsibility of an IDE before application runtime, or a simpler class that attempts to load the configuration if spinning up the app is cost-prohibitive.
The major IDEs (Elipse, NetBeans, and Intellij) all have strong Spring support. This includes class completion, jumping between config file usage(s) and definition, gutter marks to indicate a class is a Spring bean, etc.
Many Spring supported IDEs make suggestion of what the class name should be during editing. For example, Netbeans suggests this while you are typing the class names or other known attributes. However, it cannot be forced to check whether the class names you use really exist.
Without additional coding effort (for example writing your own xml editor), I do not think so. That's why annotations have been invented. You can move your configuration from xml files to annotated Java classes and methods. Then your compiler will do the work automatically.

Categories

Resources