Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

WIP: Zeitwerk #37

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,10 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.

## [Unreleased]

### Changed

- Switched to Zeitwerk for autoloading

## [2.5.0]

### Added
Expand Down
5 changes: 4 additions & 1 deletion Gemfile
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,7 @@ source 'https://rubygems.org'
# Specify your gem's dependencies in pragma.gemspec
gemspec

gem 'pry'
gem 'pragma-operation', github: 'pragmarb/pragma-operation'
gem 'pragma-policy', github: 'pragmarb/pragma-policy'
gem 'pragma-decorator', github: 'pragmarb/pragma-decorator'
gem 'pragma-contract', github: 'pragmarb/pragma-contract'
41 changes: 2 additions & 39 deletions lib/pragma.rb
Original file line number Diff line number Diff line change
@@ -1,50 +1,13 @@
# frozen_string_literal: true

require 'adaptor'

require 'pragma/operation'
require 'pragma/policy'
require 'pragma/contract'
require 'pragma/decorator'
require 'zeitwerk'

require 'pragma/version'

require 'pragma/decorator/error'

require 'pragma/filter/base'
require 'pragma/filter/equals'
require 'pragma/filter/like'
require 'pragma/filter/ilike'
require 'pragma/filter/where'
require 'pragma/filter/scope'
require 'pragma/filter/boolean'

require 'pragma/operation/filter'

require 'pragma/macro'
require 'pragma/macro/classes'
require 'pragma/macro/decorator'
require 'pragma/macro/filtering'
require 'pragma/macro/ordering'
require 'pragma/macro/pagination'
require 'pragma/macro/policy'
require 'pragma/macro/model'
require 'pragma/macro/contract/build'
require 'pragma/macro/contract/validate'
require 'pragma/macro/contract/persist'

require 'pragma/operation/macro'

require 'pragma/association_includer/base'
require 'pragma/association_includer/active_record'
require 'pragma/association_includer/poro'
require 'pragma/association_includer'

require 'pragma/operation/index'
require 'pragma/operation/show'
require 'pragma/operation/create'
require 'pragma/operation/update'
require 'pragma/operation/destroy'
Zeitwerk::Loader.for_gem.setup

# A pragmatic architecture for building JSON APIs.
#
Expand Down
35 changes: 35 additions & 0 deletions lib/pragma/macro.rb
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,41 @@ class << self
def require_skill(macro, skill, options)
options[skill] || fail(MissingSkillError.new(macro, skill))
end

def Classes
step = ->(input, options) { Classes.for(input, options) }
[step, name: 'classes']
end

def Decorator(name: :instance)
step = ->(input, options) { Decorator.for(input, name, options) }
[step, name: "decorator.#{name}"]
end

def Filtering
step = ->(input, options) { Filtering.for(input, options) }
[step, name: 'filtering']
end

def Ordering
step = ->(input, options) { Ordering.for(input, options) }
[step, name: 'ordering']
end

def Pagination
step = ->(input, options) { Pagination.for(input, options) }
[step, name: 'pagination']
end

def Policy(name: :default, action: nil)
step = ->(input, options) { Policy.for(input, name, options, action) }
[step, name: "policy.#{name}"]
end

def Model(action = nil)
step = ->(input, options) { Model.for(input, options) }
[step, name: "model.#{action || 'build'}"]
end
end

# Error raised when a skill is required but not present.
Expand Down
5 changes: 0 additions & 5 deletions lib/pragma/macro/classes.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,6 @@

module Pragma
module Macro
def self.Classes
step = ->(input, options) { Classes.for(input, options) }
[step, name: 'classes']
end

module Classes
class << self
def for(input, options)
Expand Down
65 changes: 65 additions & 0 deletions lib/pragma/macro/contract.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
# frozen_string_literal: true

require 'trailblazer/operation/contract'
require 'trailblazer/operation/persist'
require 'trailblazer/operation/validate'

module Pragma
module Macro
module Contract
def self.Build(name: 'default', constant: nil, builder: nil)
step = lambda do |input, options|
Macro.require_skill('Contract::Build', "contract.#{name}.class", options)

Trailblazer::Operation::Contract::Build.for(
input,
options,
name: name,
constant: constant,
builder: builder
).tap do |contract|
contract.current_user = options['current_user']
end
end

[step, name: "contract.#{name}.build"]
end

def self.Persist(method: :save, name: 'default')
step = lambda do |input, options|
Macro.require_skill('Contract::Persist', "contract.#{name}.class", options)

Trailblazer::Operation::Pipetree::Step.new(
Trailblazer::Operation::Contract::Persist(method: method, name: name).first
).call(input, options).tap do |result|
unless result
options['result.response'] = Pragma::Operation::Response::UnprocessableEntity.new(
errors: options["contract.#{name}"].model.errors.messages
).decorate_with(Pragma::Decorator::Error)
end
end
end

