<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet href="http://feeds.feedburner.com/~d/styles/rss2full.xsl" type="text/xsl" media="screen"?><?xml-stylesheet href="http://feeds.feedburner.com/~d/styles/itemcontent.css" type="text/css" media="screen"?><rss xmlns:geo="http://www.w3.org/2003/01/geo/wgs84_pos#" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:media="http://search.yahoo.com/mrss/" xmlns:yt="http://gdata.youtube.com/schemas/2007" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">
   <channel>
      <title>Sonatype Blogs</title>
      <description>Pipes Output</description>
      <link>http://pipes.yahoo.com/pipes/pipe.info?_id=Mhp4qJin3RGmfOqJBB50VA</link>
      <pubDate>Fri, 21 Nov 2008 05:28:58 -0800</pubDate>
      <generator>http://pipes.yahoo.com/pipes/</generator>
      <atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" href="http://feeds.feedburner.com/sonatype" type="application/rss+xml" /><item>
         <title>Announcing Nexus Maven Repository Manager Pro Beta</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/459888599/</link>
         <description>The Nexus team has been hard at work producing a new plugin model for Nexus that allows us to create some new and exciting Professional features on top of the OSS core. The first release of Nexus Pro will contain 4 new plugins:
Staging and Promotion
Staging
and promotion is designed to allow projects to be deployed to [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/brian/2008/11/20/announcing-nexus-maven-repository-manager-pro-beta/</guid>
         <pubDate>Thu, 20 Nov 2008 09:38:29 -0800</pubDate>
         <content:encoded><![CDATA[<p>The Nexus team has been hard at work producing a new plugin model for Nexus that allows us to create some new and exciting Professional features on top of the OSS core. The first release of Nexus Pro will contain 4 new plugins:</p>
<p><strong>Staging and Promotion</strong></p>
<p>Staging<br />
and promotion is designed to allow projects to be deployed to independent, temporary repositories. The contents of this repository is then evaluated and eventually either promoted or deleted. When<br />
promoted, it is merged in with a target repository and all appropriate metadata is updated. This implementation of Staging and Promotion requires no changes on the Maven side other than updating your distributionManagementUrl.</p>
<p>Staging works by defining a new url that is used for all deployments. Profiles can be created in Nexus to determine how artifacts are staged. The profile specifies name and id templates for the temporary staging repo, which groups will automatically contain the repository, and who to notify when the staging is complete.</p>
<p>When a new deployment occurs, Nexus selects the profile based on the artifact type (snapshot or release) and the repository target (regex on the artifact path). Nexus then notes the user and ip doing the deployment and makes a new staging repository instance to hold the artifacts from this build. This allows multiple parallel deployments to occur simultaneously and the artifacts are placed in independent repositories. When the staging is finished, the user goes to the Nexus UI and closes the repository to new artifacts. An authorized user can then later decide to promote or drop this repository. When the promotion is selected, the user selects a destination repository, and Nexus then merges the contents automatically, updating the metadata along the way.</p>
<p>Future enhancements include a maven side plugin to automatically start and stop staging based on a unique build id, workflow extensions for automatic handling of staging promotion and verification (ie tie into CI and other metrics), and vote based decisions on promotion.</p>
<p><strong>Procurement</strong></p>
<p>Procurement is designed to create a secured, hosted repository that contains all artifacts needed for a build that is controlled to allow only approved artifacts. Enterprises currently typically operate in one<br />
of two modes:<br />
1) Developers have free access to repositories, but QA, CI and official builds are performed against a manually populated hosted repository.<br />
2) Developers are completely blocked from external repos and only have access to a manually populated hosted repository. We&#8217;ll call this &#8220;Ask First&#8221;</p>
<p>In either mode, the artifacts must be manually loaded into the sanctioned repository. This is tedious and error prone. Many of the artifacts are required only for the build itself (org.apache.maven.*) yet they must still be manually populated.</p>
<p>The Procurement repository is a new type of repository. The repository is associated with another internal target, either a repository or a group. An authorized user is able to browse the internal target and selectively approve artifacts. They may be approved by groupId with wildcard, group and artifact, and group, artifact and version. When a request is made against the repository the current<br />
contents are served. If the requested artifact doesn&#8217;t exist, it will be retrieved from the target only if the rules explicitly allow it. Allowing the wildcard solves the problem of constantly having to approve build only artifacts like org.apache.maven.*</p>
<p>In a normal scenario, the developers may be configured to build against a group containing their required repositories. The qa and/or the CI system would be configured against a Procurement repo using the developer repository group as the internal target. This would allow developers easy access to the artifacts required, but still provide control over the artifacts used in official builds. If desired, the developers may also be shielded by the Procurement repository, which would put them in &#8220;Ask first&#8221; mode where things must be pre-approved before they can use them.</p>
<p>The Procurement repository is treated like a hosted repository in a way that excludes it from scheduled tasks that may remove artifacts accidentally. This is done to maintain a higher level of integrity and reproducibility.</p>
<p>Future enhancements include the ability to automatically approve based one license, the ability to approve an artifact and all transitive dependencies in a single operation, and taking a physical snapshot of the state of a Procurement repo for later reproducibility and tracing.</p>
<p><strong>LDAP Authentication &amp; Authorization</strong></p>
<p>The LDAP functionality supports two modes:</p>
<p>1) User/Pass is stored in LDAP only. This means that the normal user to role association is preserved and we only hit ldap for authentication.</p>
<p>2)User/Pass and group is stored in LDAP. The groups are automatically to a Nexus role by id.</p>
<p><strong>P2 Repository Proxying</strong><br />
Nexus has the ability to host P2 proxy repositories. This allows traditional caching and proxying of P2 artifacts to save bandwidth and provide internal stability when provisioning P2 based artifacts such as Eclipse. </p>
<p>Future enhancements include P2 Repository grouping and Hosting.</p>
<p>We are wrapping up the testing of these new Pro plugins along with Nexus 1.2. The Professional plugins will be released to a handful of selected Beta clients first for testing and user story validation. Once that is successful, we will begin a much wider Beta program prior to the GA release, which we anticipate would occur in the Nexus 1.3 timeframe of Mid-January &#8216;09.</p>
<p>If you are interested in partaking in the Nexus Pro Beta program, please sign up <a rel="nofollow" target="_blank" href="http://www.sonatype.com/contact/nexus-beta-contact.html">here</a>.</p>
<img src="http://feeds.feedburner.com/~r/SonatypeBrian/~4/459805112" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/459888599" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/SonatypeBrian/~3/459805112/</feedburner:origLink></item>
      <item>
         <title>Searching with the Nexus REST API: Ruby</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/458564460/</link>
         <description>When you search for artifacts using http://repository.sonatype.org, the browser is querying the Nexus repository using a REST API. In this post, I&amp;#8217;m going to show you some simple Ruby scripts which you can use to search the Maven repository without loading up the Nexus web interface. You might find these scripts more convenient and more [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=255</guid>
         <pubDate>Wed, 19 Nov 2008 08:11:49 -0800</pubDate>
         <content:encoded><![CDATA[<p><img class="alignright size-thumbnail wp-image-262" src="http://blogs.sonatype.com/people/book/files/2008/11/scripting-nexus-ruby.png" alt="" width="103" height="102"/>When you search for artifacts using <a rel="nofollow" target="_blank" href="http://repository.sonatype.org">http://repository.sonatype.org</a>, the browser is querying the Nexus repository using a REST API. In this post, I&#8217;m going to show you some simple Ruby scripts which you can use to search the Maven repository without loading up the Nexus web interface. You might find these scripts more convenient and more customizable, and you should feel free to copy and modify them for your own use.</p>
<p>The following scripts are in Ruby and they use the <a rel="nofollow" target="_blank" href="http://www.ruby-doc.org/stdlib/libdoc/rexml/rdoc/index.html">REXML</a> XML processor and the <a rel="nofollow" target="_blank" href="http://www.ruby-doc.org/stdlib/libdoc/net/http/rdoc/index.html">Net:HTTP</a> library. Both of these libraries are available in the Ruby standard library. I tested these Ruby scripts using the latest <a rel="nofollow" target="_blank" href="http://jruby.codehaus.org/">JRuby</a> release. If you want to try these scripts out on your own, they will run in any standard Ruby interpreter without requiring any extra RubyGems.<span id="more-255"></span></p>
<h2>The Nexus REST API</h2>
<p>The UI of Nexus is written in ExtJS and it makes heavy use of AJAX callbacks to REST services. In fact, if you load up Nexus in a tool like Firebug, an extension for Firefox which allows you to trace all network activity, you will see that almost every action in Nexus triggers a call to a REST service. We&#8217;re going to focus on just two services in this post: list repositories and searching for artifacts, but you should know that there are hundreds of things you can do to Nexus via the various REST interfaces that are available. In fact, you could create a custom UI tailored to your own needs that interfaces with Nexus via this REST backend. In addition to the REST services in the core Nexus installation, you can extend Nexus and add in your own REST services via a Nexus plugin. The Nexus UI is completely decoupled from the set of services Nexus provides, and the services which Nexus provides can be extended.</p>
<p><a rel="nofollow" target="_blank" href="http://blogs.sonatype.com/people/book/files/2008/11/nexus-rest-arch.png"><img class="aligncenter size-full wp-image-263" src="http://blogs.sonatype.com/people/book/files/2008/11/nexus-rest-arch.png" alt="" width="386" height="201"/></a>The Nexus REST Services are <a rel="nofollow" target="_blank" href="https://docs.sonatype.com/display/Nx/Nexus+Rest+API">documented here</a>. In this post, we&#8217;re going to be writing scripts that hit the public instance of Sonatype Nexus at <a rel="nofollow" target="_blank" href="http://repository.sonatype.org">http://repository.sonatype.org</a>, our REST URLs are going to look something like this: <a rel="nofollow" target="_blank" href="http://repository.sonatype.org/service/local/data_index?q=maven">http://repository.sonatype.org/service/local/data_index?q=maven</a>. If you were attempting to hit the services on your local Nexus installation, your REST URL would look more like this: http://localhost:8081/nexus/service/local/data_index?cn=HibernateDaoSupport. These REST URLs follow the pattern: &#8220;http://{host}:{port}/{context}/service/{instance}/{service}?{query_params}&#8221; where the {instance} will almost always be &#8220;local&#8221;.</p>
<p>If you would like to download the sample scripts in this blog post, you can download this ZIP file which contains four Ruby scripts: <a rel="nofollow" target="_blank" href="http://books.sonatype.com/tutorial-files/nexus-rest-ruby.zip">http://books.sonatype.com/tutorial-files/nexus-rest-ruby.zip</a></p>
<h2>Listing Repositories</h2>
<p>The first script simply lists all of the repositories in a Nexus installation. Here it is:</p> <div class="wp_syntax"><div class="code"><pre class="ruby ruby" style="font-family:monospace;"><span style="color:#CC0066;font-weight:bold;">require</span> <span style="color:#996600;">'net/http'</span>
<span style="color:#CC0066;font-weight:bold;">require</span> <span style="color:#996600;">'rexml/document'</span>
<span style="color:#9966CC;font-weight:bold;">include</span> REXML
&nbsp;
url = <span style="color:#996600;">'http://repository.sonatype.org/service/local/repositories'</span>
resp = <span style="color:#6666ff;font-weight:bold;">Net::HTTP</span>.<span style="color:#9900CC;">get_response</span><span style="color:#006600;font-weight:bold;">&#40;</span> <span style="color:#CC00FF;font-weight:bold;">URI</span>.<span style="color:#9900CC;">parse</span><span style="color:#006600;font-weight:bold;">&#40;</span> url <span style="color:#006600;font-weight:bold;">&#41;</span> <span style="color:#006600;font-weight:bold;">&#41;</span>
&nbsp;
doc = <span style="color:#6666ff;font-weight:bold;">REXML::Document</span>.<span style="color:#9900CC;">new</span><span style="color:#006600;font-weight:bold;">&#40;</span> resp.<span style="color:#9900CC;">body</span> <span style="color:#006600;font-weight:bold;">&#41;</span>
&nbsp;
XPath.<span style="color:#9900CC;">each</span><span style="color:#006600;font-weight:bold;">&#40;</span> doc, <span style="color:#996600;">"//repositories-item"</span> <span style="color:#006600;font-weight:bold;">&#41;</span> <span style="color:#9966CC;font-weight:bold;">do</span> |r| <span style="color:#CC0066;font-weight:bold;">puts</span> <span style="color:#996600;">"#{r.elements["</span>name<span style="color:#996600;">"].text}(#{r.elements["</span>id<span style="color:#996600;">"].text})"</span> <span style="color:#CC0066;font-weight:bold;">puts</span> <span style="color:#996600;">"<span style="color:#000099;">&#92;t</span>"</span> <span style="color:#006600;font-weight:bold;">+</span> r.<span style="color:#9900CC;">elements</span><span style="color:#006600;font-weight:bold;">&#91;</span><span style="color:#996600;">"resourceURI"</span><span style="color:#006600;font-weight:bold;">&#93;</span>.<span style="color:#9900CC;">text</span> <span style="color:#006600;font-weight:bold;">+</span> <span style="color:#996600;">"<span style="color:#000099;">&#92;n</span><span style="color:#000099;">&#92;n</span>"</span>
<span style="color:#9966CC;font-weight:bold;">end</span></pre></div></div> <p>This script sets the pattern for the scripts to follow. We construct a URL in the script (a more general script would read this from a config file), then we make the request using Net::HTTP and we parse the results with REXML by passing it to the Document constructor. At this point, I use XPath to select all of the repositories and I print out the name, id, and the URL of the repository as served by Nexus.</p>
<p>This post is simply a pointer to the service and a quick demonstration so I&#8217;m not going to dive into the meaning of every single element in the XML document returned by the repositories service. If you are interested in see the full set of elements that are available, load up the results of this service in a web browser by click on this: <a rel="nofollow" target="_blank" href="http://repository.sonatype.org/service/local/repositories">http://repository.sonatype.org/service/local/repositories</a>.</p>
<h2>Performing a &#8220;Quick Search&#8221;</h2> <div class="wp_syntax"><div class="code"><pre class="ruby ruby" style="font-family:monospace;"><span style="color:#CC0066;font-weight:bold;">require</span> <span style="color:#996600;">'net/http'</span>
<span style="color:#CC0066;font-weight:bold;">require</span> <span style="color:#996600;">'rexml/document'</span>
<span style="color:#9966CC;font-weight:bold;">include</span> REXML
&nbsp;
url = <span style="color:#996600;">'http://repository.sonatype.org/service/local/data_index?q='</span>
resp = <span style="color:#6666ff;font-weight:bold;">Net::HTTP</span>.<span style="color:#9900CC;">get_response</span><span style="color:#006600;font-weight:bold;">&#40;</span> <span style="color:#CC00FF;font-weight:bold;">URI</span>.<span style="color:#9900CC;">parse</span><span style="color:#006600;font-weight:bold;">&#40;</span> url <span style="color:#006600;font-weight:bold;">+</span> ARGV<span style="color:#006600;font-weight:bold;">&#91;</span>0<span style="color:#006600;font-weight:bold;">&#93;</span><span style="color:#006600;font-weight:bold;">&#41;</span> <span style="color:#006600;font-weight:bold;">&#41;</span>
&nbsp;
doc = <span style="color:#6666ff;font-weight:bold;">REXML::Document</span>.<span style="color:#9900CC;">new</span><span style="color:#006600;font-weight:bold;">&#40;</span> resp.<span style="color:#9900CC;">body</span> <span style="color:#006600;font-weight:bold;">&#41;</span>
&nbsp;
XPath.<span style="color:#9900CC;">each</span><span style="color:#006600;font-weight:bold;">&#40;</span> doc, <span style="color:#996600;">"//data/artifact"</span> <span style="color:#006600;font-weight:bold;">&#41;</span> <span style="color:#9966CC;font-weight:bold;">do</span> |r| <span style="color:#CC0066;font-weight:bold;">puts</span> <span style="color:#996600;">"#{r.elements["</span>groupId<span style="color:#996600;">"].text}:#{r.elements["</span>artifactId<span style="color:#996600;">"].text}:#{r.elem<span style="color:#000099;">&#92;</span>
ents["</span>version<span style="color:#996600;">"].text}"</span>
<span style="color:#9966CC;font-weight:bold;">end</span></pre></div></div> <p>This script follows the pattern of the previous script to list all repositories with the exception that it reads an argument from the command line. This script performs a quick search by hitting the <em>data_index</em> service and passing in the <em>q</em> parameter. This script simply prints out the <em>groupId:artifactId:version</em> of all the artifacts located.</p>
<p>If you would like to see an example of the XML that this service produces click here: <a rel="nofollow" title="http://repository.sonatype.org/service/local/data_index?q=activemq" target="_blank" href="http://repository.sonatype.org/service/local/data_index?q=activemq">http://repository.sonatype.org/service/local/data_index?q=activemq</a>. In the full results, you&#8217;ll see more information such as the number of search hits available, the resource URL for each artifact found, and the context (or repository) in which the artifact is available.</p>
<h2>Searching by Class Name</h2> <div class="wp_syntax"><div class="code"><pre class="ruby ruby" style="font-family:monospace;"><span style="color:#CC0066;font-weight:bold;">require</span> <span style="color:#996600;">'net/http'</span>
<span style="color:#CC0066;font-weight:bold;">require</span> <span style="color:#996600;">'rexml/document'</span>
<span style="color:#9966CC;font-weight:bold;">include</span> REXML
&nbsp;
url = <span style="color:#996600;">'http://repository.sonatype.org/service/local/data_index?cn='</span>
resp = <span style="color:#6666ff;font-weight:bold;">Net::HTTP</span>.<span style="color:#9900CC;">get_response</span><span style="color:#006600;font-weight:bold;">&#40;</span> <span style="color:#CC00FF;font-weight:bold;">URI</span>.<span style="color:#9900CC;">parse</span><span style="color:#006600;font-weight:bold;">&#40;</span> url <span style="color:#006600;font-weight:bold;">+</span> ARGV<span style="color:#006600;font-weight:bold;">&#91;</span>0<span style="color:#006600;font-weight:bold;">&#93;</span><span style="color:#006600;font-weight:bold;">&#41;</span> <span style="color:#006600;font-weight:bold;">&#41;</span>
&nbsp;
doc = <span style="color:#6666ff;font-weight:bold;">REXML::Document</span>.<span style="color:#9900CC;">new</span><span style="color:#006600;font-weight:bold;">&#40;</span> resp.<span style="color:#9900CC;">body</span> <span style="color:#006600;font-weight:bold;">&#41;</span>
&nbsp;
XPath.<span style="color:#9900CC;">each</span><span style="color:#006600;font-weight:bold;">&#40;</span> doc, <span style="color:#996600;">"//data/artifact"</span> <span style="color:#006600;font-weight:bold;">&#41;</span> <span style="color:#9966CC;font-weight:bold;">do</span> |r| <span style="color:#CC0066;font-weight:bold;">puts</span> <span style="color:#996600;">"#{r.elements["</span>groupId<span style="color:#996600;">"].text}:#{r.elements["</span>artifactId<span style="color:#996600;">"].text}:#{r.elem<span style="color:#000099;">&#92;</span>
ents["</span>version<span style="color:#996600;">"].text}"</span>
<span style="color:#9966CC;font-weight:bold;">end</span></pre></div></div> <p>This script is almost exactly the same as the prior script that performed a quick search. The difference in this script is that instead of passing the q parameter, this script passes the cn parameter. Passing the cn parameter causes Nexus to search for artifacts which contain classes that match the given value. The results are going to look the same as the quick search query script. To see the XML yourself, search for all artifacts which contain a class named HibernateDaoSupport: <a rel="nofollow" target="_blank" href="http://repository.sonatype.org/service/local/data_index?cn=HibernateDaoSupport">http://repository.sonatype.org/service/local/data_index?cn=HibernateDaoSupport</a>.</p>
<h2>Performing a GAV Search</h2> <div class="wp_syntax"><div class="code"><pre class="ruby ruby" style="font-family:monospace;"><span style="color:#CC0066;font-weight:bold;">require</span> <span style="color:#996600;">'net/http'</span>
<span style="color:#CC0066;font-weight:bold;">require</span> <span style="color:#996600;">'rexml/document'</span>
<span style="color:#9966CC;font-weight:bold;">include</span> REXML
&nbsp;
url = <span style="color:#996600;">"http://repository.sonatype.org/service/local/data_index?g=#{ARGV[0]}&amp;amp;a=#<span style="color:#000099;">&#92;</span>
{ARGV[1]}&amp;amp;v=#{ARGV[2]}"</span>
resp = <span style="color:#6666ff;font-weight:bold;">Net::HTTP</span>.<span style="color:#9900CC;">get_response</span><span style="color:#006600;font-weight:bold;">&#40;</span> <span style="color:#CC00FF;font-weight:bold;">URI</span>.<span style="color:#9900CC;">parse</span><span style="color:#006600;font-weight:bold;">&#40;</span> url <span style="color:#006600;font-weight:bold;">&#41;</span> <span style="color:#006600;font-weight:bold;">&#41;</span>
&nbsp;
doc = <span style="color:#6666ff;font-weight:bold;">REXML::Document</span>.<span style="color:#9900CC;">new</span><span style="color:#006600;font-weight:bold;">&#40;</span> resp.<span style="color:#9900CC;">body</span> <span style="color:#006600;font-weight:bold;">&#41;</span>
&nbsp;
XPath.<span style="color:#9900CC;">each</span><span style="color:#006600;font-weight:bold;">&#40;</span> doc, <span style="color:#996600;">"//data/artifact"</span> <span style="color:#006600;font-weight:bold;">&#41;</span> <span style="color:#9966CC;font-weight:bold;">do</span> |r| <span style="color:#CC0066;font-weight:bold;">puts</span> <span style="color:#996600;">"#{r.elements["</span>groupId<span style="color:#996600;">"].text}:#{r.elements["</span>artifactId<span style="color:#996600;">"].text}:#{r.elem<span style="color:#000099;">&#92;</span>
ents["</span>version<span style="color:#996600;">"].text}"</span>
<span style="color:#9966CC;font-weight:bold;">end</span></pre></div></div> <p>This final script takes three command line arguments: groupId, artifactId, version, and it performs a GAV (groupId, artifactId, version) coordinate search over the repository.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/458543484" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/458564460" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/458543484/</feedburner:origLink></item>
      <item>
         <title>Use repository.sonatype.org to Search Central Maven Repository</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/458423078/</link>
         <description>If you are looking for the easiest way to search for artifacts in the Central Maven Repository, go to http://repository.sonatype.org. Sonatype maintains a publi instance of Nexus that can be used to search for artifacts by GAV (groupId, artifactId, version) coordinates, Class Name, or Checksum. Here&amp;#8217;s a brief demonstration of [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=247</guid>
         <pubDate>Wed, 19 Nov 2008 05:47:28 -0800</pubDate>
         <content:encoded><![CDATA[<p>If you are looking for the easiest way to search for artifacts in the Central Maven Repository, go to <a rel="nofollow" target="_blank" href="http://repository.sonatype.org">http://repository.sonatype.org</a>. Sonatype maintains a publi instance of <a rel="nofollow" target="_blank" href="http://nexus.sonatype.org">Nexus</a> that can be used to search for artifacts by GAV (groupId, artifactId, version) coordinates, Class Name, or Checksum. Here&#8217;s a brief demonstration of the search capabilities on <a rel="nofollow" target="_blank" href="http://repository.sonatype.org">http://repository.sonatype.org</a>.</p>
<p style="text-align:center;"><br/>  <br /> 
<strong>NOTE:</strong> Maximize Video to Full Screen Mode to see Details<span id="more-247"></span></p>
<p>If you would like to manage your own instance of Nexus and index your own Hosted repositories, you can download an install Nexus from <a rel="nofollow" target="_blank" href="http://nexus.sonatype.org">http://nexus.sonatype.org</a>. If you manage your own instance of Nexus, you can proxy other Maven repositories (including Central) and you will have a place to publish your own organization&#8217;s artifacts.</p>
<p>When you host a Nexus instance and you proxy a remote repository, Nexus downloads a Nexus repository index, this index is what enables Nexus to quickly search the contents of a Maven repository. Downloading this small repository index is all Nexus needs to do to search the entire repository. For more information about Nexus, see <a rel="nofollow" target="_blank" href="http://nexus.sonatype.org">http://nexus.sonatype.org</a>.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/458403699" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/458423078" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/458403699/</feedburner:origLink></item>
      <item>
         <title>Searching the Maven Repository</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/449691647/</link>
         <description>A common question from Apache Maven users is &amp;#8220;How do I search the central repository?&amp;#8221; or &amp;#8220;How do I find out what groupId or artifactId I should use for a specific dependency?&amp;#8221; Use Sonatype&amp;#8217;s Nexus installation at http://repository.sonatype.org to search multiple repositories at once. Sonatype has an instance of Nexus serving as a mirror of [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=236</guid>
         <pubDate>Tue, 11 Nov 2008 08:06:24 -0800</pubDate>
         <content:encoded><![CDATA[<p><a rel="nofollow" target="_blank" href="http://blogs.sonatype.com/people/book/files/2008/11/finding-artifacts.png"><img class="alignright size-thumbnail wp-image-240" src="http://blogs.sonatype.com/people/book/files/2008/11/finding-artifacts.png" alt="" width="130" height="88"/></a>A common question from Apache Maven users is &#8220;How do I search the central repository?&#8221; or &#8220;How do I find out what groupId or artifactId I should use for a specific dependency?&#8221; Use Sonatype&#8217;s Nexus installation at <a rel="nofollow" target="_blank" href="http://repository.sonatype.org">http://repository.sonatype.org</a> to search multiple repositories at once. Sonatype has an instance of Nexus serving as a mirror of a number of repositories including Central. If you are looking for the right XML to put in your project&#8217;s POM for a dependency like Log4J or ActiveMQ, just load <a rel="nofollow" target="_blank" href="http://repository.sonatype.org">repository.sonatype.org</a> in your browser..</p>
<p><span id="more-236"></span></p>
<p>Then type in part of an <em>artifactId</em> or a <em>groupId</em>, and you should see a result screen that finds all matching artifacts across several repositories:</p>
<p><a rel="nofollow" target="_blank" href="http://repository.sonatype.org"><img class="aligncenter size-full wp-image-238" src="http://blogs.sonatype.com/people/book/files/2008/11/artifact-search.png" alt="" width="500" height="375"/></a></p>
<p>This is a quick way for you to locate the available versions for a particular version and find out what the appropriate groupId, artifactId, and version is for a dependency. If you need more detail, you can click on the POM link to the right of each entry to view the POM for that paricular artifact, and if you would like to download the artifact, click on the artifact link.</p>
<p>If you would like to browse the repositories, click on the browse repositories link on the left-hand side of the window. In the list of repositories, you will see both groups and repositories. Nexus groups are collections of repositories exposed from a single URL.</p>
<p><strong>Looking for artifacts? Go to <a rel="nofollow" target="_blank" href="http://repository.sonatype.org">http://repository.sonatype.org</a>.</strong></p>
<p>In the next episode&#8230; search for JARs by a hash or an MD5 fingerprint&#8230; and searching for class names.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/449677589" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/449691647" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/449677589/</feedburner:origLink></item>
      <item>
         <title>m2eclipse turns heads at the Stockholm JUG!</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/449640185/</link>
         <description>One of the users on the m2eclipse user list has some great feedback about a presentation he did at the Stockholm JUG on the best of breed Maven tooling which includes Nexus and m2eclipse. Apparently people are impressed with the Maven support inside m2eclipse which is good to here given the considerable amount of effort [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/jvanzyl/?p=304</guid>
         <pubDate>Tue, 11 Nov 2008 07:07:27 -0800</pubDate>
         <content:encoded><![CDATA[<p>One of the users on the <a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org">m2eclipse</a> user list has some great feedback about a presentation he did at the <a rel="nofollow" target="_blank" href="http://www.illuminet.se/jug-stx/index.xml">Stockholm JUG</a> on the best of breed <a rel="nofollow" target="_blank" href="http://maven.apache.org">Maven</a> tooling which includes <a rel="nofollow" target="_blank" href="http://nexus.sonatype.org">Nexus</a> and <a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org">m2eclipse</a>. Apparently people are impressed with the Maven support inside <a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org">m2eclipse</a> which is good to here given the considerable amount of effort Sonatype has invested in m2eclipse to take it to the next level of quality. Here&#8217;s what Anders Hammar has to say:</p> <blockquote>
Hi,
<p>
About a month ago I did a talk about core Maven things here at our local JUG in Stockholm, Sweden. m2eclipse wasn&#8217;t the main focus of the talk, but I did use it for some examples. Mainly what was used was the pom editor and the Nexus indexes.
<p>
Even though I think the actual topics of my talk are highly interesting, most of the questions afterwards were regarding &#8220;the plugins I used in Eclipse&#8221;. Not only did some people think I hade created my own best of breed mixture, but also were a lot of people very impressed of the actual Maven support. I spoke to some people who had looked at Eclipse support some time ago (6 months - a year) but had then found it very poor. These people said that they would have a look at m2eclipse again now after my talk.
<p>
So, thanks and keep up the great job!
<p>
/Anders
</blockquote> <p>Thanks for the great feedback Anders. I think it&#8217;s good to see users&#8217; sharing their experiences about <a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org">m2eclipse</a> and <a rel="nofollow" target="_blank" href="http://nexus.sonatype.org">Nexus</a> because it does make the choice for the next set of users much easier.</p>
<img src="http://feeds.feedburner.com/~r/sonatype-jason/~4/449620084" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/449640185" height="1" width="1"/>]]></content:encoded>
         <category>Uncategorized</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/sonatype-jason/~3/449620084/</feedburner:origLink></item>
      <item>
         <title>General Framework For Model Inheritance</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/448952538/</link>
         <description>Maven 3.0 uses a new standalone component that handles inheritance and interpolation of a model in any format. The model needn&amp;#8217;t even be XML based. If you can translate your model into a list of property-value pairs, you can use this framework for inheritance.
ModelProperties are the building blocks and consist of a URI and a [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/shane/?p=48</guid>
         <pubDate>Mon, 10 Nov 2008 15:54:02 -0800</pubDate>
         <content:encoded><![CDATA[<p>Maven 3.0 uses a new standalone component that handles inheritance and interpolation of a model in any format. The model needn&#8217;t even be XML based. If you can translate your model into a list of property-value pairs, you can use this framework for inheritance.</p>
<p>ModelProperties are the building blocks and consist of a URI and a value. If you want to create a hierarchy (or a node), you would specify something like:</p> <div class="wp_syntax"><div class="code"><pre class="java java" style="font-family:monospace;">mp<span style="color:#009900;">&#40;</span><span style="color:#0000ff;">"http://myorg.org/model/foo"</span>, <span style="color:#000066;font-weight:bold;">null</span><span style="color:#009900;">&#41;</span>
mp<span style="color:#009900;">&#40;</span><span style="color:#0000ff;">"http://myorg.org/model/foo/bar"</span>, <span style="color:#0000ff;">"fooey"</span><span style="color:#009900;">&#41;</span></pre></div></div> <p>In XML, this would correspond to:</p>
<pre> &lt;foo&gt; &lt;bar&gt;fooey&lt;/bar&gt; &lt;/foo&gt;
</pre>
<p>
If two of the same properties are stacked, say &#8220;http://myorg.org/model/foo/bar&#8221;, then the top most property value will be used. This allows for a simple linearized inheritance, where the most specialized model overrides values of its parent model. But what happens to collections, like dependencies, that need to be merged as we move up the hierarchy of parent poms?</p>
<p>That&#8217;s where the concept of the ModelContainer comes in. The first thing to do is to specify #collection in the URI: http://apache.org/maven/project/dependencies#collection. </p>
<p>This tells the ModelTransformer implementation instance not to override the property, as it is part of a collection. Instead, the framework just to adds the property to the general collection. Obviously, the framework doesn&#8217;t know anything about how to handle the specifics of these URI collections, as that is a model specific rule. Thus the framework must delegate the decision, calling all the ModelContainerFactories that is has been initialized with, asking each if they can provide a container to handle the property.</p> <div class="wp_syntax"><div class="code"><pre class="java java" style="font-family:monospace;"> ModelDataSource source <span style="color:#339933;">=</span> <span style="color:#000000;font-weight:bold;">new</span> DefaultModelDataSource<span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>; source.<span style="color:#006633;">init</span><span style="color:#009900;">&#40;</span> props, <span style="color:#003399;">Arrays</span>.<span style="color:#006633;">asList</span><span style="color:#009900;">&#40;</span> <span style="color:#000000;font-weight:bold;">new</span> ArtifactModelContainerFactory<span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>, <span style="color:#000000;font-weight:bold;">new</span> IdModelContainerFactory<span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#41;</span>;</pre></div></div> <p>A ModelContainer implementation is rather simple. The framework just passes in all like model containers and asks what it should do. A ModelContainer is required to implement the following method:</p> <div class="wp_syntax"><div class="code"><pre class="java java" style="font-family:monospace;"> ModelContainerAction containerAction<span style="color:#009900;">&#40;</span> ModelContainer modelContainer <span style="color:#009900;">&#41;</span>;</pre></div></div> <p>
A ModelContainer implementation instance will know its own model properties (say version, groupId and artifactId) and decides what action to take in relation to the specified modelContainer, which is passed to it by the framework. The returned ModelContainerAction is an enum that specifies an action: no operation, delete or join of containers. </p>
<p>For example, if either the groupIds or versions are different, the container would return a NOP, telling maven-shared-model to leave the specified container in the collection. If the artifactIds, versions and groupIds are all the same, then the container would tell the framework to join the containers. That&#8217;s where the implementation of ModelDataSource comes in. It has join, delete and query methods for handling the operations on ModelContainers. If the ModelContainer implementation told the framework to join model containers, the framework would then take both model containers and invoke: ModelDataSource.join(ModelContainer a, ModelContainer b)</p>
<p>Out of the box, you can use the ModelTransformer for transforming XML to a list of model properties, but nothing would stop someone from plugging in their own transformer for virtually any other format. Thus you can used maven-shared-model for inheriting any data format according to a general rule set that you can customize.</p>
<p>Clearly the component name, maven-shared-model, is not appropriate, as it can be used independently of Maven and does not dictate the use of the Maven model. After the first alpha release of Maven 3.0, I&#8217;ll be creating a separate project, independent of trunk, for maven-shared-model.</p>
<img src="http://feeds.feedburner.com/~r/sonatype/Shane/~4/448952354" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/448952538" height="1" width="1"/>]]></content:encoded>
         <category>Maven</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/sonatype/Shane/~3/448952354/</feedburner:origLink></item>
      <item>
         <title>MySQL’s Zack Urlocker writes about Sonatype’s new CEO in InfoWorld</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/448822151/</link>
         <description>There&amp;#8217;s are lots of people who already know that Mark de Visser is the new CEO of Sonatype, but Zack wrote a nice bit about it today in his InfoWorld blog: http://weblog.infoworld.com/openresource/archives/2008/11/marketing_maven.html I am really excited to be working with Mark. More good news to come!</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/jvanzyl/?p=302</guid>
         <pubDate>Mon, 10 Nov 2008 13:12:58 -0800</pubDate>
         <content:encoded><![CDATA[<p>There&#8217;s are lots of people who already know that <a rel="nofollow" target="_blank" href="http://blogs.sonatype.com/people/mark">Mark de Visser</a> is the new CEO of Sonatype, but Zack wrote a nice bit about it today in his <a rel="nofollow" target="_blank" href="http://weblog.infoworld.com/openresource/">InfoWorld blog</a>:</p> <p><a rel="nofollow" target="_blank" href="http://weblog.infoworld.com/openresource/archives/2008/11/marketing_maven.html">http://weblog.infoworld.com/openresource/archives/2008/11/marketing_maven.html</a></p> <p>I am really excited to be working with Mark. More good news to come!</p>
<img src="http://feeds.feedburner.com/~r/sonatype-jason/~4/448821839" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/448822151" height="1" width="1"/>]]></content:encoded>
         <category>Uncategorized</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/sonatype-jason/~3/448821839/</feedburner:origLink></item>
      <item>
         <title>To Mercury and Beyond</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/448822152/</link>
         <description>Last month, I went down to Sonatype&amp;#8217;s offices to meet up with the guys down there. I soon found myself being cornered by a serious looking Oleg, who wanted Maven integration with Mercury ASAP, and who I believed I promised Maven integration two weeks prior. We setup our laptops outside to work on Mercury, in [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/shane/?p=22</guid>
         <pubDate>Mon, 10 Nov 2008 13:08:33 -0800</pubDate>
         <content:encoded><![CDATA[<p>Last month, I went down to Sonatype&#8217;s offices to meet up with the guys down there. I soon found myself being cornered by a serious looking Oleg, who wanted Maven integration with Mercury ASAP, and who I believed I promised Maven integration two weeks prior. We setup our laptops outside to work on Mercury, in what later proved to be a mistake as the burning California sun beat down on us.</p>
<p>Oleg needed a version of project builder that didn&#8217;t require a bunch of dependencies from the Maven trunk, as he designed Mercury to be a standalone module, resolving of any type of artifact, not just Maven specific ones. The bulk of the project builder work was already standalone and isolated into maven-shared-model, a component that handles inheritance and interpolation of generic models (including XML ones). So I stripped out some of the interfaces and a few classes from the maven-project component, which had unneeded tie-ins with the rest of Maven core.</p>
<p>Next came the implementation. Mercury has an interface called DependencyProcessor, with the following method that I needed to implement (MavenDependencyProcessor):</p> <div class="wp_syntax"><div class="code"><pre class="java java" style="font-family:monospace;"><span style="color:#000000;font-weight:bold;">public</span> <span style="color:#003399;">List</span> getDependencies<span style="color:#009900;">&#40;</span>ArtifactBasicMetadata bmd, MetadataReader mdReader<span style="color:#009900;">&#41;</span></pre></div></div> <p>The point of this method is to build a full project model, including inheritance, interpolation and profiles, returning the list of ArtifactBasicMetadata dependencies of the processed model to Mercury.</p>
<p>The ArtifactBasicMetadata is a simple value class, giving the MavenDependencyProcessor instance information like version, groupId, artifactId of the artifact for which to process the returned dependency list. The MetadataReader allows the MavenDependencyProcessor instance a way to call back into Mercury to get the parent of the project.</p>
<p>Since the project builder uses basic property lists to store all Maven properties, converting from dependencies to ArtifactBasicMetadata couldn&#8217;t be simpler: The core of the conversion is:</p> <div class="wp_syntax"><div class="code"><pre class="java java" style="font-family:monospace;"><span style="color:#003399;">List</span> modelProperties <span style="color:#339933;">=</span> container.<span style="color:#006633;">getProperties</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>;
ArtifactBasicMetadata metadata <span style="color:#339933;">=</span> <span style="color:#000000;font-weight:bold;">new</span> ArtifactBasicMetadata<span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>;
<span style="color:#000000;font-weight:bold;">for</span> <span style="color:#009900;">&#40;</span> ModelProperty mp <span style="color:#339933;">:</span> modelProperties <span style="color:#009900;">&#41;</span>
<span style="color:#009900;">&#123;</span> <span style="color:#000000;font-weight:bold;">if</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getUri</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>.<span style="color:#006633;">equals</span><span style="color:#009900;">&#40;</span>ProjectUri.<span style="color:#006633;">Dependencies</span>.<span style="color:#006633;">Dependency</span>.<span style="color:#006633;">groupId</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#123;</span> metadata.<span style="color:#006633;">setGroupId</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getValue</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span>; <span style="color:#009900;">&#125;</span> <span style="color:#000000;font-weight:bold;">else</span> <span style="color:#000000;font-weight:bold;">if</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getUri</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>.<span style="color:#006633;">equals</span><span style="color:#009900;">&#40;</span>ProjectUri.<span style="color:#006633;">Dependencies</span>.<span style="color:#006633;">Dependency</span>.<span style="color:#006633;">artifactId</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#123;</span> metadata.<span style="color:#006633;">setArtifactId</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getValue</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span>; <span style="color:#009900;">&#125;</span> <span style="color:#000000;font-weight:bold;">else</span> <span style="color:#000000;font-weight:bold;">if</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getUri</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>.<span style="color:#006633;">equals</span><span style="color:#009900;">&#40;</span>ProjectUri.<span style="color:#006633;">Dependencies</span>.<span style="color:#006633;">Dependency</span>.<span style="color:#006633;">version</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#123;</span> metadata.<span style="color:#006633;">setVersion</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getValue</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span>; <span style="color:#009900;">&#125;</span> <span style="color:#000000;font-weight:bold;">else</span> <span style="color:#000000;font-weight:bold;">if</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getUri</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>.<span style="color:#006633;">equals</span><span style="color:#009900;">&#40;</span>ProjectUri.<span style="color:#006633;">Dependencies</span>.<span style="color:#006633;">Dependency</span>.<span style="color:#006633;">classifier</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#123;</span> metadata.<span style="color:#006633;">setClassifier</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getValue</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span>; <span style="color:#009900;">&#125;</span> <span style="color:#000000;font-weight:bold;">else</span> <span style="color:#000000;font-weight:bold;">if</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getUri</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>.<span style="color:#006633;">equals</span><span style="color:#009900;">&#40;</span>ProjectUri.<span style="color:#006633;">Dependencies</span>.<span style="color:#006633;">Dependency</span>.<span style="color:#006633;">scope</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#123;</span> metadata.<span style="color:#006633;">setScope</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getValue</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span>; <span style="color:#009900;">&#125;</span> <span style="color:#000000;font-weight:bold;">else</span> <span style="color:#000000;font-weight:bold;">if</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getUri</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>.<span style="color:#006633;">equals</span><span style="color:#009900;">&#40;</span>ProjectUri.<span style="color:#006633;">Dependencies</span>.<span style="color:#006633;">Dependency</span>.<span style="color:#006633;">type</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#123;</span> metadata.<span style="color:#006633;">setType</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getValue</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span>; <span style="color:#009900;">&#125;</span> <span style="color:#000000;font-weight:bold;">else</span> <span style="color:#000000;font-weight:bold;">if</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getUri</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span>.<span style="color:#006633;">equals</span><span style="color:#009900;">&#40;</span>ProjectUri.<span style="color:#006633;">Dependencies</span>.<span style="color:#006633;">Dependency</span>.<span style="color:#006633;">optional</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span> <span style="color:#009900;">&#123;</span> metadata.<span style="color:#006633;">setOptional</span><span style="color:#009900;">&#40;</span>mp.<span style="color:#006633;">getValue</span><span style="color:#009900;">&#40;</span><span style="color:#009900;">&#41;</span><span style="color:#009900;">&#41;</span>; <span style="color:#009900;">&#125;</span>
<span style="color:#009900;">&#125;</span></pre></div></div> <p>One problem we did encounter was how to handle passing in system and user properties for interpolation and profile activation to the MavenDependencyProcessor, as these properties are currently passed by the MavenEmbedder to the project builder. This requires that Maven core explicitly initialize the MavenDependencyProcessor, passing in all properties through the MavenDependencyProcessor constructor.</p>
<p>Mercury integration is pretty exciting because it will allow us to hemorrhage a lot of resolving code which we have to use in the core, as well as providing a deterministic resolver. Full Mercury integration is not slated for the Maven-3.0-alpha1 release and will likely be a core focus of the alpha-2 release. Initial integration looks promising, as Mercury is already able to process classpaths and dependencies from POMs.</p>
<img src="http://feeds.feedburner.com/~r/sonatype/Shane/~4/448818172" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/448822152" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/sonatype/Shane/~3/448818172/</feedburner:origLink></item>
      <item>
         <title>MASA: Building Android Applications with Maven</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/448763677/</link>
         <description>When I first downloaded the SDK for Android nearly a year ago, I was greeted by an ant build file. I wanted to start developing Android applications but wasn&amp;#8217;t willing to go back to ant to do it; so I decided to throw together a quick set of plugins to build Android with Maven: MASA [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/shane/?p=37</guid>
         <pubDate>Mon, 10 Nov 2008 11:12:16 -0800</pubDate>
         <content:encoded><![CDATA[<p>When I first downloaded the SDK for Android nearly a year ago, I was greeted by an ant build file. I wanted to start developing Android applications but wasn&#8217;t willing to go back to ant to do it; so I decided to throw together a quick set of plugins to build Android with Maven: <a rel="nofollow" target="_blank" href="http://code.google.com/p/masa/">MASA Plugins</a>. The name MASA comes from PKD&#8217;s book <em>We Can Build You</em>. In the book, there is a company MASA Associates (Multiplex Acoustical System of America), responsible for building simulacra (or androids). PKD&#8217;s MASA is also a play on the word NASA, and as we all know, Maven is as simple as rocket science.</p>
<p>After starting, I found there was little documentation on how to use the command line to build Android apps, leading me to dissect the build.xml file to learn how the command line options worked.</p>
<p>After that, it was just a matter of creating a custom lifecycle for the packaging type &#8216;android:apk&#8217;. The plugins largely consisted of translating POM parameters to the command line, similar to Apache NMaven, undergoing incubation at the ASF.</p>
<p>A sample POM looks like:</p>
<pre>&lt;project&gt; &lt;modelVersion&gt;4.0.0&lt;/modelVersion&gt; &lt;groupId&gt;org.jvending.masa&lt;/groupId&gt; &lt;artifactId&gt;maven-test&lt;/artifactId&gt; &lt;version&gt;1.0.1&lt;/version&gt; &lt;packaging&gt;android:apk&lt;/packaging&gt; &lt;name&gt;maven-test&lt;/name&gt; &lt;dependencies&gt; &lt;dependency&gt; &lt;groupId&gt;android&lt;/groupId&gt; &lt;artifactId&gt;android&lt;/artifactId&gt; &lt;version&gt;1.0&lt;/version&gt; &lt;/dependency&gt; &lt;/dependencies&gt; &lt;build&gt; &lt;sourceDirectory&gt;src&lt;/sourceDirectory&gt; &lt;plugins&gt; &lt;plugin&gt; &lt;groupId&gt;org.apache.maven.plugins&lt;/groupId&gt; &lt;artifactId&gt;maven-compiler-plugin&lt;/artifactId&gt; &lt;configuration&gt; &lt;source&gt;1.5&lt;/source&gt; &lt;target&gt;1.5&lt;/target&gt; &lt;/configuration&gt; &lt;/plugin&gt; &lt;plugin&gt; &lt;groupId&gt;org.jvending.masa.plugins&lt;/groupId&gt; &lt;artifactId&gt;maven-dx-plugin&lt;/artifactId&gt; &lt;extensions&gt;true&lt;/extensions&gt; &lt;/plugin&gt; &lt;/plugins&gt; &lt;/build&gt;
&lt;/project&gt;</pre>
<p>So by specifying the packaging type as &#8216;android:apk&#8217; and the sourceDirectory as &#8217;src&#8217;, you can build your android project with Maven. If you type &#8216;mvn install -Dmasa.debug&#8217; the plugins will also deploy the apk to the G1 device over USB or to the emulator.</p>
<p>For the latest SDK, I included the packaging type: &#8216;android:apk:platformTest&#8217;<br />
that will deploy the apk to the device and run the unit tests on the target device.</p>
<p>At the time, the Android source was not open-source, so MASA provides a build script for importing the android.jar into the local repo. Now that Android is open-source, I&#8217;ll be looking to deploy the android.jar into the Maven repo to avoid this additional step and then getting a release of MASA deployed as well.</p>
<p>One area that I still need to work on is the delayed signing of apks, so expect to see future updates.</p>
<img src="http://feeds.feedburner.com/~r/sonatype/Shane/~4/448719731" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/448763677" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/sonatype/Shane/~3/448719731/</feedburner:origLink></item>
      <item>
         <title>Book Version 0.20 Released: Typos and Upgrade</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/447803639/</link>
         <description>I have just released version 0.20 of Maven: The Definitive Guide. This release is mostly a produce of the feedback from GetSatisfaction and it consists of a large number of grammar and spelling errors being caught by readers. Here&amp;#8217;s a list of the changes in version 0.20: A section in the installation chapter about upgrading from [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=231</guid>
         <pubDate>Sun, 09 Nov 2008 14:19:58 -0800</pubDate>
         <content:encoded><![CDATA[<p><img class="alignright size-thumbnail wp-image-175" src="http://blogs.sonatype.com/people/book/files/2008/11/maven-book1.jpg" alt="" width="88" height="115"/>I have just released version 0.20 of Maven: The Definitive Guide. This release is mostly a produce of the feedback from GetSatisfaction and it consists of a large number of grammar and spelling errors being caught by readers. Here&#8217;s a list of the changes in version 0.20:</p>
<ul>
<li>A section in the installation chapter about upgrading from Maven 1 to Maven 2. I&#8217;m constantly getting questions from people about customizing a Maven 2 build by string goal names together on the command-line so I put some language into the installation chapter that points people at the Maven Lifecycle. The Maven Lifecycle really is the thing to learn first in Maven, if you figure out how the Maven Lifecycle works and if you become familiar with the Default lifecycle, Maven 2 will make more sense. This new section is small, but it points people toward the Maven One plugin and configuring a legacy repository. If you are upgrading from Maven 1 to Maven 2, let me know if this section is what you needed.</li>
<li>Arun Kumar submitted a list of typos and grammar errors throughout the Introduction. A number of typos were fixed in the introduction.</li>
<li>A number of typos were fixed in the Assemblies chapter.</li>
<li>A number of typos were fixed in the Profiles chapter.</li>
<li>A number of typos were fixed in the Writing Plugins chapter.</li>
</ul>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/447786824" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/447803639" height="1" width="1"/>]]></content:encoded>
         <category>book</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/447786824/</feedburner:origLink></item>
      <item>
         <title>On Maven Model Transforms and C#</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/445990942/</link>
         <description>Maven 3.0 does all project model processing on a canonical data format, consisting of nearly 500 property values. Using a canonical data format makes it easy to do bidirectional transforms between the Maven pom and other model types.
To transform from an XML format to the property format, you can take any stream containing data in [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/shane/?p=16</guid>
         <pubDate>Fri, 07 Nov 2008 15:18:10 -0800</pubDate>
         <content:encoded><![CDATA[<p><img class="alignright size-thumbnail wp-image-33" src="http://blogs.sonatype.com/people/shane/files/2008/11/maven-for-csharp.png" alt="" width="99" height="88"/>Maven 3.0 does all project model processing on a canonical data format, consisting of nearly 500 property values. Using a canonical data format makes it easy to do bidirectional transforms between the Maven pom and other model types.</p>
<p>To transform from an XML format to the property format, you can take any stream containing data in XML and pass it the static method ModelMarshaller.marshallXmlToModelProperties. In the case of the Visual Studio&#8217;s C# project file, it would look something like:<span id="more-16"></span></p> <div class="wp_syntax"><div class="code"><pre class="csharp csharp" style="font-family:monospace;"><span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project"</span>, <span style="color:#666666;">"null"</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/ItemGroup"</span>, <span style="color:#666666;">"null"</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/ItemGroup/Reference"</span>, <span style="color:#666666;">"null"</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/ItemGroup/Reference#property/Include"</span>, <span style="color:#666666;">"NGenerics, Version=1.3.0.0, Culture=neutral, processorArchitecture=MSIL"</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/ItemGroup/Reference/SpecificVersion"</span>, <span style="color:#666666;">"False"</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/ItemGroup/Reference/HintPath"</span>, <span style="color:#666666;">"..libNGenerics.dll"</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/ItemGroup/Reference"</span>, <span style="color:#666666;">""</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/ItemGroup/Reference#property/Include"</span>, <span style="color:#666666;">"System"</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/Import"</span>, <span style="color:#666666;">""</span><span style="color:#000000;">&#41;</span>
<span style="color:#000000;">&#40;</span><span style="color:#666666;">"http://microsoft.com/Project/Import#property/Project"</span>, <span style="color:#666666;">"$(MSBuildBinPath)Microsoft.CSharp.targets"</span><span style="color:#000000;">&#41;</span></pre></div></div> <p>The next step is to transform from the above properties to the canonical format that Maven understands. This requires creating rules that rename (and possibly reorder) the URI elements of each property. For example, to create the dependency section of the pom we would transform assembly references from the C# project file to a Maven project dependency:</p> <div class="wp_syntax"><div class="code"><pre class="csharp csharp" style="font-family:monospace;">List p <span style="color:#008000;">=</span> <span style="color:#008000;">new</span> ArrayList<span style="color:#000000;">&#40;</span><span style="color:#000000;">&#41;</span>;
p.<span style="color:#0000FF;">add</span><span style="color:#000000;">&#40;</span><span style="color:#008000;">new</span> ModelProperty<span style="color:#000000;">&#40;</span>ProjectUri.<span style="color:#0000FF;">xUri</span>, <span style="color:#0600FF;">null</span><span style="color:#000000;">&#41;</span><span style="color:#000000;">&#41;</span>;
p.<span style="color:#0000FF;">add</span><span style="color:#000000;">&#40;</span><span style="color:#008000;">new</span> ModelProperty<span style="color:#000000;">&#40;</span>ProjectUri.<span style="color:#0000FF;">Dependencies</span>.<span style="color:#0000FF;">xUri</span>, <span style="color:#0600FF;">null</span><span style="color:#000000;">&#41;</span><span style="color:#000000;">&#41;</span>;
<span style="color:#0600FF;">for</span><span style="color:#000000;">&#40;</span>ModelProperty mp <span style="color:#008000;">:</span> modelProperties<span style="color:#000000;">&#41;</span> <span style="color:#000000;">&#123;</span> <span style="color:#0600FF;">if</span><span style="color:#000000;">&#40;</span>mp.<span style="color:#0000FF;">getUri</span><span style="color:#000000;">&#40;</span><span style="color:#000000;">&#41;</span>.<span style="color:#0000FF;">equals</span><span style="color:#000000;">&#40;</span>CSharpUri.<span style="color:#0000FF;">ItemGroup</span>.<span style="color:#0000FF;">Reference</span>.<span style="color:#0000FF;">include</span><span style="color:#000000;">&#41;</span><span style="color:#000000;">&#41;</span> <span style="color:#000000;">&#123;</span> p.<span style="color:#0000FF;">add</span><span style="color:#000000;">&#40;</span><span style="color:#008000;">new</span> ModelProperty<span style="color:#000000;">&#40;</span>ProjectUri.<span style="color:#0000FF;">Dependencies</span>.<span style="color:#0000FF;">Dependency</span>.<span style="color:#0000FF;">xUri</span>, <span style="color:#0600FF;">null</span><span style="color:#000000;">&#41;</span><span style="color:#000000;">&#41;</span>; p.<span style="color:#0000FF;">add</span><span style="color:#000000;">&#40;</span><span style="color:#008000;">new</span> ModelProperty<span style="color:#000000;">&#40;</span>ProjectUri.<span style="color:#0000FF;">Dependencies</span>.<span style="color:#0000FF;">Dependency</span>.<span style="color:#0000FF;">groupId</span>, mp.<span style="color:#0000FF;">getValue</span><span style="color:#000000;">&#40;</span><span style="color:#000000;">&#41;</span><span style="color:#000000;">&#41;</span><span style="color:#000000;">&#41;</span>; p.<span style="color:#0000FF;">add</span><span style="color:#000000;">&#40;</span><span style="color:#008000;">new</span> ModelProperty<span style="color:#000000;">&#40;</span>ProjectUri.<span style="color:#0000FF;">Dependencies</span>.<span style="color:#0000FF;">Dependency</span>.<span style="color:#0000FF;">artifactId</span>, mp.<span style="color:#0000FF;">getValue</span><span style="color:#000000;">&#40;</span><span style="color:#000000;">&#41;</span><span style="color:#000000;">&#41;</span><span style="color:#000000;">&#41;</span>; <span style="color:#000000;">&#125;</span>
<span style="color:#000000;">&#125;</span></pre></div></div> <p>When the transformed list of properties above are fed back into ModelMarshaller.unmarshalModelPropertiesToXml, we would see an XML snippet similar to</p>
<pre>&lt;dependencies&gt; &lt;dependency&gt; &lt;groupId&gt;System&lt;/groupId&gt; &lt;artifactId&gt;System&lt;/artifactId&gt; &lt;/dependency&gt;
&lt;/dependencies&gt;</pre>
<p>In this way, we can construct an entire Maven pom from a C# project file or vice versa. You could even translate a hierarchy of C# project files into a multi-module Maven build and have the Maven project builder process the inheritance and interpolation of the C# project files.</p>
<p>Maven handles transforms similar to a messaging bus. Say you build the bidirectional transforms from VS 2005 project files to the Maven canonical format. Now say someone else builds the transforms for VS 2008 (or 2003) project files. You can now do transforms to and from VS 2005 and 2008 project files with no additional work.</p>
<img src="http://feeds.feedburner.com/~r/sonatype/Shane/~4/445983818" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/445990942" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/sonatype/Shane/~3/445983818/</feedburner:origLink></item>
      <item>
         <title>Book Update to Version 0.19</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/445971041/</link>
         <description>Once again, this is a small update to the book, but I want to err on the side of transparency. I&amp;#8217;m announcing every version update even if it is small. I just cut a 0.19 version release, this captures some small changes to the book content driven by the reports from our users on GetSatisfaction. [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=227</guid>
         <pubDate>Fri, 07 Nov 2008 14:59:19 -0800</pubDate>
         <content:encoded><![CDATA[<p><img class="alignright size-thumbnail wp-image-175" src="http://blogs.sonatype.com/people/book/files/2008/11/maven-book1.jpg" alt="" width="88" height="115"/>Once again, this is a small update to the book, but I want to err on the side of transparency. I&#8217;m announcing every version update even if it is small. I just cut a 0.19 version release, this captures some small changes to the book content driven by the reports from our users on GetSatisfaction. This update contains a number of changes triggered by Paco Soberón and &#8220;Fred&#8221;. Here is a list of updates for the 0.19 release:</p>
<p><span id="more-227"></span></p>
<ol>
<li>Removed the references to the Geronimo implementations of servlet-api and jsp-api. There was once a time when this was very relevant. Sun wasn&#8217;t distributing the servlet-api JARs from central and Geronimo was the only implementation in the repository. Ever since the Glassfish team started publishing the javax.servlet:servlet-api JAR there is no longer a need to tell new users to substitute the Geronimo JARs for the Servlet and JSP spec JARs. I&#8217;ve kept the appendix which lists alternatives, but I don&#8217;t think it makes sense (especially for beginners) to spend value intro time talking about the Geronimo implementations.</li>
<li>I added a section at the end of Chapter 4 which shows you how to configure the assembly:attached goal using the executions elememtn in your plugin config. String goal names along on the command-line is an acceptable way to run a plugin goal, but it ignore a critical part of Maven 2. I&#8217;ve had many users ask me questions that suggest that they don&#8217;t know how to bind a goal to a phase in a POM. I think that the executions element is important to introduce earlier in the book. In general, I&#8217;m seeing that many users haven&#8217;t grok&#8217;d the Maven Lifecycle. This is my fault, and we&#8217;re going to emphasize more Lifecycle explanation both on this blog and in future versions of the book.</li>
<li>In Chapter 6, I had some inconsistent references to the groupId. I forgot to modify references to the com.sonatype.maven groupId to org.sonatype.mavenbook.ch06 - apologies for the oversight.</li>
</ol>
<p>PS: Anders Hammar: I see those reports. Thanks for commenting on them. Commenting on an issue that you think has fallen to the bottom of the stack puts it on the top.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/445971025" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/445971041" height="1" width="1"/>]]></content:encoded>
         <category>book</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/445971025/</feedburner:origLink></item>
      <item>
         <title>Building Eclipse Plugins with Maven: Tycho</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/445558664/</link>
         <description>Yesterday&amp;#8217;s post was in response to a question from Anders Nawroth of the Neo4J effort, and today&amp;#8217;s post is no different. On Tuesday (or maybe it was Monday), Anders asked the neo4j-users list whether it made sense to build the neo4j eclipse plugin with Maven.
I have looked into building Neoclipse using Maven, but at the [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=204</guid>
         <pubDate>Fri, 07 Nov 2008 05:47:48 -0800</pubDate>
         <content:encoded><![CDATA[<p><img class="alignright size-thumbnail wp-image-209" src="http://blogs.sonatype.com/people/book/files/2008/11/building-eclipse-plugins.png" alt="" width="89" height="99"/>Yesterday&#8217;s post was in response to a question from <a rel="nofollow" target="_blank" href="http://explore.twitter.com/nawroth">Anders Nawroth</a> of the <a rel="nofollow" target="_blank" href="http://neo4j.org/">Neo4J</a> effort, and today&#8217;s post is no different. On Tuesday (or maybe it was Monday), Anders asked the neo4j-users list <a rel="nofollow" target="_blank" href="http://lists.neo4j.org/pipermail/user/2008-November/000880.html">whether it made sense to build the neo4j eclipse plugin with Maven</a>.</p>
<blockquote><p>I have looked into building Neoclipse using Maven, but at the moment I&#8217;m not convinced there are more advantages then disadvantages in this case. Building Eclipse plugins and products has quite many quirks. With increasing use of product configuration options, the number of build quirks increases as well.</p>
<p>There seems to be no really automated build system for Eclipse plugins/products, even when using maven you have to install and update the dependencies manually (the Eclipse artifacts are not deployed to a maven repository).</p></blockquote>
<p>Sonatype is busily working to address these gaps, and we already have some solutions you can use to start building your Eclipse plugins in Maven. Igor Fedorenko has been working on Tycho and Maven to create a system to facilitate OSGi and Eclipse development in Maven, and m2eclipse is currently built using Tycho. To prove that Tycho is a viable path for build the Neoclipse plugin, I took some time yesterday to generate Maven pom.xml files with Tycho and build an update site for Neoclipse.<span id="more-204"></span></p>
<h2>A Basic Summary of Tycho</h2>
<p>The general idea of <a rel="nofollow" target="_blank" href="http://docs.codehaus.org/display/M2ECLIPSE/Tycho+project+overview">Tycho</a> is that it acts as a bridge between Maven and OSGi. It supports a number of usage scenarios and is under active development. It can be used in a manfiest-first mode which builds a Maven POM from an OSGi manifest and it can also be used in a pom-first mode in which <a rel="nofollow" target="_blank" href="http://docs.codehaus.org/display/M2ECLIPSE/Tycho+project+overview">Tycho</a> is responsible for generating an OSGi manifest from a Maven POM. Future plans include the ability to build a project usin Maven/Tycho without requiring the presence of a Maven POM, and there is active work under way to allow Nexus Maven repository manager to interact with Eclipse update sites and p2 repositories, that would allow Tycho to consume artifacts from those repositories. If you are looking for a more in depth explanation of Tycho, check out the <a rel="nofollow" target="_blank" href="http://docs.codehaus.org/display/M2ECLIPSE/Tycho+project+overview">Tycho Project Overview</a>.</p>
<p><img class="size-full wp-image-210 alignnone" src="http://blogs.sonatype.com/people/book/files/2008/11/tycho-manifest-first.png" alt="" width="372" height="151"/></p>
<p>If you are looking for a solution to automate Eclipse builds with Maven, look no further, Tycho is your answer. In this post, I&#8217;m going to walk you through the process of configuring a Maven build for a real Eclipse plugin. This process involves the following, high-level steps:</p>
<ol>
<li>Configuring Eclipse</li>
<li>Downloading Tycho</li>
<li>Checking out Eclipse Plugin Source from Subversion</li>
<li>Generating Maven POMs using Tycho</li>
<li>Packaging Your Eclipse Plugin and Generating an Update Site with Maven</li>
</ol>
<p>At this point in the development of Tycho, you&#8217;ll have to point the system at an installation of Eclipse, your targetPlatform. Let&#8217;s get started.</p>
<h2>Configuring Eclipse</h2>
<p>Tycho currently builds Maven pom.xml using a local installation of Eclipse which should contain the Plugin Development Environment (PDE) and other Eclipse components your specific plugin depends on. Future versions of the Tycho product will likely interrogate remote p2 repositories and Eclipse update sites, but for now we have to configure a local Eclipse Target Platform with the necessary components. For this particular example, you&#8217;ll need to install Eclipse 3.4 and download a few plugins that the Neoclipse plugin depends upon. For more information about what Neoclipse requires, see the <a rel="nofollow" target="_blank" href="http://wiki.neo4j.org/content/Neoclipse_Guide">Neo4J Wiki Page for Neoclipse</a>. These steps are also needed when you need to work with Neoeclipse code using Eclipse PDE. You need to:</p>
<ol>
<li>Download and install Eclipse 3.4 if you don&#8217;t already have it installed.</li>
<li>Neoclipse has a graphical editor component which relies on GEF. To build the plugin, you&#8217;ll need some of the Draw2D components. The easiest way to install this particular plugin is not via the standard Eclipse update manager. You should download GEF ALL distribution for Eclipse 3.4 from the <a rel="nofollow" target="_blank" href="http://www.eclipse.org/gef/downloads/">GEF Download page</a>. The direct link for the GEF-ALL distribution is <a rel="nofollow" target="_blank" href="http://www.eclipse.org/downloads/download.php?file=/tools/gef/downloads/drops/3.4.1/R200809101400/GEF-ALL-3.4.1.zip">here</a>.</li>
<li>To install the GEF-ALL distribution, unpack the ZIP file to a directory and then copy that directory to your Eclipse installation. This will install all the necessary features and plugins that neoclipse depends on.</li>
<li>As usual, I would recommend installing both the m2eclipse plugin and the Subclipse plugin. These are two plugins I almost always need:
<ol>
<li>m2eclipse update site: <a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org/update">http://m2eclipse.sonatype.org/update</a> (or if you want to use the latest stable DEV build <a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org/update-dev">http://m2eclipse.sonatype.org/update-dev</a>)</li>
<li>Subclipse Update site: <a rel="nofollow" target="_blank" href="http://subclipse.tigris.org/update_1.4.x">http://subclipse.tigris.org/update_1.4.x</a></li>
</ol>
</li>
</ol>
<p>I&#8217;m on a Mac, so I usually install my eclipse distribution in /Applications/eclipse. For the remainder of this document, if you see /Application/eclipse, you should substitute your own eclipse installation directory.</p>
<h2>Downloading and Configuring Tycho</h2>
<p>At this point, you have Eclipse installed and configured with the necessary plugins to build the Neoclipse plugin. Now you need to download and configure Tycho. Tycho contains a development version of Maven 3.0 that has been extended to allow for Tycho to interact with the the OSGi components and format of the plugins directory of your Eclipse plugin. In the future versions you could use regular Maven 3.0 and use Tycho as any other Maven plugin.</p>
<ol>
<li>Download Tycho from <a rel="nofollow" target="_blank" href="http://docs.codehaus.org/display/M2ECLIPSE/Tycho+builds">http://docs.codehaus.org/display/M2ECLIPSE/Tycho+builds</a>. I downloaded the latest DEV build, and I installed it in <em>~/programs/tycho</em> - Tycho includes a development SNAPSHOT of Maven.</li>
<li>Set M2_HOME to point to <em>~/programs/tycho</em>. If you don&#8217;t do this and you already have Maven 2 installed, you are going to run into errors and issues if you try to run either Maven or Tycho. I usually set M2_HOME to point to my Tycho installation by running &#8220;export M2_HOME=~/programs/tycho&#8221; in bash.</li>
</ol>
<p>Once Tycho is configured, you are ready to generate Maven POMs from your Eclipse plugin.</p>
<h2>Generating Maven POMs with Tycho and Building an Update Site</h2>
<p>The demo script for Tycho uses a contrived a demo project called tychodemo.zip which contains a simple Eclipse plugin. I wanted to demonstrate that Tycho is ready to be used today with a real Eclipse project. This project is the Neoclipse plugin for Eclipse that allows users to interact with a Neo4J database in the Eclipse IDE.</p>
<ol>
<li>Change directories to a working directory. I usually do all of my coding in a ~/svnw directory which is segmented by focus. So, I check out Open Source projects like neo4j in a ~/svnw/os directory: <strong><em>cd ~/svnw/os</em></strong></li>
<li>Checkout the source code for the neoclipse Eclipse plugin with Subversion: <strong><em>svn co https://svn.neo4j.org/components/neoclipse/trunk neoclipse</em></strong></li>
<li>Change directories into the neoclipse directory: <strong><em>cd neoclipse</em></strong></li>
<li>Generate a set of Maven POMs from the Neoclipse source using Tycho: <strong><em>~/programs/tycho/bin/mvn -X org.codehaus.tycho:maven-tycho-plugin:generate-poms -DgroupId=tycho.demo -Dtycho.targetPlatform=/Applications/eclipse</em></strong></li>
</ol>
<p>At this point, you&#8217;ll have pom.xml files in all of your plugins and at the top level. Tycho has generated a multi-module Maven project that references components in your targetPlatform, specified using “tycho.targetPlatform” property on the command line. Tycho doesn&#8217;t need Eclipse to be running, all it needs is access to the Eclipse directory so that it can resolve components such as the Eclipse Plugin SDK at the GEF plugin installed in the previous section.</p>
<p>To build the update site, run: <strong><em>~/programs/tycho/bin/mvn package -Dtycho.targetPlatform=/Applications/eclipse</em></strong> You should then have an update site in <strong><em>./org.neo4j.neoclipse.updatesite/target/site</em></strong></p>
<p>To avoid specifying tycho.targetPlatform property every time, it could be added to your settings.xml. For example:</p>
<pre>... &lt;profiles&gt; &lt;profile&gt; &lt;id&gt;tycho.default&lt;/id&gt; &lt;activation&gt; &lt;activeByDefault&gt;true&lt;/activeByDefault&gt; &lt;/activation&gt; &lt;properties&gt; &lt;tycho.targetPlatform&gt;/Applications/eclipse&lt;/tycho.targetPlatform&gt; &lt;/properties&gt; &lt;/profile&gt; &lt;/profiles&gt;
...</pre>
<p><img class="size-full wp-image-211 alignnone" src="http://blogs.sonatype.com/people/book/files/2008/11/tycho-maven-plugin-yes.png" alt="" width="410" height="84"/></p>
<p><strong>UPDATE (9:21 AM CST):</strong> Eugene Kuleshov just sent in a bunch of edits and improvements which were incorporated. Removed the section about adding the repository as it should already be in the public group hosted on Sonatype&#8217;s Nexus repository.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/445493915" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/445558664" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/445493915/</feedburner:origLink></item>
      <item>
         <title>Maven 3.0 Project Model and Mixins</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/445145726/</link>
         <description>The Apache Maven project model consists of a fairly rich model structure, consisting of 465 possible elements, specifying everything from the plugins Maven uses to build the project to the dependencies it needs for compiling. How Maven processes the model prior to a build can be a little confusing, dealing with the inheritance of parent [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/shane/?p=3</guid>
         <pubDate>Thu, 06 Nov 2008 22:10:58 -0800</pubDate>
         <content:encoded><![CDATA[<p><img class="alignright size-thumbnail wp-image-7" src="http://blogs.sonatype.com/people/shane/files/2008/11/rethinking-inheritance.png" alt="" width="120" height="99"/>The Apache Maven project model consists of a fairly rich model structure, consisting of 465 possible elements, specifying everything from the plugins Maven uses to build the project to the dependencies it needs for compiling. How Maven processes the model prior to a build can be a little confusing, dealing with the inheritance of parent poms (or the super pom), the applying of profiles, the merging in of dependency management information, to name just a few of the operations.</p>
<p>Back in May, Jason started talking to me about adding in mixin support for the pom, and it became clear that we needed to reconsider the Maven 2.0 design of project builder so that we could support such features. Maven 2.0 took the approach of merging trees of information (XML nodes), a perfectly reasonable approach for single inheritance. For things like mixins and multiple pom inheritance, linearizing the information proves a much simpler approach. In this post I discuss the ramifications of linearizing POM information to support multiple inheritance for POMs.</p>
<p><span id="more-3"></span>To linearize, of course, means that we have to flatten the XML nodes. I did this by creating a list of model properties, consisting of a URI and a value. So for example, the version would be modelProperty(&#8221;http://apache.org/maven/project/version&#8221;, &#8220;1.0&#8243;). The Maven 3.0 project builder creates a rather large list of model properties, stacking them, the child model properties being on top, while each of the parent model properties are placed lower in the list. Inheritance is now just a matter of sorting and removing model properties according to a set of rules.</p>
<p><img class="aligncenter size-full wp-image-14" src="http://blogs.sonatype.com/people/shane/files/2008/11/linearized-inheritance1.png" alt="" width="500" height="161"/></p>
<p>To see how easy mixins is under linearized inheritance, let&#8217;s say we have project A and project B, where project B is the child. Under single inheritance, Maven applies the sorting rules. For a mixin, we just place its model properties below project B&#8217;s properties in the list and above those of project A. Maven applies the same sorting rules as single inheritance and doesn&#8217;t care whether it&#8217;s dealing with a parent model, a mixin or even a second parent model.</p>
<p>I&#8217;ve created a detailed specification of how Maven builds the project model, which I will be releasing shortly, giving all the precise rules Maven 3.0 follows for project construction.</p>
<img src="http://feeds.feedburner.com/~r/sonatype/Shane/~4/445145711" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/445145726" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/sonatype/Shane/~3/445145711/</feedburner:origLink></item>
      <item>
         <title>Using the Project Assembly: To Create Example Projects</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/444490689/</link>
         <description>Anders Nawroth of the Neo4J project asked an interesting question on the neo4j-user list:
What&amp;#8217;s the best option when deploying neo4j code examples
using Maven? It&amp;#8217;s really not of any interest to deploy the artifact
itself, it&amp;#8217;s the sources (if possible with some exclusion of resources)
that we want.
Anders&amp;#8217; requirements: create a project which packages itself, wire the appropriate [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=192</guid>
         <pubDate>Thu, 06 Nov 2008 07:02:31 -0800</pubDate>
         <content:encoded><![CDATA[<p><a rel="nofollow" target="_blank" href="http://explore.twitter.com/nawroth">Anders Nawroth</a> of the <a rel="nofollow" target="_blank" href="http://neo4j.org/">Neo4J</a> project asked an interesting question on the <a rel="nofollow" target="_blank" href="http://lists.neo4j.org/pipermail/user/2008-November/000879.html">neo4j-user</a> lis<a rel="nofollow" target="_blank" href="http://blogs.sonatype.com/people/book/files/2008/11/assembly-plugin.png"><img class="alignright size-thumbnail wp-image-200" src="http://blogs.sonatype.com/people/book/files/2008/11/assembly-plugin.png" alt="" width="102" height="72"/></a>t:</p>
<blockquote><p><strong>What&#8217;s the best option when deploying neo4j code examples<br />
using Maven?</strong> It&#8217;s really not of any interest to deploy the artifact<br />
itself, it&#8217;s the sources (if possible with some exclusion of resources)<br />
that we want.</p></blockquote>
<p><em>Anders&#8217; requirements:</em> create a project which packages itself, wire the appropriate goal into the lifecycle. He&#8217;s headed in the right direction, the Maven Assembly Plugin, but he might not know about the pre-defined assembly descriptors as they are somewhat <a rel="nofollow" target="_blank" href="http://maven.apache.org/plugins/maven-assembly-plugin/descriptor-refs.html#project">hidden</a> on the Apache Maven site. Since other projects might have similar requirements, here&#8217;s a quick explanation of all the moving parts&#8230;</p>
<h2><span id="more-192"></span>What is the Maven Assembly Plugin?</h2>
<p>The Maven Assembly Plugin allows you to create an archive with an arbitrary structure. If you have a project which needs to produce a ZIP file with a <em>bin/</em> directory an a set of shell scripts, or if you want to create an archive which contains a particular project&#8217;s bytecode and all the runtime dependencies, Maven Assembly Plugin is the place to look. To generate an archive, you&#8217;ll need to do a few things:</p>
<ul>
<li>Include the Maven Assembly Plugin in your project&#8217;s <em>pom.xml </em>file.</li>
<li>Configure an assembly by referencing a built-in assembly or define your own assembly.</li>
<li>(optional) configure the lifecycle to bind the assembly goal to the package phase of the lifecycle.</li>
</ul>
<h2>What is an Assembly?</h2>
<p>The Maven Assembly Plugin produces an assembly of files and folders using an Assembly descriptor which describes the contents of a directory. You can use one of several predefined assembly descriptors which are built into the Maven Assembly plugin, or you can define your own assembly by configuring your assembly in an assembly descriptor. An assembly descriptor is an XML file which selects files and directories to include in the final, assembled artifact.</p>
<p><a rel="nofollow" target="_blank" href="http://blogs.sonatype.com/people/book/files/2008/11/assembly-graphic1.png"><img class="aligncenter size-full wp-image-197" src="http://blogs.sonatype.com/people/book/files/2008/11/assembly-graphic1.png" alt="" width="500" height="208"/></a></p>
<p>Just what sort of &#8220;assemblies&#8221; can you create on your own with an Assembly descriptor? Just about anything, a collection of .class files and all of your runtime dependency JARs? Sure. The assembly descriptor is flexible enough to describe just about anything. If you want a full explanation of the power of Maven Assemblies, read the <a rel="nofollow" target="_blank" href="http://www.sonatype.com/book/reference/assemblies.html">Assemblies Chapter of the Free Maven Book</a> or <a rel="nofollow" target="_blank" href="http://www.sonatype.com/book/reference/customizing.html#section-custom-packaged">Chapter 4</a> which introduces a built-in assembly descriptor.</p>
<h2>A Project Which Assembles Itself</h2>
<p>Back to Anders&#8217; requirements, he wants a project that can package itself up as an example project. He also wants this assembly to be created when he runs mvn deploy. To do this, he can use the built-in project descriptor. Adding the following plugin configuration to any project will configure this built-in project descriptor to create an assembly of a project itself (a self-replicating project) and the executions section will attach the &#8220;assembly:attached&#8221; goal to the package phase of the lifecycle.</p>
<pre> &lt;build&gt; &lt;plugins&gt; &lt;plugin&gt; &lt;artifactId&gt;maven-assembly-plugin&lt;/artifactId&gt; &lt;configuration&gt; &lt;descriptorRefs&gt; &lt;descriptorRef&gt;project&lt;/descriptorRef&gt; &lt;/descriptorRefs&gt; &lt;/configuration&gt; &lt;executions&gt; &lt;execution&gt; &lt;id&gt;examples&lt;/id&gt; &lt;phase&gt;package&lt;/phase&gt; &lt;goals&gt; &lt;goal&gt;attached&lt;/goal&gt; &lt;/goals&gt; &lt;/execution&gt; &lt;/executions&gt; &lt;/plugin&gt; &lt;/plugins&gt; &lt;/build&gt;</pre>
<p>Go ahead, try it. Run mvn package or mvn deploy and you&#8217;ll end up with an assembly in ${basedir}/target. If you want to customize the name of the final product, use the finalName element in the build section of your POM.</p>
<h2>The Lifecycle</h2>
<p>My next post will likely be on the lifecycle, I&#8217;ve had a few questions from people over the past few weeks about running specific goals directly from the command-line. It appears that many people haven&#8217;t fully grok&#8217;d the Maven Lifecycle. Many people grew familiar with Maven 1, the way that people customized a build in Maven 1 was to string along a number of goals. If you needed to run a specific goal, you would just craft a long command line. In Maven 2, you should shy away from running specific goals on the command line, and you should configure executions (see above). This is the more natural way to customize a build, think of it as hooking your own project&#8217;s customized goals to the default lifecycle. If you find yourself running &#8220;mvn deploy assembly:assembly&#8221; often, you should take a look at the executions element in your plugin configuration.</p>
<p>For more information about the Maven 2 Lifecycle, read <a rel="nofollow" target="_blank" href="http://www.sonatype.com/book/reference/lifecycle.html">Chapter 10: Lifecycles</a>.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/444440249" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/444490689" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/444440249/</feedburner:origLink></item>
      <item>
         <title>Nexus Maven Repository Manager 1.1 Released</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/443391031/</link>
         <description>We would like to announce the release of Nexus 1.1. This release was primarily focused on architecture improvements in the form of ExtJs and Restlet framework upgrades as well as improvements aimed at allowing the introduction of plugins. It also marks the first release of Nexus that is available as a War.
The War has been [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/brian/?p=194</guid>
         <pubDate>Wed, 05 Nov 2008 07:55:15 -0800</pubDate>
         <content:encoded><![CDATA[<p>We would like to announce the release of Nexus 1.1. This release was primarily focused on architecture improvements in the form of ExtJs and Restlet framework upgrades as well as improvements aimed at allowing the introduction of plugins. It also marks the first release of Nexus that is available as a War.</p>
<p>The War has been successfully tested on Resin, Tomcat and Jetty but is considered Beta. It is currently known to not work on Glassfish due to that container&#8217;s conflict with Log4j. You can find more information regarding the war support at <a rel="nofollow" target="_blank" href="https://issues.sonatype.org/browse/NEXUS-58">Nexus-58</a> and <a rel="nofollow" target="_blank" href="https://issues.sonatype.org/browse/Nexus-1055">Nexus-1055</a>. Please report any issues to the <a rel="nofollow" target="_blank" href="http://nexus.sonatype.org/dev/mailing-lists.html">nexus-user</a> list or <a rel="nofollow" target="_blank" href="https://issues.sonatype.org/browse/NEXUS">Jira</a>.</p>
<p>Also included are several enhancements aimed at improving the user experience:</p>
<h2>Index Browsing</h2>
<p>Previously the browse repository screens only included items already cached by Nexus. The new screen allows you to browse the tree view for a remote repository when the remote index has been downloaded:</p>
<div style="text-align:center;"><img src="http://blogs.sonatype.com/people/brian/files/2008/11/repoindexview.jpg" border="0" alt="RepoIndexView.jpg" width="600"/></div>
<h2>Log Viewing</h2>
<p>Tail functionality has been added to the log screen:</p>
<div style="text-align:center;"><img src="http://blogs.sonatype.com/people/brian/files/2008/11/taillogs.jpg" border="0" alt="TailLogs.jpg" width="536" height="309"/></div>
<h2>Admin can directly set a user password</h2>
<p>It is now possible to set a password directly without requiring an SMTP server:</p>
<div style="text-align:center;"><img src="http://blogs.sonatype.com/people/brian/files/2008/11/setpassword.jpg" border="0" alt="SetPassword.jpg" width="526" height="188"/></div>
<p><a rel="nofollow" target="_blank" href="https://issues.sonatype.org/browse/NEXUS-1055"></a></p>
<p>Many other improvements and bug fixes are included. The full list can be retrieved from <a rel="nofollow" target="_blank" href="https://issues.sonatype.org/secure/ReleaseNote.jspa?version=10090&amp;styleName=Html&amp;projectId=10001&amp;Create=Create">Jira</a>.</p>
<p>Download your copy of Nexus <a rel="nofollow" target="_blank" href="http://nexus.sonatype.org/using/download.html">here</a>.</p>
<img src="http://feeds.feedburner.com/~r/SonatypeBrian/~4/443364599" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/443391031" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/SonatypeBrian/~3/443364599/</feedburner:origLink></item>
      <item>
         <title>Book Update (Version Beta 0.18)</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/441316275/</link>
         <description>I hesitate to even announce this release as it is a series of subtle typo fixes and corrections driven by our Get Satisfaction page, but I also think that there is a certain value in being completely transparent and announcing every release (even the minor ones). I&amp;#8217;ve cut this release because there [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=187</guid>
         <pubDate>Mon, 03 Nov 2008 11:21:18 -0800</pubDate>
         <content:encoded><![CDATA[<p><img class="alignright size-thumbnail wp-image-172" src="http://blogs.sonatype.com/people/book/files/2008/11/maven-book.jpg" alt="" width="88" height="115"/>I hesitate to even announce this release as it is a series of subtle typo fixes and corrections driven by our Get Satisfaction page, but I also think that there is a certain value in being completely transparent and announcing every release (even the minor ones). I&#8217;ve cut this release because there are a number of small typo fixes that were building up, and I&#8217;m getting ready to add more weigh to some of the reference chapters. Instead of sitting on these simple updates, I&#8217;d rather get them published and released.<br />
<span id="more-187"></span><br />
This version contains the following updates:</p>
<ul>
<li>Added a reference from the Lifecycle Chapter to the Writing Plugins Chapter. I had incorrectly stated that we were going to illustrate the process of creating a custom lifecycle in this chapter. Custom lifecycles and packaging types are not introduced until the Writing Plugins Chapter. An XREF has been inserted into the Lifecycle chapter.</li>
<li>Changed the installation directory to /usr/local/apache-maven-2.0.9 from /usr/local/maven-2.0.9. This might seem like a small change, but it brings the documentation more in line with what the archive will produce when unpacked. I have not changed the book&#8217;s installation instructions to match the install directory on the Maven site. The Maven site suggests that the correct directory for Maven is /usr/local/apache-maven/apache-maven-2.0.9&#8230; I&#8217;d rather install multiple versions in /usr/local and then use symlinks.</li>
<li>Added instructions for the installation of Maven 2.0.9 using MacPorts.</li>
<li>Removed some confusing language in the Settings Details Appendix that talked about &#8220;two different kinds of artifacts&#8221;</li>
<li>Added a note to Chapter 8 that references the Optimization chapter. Some people, already familiar with the dependencyManagement element, were getting a bit disturbed to see a top-level POM without this element. I&#8217;m leaving the dependencyManagement element to the Optimization chapter to illustrate the progression from a simple POM to a highly-optimized POM.</li>
<li>Changing the Version Number of the Book</li>
</ul>
<p>Many of these changes may seem trivial: fixing dangling references, small typos, version numbers. I tend to think that these small changes are critical to creating a book that doesn&#8217;t create the sort of friction the community has grown accustomed to. Too often, you&#8217;ll be reading documentation for an open source project and it will refer to an as yet unfinished or yet to be realized document, this can be one of the most frustrating experiences&#8230;. &#8220;For more information about X see the (unwritten) Document Y&#8230;&#8221;</p>
<p>Thanks again to all of the people paying attention and submiting errata through both the O&#8217;Reilly production staff and GetSatisfaction.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/441291707" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/441316275" height="1" width="1"/>]]></content:encoded>
         <category>book</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/441291707/</feedburner:origLink></item>
      <item>
         <title>Nginx is Central’s new friend</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499085/</link>
         <description>The load on Central has been increasing steadily over the past few months. Coincidence or not, it started shortly after Maven: The Definitive Guide was translated into Chinese. First, httpd was running out of connections, then as we adjusted those higher, the load on the system was getting out of hand. Most recently we were [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/brian/2008/10/29/nginx-is-centrals-new-friend/</guid>
         <pubDate>Wed, 29 Oct 2008 19:17:38 -0700</pubDate>
         <content:encoded><![CDATA[<p><a rel="nofollow" target="_blank" href="http://blogs.sonatype.com/people/brian/files/2008/11/nginx1.png"><img class="alignright size-medium wp-image-188" src="http://blogs.sonatype.com/people/brian/files/2008/11/nginx1.png" alt="" width="127" height="36"/></a>The load on Central has been increasing steadily over the past few months. Coincidence or not, it started shortly after <a rel="nofollow" target="_blank" href="http://www.sonatype.com/community/definitive_guide.html">Maven: The Definitive Guide</a> was translated into Chinese. First, httpd was running out of connections, then as we adjusted those higher, the load on the system was getting out of hand. Most recently we were getting 15 minute load averages above 200 on a regular basis. To solve this and provide more redundancy, we started the process of installing a load balancer to share the load with a second machine. On a tip from James, we looked into <a rel="nofollow" target="_blank" href="http://nginx.net/">Nginx</a> &#8220;engine x&#8221;, which is supposed to be high performance http server. The central repository is currently not doing anything dynamic, the files are just sitting there on disk, updated occasionally via rsync. This means we are not leveraging the flexibility of httpd mods and the overhead was killing us.</p>
<p>To check it out, we installed Nginx in parallel to httpd and once everything looked good, swapped the ports to put it into production. How did it work out? Simply amazing. Since the swap, the loads are averging around .30. This is a quad core machine, so that means that it went from being 28x overloaded to using a third of ONE cpu. Being suspicious, I checked the bandwidth logs and response times. The average response time is 8x faster (no doubt because there&#8217;s 3 cpus sipping Mai Tais) and the total throughput shows no discernable change. So we&#8217;re now serving the same bandwidth that was swamping the cpus under httpd with next to no cpu with Nginx.</p>
<p>During the ongoing process of tracking the load on Central, we found a surprising number of large organizations out there with a very high connection usage. Please, if you&#8217;re using Maven in an enterprise, do us both a favor and install a repository manager such as <a rel="nofollow" target="_blank" href="http://nexus.sonatype.org/">Nexus</a>. The entire community will benefit because the Central repo will be able to serve the needed artifacts in a timely fashion. You will benefit because it will give you centralized control over your artifacts, less external bandwidth use, less dependency on an external connection, indexing, searching and storage of your internal artifacts, and a ton of other functionality.</p>
<img src="http://feeds.feedburner.com/~r/SonatypeBrian/~4/438476766" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/438499085" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/SonatypeBrian/~3/438476766/</feedburner:origLink></item>
      <item>
         <title>Sonatype: Free Maven, m2eclipse, Nexus &amp; Hudson training in New Orleans!</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499086/</link>
         <description>At Sonatype we&amp;#8217;re always working on our training material and always looking for better ways to improve it. Brian Fox, Bruce Snyder, and myself are going to be at ApacheCon this year to catch up with folks so we decided to provide a free one day training to gather feedback on the course material we [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/jvanzyl/?p=268</guid>
         <pubDate>Tue, 28 Oct 2008 08:11:08 -0700</pubDate>
         <content:encoded><![CDATA[<p><a rel="nofollow" target="_blank" href="http://us.apachecon.com/c/acus2008/"><img class="alignright size-medium wp-image-283" src="http://blogs.sonatype.com/people/jvanzyl/files/2008/11/acus08basic1-300x80.jpg" alt="" width="300" height="80"/></a>At Sonatype we&#8217;re always working on our training material and always looking for better ways to improve it. <a rel="nofollow" target="_blank" href="http://blogs.sonatype.com/people/brian">Brian Fox</a>, <a rel="nofollow" target="_blank" href="http://bsnyderblog.blogspot.com/">Bruce Snyder</a>, and myself are going to be at ApacheCon this year to catch up with folks so we decided to provide a free one day training to gather feedback on the course material we have produced. The training will be held at the <a rel="nofollow" target="_blank" href="http://www.marriott.com/hotels/travel/msyla-new-orleans-marriott/">Marriot</a> on Tuesday November 4th from 9am to 4pm. If you come to the training you&#8217;ll learn about learn about:</p> <ul>
<li><a rel="nofollow" target="_blank" href="http://maven.apache.org">Maven</a></li>
<li><a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org">m2eclipse</a></li>
<li><a rel="nofollow" target="_blank" href="http://nexus.sonatype.org">Nexus</a></li>
<li><a rel="nofollow" target="_blank" href="http://hudson.dev.java.net/">Hudson</a></li>
</ul> <p>This course is intended for folks who are already somewhat familiar with Maven as the goal of the course is to show you how to setup your development environment where Maven is working optimally for a team setup, your developers are productive with Maven in Eclipse with m2eclipse, where your team artifacts are managed and secured by Nexus, and your build automation is humming along in Hudson.</p> <p>We don&#8217;t have a lot of room available as this was a spontaneous decision given our training material is coming along faster then we expected. If you are interested in participating please email as at training at sonatype dot com and we&#8217;ll get you signed up. This is on a first come, first serve basis so if you&#8217;re interested I suggest you sign up quickly!</p> <p>Everyone is welcome to sign up for the training. If you happen to be at ApacheCon or if you live in the area and are interested in Maven related technologies then by all means sign up!</p>
<img src="http://feeds.feedburner.com/~r/sonatype-jason/~4/438476399" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/438499086" height="1" width="1"/>]]></content:encoded>
         <category>Uncategorized</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/sonatype-jason/~3/438476399/</feedburner:origLink></item>
      <item>
         <title>Nexus as a War</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499087/</link>
         <description>One of the most requested features of Nexus has been to bundle it as a war. Well, i just finished testing 1.1 as a war in Jetty and Tomcat and it looks good. So stay tuned, the 1.1 release is just around the corner and the war bundle will be included.</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/brian/?p=177</guid>
         <pubDate>Tue, 28 Oct 2008 06:18:34 -0700</pubDate>
         <content:encoded><![CDATA[<p>One of the most requested features of Nexus has been to bundle it as a war. Well, i just finished testing 1.1 as a war in Jetty and Tomcat and it looks good. So stay tuned, the 1.1 release is just around the corner and the war bundle will be included.</p>
<img src="http://feeds.feedburner.com/~r/SonatypeBrian/~4/438476767" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/438499087" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/SonatypeBrian/~3/438476767/</feedburner:origLink></item>
      <item>
         <title>m2eclipse: Importing from Subversion and Materializing from a POM</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499088/</link>
         <description>I just published this screencast which provides a quick demonstration of importing projects from Subversion and materializing a project from a Maven POM. m2eclipse has some compelling features that allow you to quickly import existing projects from Subversion. If you point m2eclipse at a Subversion repository that contains a Maven multi-module project, m2eclipse can [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=157</guid>
         <pubDate>Fri, 24 Oct 2008 13:04:13 -0700</pubDate>
         <content:encoded><![CDATA[<p>I just published <a rel="nofollow" target="_blank" href="http://vimeo.com/2057706">this screencast</a> which provides a quick demonstration of importing projects from Subversion and materializing a project from a Maven POM.</p>
<p style="text-align:center;"><br/>  </p> 
<p><a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org"><span id="more-157"></span>m2eclipse</a> has some compelling features that allow you to quickly import existing projects from Subversion. If you point m2eclipse at a Subversion repository that contains a Maven multi-module project, m2eclipse can checkout all of the source code, scan the code for Maven projects and create Eclipse projects from the information stored in the project POMs.</p>
<p>You can also &#8220;materialize&#8221; a project from a POM. <a rel="nofollow" target="_blank" href="http://vimeo.com/2057706">The screencast</a> demonstrates the materialization of commons-beanutils and then the materialization and import of one of the dependencies of commons-beanutils.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/438475453" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/438499088" height="1" width="1"/>]]></content:encoded>
         <category>Uncategorized</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/438475453/</feedburner:origLink></item>
      <item>
         <title>Bechtolsheim’s lesson</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499089/</link>
         <description>Bechtolsheim helped turn Sun, Granite, Google, VMWare and now Arista into some of the most successful startups ever. You could pick worse role models than Andreas von Bechtolsheim, when it comes to starting a company.
The Sonatype I joined is a loose confederation of top open source developers, tackling really hard problems, validated by some of the [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/mark/?p=8</guid>
         <pubDate>Thu, 23 Oct 2008 23:14:30 -0700</pubDate>
         <content:encoded><![CDATA[<p><img class="alignright size-thumbnail wp-image-13" src="http://blogs.sonatype.com/people/mark/files/2008/11/sonatype-logo-150.png" alt="" width="150" height="47"/>Bechtolsheim helped turn Sun, Granite, Google, VMWare and now Arista into some of the most successful startups ever. You could pick worse role models than <a rel="nofollow" target="_blank" href="http://en.wikipedia.org/wiki/Andy_Bechtolsheim">Andreas von Bechtolsheim</a>, when it comes to starting a company.</p>
<p><span id="more-8"></span>The Sonatype I joined is a loose confederation of top open source developers, tackling really hard problems, validated by some of the largest enterprise software development teams in the world. Jason Van Zyl and Brian Fox have managed to get this team focused, and they are delivering iterations on Maven, Nexus and M2Eclipse with better predictability than most more traditional teams I have worked with. And the users I talk to are excited about and keen to use these products.</p>
<p>So what should I do as the new CEO of this company? Many would choose to impose structure and bring in an executive team than will predict revenues, define corporate messaging, create multi-year product schedules, international expansion and more.</p>
<p>See what Bechtolsheim has to say in this <a rel="nofollow" target="_blank" href="http://www.nytimes.com/2008/10/23/technology/start-ups/23switch.html">New York Times article</a>: “One mistake a lot of start-ups make with the encouragement of venture capitalists is to hire the whole management team upfront, You have a lot of people twiddling their thumbs and spending money.”</p>
<p>It resonates with me. Customers are already expressing interest, so rather than invest in aggressive marketing and sales, let me make it easy for these customers to transact with us. Rather than having product managers offering R&amp;D their own biased opinions, let me further facilitate the conversation between users and our engineers. And rather than drive to an &#8216;industry standard&#8217; percentage for R&amp;D costs, G&amp;A, Marketing and Sales, let me minimize all the none-core staffing.</p>
<p>A venture backed company like Sonatype needs to impress investors, and high-profile executives coming from top enterprise software companies are a standard way to do so. I suggest that the VC&#8217;s should be impressed instead by our focus on open source to drive product excellence and corporate communications.</p>
<img src="http://feeds.feedburner.com/~r/MarksSonatypeBlog/~4/438477578" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/438499089" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MarksSonatypeBlog/~3/438477578/</feedburner:origLink></item>
      <item>
         <title>Browsing Javadoc for Dependencies in Eclipse: m2eclipse</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499090/</link>
         <description>I created this video as a response to Martjin Dashorst&amp;#8217;s post on why Javadoc isn&amp;#8217;t distributed with Wicket. Given the ease with which you can browse Javadoc in m2eclipse, I think the days of cutting a &amp;#8220;distribution&amp;#8221; with aggregated Javadoc are behind us. While it is entirely possible to create [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/book/?p=141</guid>
         <pubDate>Thu, 23 Oct 2008 21:14:48 -0700</pubDate>
         <content:encoded><![CDATA[<p>I created <a rel="nofollow" target="_blank" href="http://www.vimeo.com/2057354">this video</a> as a response to <a rel="nofollow" target="_blank" href="http://martijndashorst.com/blog/2008/10/22/no-javadoc-in-wicket-distribution/">Martjin Dashorst&#8217;s post on why Javadoc isn&#8217;t distributed with Wicket</a>. Given the ease with which you can browse Javadoc in m2eclipse, I think the days of cutting a &#8220;distribution&#8221; with aggregated Javadoc are behind us. While it is entirely possible to create aggregated Javadoc with Maven, I wanted to use this as an opportunity to show people how simple it is to browse Javadoc and Source in m2eclipse.</p>
<p style="text-align:center;"><br/>  </p> 
<h4><span id="more-141"></span>The Javadoc is Already in the Maven Repository</h4>
<p>If people are looking for JavaDoc, point them at the Maven Repository - they can use m2eclipse to easily browse the Javadoc. You&#8217;ve already published the Javadoc and the Source code for Wicket 1.3.5 <a rel="nofollow" target="_blank" href="http://repo1.maven.org/maven2/org/apache/wicket/wicket/1.3.5/">alongside the Wicket JARs</a>. If you want to point people toward the easiest way to read JavaDoc, point people at this <a rel="nofollow" target="_blank" href="http://www.vimeo.com/2057354">5 minute video screencast</a>. This screencast demonstrates:</p>
<ol>
<li>Creating a Wicket project using the Maven Archetype</li>
<li>Configuring Eclipse to download the Source and JavaDoc archives</li>
<li>Browsing Wicket JavaDoc using Eclipse</li>
<li>Browsing Wicket Source using Eclipse</li>
<li>Starting Jetty using m2eclipse</li>
</ol>
<p><a rel="nofollow" target="_blank" href="http://m2eclipse.sonatype.org">m2eclipse</a> makes most of this trivial, and it should reduce the pressure on you to have to jump through all the hoops necessary to create aggregate Javadoc in the Wicket distribution. &#8220;You want Javadoc? We&#8217;ve published all the Javadoc in the Maven repository.&#8221;</p>
<h4>&#8230;but if you really need to generate aggregate Javadoc&#8230;</h4>
<p>The more direct answer to Martjin&#8217;s core problem - generating Javadoc to include in the Wicket distribution: I understand his frustration with the Maven Site plugin, I share it and have gone to great lengths to avoid using it. But, it should be easy to generate aggregate JavaDoc for Wicket. My advice would be to forget the Maven Site plugin and:</p>
<ul>
<li>Bind <em>javadoc:aggregate</em> to a phase in the top-level project.</li>
<li>Include the resulting <em>${basedir}/target/site/apidocs</em> in your Wicket distribution assembly</li>
</ul>
<p>I ran javadoc:aggregate for a while to generate aggregate Wicket Javadoc on Minotaur, but I&#8217;ve stopped doing this in favor of just configuring m2eclipse to automatically download sources in m2eclipse. I understand that such an answer isn&#8217;t going to satisfy people that don&#8217;t use Eclipse as an IDE, but nothing stops others from developing tools that make use of the Javadoc and Source code available in the Maven repository. Anyway, hope this helps.</p>
<img src="http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~4/438475454" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/438499090" height="1" width="1"/>]]></content:encoded>
         <category>Uncategorized</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/MavenTheDefinitiveBlog/~3/438475454/</feedburner:origLink></item>
      <item>
         <title>What is Mercury?</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499092/</link>
         <description>Mercury is a serious attempt to: Decouple major Maven components, making them available as stand-alone building blocks rather then having Maven as as one big monolith, not usable outside of its environment. Artifact - clearly separate an Artifact from its metadata.
Repository - convert a repository into active component. It used to give back just pathOf(), now it [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/oleg/?p=52</guid>
         <pubDate>Tue, 21 Oct 2008 17:51:55 -0700</pubDate>
         <content:encoded><![CDATA[<p>Mercury is a serious attempt to:</p> <ul>
<li>Decouple major Maven components, making them available as stand-alone building blocks rather then having Maven as as one big monolith, not usable outside of its environment. <ul>
<li><strong>Artifact</strong> - clearly separate an Artifact from its metadata.</li>
<li><strong>Repository</strong> - convert a repository into active component. It used to give back just pathOf(), now it accepts GAV collections and gives back either metadata or full blown Artifacts.</li>
<li><strong>Transport</strong> - an API in development. </li>
<li><strong>DependencyTreeBuilder</strong> main API for dependency graph creation and conflict resolution. </li>
</ul></li>
<li>Decouple container, so that these components are just plain pojos.</li>
<li>Introduce <strong>Jetty</strong>-based HTTP/HTTPS and WebDAV transactional transport layer. <ul>
<li>Asynchronous downloads and uploads. One of the few successful usages of Java NIO in OSS.</li>
<li>Transactional operations - all-or-nothing for file sets.</li>
<li>Move integrity control into transport layer, upper level components should not care about these details.</li>
</ul></li>
<li>Abstract out metadata cache, provide at least one implementation there.</li>
<li>Integrate these changes back to Maven 3.x to make it even better platform than it is right now (if it is possible to be better <img src='http://blogs.sonatype.com/people/oleg/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley'/> )</li>
</ul> <p>Currently Mercury can already be used for accessing repositories, and conflict resolution is under testing.</p>
<img src="http://feeds.feedburner.com/~r/OlegsBlog/~4/438479188" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/438499092" height="1" width="1"/>]]></content:encoded>
      <feedburner:origLink>http://feeds.feedburner.com/~r/OlegsBlog/~3/438479188/</feedburner:origLink></item>
      <item>
         <title>A Late Report on a Late Event</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499094/</link>
         <description>It&amp;#8217;s been more than a year that I&amp;#8217;m working for Sonatype (mainly on Nexus), the successor of Proximity. It was a great year, spent with cool people, and with great events like (in order as they happened): my daughter was born,
we released Nexus 1.0 to general public. The events were originally planned to be in the opposite [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/tamas/?p=12</guid>
         <pubDate>Tue, 21 Oct 2008 07:34:36 -0700</pubDate>
         <content:encoded><![CDATA[<p>It&#8217;s been more than a year that I&#8217;m working for Sonatype (mainly on Nexus), the successor of Proximity. It was a great year, spent with cool people, and with great events like (in order as they happened):</p>
<ul>
<li>my daughter was born,</li>
<li>we released Nexus 1.0 to general public.</li>
</ul>
<p>The events were originally planned to be in the opposite order, but Brian was delaying Nexus with his nitty-gritty wishes &#8212; you know him <img src='http://blogs.sonatype.com/people/tamas/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley'/> &#8211;, and my daughter decided to take over. All this happened before almost 8 months. So, sorry for this late report.</p>
<p>But since then, my daughter was contributing a lot to quality, design and implementation of Nexus MRM. Almost at the start, she jumped in the role of &#8220;lead gaffer&#8221; (it resembles the &#8220;superman&#8221; pose slightly):</p>
<p style="text-align:center;"><a rel="nofollow" target="_blank" href="http://picasaweb.google.com/lh/photo/g_mQIwigU30CRQQ1KrEX8A"><img src="http://lh3.ggpht.com/t.cservenak/SBZxN_qhcKI/AAAAAAAAAig/x3i4Wm_oeb0/s144/dsc00854.jpg" alt=""/></a></p>
<p>Also, she insisted on using the &#8220;thinking hat&#8221; very much, when solving almost impossible tasks requested by Brian:</p>
<p style="text-align:center;"><a rel="nofollow" target="_blank" href="http://picasaweb.google.com/lh/photo/KpfXzEkdOcLDwjcVI9XbFg"><img src="http://lh4.ggpht.com/t.cservenak/SP3hbdDxjbI/AAAAAAAABCg/8ZgBC9i5OJ0/s144/DSC00061.JPG" alt=""/></a></p>
<p>Examined all the tools she had at disposal to solve problems:</p>
<p style="text-align:center;"><a rel="nofollow" target="_blank" href="http://picasaweb.google.com/lh/photo/I2HVoAnFIAE7e8R_ZIw1Pw"><img src="http://lh3.ggpht.com/t.cservenak/SP3ifYgsuGI/AAAAAAAABC4/dpqSYQuiE4c/s144/DSC00013.JPG" alt=""/></a></p>
<p>She had a lot of &#8220;developer to developer&#8221;-like consultations with some open-source gurus:</p>
<p style="text-align:center;"><a rel="nofollow" target="_blank" href="http://picasaweb.google.com/lh/photo/SNkO3yO9mrH7SfkwCrJIXA"><img src="http://lh3.ggpht.com/t.cservenak/SODWN22PTYI/AAAAAAAAA14/E3oHFTxLeNs/s144/_9241879.JPG" alt=""/></a></p>
<p>And attended the &#8220;How to write server applications to suite all Brian&#8217;s needs, 2008&#8243; conference held in Prague (no, she was not having beer, rather just &#8220;light refreshing discussion&#8221;):</p>
<p style="text-align:center;"><a rel="nofollow" target="_blank" href="http://picasaweb.google.com/lh/photo/dqdvGm7AEXKrXmXx2g7VQQ"><img src="http://lh6.ggpht.com/t.cservenak/SP3khU5LbwI/AAAAAAAABC8/Qd4wMu2mV4w/s144/_9241887_2.JPG" alt=""/></a></p>
<p>&#8212;</p>
<p>Oh, and why was it a &#8220;late event&#8221;? Since we have a huge shift in timezones (I am GMT+2, Brian is GMT-4 and mr. Cupertino is usually GMT-7, if not at home), and I am the &#8220;minority&#8221; &#8212; at least in head-count. So, the common sense dictated that I should live the &#8220;vampire life&#8221; and follow their work hours, as I did.</p>
<p>And my daughter Petra was patient, she waited for me to finish, and came at the end of my work day, hence, in late hours in local time.</p>
<img src="http://feeds.feedburner.com/~r/TamasSonatypeBlog/~4/438479914" height="1" width="1"/><img src="http://feeds.feedburner.com/~r/sonatype/~4/438499094" height="1" width="1"/>]]></content:encoded>
         <category>Nexus</category>
      <feedburner:origLink>http://feeds.feedburner.com/~r/TamasSonatypeBlog/~3/438479914/</feedburner:origLink></item>
      <item>
         <title>Mercury - externalized dependencies</title>
         <link>http://feeds.feedburner.com/~r/sonatype/~3/438499095/</link>
         <description>Inspiration In Mercury we made an attempt to bring some contemporary ideas into Maven, make Maven not a monolithic build system, but rather a lego-like construction set that allows users to create systems they need. One set of building blocks in particular - implementation of the idea that dependencies is a universal commodity, that [...]</description>
         <guid isPermaLink="false">http://blogs.sonatype.com/people/oleg/?p=4</guid>
         <pubDate>Mon, 20 Oct 2008 17:27:08 -0700</pubDate>
         <content:encoded><![CDATA[<h2>Inspiration</h2> <p>In Mercury we made an attempt to bring some contemporary ideas into Maven, make Maven not a monolithic build system, but rather a lego-like construction set that allows users to create systems they need. One set of building blocks in particular - implementation of the idea that dependencies is a universal commodity, that exists outside of Maven world. And operation of resolving conflicts on those dependencies can apply to a broader range of dependencies, not just tag in the POM file.</p> <p>For example - it should be relatively easy to plug in an implementation to read OSGi bundle dependencies. Or read a <em>.properties</em> file with dependencies.</p> <p>Or - my favorite - keep dependencies in a <a rel="nofollow" target="_blank" href="http://www.jboss.org/drools/" title="Drools home page">Drools</a>-backed DSL file. I will try to
create this implementation after we integrate Maven POM dependency reader into Mercury.</p> <p>How is it done:</p> <ul>
<li>Dependency trees and manipulated by <strong>DependencyTreeBuilder</strong> object</li>
<li>DependencyTreeBuilder instance is created out of a collection of <strong>Repositories</strong> (to find Artifacts)
and and instance of <strong>DependencyProcessor</strong>.</li>
<li>DependencyProcessor abstraction is that externalization component for reading/processing dependencies, making the builder independent of actual dependency information storage</li>
</ul> <h2>Exapmple code</h2> <div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
</pre></td><td class="code"><pre class="java java" style="font-family:monospace;