Automatically Cloning a Wildfly Instance Using Chef

As we have started moving to a service based architecture, we have been developing processes to create and configure our infrastructure in a predictable and repeatable way using Vagrant and Chef.  One challenge that we have faced is trying to replicate a production Wildfly server on a dev box, including the applications are installed on it and their correct versions.

Ideally, we’d like the developer to be able to specify which server they want to clone when kicking off the Chef process.  Chef would then create a new Wildfly instance and download and install all the web applications running on the specified instance.

The first question Chef will need to know, is “what what Wildfly servers are running on the network?”  The next question is then, “which applications, and what versions are installed on those servers?”

In order to answer these questions, we developed a “WildflyMonitor” web application which is installed on each of our Wildfly instances.  The application will collect information about the local Wildfly instance that it’s running on, including the names and versions of the hosted apps, and publish that information to our messaging system.  This information eventually makes it into our Wildfly Registry DB, where it is collected and organized by Wildfly instance.

A rough diagram of the architecture appears below.

WildflyRegistry

In the example, there are 3 Wildfly instances, lisprod01, 02, and 03, which are reporting their applications to the registry. The table below the DB illustrates how the data is organized by server, and then by applications, with each Wildfly instance is running 2 applications.    The WildflyRegistry REST service then makes this information available to any client on the network, including Chef recipes.

 

The next step is then to modify the Chef script


require 'net/http'
require 'json'
url = 'http://lweb.lynden.com/WildflyRegistry/registry/services'
webapps = []
resp = Net::HTTP.get_response(URI.parse(url))
resp_text = resp.body
data =JSON.parse(resp_text)
servers = data
# Loop through each Wildfly server that was found
servers.each do |server|
serverName = server["serverName"]
#Is this the server we want to clone?
if serverName == cloneServer then
wildFlyApps = server["wildflyApp"]
#Loop through app on the server
wildFlyApps.each do |app|
#Create a hash of app name to app version
if app["appRuntimeName"].end_with? ".war" then
appTokens = app["appName"].split("-")
myHash = Hash[ :name, appTokens[0], :version, appTokens[1]]
webapps.push(myHash)
end
end
end

view raw

getAppNames.rb

hosted with ❤ by GitHub

The snippet above shows the script contacting the REST service, looping through all the servers that were returned until the desired server to clone is found.  Once the server is found, the script loops through that server’s list of applications and creates a list of hashes with the app name mapped to its version number.

Next, the script loops through each of the apps which were discovered in the previous snippet.


webapps.each do |app|
url = "http://nexus.lynden.com/repo/com/lynden/" + app[:name] + "/" + app[:version] + "/" + app[:name] + "-" + app[:version] + ".war"
puts "deploying " + app[:name] + "-" + app[:version]
fullFileNameNew = app[:name] + "-" + app[:version]
fullPath = "/tmp/" + app[:name] + "-" + app[:version]
fullPath = fullPath + ".war"
puts "Full path to apps " + fullPath
remote_file fullPath do
source url
action :create_if_missing
end
bash 'deploy_app' do
cwd '/usr/local/wildfly/bin'
command = '/tmp/deployWildfly.sh ' + fullPath
code <<-EOH
echo COMMAND #{command}
#{command}
EOH
end
end

view raw

deploy.rb

hosted with ❤ by GitHub

 

First the script constructs the URL to the web app in our Nexus repository. The script then downloads each web app to the tmp folder on the server.  The script then calls a shell script which deploys the applications to Wildfly utilizing the Wildfly command line interface.

The shell script which is called by Chef to perform the actual deployment to Wildfly is fairly straightforward and appears below.


!/bin/sh
FILENAME=$1
PATH=$PATH:/usr/local/java/bin
cd /usr/local/wildfly/bin
./jboss-cli.sh -c –user=myUser –password=myPassword –command="deploy $FILENAME"

 

That’s it, based on the data in our WildflyRegistry we are able to use this Chef script and shell script to create a clone of an existing Wildfly instance running on our network.

 

 

2 thoughts on “Automatically Cloning a Wildfly Instance Using Chef

  1. This is a great blog, thanks for referencing our Nexus product! We’d like to publish this on our community page. If you’re interested, let’s get in touch. Hope to hear from you soon!

    • Sure, I’d have no problem if you would like to publish this on your community page. Let me know what info you would need.

      Thanks,
      -Rob

Leave a Reply