[step, name: "contract.#{name}.#{method}"]
end

def self.Validate(name: 'default', **args)
step = lambda do |input, options|
Macro.require_skill('Contract::Validate', "contract.#{name}.class", options)

Trailblazer::Operation::Pipetree::Step.new(
Trailblazer::Operation::Contract::Validate(**args).first
).call(input, options).tap do |result|
unless result
options['result.response'] = Pragma::Operation::Response::UnprocessableEntity.new(
errors: options["contract.#{name}"].errors.messages
).decorate_with(Pragma::Decorator::Error)
end
end
end

[step, name: "contract.#{name}.validate"]
end
end
end
end
27 changes: 0 additions & 27 deletions lib/pragma/macro/contract/build.rb

This file was deleted.

27 changes: 0 additions & 27 deletions lib/pragma/macro/contract/persist.rb

This file was deleted.

27 changes: 0 additions & 27 deletions lib/pragma/macro/contract/validate.rb

This file was deleted.

5 changes: 0 additions & 5 deletions lib/pragma/macro/decorator.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,6 @@

module Pragma
module Macro
def self.Decorator(name: :instance)
step = ->(input, options) { Decorator.for(input, name, options) }
[step, name: "decorator.#{name}"]
end

module Decorator
class << self
def for(_input, name, options)
Expand Down
5 changes: 0 additions & 5 deletions lib/pragma/macro/filtering.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,6 @@

module Pragma
module Macro
def self.Filtering
step = ->(input, options) { Filtering.for(input, options) }
[step, name: 'filtering']
end

module Filtering
class << self
def for(_input, options)
Expand Down
33 changes: 14 additions & 19 deletions lib/pragma/macro/model.rb
Original file line number Diff line number Diff line change
@@ -1,30 +1,25 @@
# frozen_string_literal: true

require 'trailblazer/operation/model'

module Pragma
module Macro
def self.Model(action = nil)
step = lambda do |input, options|
klass = Macro.require_skill('Model', 'model.class', options)
module Model
class << self
def for(input, options)
klass = Macro.require_skill('Model', 'model.class', options)

Trailblazer::Operation::Pipetree::Step.new(
Trailblazer::Operation::Model.for(klass, action),
'model.class' => klass,
'model.action' => action
).call(input, options).tap do |result|
unless result
options['result.response'] = Pragma::Operation::Response::NotFound.new.decorate_with(
Pragma::Decorator::Error
)
Trailblazer::Operation::Pipetree::Step.new(
Trailblazer::Operation::Model.for(klass, action),
'model.class' => klass,
'model.action' => action
).call(input, options).tap do |result|
unless result
options['result.response'] = Pragma::Operation::Response::NotFound.new.decorate_with(
Pragma::Decorator::Error
)
end
end
end
end

[step, name: "model.#{action || 'build'}"]
end

module Model
end
end
end
5 changes: 0 additions & 5 deletions lib/pragma/macro/ordering.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,6 @@

module Pragma
module Macro
def self.Ordering
step = ->(input, options) { Ordering.for(input, options) }
[step, name: 'ordering']
end

module Ordering
class << self
def for(_input, options)
Expand Down
5 changes: 0 additions & 5 deletions lib/pragma/macro/pagination.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,6 @@

module Pragma
module Macro
def self.Pagination
step = ->(input, options) { Pagination.for(input, options) }
[step, name: 'pagination']
end

module Pagination
class << self
def for(_input, options)
Expand Down
5 changes: 0 additions & 5 deletions lib/pragma/macro/policy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,6 @@

module Pragma
module Macro
def self.Policy(name: :default, action: nil)
step = ->(input, options) { Policy.for(input, name, options, action) }
[step, name: "policy.#{name}"]
end

module Policy
class << self
def for(input, name, options, action = nil)
Expand Down
1 change: 1 addition & 0 deletions pragma.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ Gem::Specification.new do |spec|
spec.add_dependency 'pragma-operation', '~> 2.0'
spec.add_dependency 'pragma-policy', '~> 2.0'
spec.add_dependency 'trailblazer', '~> 2.0'
spec.add_dependency 'zeitwerk', '~> 2.1'

spec.add_development_dependency 'bundler'
spec.add_development_dependency 'coveralls'
Expand Down
2 changes: 0 additions & 2 deletions spec/spec_helper.rb
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
require 'coveralls'
Coveralls.wear!

require 'pry'

$LOAD_PATH.unshift File.expand_path('../../lib', __FILE__)
require 'pragma'

Expand Down