I am quite a new user of artifactory and at the moment would like to check the number of docker images in an already existing setup. I have several docker registries in artifactory and would like to automate this check. Is there an api for it maybe?
Thanks for all help :)
BR,
Rafal.
You can use AQL for searching all the manifest.json files (since each image has exactly one such file).
For example (using curl):
curl -XPOST https://your.artifactory.domain/api/search/aql -T aql.json -u user:pass
Where aql.json is:
items.find({"repo":"docker-local","name":"manifest.json","path":{"$match":"*"}}).include("repo","path","name")
The query above searches for all the manifest.json files in the docker-local repository under any path (match *). It returns the following (example):
{
"results" : [ {
"repo" : "docker-local",
"path" : "hello-world/latest",
"name" : "manifest.json"
}, {
"repo" : "docker-local",
"path" : "hello-world/1.0",
"name" : "manifest.json"
} ],
"range" : {
"start_pos" : 0,
"end_pos" : 2,
"total" : 2
}
}
You can take the range.total as the number of images.
HTH,
Yinon
Related
Artifactory 6.9.1
The artifact existing in the Artifactory is shown below:
I am using the following query based on the REST API doc. for artifact version search:
curl --request GET "https://repository.net/artifactory/api/search/versions?g=com.name&a=core-api-error&repos=core-services&v=0.4.0-56204b7*"
{
"results" : [ {
"version" : "0.4.0-56204b7",
"integration" : false
} ]
}
but if I try to use the exact version by removing '*' from the 'v' argument,
curl --request GET "https://repository.name.net/artifactory/api/search/versions?g=com.name&a=core-api-error&repos=core-services&v=0.4.0-56204b7"
{
"errors" : [ {
"status" : 404,
"message" : "Unable to find artifact versions"
} ]
}
The usage of '*' is dangerous as it might return some other versions. I just want to check if the artifact with that version exists.
I'm able to search using
GET /api/search/prop?[p1=v1,v2][&p2=v3][&repos=x[,y]]
as per the documentation. But how to use optional headers to get extra information for the found artifacts?
You need to set the HTTP header X-Result-Detail to properties. Using a curl command it would look something like this
curl -uUSERNAME:PASSWORD --request GET \
--url 'http://jfrog.local/artifactory/api/search/prop?build.number=1&repos=generic-prod' \
--header 'X-Result-Detail: properties'
This will look in my repository called generic-prod for all artifacts that have build.number = 1 as a property.
That would return with the results you're looking for
{
"results" : [ {
"properties" : {
"build.name" : [ "docker-jenkins-build" ],
"build.number" : [ "1" ],
"build.timestamp" : [ "1556557591780" ]
},
"uri" : "http://jfrog.local:80/artifactory/api/storage/generic-prod/jenkins.zip"
} ]
}
This lists the properties I have for my artifact.
I am trying to query which build number(s) produced artifacts from build foo with artifact property vcs.Revision=aabbccddee123456.
In Artifactory 5.1.3.
I was trying like this so far:
curl -u user:apikey -i -X POST https://artifactory.foobar.com/artifactory/api/search/aql -H "content-type:text/plain" -T query.json
query.json:
builds.find(
{
"module.artifact.item.repo":"snapshot-local",
"name":"foo",
"module.artifact.item.#vcs.Revision":"aabbccddee123456"
}
)
However, none of these 3 lines seem individually correct:
builds.find({"module.artifact.item.repo":"snapshot-local"})
returns nothing,
builds.find({"name":"foo"})
returns the same empty response,
builds.find({"module.artifact.item.#vcs.Revision":"aabbccddee123456"}) also returns this:
{
"results" : [ ],
"range" : {
"start_pos" : 0,
"end_pos" : 0,
"total" : 0
}
}
What am I doing wrong here? I do see in the webapp the builds I published with this name, and with the correct artifact properties.
Here's a working solution that will give build numbers (since giving admin rights to query builds is not a solution for us):
query.json:
items.find(
{
"repo":"snapshot-local",
"artifact.module.build.name":"foo",
"artifact.item.#vcs.Revision":"aabbccddee123456"
}
).include("artifact.module.build.number")
This returns a list of all the artifacts that were built with the relevant properties, with the build number attached, e.g:
{
"results" : [ {
"repo" : "snapshot-local",
"path" : "foo/42",
"name" : "a.out",
"type" : "file",
"size" : 123456789,
"created" : "2018-07-05T12:34:56.789+09:00",
"created_by" : "jenkins",
"modified" : "2018-07-05T12:34:56.789+09:00",
"modified_by" : "jenkins",
"updated" : "2018-07-05T12:34:56.789+09:00",
"artifacts" : [ {
"modules" : [ {
"builds" : [ {
"build.number" : "42"
} ]
} ]
} ]
},
[SNIP]
}
],
"range" : {
"start_pos" : 0,
"end_pos" : 30,
"total" : 30
}
}
I can then parse this to extract build.number.
Certain AQL queries requires a user with admin permissions.
To ensure that non-privileged users do not gain access to information without the right permissions, users without admin privileges have the following restrictions:
The primary domain in the query may only be item.
The following three fields must be included in the include directive: name, repo, and path.
In your case, you are using the build domain in the query which requires admin permissions
I am using Artifactory 4.8.0 (OSS)
I have deployed artifacts to 2 repos: libs-devel and libs-release-candidates.
When I execute
$ curl -u denham:password -X GET https://artifactory.server/artifactory/api/search/artifact?name=MyPackage&repos=libs-devel
The response I receive is:
"results" : [ {
"uri" : "https://artifactory.server/artifactory/api/storage/libs-devel/com/acme/MyPackage/17.10.1-SNAPSHOT/MyPackage-17.10.1-20170908.092803-1.pom"
}, {
"uri" : "https://artifactory.server/artifactory/api/storage/libs-devel/com/acme/MyPackage/17.10.1-SNAPSHOT/MyPackage-17.10.1-20170908.092803-1.war"
}, {
"uri" : "https://artifactory.server/artifactory/api/storage/libs-release-candidates/com/acme/MyPackage/17.10.1-24/MyPackage-17.10.1-24.pom"
}, {
"uri" : "https://artifactory.server/artifactory/api/storage/libs-release-candidates/com/acme/MyPackage/17.10.1-24/MyPackage-17.10.1-24.war"
}, {
"uri" : "https://artifactory.server/artifactory/api/storage/libs-devel/com/acme/MyPackage/17.9.3-SNAPSHOT/MyPackage-17.9.3-20170907.105908-1.pom"
}, {
"uri" : "https://artifactory.server/artifactory/api/storage/libs-devel/com/acme/MyPackage/17.9.3-SNAPSHOT/MyPackage-17.9.3-20170907.105908-1.war"
} ]
}
I would expect that the results would be limited to the the libs-devel repo, as specified in the url.
Have I done something wrong? Is this a bug?
Here's the API reference (for version 4) that I followed:
https://www.jfrog.com/confluence/display/RTF4X/Artifactory+REST+API#ArtifactoryRESTAPI-ArtifactSearch(QuickSearch)
Thanks in advance.
Yes. This is correct.
You will be able to limit the search query to specific repositories by adding the 'repos' parameter on this rest call.
We (JFrog) are not familiar with a bug on this subject and it is working on our side (Artifactory OSS - same version: 4.8.0).
We will be interested to know if the same is working for you using the UI quick search.
If using curl, the full URL needs to be encapsulated in quotes. Otherwise the & is left off the request.
I tried using Postman and it works as expected.
Bested by quote marks. :-(
According to below link, Artifactory AQL allows "Displaying of specific fields" via REST API by returning only fields of interest.
https://www.jfrog.com/confluence/display/RTF/Artifactory+Query+Language#ArtifactoryQueryLanguage-DisplayingSpecificFields
It doesn't work if I provide a list of fields, see below
Not Work - Bad request (400)
items.find(...).include("name", "repo")
Works
items.find(...).include("*")
Can anyone advise
Thanks, Jag
I suspect that the problem is related to encoding during the REST call, therefore I suggest to upload the query as a file Here is a working example:
Save the following query to file, lets call it aql.query
items.find
(
{
"repo": {"$match":"*"}
}
)
.include("name","repo")
Run the following curl command from the same directory that contains the aql.query file and don't forget to replace the templates in the command with your user name, password, host and port.
curl -X POST -uuser:password 'http://host:port/artifactory/api/search/aql' -Taql.query
In the result you will get:
{
"results" :
[
{
"repo" : "ext-snapshot-local",
"name" : "maven-metadata.xml"
},{
"repo" : "ext-snapshot-local",
"name" : "multi-3.0.0-20150705.195404-1.pom"
},{
.
.
.
}
],
"range" :
{
"start_pos" : 0,
"end_pos" : 46,
"total" : 46
}
}
As you can see that the result contains only the "item repo" and the "item name" fields.
Had the same issue. Spent quite a bit of time trying to figure this out. Couldn't find an answer online.
With a bad request(400), I printed the response text: "For permissions reasons AQL demands the following fields: repo, path and name."
This solution worked for me -
at a minimum: have repo, path, name.
ie... items.find(...).include("name", "repo", "path", "created_by")