Add a JSON-based API #381
Replies: 5 comments 8 replies
-
Regarding OAuth2, the doorkeeper gem seems robust enough and could handle the server-side logic. I see a recent issue regarding Rails 7.1, but the maintainer seems active and responsive with the project. https://doorkeeper.gitbook.io/guides/ruby-on-rails/getting-started |
Beta Was this translation helpful? Give feedback.
-
@matthewbennink I'm all in favor of making the major endpoints respond to API requests with JSON in addition to the current view templates. I think we should wait on trying to version the API. Let's get a first version working without namespacing things. I've maintained some APIs in the past and the biggest challenge with versioning isn't the routing or namespace pollution, it's the commitment to keeping old versions alive when you're doing major changes and refactoring. It's a form of technical debt that you're never allowed to pay down, until you remove the old version of the API. Let's not go there yet. That matters the most in a situation where you have an ecosystem of clients you're trying to encourage development of and you want to make this commitment to them that you'll not break old API endpoints. But your situation is one where we/you control both the backend serving the API and the front-end consuming the API so in the future you can co-evolve those in tandem. With regards to auth, how about we just do simple token key issuance which can be used as bearer tokens? Anticipating this, I already laid some foundation in another branch which will create multiple types of Credentials and Authentications. I can do the work to have a logged in user easily generate an API key (which is revokable if they ever need to) and add a before_filter that recognizes this in the Bearer field. But all the controller endpoints would need to be updated to reply appropriately. I don't have the bandwidth to take that one on. |
Beta Was this translation helpful? Give feedback.
-
With regard to handling CORS headers, are you OK with using the rack-cors gem? I've got the following working well enough in an initializer. I'm expecting the API to be available to web browsers, not just other backends. if (allowed_request_origins = ENV['ALLOWED_REQUEST_ORIGINS'].to_s.split(',')).any?
Rails.application.configure do
config.action_cable.allowed_request_origins = allowed_request_origins
config.middleware.insert_before 0, Rack::Cors do
allow do
origins allowed_request_origins
resource "*",
headers: :any,
methods: [:get, :post, :put, :patch, :delete, :options, :head],
credentials: true,
max_age: 86400
end
end
end
end The ENV variable would contain a value like |
Beta Was this translation helpful? Give feedback.
-
Hi Matthew, I think I’m on track to merge in the foundation of this stuff
tomorrow. I got about 90% of the way done today. I don’t think it’ll be
everything you need but it should be close.
I’ll have a way to generate (and revoke/re-generate) an API key from your
account page. I got the underlying authentication refactored to support
this in a nice way (and multiple other authentication schemes). I also have
a proof of concept for an application_controller level way of causing all
the actions to return API responses.
It’ll need testing and likely tweaking for some controller actions. And you
may need better API key management within settings.
|
Beta Was this translation helpful? Give feedback.
-
@matthewbennink I have an update on API response. It's taken longer than I expected — I probably shouldn't have shared with you the optimistic-programmer-estimate :) but I have a PR tee'd up now. Why don't you take a look at this and try it out: I'm really pleased with how that code turned out! In your dev environment, put a breakpoint right here: and then run that test. You can inspect the response. What you'll see is that every @instance_var that gets set within a controller action automatically gets serialized in the JSON response. So we shouldn't have to touch any controller actions. I think I managed to make them all "smart" with this single application_controller logic. The piece I didn't get done is the user-facing piece of this. I'd love help with this because I need to turn my attention to some other items this week. After you review this 407 and we get it merged in, what's left is:
|
Beta Was this translation helpful? Give feedback.
-
I wanted to start some discussion on a JSON-based API that could be used alongside the existing Hotwire-based frontend. There are two pieces in particular that deserve some attention. The first is how the API is versioned and second is authentication.
I asked HostedGPT for some info on API versioning, and it gave me -
The first way seems simplest, so we might end up with routes like
/api/v1/messages
,/api/v1/conversations
, and/api/v1/assistants
. Does that seem reasonable or would we prefer to do it some other way?As for authentication, I'm thinking OAuth2 could be used to allow access to the various resources (users, conversations, messages, etc). Certain users may have more access than others, such as a superuser role of sorts that can create other user accounts. And so if another service wanted to access the HostedGPT API, it would first need to register with HostedGPT to get a client id and secret. From there, it could authenticate with the
client_credentials
grant type. And if individual users wanted to use the API access, thepassword
grant type should work fine. (I'm getting this info from https://aaronparecki.com/oauth-2-simplified/#others.)Thoughts?
Beta Was this translation helpful? Give feedback.
All reactions