Project

Profile

Help

Issue #2665

API documentation doesn't explain how to manage tags

Added by Ichimonji10 over 4 years ago. Updated over 2 years ago.

Status:
CLOSED - WONTFIX
Priority:
Normal
Assignee:
-
Start date:
Due date:
Estimated time:
Severity:
2. Medium
Version - Docker:
Platform Release:
Target Release - Docker:
OS:
Triaged:
Yes
Groomed:
No
Sprint Candidate:
No
Tags:
Pulp 2
Sprint:
Quarter:

Description

Let's say I've created and populated a docker repository, and that I'd now like to create a new tag, or update an existing tag. How do I do that? If using pulp-admin, it's doable. I can look at the recipes on GitHub. But what if I want to do that via the API? There's no guidance on how to work with the API. In order to work with the API endpoints exposed by the pulp_docker plugin, I find myself running pulp-admin -vvv .... That's no fun. :(

To take a specific example, let's say that I have a repository containing a tag with the name "latest." How do I update this tag? Intuitively, I'd expect that I can make a POST or PUT request to this tag's _href. In reality, tags don't have an _href, or at least none that's advertised by the API. Here's an example of information about a tag from a search:

[{'_id': {'$oid': '58d40d036b45ba954e332fe3'},
  'created': '2017-03-23T17:59:31Z',
  'metadata': {'_content_type_id': 'docker_tag',
               '_id': '6cf8e32b-5ae9-476f-9e1c-450676a3b904',
               '_last_updated': 1490291971,
               '_ns': 'units_docker_tag',
               'manifest_digest': 'sha256:32f093055929dbc23dec4d03e09dfe971f5973a9ca5cf059cbfb644c206aa83f',
               'name': 'latest',
               'pulp_user_metadata': {},
               'repo_id': 'db333e84-52a7-49a3-81e8-cf84435b6824',
               'schema_version': 2},
  'repo_id': 'db333e84-52a7-49a3-81e8-cf84435b6824',
  'unit_id': '6cf8e32b-5ae9-476f-9e1c-450676a3b904',
  'unit_type_id': 'docker_tag',
  'updated': '2017-03-23T17:59:31Z'}]

There's no _href. Instead, a request is made to {repository_href}/actions/import_upload/. Fair enough. It's not what I expected, but it makes some sense.

Now, what's included in the body of the POST request? Intuitively, I would expect that I could send something like this:

{
  'metadata': {'manifest_digest': 'sha256:some-new-value'},
  'unit_id': '6cf8e32b-5ae9-476f-9e1c-450676a3b904',
}

What I've done is named the unit that I want to update (because that information isn't embedded in the path I'm POSTing to) and twiddled some of the attributes as they were in response to my GET request, earlier. But that doesn't work. In reality, the body of the request should look like this:

{'unit_key': {'name': 'latest',
              'repo_id': '1f399fa7-7109-45be-bbae-15baa92c369a'},
 'unit_metadata': {'digest': 'sha256:d71ce73158269ca5688e129fd8a6dbc47e449b0608e0ec1603a0408dff575a5e',
                   'name': 'latest'},
 'unit_type_id': 'docker_tag'}

Why do I need to insert 'name': 'latest' into this request twice? I don't know. Again, the reason I know how to make this request is that I've observed the output of pulp-admin -vvv ....

Can we improve this situation? It's not fun to write tests for a plugin that only has pulp-admin documentation. It's also hard to fix the tests that have broken in 2.13 (due to an backwards-incompatible change in manifest paths - is that OK?) without knowing this stuff.

History

#1 Updated by Ichimonji10 over 4 years ago

  • Description updated (diff)

#2 Updated by Ichimonji10 over 4 years ago

  • Description updated (diff)

#3 Updated by ttereshc over 4 years ago

  • Triaged changed from No to Yes

Someone will explain it in person or fixed this issue before the release.

#4 Updated by daviddavis over 4 years ago

@Ichimonji10 will try to answer some questions that you raise.

First off, to give you some background, the docker tag API was based off our upload API for langpacks (for better or for worse) . More info:

https://github.com/pulp/pulp_rpm/pull/863
https://pulp.plan.io/issues/1367
https://github.com/PulpQE/pulp-smash/issues/234

Intuitively, I'd expect that I can make a POST or PUT request to this tag's _href.

This sounds like something that would be nice to have although I think we'd just want PUT? Not sure what a POST would do to the url for an existing tag.

Now, what's included in the body of the POST request? Intuitively, I would expect that I could send something like this:

This would only work for updating tags and we're using a single endpoint for both creating and updating docker tags. I'd argue that we use import_upload to both create/update units elsewhere in say pulp_rpm (albeit by uploading a file). However, I wouldn't be opposed to splitting this up into two endpoints like you outline.

Why do I need to insert 'name': 'latest' into this request twice?

I think this is a good question. Scanning the code, I am not sure that tag name needs to be passed in unit_key and unit_metadata so I think we should investigate.

#5 Updated by Ichimonji10 over 4 years ago

  • Description updated (diff)

#6 Updated by Ichimonji10 over 4 years ago

Intuitively, I'd expect that I can make a POST or PUT request to this tag's _href.

This sounds like something that would be nice to have although I think we'd just want PUT? Not sure what a POST would do to the url for an existing tag.

Concisely: issuing a POST request to an existing resource performs a non-idempotent update of that resource.

Verbosely: Both POST and PUT can be used to create a new resource. Similarly, both POST and PUT can be used to modify an existing resource. However, POST and PUT are not interchange-able. Their usages and effects differ.

PUT requests are simpler. When a PUT request is made to a URL, the body of that request is stored at that URL (in some form). End of story. Was there already a resource at that URL? It'll be replaced. Was there no resource at that URL? One will be created. PUT requests are idempotent, meaning that repeated PUT requests to the same URL produce the same resource. This is possible because the body of a PUT request is a complete description of a resource.

POST requests are more odd. POST requests can only be made to existing resources. If one POSTs to /reports/5 and that report doesn't exist, an HTTP 404 is returned. But what if /reports/5 does exist? In this case, POSTing to /reports/5 causes that report to be updated. Sounds like PUT, right? Not quite. If repeated POST requests are made to a resource, then that resource can look different after each request. This is possible because the body of a POST request isn't guaranteed to be a complete description of a resource.

To summarize: PUT requests are idempotent, and they can be made to existing and non-existent resources. POST requests are non-idempotent, and they can only be made to existing resources.

I think this is a good question. Scanning the code, I am not sure that tag name needs to be passed in unit_key and unit_metadata so I think we should investigate.

Thanks.

#7 Updated by bmbouter over 2 years ago

  • Status changed from NEW to CLOSED - WONTFIX

#8 Updated by bmbouter over 2 years ago

Pulp 2 is approaching maintenance mode, and this Pulp 2 ticket is not being actively worked on. As such, it is being closed as WONTFIX. Pulp 2 is still accepting contributions though, so if you want to contribute a fix for this ticket, please reopen or comment on it. If you don't have permissions to reopen this ticket, or you want to discuss an issue, please reach out via the developer mailing list.

#9 Updated by bmbouter over 2 years ago

  • Tags Pulp 2 added

Please register to edit this issue

Also available in: Atom PDF