Skip to content

Instantly share code, notes, and snippets.

@oliverdaff
Created March 29, 2012 05:47
Show Gist options
  • Star 11 You must be signed in to star a gist
  • Fork 13 You must be signed in to fork a gist
  • Save oliverdaff/2233777 to your computer and use it in GitHub Desktop.
Save oliverdaff/2233777 to your computer and use it in GitHub Desktop.
Clean up nexus artifacts with API
import groovyx.net.http.*;
import static groovyx.net.http.ContentType.*;
import static groovyx.net.http.Method.*;
class NexusArtifactCleanup {
/**
* Settings in which to run script.
*/
def settings = [
baseUrl: 'http://localhost:8083/nexus',
repositoryId: 'snapshots',
pattern: '.*SNAPSHOT',
age: 0,
nexusUsername: 'admin',
nexusPassword: 'admin'
];
/**
* MAIN Method.
*/
def static main( def args ) {
NexusArtifactCleanup cleanup = new NexusArtifactCleanup();
cleanup.cleanupArtifacts();
}
/**
* Controller method. Has 3 steps.
* 1) Find Artifacts to delete.
* 2) Delete Artifacts.
* 3) Rebuild Nexus Repository Metadata.
*/
def cleanupArtifacts() {
def nexusRepositoriesServiceUrl = settings.baseUrl + '/service/local/repositories/' + settings.repositoryId + '/content/';
def nexusMetadataServiceUrl = settings.baseUrl + '/service/local/metadata/repositories/' + settings.repositoryId + '/content/';
// Find all repository items that match the regular expression pattern defined in settings.
def urls = findArtifacts(nexusRepositoriesServiceUrl, settings.pattern, settings.age);
// The number of artifacts to be deleted.
def size = urls.size();
// Delete each artifact via the Nexus Rest API.
urls.each {
println "DELETING... " + it;
deleteContent(it, settings.nexusUsername, settings.nexusPassword);
}
// Rebuild Nexus repository metadata, if we have deleted artifacts.
if (size > 0) {
println "REBUILDING REPOSITORY METADATA... ";
rebuildRepoMetadata(nexusMetadataServiceUrl, settings.nexusUsername, settings.nexusPassword);
}
}
/**
* Finds artifacts that match the inputted regex pattern, and meet the age requirement.
*/
def findArtifacts ( String url, String pattern, int age ) {
def artifactUrls = [];
def xml = fetchContent(url);
xml.data.'content-item'.each {
def text = it.text.text();
def resourceURI = it.resourceURI.text();
def isLeaf = it.leaf.text();
if (text ==~ pattern) {
def lastModifiedDate = new Date().parse('yyyy-MM-dd HH:mm:ss.SSS z', it.lastModified.text());
if ((new Date() - age) > lastModifiedDate) {
artifactUrls << resourceURI;
}
}
if (isLeaf == 'false') {
artifactUrls += findArtifacts(resourceURI, pattern, age);
}
}
return artifactUrls;
}
/**
* Queries Nexus Repository.
*/
def fetchContent ( String url ) {
RESTClient rc = new RESTClient(url);
def response = rc.get(contentType: XML);
return response.data;
}
/**
* Deletes Nexus Artifact.
*/
def deleteContent (String url, String username, String password ) {
RESTClient rc = new RESTClient(url);
rc.auth.basic(username, password);
def response = rc.delete(contentType: ANY);
}
/**
* Rebuilds Nexus Metadata.
*/
def rebuildRepoMetadata( String url, String username, String password ) {
RESTClient rc = new RESTClient(url);
rc.auth.basic(username, password);
def response = rc.delete(contentType: ANY);
}
}
@oliverdaff
Copy link
Author

Requires

<dependency>
    <groupId>org.codehaus.groovy.modules.http-builder</groupId>
    <artifactId>http-builder</artifactId>
    <version>0.5.1</version>
</dependency>

Created by Jeff Blaisdell taken from http://maven.40175.n5.nabble.com/file/n4413284/NexusArtifactCleanup.groovy and stored here for reference.

@hujirong
Copy link

Hi Oliver

While I am trying to port this program to C#, I find the following:

  1. It's deleting the entire directory (parent directory of the artifact), this is very efficient, because deleting only the artifact will leave all the other files such as .pom, .md5, etc.
  2. It's identify the item to delete by a pattern: '.*SNAPSHOT', which locate the parent directory of the target artifact. As the directory has the same lastModified as the artifact so it works.

However, I am having a bit difficulty in the following:

  1. When I am trying to use this for a Release type of repository, I can't find a proper pattern to identify these directories. Let's say we use GitVersion or something else to version the artifacts, what's the proper pattern to be used?
  2. My another requirement is to keep the last artifact if all of them are expired (older than specified days). How to implement this?

Appreciate if you can give me some advice. Thanks!
Jirong

@andrast0th
Copy link

andrast0th commented Sep 23, 2017

Created 6 years ago, still works perfectly, thanks, this is exactly what I was looking for.
For people who want to use Grape for dependency management this seems to work:

// https://mvnrepository.com/artifact/org.codehaus.groovy.modules.http-builder/http-builder
@Grapes([
        @Grab(group = 'org.codehaus.groovy.modules.http-builder', module = 'http-builder', version = '0.6'),
        @GrabExclude('xml-apis:xml-apis'),
        @GrabExclude('xerces:xercesImpl'),
])
import groovyx.net.http.*
import static groovyx.net.http.ContentType.*

@aamirkhakhu
Copy link

Do you have something same in python?

@bpbhai
Copy link

bpbhai commented Jun 18, 2019

Does it also works for Nexus 3?

@oliverdaff
Copy link
Author

I've not tried this on Nexus 3 since I am not using Nexus any more.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment