Skip to content

Allow to define the API version where a endpoint is available #2380

Closed
@jcagarcia

Description

@jcagarcia

Hey 👋

I want to share a possible improvement for reusing the same endpoint through different api versions.

I have the v1 of my API that only exposes the /foo endpoint.

class MyAPI < Grape::API
  class MyError < StandardError; end

  version 'v1', using: :path

  get '/foo' do
    { version: version }
  end
end
GET /v1/foo => { version: "v1" }

For the next version of my API, I want to add a new endpoint /var

class MyAPI < Grape::API
  class MyError < StandardError; end

  version 'v1', using: :path

  get '/foo' do
    { version: version }
  end

  version 'v2', using: :path

  get '/var' do
    { version: version }
  end
end

The examples above results in:

GET /v1/foo => { version: "v1" }
GET /v2/var => { version: "v2" }

But if i try to access the /foo endpoint in my v2 version I'm getting a 404.

GET /v2/foo => 404
GET /v2/var => { version: "v2" }

Taking a look to the code (not present in the documentation), seems I can specify multiple versions if passing an array of values

class MyAPI < Grape::API
  class MyError < StandardError; end

  version 'v1', 'v2',  using: :path

  get '/foo' do
    { version: version }
  end

  get '/var' do
    { version: version }
  end
end

So now, both endpoints are available under v1 and v2 endpoint.

GET /v1/foo => { version: "v1" }
GET /v1/var => { version: "v1" }
GET /v2/foo => { version: "v2" }
GET /v2/var => { version: "v2" }

However, this is not desired behavior. As /foo should be available in v2, but /var should not be present in /v1.

My proposal is to configure each of the endpoints for being available in the different versions of the api. For example, using a for_versions method like:

class MyAPI < Grape::API
  class MyError < StandardError; end

  version 'v1', 'v2', using: :path

  get '/foo', for_versions: ['v1', 'v2'] do
    { version: version }
  end

  get '/var', for_versions: ['v2'] do
    { version: version }
  end
end

And expecting this behavior:

GET /v1/foo => { version: "v1" }
GET /v1/var => 404
GET /v2/foo => { version: "v2" }
GET /v2/var => { version: "v2" }

What do you think about this approach?

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions