Skip to content

Commit

Permalink
Add authorization and response handlers (#5)
Browse files Browse the repository at this point in the history
  • Loading branch information
vivekmiyani authored Mar 25, 2024
1 parent d3790b2 commit 999fa11
Show file tree
Hide file tree
Showing 4 changed files with 75 additions and 4 deletions.
36 changes: 32 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,36 @@

## Graphql

Includes `enum` shorthand,
### Shorthand

```rb
field :status, enum("PersonStatusEnum", Person.statuses.keys), null: false
```
- Includes `enum` shorthand,

```rb
field :status, enum("PersonStatusEnum", Person.statuses.keys), null: false
```

### Response handler

- Catches errors automatically:

- `ActiveRecord::RecordNotFound`

- Includes `raise_error` response handler in `GraphQL::Schema::RelayClassicMutation`

```rb
raise_error person.errors.full_messages.to_sentence unless person.update(status: :active)
```

### Authorization

- Add `authorize` option to `field`

```rb
# app/graphql/types/base_field.rb

field_class.include(Phantom::Graphql::Authorization)
```

```rb
field :posts, [Types::PostType], authorize: "PostPolicy#index?", null: false
```
5 changes: 5 additions & 0 deletions lib/phantom/graphql.rb
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,13 @@
module Phantom::Graphql
end

require "phantom/graphql/authorization"
require "phantom/graphql/enum"
require "phantom/graphql/response"

GraphQL::Schema::InputObject.extend(Phantom::Graphql::Enum)
GraphQL::Schema::Object.extend(Phantom::Graphql::Enum)
GraphQL::Schema::RelayClassicMutation.extend(Phantom::Graphql::Enum)

GraphQL::Schema.include(Phantom::Graphql::Response::ExceptionsHandler)
GraphQL::Schema::RelayClassicMutation.include(Phantom::Graphql::Response::Helpers)
23 changes: 23 additions & 0 deletions lib/phantom/graphql/authorization.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
# frozen_string_literal: true

module Phantom::Graphql::Authorization
class AuthorizeExtension < GraphQL::Schema::FieldExtension
def resolve(context:, object:, arguments:, **_rest)
name, action = options.split("#")

authorized = name.constantize.new(context[:current_session]).send(action)

raise GraphQL::ExecutionError, "Unauthorized" unless authorized

yield object, arguments
end
end

def initialize(*args, authorize: nil, **kwargs, &block)
extensions = (kwargs[:extensions] ||= [])

extensions << { Phantom::Graphql::Authorization::AuthorizeExtension => authorize } if authorize.present?

super(*args, **kwargs, &block)
end
end
15 changes: 15 additions & 0 deletions lib/phantom/graphql/response.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# frozen_string_literal: true

module Phantom::Graphql::Response
module ExceptionsHandler
def self.included(base)
base.rescue_from(ActiveRecord::RecordNotFound) { |e| raise GraphQL::ExecutionError, "#{e.model} not found" }
end
end

module Helpers
def raise_error(error)
raise GraphQL::ExecutionError, error
end
end
end

0 comments on commit 999fa11

Please sign in to comment.