Ivysettings.xml
In my last project I was introduced to Ivy and Ant working together to handle library dependencies. Since Ant does not have a native automatic dependency resolution built in, we had to incorporate Ivy into the picture to manage all the necessary files for the code to compile. If you want to read more about how to use Ivy and Ant together please read the blog from my colleague Glenn Buckholz called Ivy – Ant Dependency Bolt On
Once you have Ant and Ivy setup, you will notice that every module on your project will have to have its own ivysettings.xml file (sample below). It holds information like repository location, username and password to repository, resolvers for dependencies, external dependency information, etc. This xml holds a lot of vital information to make sure your modules pull correct dependencies and build. However, a lot of information in this file is repetitive and can be seen in other modules. Unless, you have multiple Artifact Repository Managers, repository hostname, username, password, etc. will be the same across different modules of this project.
<ivysettings> <settings defaultResolver="archiva" defaultBranch="" latest="latest-compatible" /> <credentials host="archiva" realm="Repository Archiva Managed releases Repository" username="build" passwd="build12345" /> <credentials host="archiva" realm="Repository Archiva Managed integration-releases Repository" username="build" passwd="build12345" /> <credentials host="archiva" realm="Repository Archiva Managed thirdparty Repository" username="build" passwd="build12345" /> <property name="archiva-public" value="http://archiva:8080/archiva/repository/public/"/> <property name="archiva-releases" value="http://archiva:8080/archiva/repository/releases/"/> <property name="archiva-integration-releases" value="http://archiva:8080/archiva/repository/integration-releases/"/> <property name="archiva-snapshots" value="http://archiva:8080/archiva/repository/snapshots/"/> <resolvers> <ibiblio name="archiva" m2compatible="true" useMavenMetadata="false" root="${archiva-public}" /> <filesystem name="snapshot-local" checkmodified="true"> <ivy pattern="${basedir}/../repo/[branch]/[organisation]/[module]/[revision]/[artifact]-[revision].[ext]" /> <artifact pattern="${basedir}/../repo/[branch]/[organisation]/[module]/[revision]/[artifact]-[revision].[ext]" /> </filesystem> <ibiblio name="archiva-releases" m2compatible="true" root="${archiva-releases}" /> <ibiblio name="archiva-integration-releases" m2compatible="true" useMavenMetadata="false" root="${archiva-integration-releases}" pattern="[branch]/[organisation]/[module]/[revision]/[artifact]-[revision].[ext]" /> <chain name="archiva-chain"> <filesystem name="snapshot-local" checkmodified="true"> <ivy pattern="${basedir}/../repo/[branch]/[organisation]/[module]/[revision]/[artifact]-[revision].[ext]" /> <artifact pattern="${basedir}/../repo/[branch]/[organisation]/[module]/[revision]/[artifact]-[revision].[ext]" /> </filesystem> <ivyrep name="archiva-chain-integration-releases" ivypattern="" ivyroot="${archiva-integration-releases}" /> <ivyrep name="archiva-chain-release" ivyroot="${archiva-releases}"/> <url name="chain2-releases" m2compatible="true" > <ivy pattern="${archiva-releases}/[branch]/[organisation]/[module]/[revision]/ivy-[revision].xml" /> <artifact pattern="${archiva-releases}/[branch]/[organisation]/[module]/[revision]/[artifact]-[revision].[ext]" /> </url> <url name="chain2-integration-releases" m2compatible="true" > <ivy pattern="${archiva-integration-releases}/[branch]/[organisation]/[module]/[revision]/ivy-[revision].xml" /> <artifact pattern="${archiva-integration-releases}/[branch]/[organisation]/[module]/[revision]/[artifact]-[revision].[ext]" /> </url> </chain> </resolvers> <modules> <module organisation="org.test" name="MODULE1" matcher="regexp" resolver="nexus-chain"/> <module organisation="org.test" name="MODULE2" matcher="regexp" resolver="nexus-chain"/> <module organisation="org.tes" name="MODULE3" matcher="regexp" resolver="nexus-chain"/> </modules> </ivysettings>
Now imagine that you have 100 modules on your project and Each one of them contains ivysettings.xml file. If for some odd reason someone decides to rename your repository manager or password for the user that accesses it that repository you will have to go into each file and make that change. Sounds like a lot of work for such a small change and I guarantee no one would want to volunteer for this job. Instead of going through all that trouble we can create a common settings file that can hold common properties which are being used across the board. Here is an example below:
<ivysettings> <settings defaultResolver="archiva" defaultBranch="" latest="latest-compatible" /> <credentials host="archiva" realm="Repository Archiva Managed releases Repository" username="build" passwd="build12345" /> <credentials host="archiva" realm="Repository Archiva Managed integration-releases Repository" username="build" passwd="build12345" /> <credentials host="archiva" realm="Repository Archiva Managed thirdparty Repository" username="build" passwd="build12345" /> <property name="archiva-public" value="http://archiva:8080/archiva/repository/public/"/> ... <url name="chain2-integration-releases" m2compatible="true" > <ivy pattern="${archiva-integration-releases}/[branch]/[organisation]/[module]/[revision]/ivy-[revision].xml" /> <artifact pattern="${archiva-integration-releases}/[branch]/[organisation]/[module]/[revision]/[artifact]-[revision].[ext]" /> </url> </chain> </resolvers> </ivysettings>
Since a lot of information is standard for every module, we are able toput it in a single file that every module can access. Now we have ivysettings-common.xml file that we can utilize in all of our modules and to do that we can just write the following line:
<include url="../MAIN/ivysettings-common.xml"/>
With this 1 line of code you import all properties from that file. So now you have a centralized location to manage your Artifact Repository specific properties. Any time you need to make a change to a property, you can be done with just 1 commit. This is especially useful if you have strict password reset policies or if you want to switch from localhost to a proxy server to route your requests.