{
    "componentChunkName": "component---src-templates-blog-post-tsx",
    "path": "/blog/2011-01-06-wrapping-each-hudson-distribution-in-its-own-rubygem/",
    "result": {"data":{"blogPost":{"title":"Wrapping each Hudson distribution in its own RubyGem","slug":"/blog/2011-01-06-wrapping-each-hudson-distribution-in-its-own-rubygem/","authorNodes":[{"name":"Charles Lowell","slug":"/people/charles-lowell/"}],"markdown":{"html":"<blockquote>\n<p><em><strong>Update</strong></em>: As of version <code class=\"language-text\">1.396</code>, this is applicable to the <a href=\"http://jenkins-ci.org\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">Jenkins</a> project.\n<code class=\"language-text\">1.395</code> will be the last version of the hudson-war gem</p>\n</blockquote>\n<p>As you may or may not know, we here at The FrontSide have been working since\nlate last year to create a proper ruby environment for extending hudson. This\nis no mean feat because it implies not only the ability to use nothing but ruby\n<em>code</em> to implement hudson plugins, but just as importantly, the ability to use\nnothing but ruby <em>tools</em> to develop them. That means no javac, no\n<a href=\"http://en.wikipedia.org/wiki/Jar_file\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">jar files</a>, no <a href=\"http://en.wikipedia.org/wiki/WAR_%28Sun_file_format%29\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">war files</a>, and for the love of all that is holy: <a href=\"http://kent.spillner.org/blog/work/2009/11/14/java-build-tools.html\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">absolutely,\npositively, no maven</a>. In short, the only folks you'll need to know to get in\nthe door with Hudson are your pals Ruby, Rake and Bundler.</p>\n<p>Of course, all those jars and wars and perhaps some class generation will be\nthere behind the scenes. After all, we'll still need to compile java stubs that\ndepend on core Hudson classes. We'll still need to package your plugin along\nwith its ruby code and dependencies in a jar file, and we'll still need to take\ncare of all the blah, blah, MANIFEST, blah, META-INF, WEB-INF, blah, blah, blah...</p>\n<h2 id=\"the-war\" style=\"position:relative;\"><a href=\"#the-war\" aria-label=\"the war permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>The War</h2>\n<p>If we're going to do the compilation against Hudson core from within ruby and\nRake instead of maven, then we're going to need a reliable way to get at the\ncore hudson classes so that we can use them in our compilation classpath. Not\nonly that, but as part of the development process, you're going to want to test\nyour plugins against a fully functioning hudson server. Luckily, both of these\nare contained in the full hudson distribution that you download as a single\nwar file. Wouldn't it be nice if you had a simple way to get at a specific\nversion of one of those wars and then get at all those java goodies contained\ntherein?</p>\n<h2 id=\"the-gem\" style=\"position:relative;\"><a href=\"#the-gem\" aria-label=\"the gem permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>The Gem</h2>\n<p>To my thinking, this sounds like a job for: RubyGems! That's why we're introducing\nthe new <a href=\"https://rubygems.org/gems/hudson-war\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">hudson-war</a> gem, which does nothing except wrap a single hudson\ndistribution so that it can be managed coherently just like any other ruby\ncomponent. Want the latest warfile?</p>\n<div class=\"gatsby-highlight\" data-language=\"text\"><pre class=\"language-text\"><code class=\"language-text\">gem install hudson-war</code></pre></div>\n<p>Or perhaps you need hudson 1.386? That's fine, hudson-war versions are the same\nas the hudson distributions they wrap.</p>\n<div class=\"gatsby-highlight\" data-language=\"text\"><pre class=\"language-text\"><code class=\"language-text\">gem install hudson-war --version 1.386</code></pre></div>\n<p>It's not just a war file either. In keeping with the best traditions of OOP\ndata comes bundled with behavior. The gem comes with a ruby API and a CLI baked\nin to help us do all the nifty things we might want to do with a war file.\nFor starters, you might want to know where it is.</p>\n<div class=\"gatsby-highlight\" data-language=\"text\"><pre class=\"language-text\"><code class=\"language-text\">legolas:~ cowboyd$ hudson.war location\n/Users/cowboyd/.rvm/gems/ruby-1.8.7-p174/gems/hudson-war-1.386/lib/hudson/hudson.war</code></pre></div>\n<p>If you want to unpack it to a particular location then</p>\n<div class=\"gatsby-highlight\" data-language=\"text\"><pre class=\"language-text\"><code class=\"language-text\">legolas:~ cowboyd$ hudson.war unpack tmp\njar xvf /Users/cowboyd/.rvm/gems/ruby-1.8.7-p174/gems/hudson-war-1.386/lib/hudson/hudson.war -C tmp/</code></pre></div>\n<p>You can run a test server with it</p>\n<div class=\"gatsby-highlight\" data-language=\"text\"><pre class=\"language-text\"><code class=\"language-text\">legolas:~ cowboyd$ hudson.war server --daemon\nForking into background to run as a daemon.\nUse --logfile to redirect output to a file\nlegolas:~ cowboyd$ hudson.war server --kill</code></pre></div>\n<p>Beyond the basics, let's say you want to do something interesting like compile\nsome java code against the hudson core. You're gonna need a classpath, and you\ncan get it with:</p>\n<div class=\"gatsby-highlight\" data-language=\"text\"><pre class=\"language-text\"><code class=\"language-text\">legolas:~ cowboyd$ hudson.war classpath\n/Users/cowboyd/.hudson/wars/1.386/WEB-INF/lib/hudson-core-1.386.jar</code></pre></div>\n<p>You can even compile java code with it directly. Here we compile a trivial\nclass that has a dependency on hudson.</p>\n<div class=\"gatsby-highlight\" data-language=\"text\"><pre class=\"language-text\"><code class=\"language-text\">legolas:~ cowboyd$ cat > ImportsHudson.java\nimport hudson.model.Hudson;\npublic class ImportsHudson {\n  public static void main(String args[]) {\n    System.out.printf(\"The Hudson Model object's class is %s\\n\", Hudson.class.getName());\n  }\n}\nlegolas:~ cowboyd$ hudson.war javac ImportsHudson.java\nlegolas:~ cowboyd$ java -cp .:`hudson.war classpath` ImportsHudson\nThe Hudson Model object's class is hudson.model.Hudson</code></pre></div>\n<p>It's like RVM for hudson. Wrangling java has never been so fun!</p>\n<h2 id=\"the-war-gemmer\" style=\"position:relative;\"><a href=\"#the-war-gemmer\" aria-label=\"the war gemmer permalink\" class=\"anchor before\"><svg aria-hidden=\"true\" focusable=\"false\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>The War Gemmer</h2>\n<p>Befitting a continuous integration project, the Hudson team releases a new\nversion at least every two weeks, and sometimes even sooner. It can be a bitch\nto keep up with, so I've set up a\n<a href=\"http://github.com/cowboyd/hudson-wargemmer\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">wargemmer hudson</a> task to\nperiodically poll the update center to see if there is a new release. If there\nis, it'll gem it right up and push it to rubygems. No fuss no muss.</p>\n<p>Let the war begin!</p>","frontmatter":{"date":"January 06, 2011","description":null,"tags":["ruby","hudson","java","jenkins"],"img":null}}}},"pageContext":{"id":"909d1cce-a530-54e5-987c-028813e0f18b"}},
    "staticQueryHashes": ["1241260443"]}