Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

HTTP: Is it acceptable to use the COPY method where the Destination header is not a URI?

Tags:

http

copy

rfc

api

Background

I'm building an API that allows clients to manipulate geospatial objects. These objects contain a location on the world (in latitude/longitude), and a good bit of metadata. The actual API is rather large, so I present a simplified version here.

Current API

Consider an API with two objects, features and attributes.

The feature endpoint is /api/feature and looks like:

{
    id: 5,
    name: "My super cool feature",
    geometry: {
        type: "Point",
        coordinates: [
            -88.043355345726,
            43.293055846667315
        ]
    }
}

The attribute endpoint is /api/attribute. An attribute looks like:

{
    id: 3,
    feature_id: 5,
    name: "attr-name",
    value: "value"
}

You can interact with these objects by issuing HTTP requests to their endpoints using different HTTP methods, like you might expect:

  • GET /api/feature/5 reads the feature with id 5.
  • PUT /api/feature/5 updates the feature with id 5.
  • POST /api/feature creates a new feature.
  • DELETE /api/feature/5 deletes the feature with id 5.

Same goes for attributes.

Attributes are related to features by foreign key (commonly expressed as "features have many attributes").

The Problem

It would be useful to be able to make a copy of a feature and all its metadata (all the attributes that belong to it). The use case is more or less, "I just made this feature and gave it a bunch of attributes, now I want the same thing... but over there." So the only difference between the two features would be their geometries.

Solution #1: Make the client do it.

My first thought was to just have the client do it. Create a new feature with the same name at a new location, then iterate through all the attributes on the source feature, issuing POST requests to make copies of them on the new feature. This, however, suffers from a few problems. First, it isn't atomic. Should the client's Internet connection flake out during this process, you'd be left with an incomplete copy, which is lame. Second, it'd probably be slow, especially for features with many attributes. Anyway, this is a bad idea.

Solution #2: Add copy functionality to the API.

Doing the copy server-side, in a single API call, would be the better approach. This leads me to https://www.rfc-editor.org/rfc/rfc2518#section-8.8 and the COPY method. Being able to do a deep copy of a feature in a single COPY /api/feature/5 request seems ideal.

The Question

My issue, here, is the semantics of COPY don't quite fit the use I envision for it. Issuing a COPY request on a resource executes a copy of that resource to the destination specified in the Destination header. According to the RFC, Destination must be present, and it must be a URI specifying where the copied resource will end up. In my case, the destination for the copied feature is a geometry, which is decidedly not a URI.

So, my questions are: Would stuffing json for the geometry into the Destination header of a COPY request be a perversion of the spec? Is COPY even the right thing to use, here? If not, what alternatives are there? I just want to be sure I'm implementing this in the most HTTP-kosher way.

like image 315
jpk Avatar asked Jul 26 '12 02:07

jpk


1 Answers

Well, you'll need a way to make the Destination a URI then (why is that a problem). If you're using the Destination header field for something else, you're not using COPY per spec. (And, BTW, the current specification is RFC 4918)

like image 168
Julian Reschke Avatar answered Oct 27 '22 00:10

Julian Reschke