yaso 1.1.0 → 1.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: e562bf748ebc163661813eed594c0abdecc4bf2027f68cb3cfb389464066fd82
4
- data.tar.gz: 4fd59f39375881b4c9b04442405318a82f58792a7d759edfef302cc25b2b3107
3
+ metadata.gz: 1d9de791b4d45e8ea1cd2ffb6d75738f9d5eef8376261437b923d0795f81a5a2
4
+ data.tar.gz: 1d6234c4203c8cd9acdec73b5267ff16a45563caf67fd757f8fbed7fb2228d79
5
5
  SHA512:
6
- metadata.gz: bb6e535a13645a6831364324459a76808affb02715d6f6f173d3e913058befa03bd7af75828bdf627e54d8daccf060e7d0fae693dda4b65c224573c0afb0a7a5
7
- data.tar.gz: '0987332c9e58733298f8b7c5c164222d91835492afb2107fb7bffbfaaeeec2b3234d2f34fdf57b6b0fcc7055b95669a42b803449f351f4c8d243a00147ca4a9d'
6
+ metadata.gz: 8d8a4268ef7295d5eef6a6f8a45a73cc823f7d3322ad0c2cfea2f46a627f415af1c1974a8806318c290961ecd01bef29f4ad521e8d12f9f360c9f6a76d7426d9
7
+ data.tar.gz: 3b3e2a00818e075f555f47302033d6b6f292413291c4991e6d5e7831e58a95877a257dc0bb377b526736f516da5c71e58690b6e557e2805ac5a40e466e068bae
data/.rubocop.yml CHANGED
@@ -8,6 +8,7 @@ AllCops:
8
8
  NewCops: enable
9
9
  Exclude:
10
10
  - vendor/bundle/**/*
11
+ - benchmark/vendor/bundle/**/*
11
12
 
12
13
  Gemspec/RequiredRubyVersion:
13
14
  Enabled: false
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- yaso (1.1.0)
4
+ yaso (1.3.0)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
@@ -14,7 +14,7 @@ GEM
14
14
  lefthook (1.0.5)
15
15
  method_source (1.0.0)
16
16
  parallel (1.22.1)
17
- parser (3.1.2.0)
17
+ parser (3.1.2.1)
18
18
  ast (~> 2.4.1)
19
19
  pry (0.14.1)
20
20
  coderay (~> 1.1)
@@ -29,13 +29,13 @@ GEM
29
29
  rspec-mocks (~> 3.11.0)
30
30
  rspec-core (3.11.0)
31
31
  rspec-support (~> 3.11.0)
32
- rspec-expectations (3.11.0)
32
+ rspec-expectations (3.11.1)
33
33
  diff-lcs (>= 1.2.0, < 2.0)
34
34
  rspec-support (~> 3.11.0)
35
35
  rspec-mocks (3.11.1)
36
36
  diff-lcs (>= 1.2.0, < 2.0)
37
37
  rspec-support (~> 3.11.0)
38
- rspec-support (3.11.0)
38
+ rspec-support (3.11.1)
39
39
  rubocop (1.28.2)
40
40
  parallel (~> 1.10)
41
41
  parser (>= 3.1.0.0)
@@ -59,7 +59,7 @@ GEM
59
59
  simplecov_json_formatter (~> 0.1)
60
60
  simplecov-html (0.12.3)
61
61
  simplecov_json_formatter (0.1.4)
62
- unicode-display_width (2.2.0)
62
+ unicode-display_width (2.3.0)
63
63
 
64
64
  PLATFORMS
65
65
  x86_64-darwin-21
data/README.md CHANGED
@@ -1,8 +1,7 @@
1
1
  # Yaso
2
2
  [![Ruby](https://github.com/Ar2emis/yaso/actions/workflows/main.yml/badge.svg?branch=master)](https://github.com/Ar2emis/yaso/actions/workflows/main.yml) ![gem](https://img.shields.io/gem/v/yaso) [![GitHub license](https://img.shields.io/github/license/Ar2emis/yaso)](https://github.com/Ar2emis/yaso/blob/master/LICENSE.txt)
3
3
 
4
- That's my (Yet Another) ServiceObject pattern implementation. I made it fast ([the fastest actually](https://github.com/Ar2emis/yaso/wiki/Benchmarks)) and simple to use.
5
- I was inspired by those alternatives and I hope this will encourage them to be even better:
4
+ That's my (Yet Another) ServiceObject pattern implementation. I made it fast ([the fastest of this kind actually](https://github.com/Ar2emis/yaso/wiki/Benchmarks); [simple_command](https://github.com/nebulab/simple_command), you got me this time) and simple to use (I hope). I was inspired by those alternatives and I hope this will encourage them to be even better:
6
5
  - [Trailblazer](https://github.com/trailblazer/trailblazer)
7
6
  - [Decouplio](https://github.com/differencialx/decouplio)
8
7
 
@@ -28,7 +27,7 @@ All the information you can find in the gem [wiki](https://github.com/Ar2emis/ya
28
27
 
29
28
  ## Development
30
29
 
31
- I don't think that someone would like to help me developing the gem but if so just fork a new branch from the master, do your dark business, open a pull request and assign me as a reviewer.
30
+ I don't think that someone would like to help me developing the gem but if so just fork a repository, do your dark business, open a pull request and assign me as a reviewer.
32
31
 
33
32
  ## Contributing
34
33
 
data/benchmark/Gemfile CHANGED
@@ -5,7 +5,9 @@ source 'https://rubygems.org'
5
5
  gem 'benchmark-ips', '~> 2.10.0'
6
6
  gem 'interactor', '~> 3.1.2'
7
7
  gem 'kalibera', '~> 0.1.2'
8
+ gem 'simple_command', RUBY_VERSION.include?('2.5') ? '~> 0.2.0' : '~> 1.0.1'
8
9
  gem 'trailblazer', '~> 2.1.0'
10
+ gem 'yaso', path: '..'
9
11
 
10
12
  gem 'active_interaction', %w[2.5 2.6].any? { |version| RUBY_VERSION.include?(version) } ? '~> 4.1.0' : '~> 5.1.0'
11
13
 
data/benchmark/index.rb CHANGED
@@ -2,17 +2,18 @@
2
2
 
3
3
  require 'bundler/setup'
4
4
 
5
- require_relative '../lib/yaso'
6
-
7
5
  require 'benchmark/ips'
8
6
  RUBY_VERSION.include?('2.5') || require('decouplio')
9
7
  require 'interactor'
10
8
  require 'active_interaction'
11
9
  require 'trailblazer'
10
+ require 'simple_command'
11
+ require 'yaso'
12
12
 
13
13
  require_relative 'shared/yaso_service'
14
14
  RUBY_VERSION.include?('2.5') || require_relative('shared/decouplio_service')
15
15
  require_relative 'shared/pure_service'
16
+ require_relative 'shared/simple_command_service'
16
17
  require_relative 'shared/interactor_service'
17
18
  require_relative 'shared/active_interaction_service'
18
19
  require_relative 'shared/trailblazer_service'
@@ -21,6 +22,7 @@ require_relative 'shared/callable_step'
21
22
  require_relative 'step/yaso'
22
23
  RUBY_VERSION.include?('2.5') || require_relative('step/decouplio')
23
24
  require_relative 'step/pure'
25
+ require_relative 'step/simple_command'
24
26
  require_relative 'step/interactor'
25
27
  require_relative 'step/active_interaction'
26
28
  require_relative 'step/trailblazer'
@@ -0,0 +1,11 @@
1
+ # frozen_string_literal: true
2
+
3
+ class SimpleCommandService
4
+ prepend SimpleCommand
5
+
6
+ attr_reader :ctx
7
+
8
+ def initialize(**ctx)
9
+ @ctx = ctx
10
+ end
11
+ end
@@ -7,6 +7,7 @@ Benchmark.ips do |x|
7
7
  x.config(stats: :bootstrap, confidence: 95)
8
8
 
9
9
  x.report('Pure Service') { PureStepsService.call }
10
+ x.report('SimpleCommand') { SimpleCommandStepsService.call }
10
11
  x.report('Yaso') { YasoStepsService.call }
11
12
  x.report('Decouplio') { DecouplioStepsService.call } unless RUBY_VERSION.include?('2.5')
12
13
  x.report('Interactor') { InteractorStepsService.call }
@@ -21,6 +22,7 @@ Benchmark.ips do |x|
21
22
  x.config(stats: :bootstrap, confidence: 95)
22
23
 
23
24
  x.report('Pure Service') { PureCallablesService.call }
25
+ x.report('SimpleCommand') { SimpleCommandCallablesService.call }
24
26
  x.report('Yaso') { YasoCallablesService.call }
25
27
  x.report('Decouplio') { DecouplioCallablesService.call } unless RUBY_VERSION.include?('2.5')
26
28
  x.report('Interactor') { InteractorCallablesService.call }
@@ -0,0 +1,77 @@
1
+ # frozen_string_literal: true
2
+
3
+ class SimpleCommandStepsService < SimpleCommandService
4
+ # rubocop:disable Metrics/MethodLength
5
+ def call
6
+ one
7
+ two
8
+ three
9
+ four
10
+ five
11
+ six
12
+ seven
13
+ eight
14
+ nine
15
+ ten
16
+ ctx
17
+ end
18
+ # rubocop:enable Metrics/MethodLength
19
+
20
+ def one
21
+ ctx[:one] = true
22
+ end
23
+
24
+ def two
25
+ ctx[:two] = true
26
+ end
27
+
28
+ def three
29
+ ctx[:three] = true
30
+ end
31
+
32
+ def four
33
+ ctx[:four] = true
34
+ end
35
+
36
+ def five
37
+ ctx[:five] = true
38
+ end
39
+
40
+ def six
41
+ ctx[:six] = true
42
+ end
43
+
44
+ def seven
45
+ ctx[:seven] = true
46
+ end
47
+
48
+ def eight
49
+ ctx[:eight] = true
50
+ end
51
+
52
+ def nine
53
+ ctx[:nine] = true
54
+ end
55
+
56
+ def ten
57
+ ctx[:ten] = true
58
+ end
59
+ end
60
+
61
+ class SimpleCommandCallablesService < SimpleCommandService
62
+ # rubocop:disable Metrics/AbcSize, Metrics/MethodLength
63
+ def call
64
+ CallableStep.call(ctx, key: :one, value: true)
65
+ CallableStep.call(ctx, key: :two, value: true)
66
+ CallableStep.call(ctx, key: :three, value: true)
67
+ CallableStep.call(ctx, key: :four, value: true)
68
+ CallableStep.call(ctx, key: :five, value: true)
69
+ CallableStep.call(ctx, key: :six, value: true)
70
+ CallableStep.call(ctx, key: :seven, value: true)
71
+ CallableStep.call(ctx, key: :eight, value: true)
72
+ CallableStep.call(ctx, key: :nine, value: true)
73
+ CallableStep.call(ctx, key: :ten, value: true)
74
+ ctx
75
+ end
76
+ # rubocop:enable Metrics/AbcSize, Metrics/MethodLength
77
+ end
data/docker/Dockerfile ADDED
@@ -0,0 +1,7 @@
1
+ ARG VERSION=latest
2
+
3
+ FROM ruby:${VERSION}
4
+
5
+ ENTRYPOINT [ "/yaso/docker/entrypoint.sh" ]
6
+
7
+ WORKDIR /yaso/benchmark
@@ -0,0 +1,15 @@
1
+ #!/bin/bash
2
+
3
+ if [[ `bundle -v` =~ "Bundler version 2" ]]; then
4
+ bundle config set --local path '/bundle/cache'
5
+ bundle config set --local without 'development'
6
+ else
7
+ bundle config --local path '/bundle/cache'
8
+ bundle config --local without 'development'
9
+ fi
10
+
11
+ bundle
12
+
13
+ ruby index.rb
14
+
15
+ rm Gemfile.lock
@@ -0,0 +1,15 @@
1
+ services:
2
+ benchmark:
3
+ build: docker
4
+ volumes:
5
+ - .:/yaso
6
+ - bundle:/bundle/cache
7
+ deploy:
8
+ resources:
9
+ limits:
10
+ cpus: '1.5'
11
+ reservations:
12
+ cpus: '1.5'
13
+
14
+ volumes:
15
+ bundle:
data/lib/yaso/errors.rb CHANGED
@@ -20,4 +20,10 @@ module Yaso
20
20
  super("Unhandled switch case in #{klass}")
21
21
  end
22
22
  end
23
+
24
+ class UnknownFlowError < Error
25
+ def initialize(klass, name)
26
+ super("Unknown flow \"#{name}\" is set in #{klass}")
27
+ end
28
+ end
23
29
  end
@@ -0,0 +1,51 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Yaso
4
+ class Invocable
5
+ METHOD = :method
6
+ CALLABLE = :callable
7
+ YASO = :yaso
8
+
9
+ class << self
10
+ def call(object, options: {}, with_block: false, **)
11
+ type = object_type(object)
12
+ invocable = case type
13
+ when YASO then proc { |context| object.call(context).success? }
14
+ when CALLABLE then callable_invocable(object, options, with_block: with_block)
15
+ else method_invocable(object, with_block: with_block)
16
+ end
17
+ [type, invocable]
18
+ end
19
+
20
+ private
21
+
22
+ def object_type(object)
23
+ return Invocable::METHOD unless object.is_a?(Class)
24
+
25
+ object < ::Yaso::Service ? Invocable::YASO : Invocable::CALLABLE
26
+ end
27
+
28
+ def callable_invocable(object, options, with_block:)
29
+ return proc { |context, &block| object.call(context, **options, &block) } if with_block
30
+
31
+ proc { |context| object.call(context, **options) }
32
+ end
33
+
34
+ def method_invocable(object, with_block:)
35
+ if with_block
36
+ return instance_eval <<-RUBY, __FILE__, __LINE__ + 1
37
+ proc { |context, instance, &block| # proc { |context, instance, &block|
38
+ instance.#{object}(context, **context, &block) # instance.<method_name>(context, **context, &block)
39
+ } # }
40
+ RUBY
41
+ end
42
+
43
+ instance_eval <<-RUBY, __FILE__, __LINE__ + 1
44
+ proc { |context, instance| # proc { |context, instance|
45
+ instance.#{object}(context, **context) # instance.<method_name>(context, **context)
46
+ } # }
47
+ RUBY
48
+ end
49
+ end
50
+ end
51
+ end
@@ -5,9 +5,9 @@ module Yaso
5
5
  class Base
6
6
  attr_reader :name, :on_success, :on_failure
7
7
 
8
- def initialize(name:, invokable:, **options)
8
+ def initialize(name:, invocable:, **options)
9
9
  @name = name
10
- @invokable = invokable
10
+ @invocable = invocable
11
11
  @fast = options[:fast]
12
12
  @on_success = options[:on_success]
13
13
  @on_failure = options[:on_failure]
@@ -4,8 +4,7 @@ module Yaso
4
4
  module Logic
5
5
  class Failure < Base
6
6
  def call(context, instance)
7
- context.success = false
8
- @invokable.call(context, instance) ? @next_step : @failure
7
+ [@invocable.call(context, instance) ? @next_step : @failure, false]
9
8
  end
10
9
  end
11
10
  end
@@ -4,8 +4,7 @@ module Yaso
4
4
  module Logic
5
5
  class Pass < Base
6
6
  def call(context, instance)
7
- context.success = true
8
- @invokable.call(context, instance) ? @next_step : @failure
7
+ [@invocable.call(context, instance) ? @next_step : @failure, true]
9
8
  end
10
9
  end
11
10
  end
@@ -0,0 +1,40 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Yaso
4
+ module Logic
5
+ class Rollback < Classic
6
+ def call
7
+ super
8
+ logicals.detect { |step| !step.is_a?(Failure) }
9
+ end
10
+
11
+ private
12
+
13
+ def link_step(step, index)
14
+ next_success = step.on_success ? find_step(step.on_success) : next_step(index)
15
+ next_failure = if step.on_failure then find_step(step.on_failure)
16
+ else
17
+ step.is_a?(Pass) ? next_success : previous_failure(index)
18
+ end
19
+
20
+ step.add_next_step(next_success)
21
+ step.add_failure(next_failure)
22
+ end
23
+
24
+ def link_previous_steps(failure, index)
25
+ prev_failure = previous_failure(index)
26
+
27
+ failure.add_failure(prev_failure) unless failure.on_failure
28
+ failure.add_next_step(prev_failure) unless failure.on_success
29
+ end
30
+
31
+ def next_step(index)
32
+ logicals[index.next..-1].detect { |next_node| !next_node.is_a?(Failure) }
33
+ end
34
+
35
+ def previous_failure(index)
36
+ logicals[0...index].reverse_each.detect { |previous_step| previous_step.is_a?(Failure) }
37
+ end
38
+ end
39
+ end
40
+ end
@@ -4,13 +4,7 @@ module Yaso
4
4
  module Logic
5
5
  class Step < Base
6
6
  def call(context, instance)
7
- context.success = true
8
- if @invokable.call(context, instance)
9
- @next_step
10
- else
11
- context.success = false
12
- @failure
13
- end
7
+ @invocable.call(context, instance) ? [@next_step, true] : [@failure, false]
14
8
  end
15
9
  end
16
10
  end
@@ -16,13 +16,13 @@ module Yaso
16
16
  end
17
17
 
18
18
  def call(object:, category:, block:, **opts)
19
- invokable_type, invokable = Invokable.call(object, **opts)
20
19
  logic_class = CATEGORIES[category]
21
- if invokable_type == Invokable::METHOD
20
+ invocable_type, invocable = Invocable.call(object, with_block: logic_class == Wrap, **opts)
21
+ if invocable_type == Invocable::METHOD
22
22
  opts[:name] = logic_class == Switch ? build_switch(object, **opts, &block) : build_method(object, &block)
23
23
  end
24
24
  opts[:wrapper] = build_wrapper(&block) if logic_class == Wrap
25
- logic_class.new(invokable: invokable, **opts)
25
+ logic_class.new(invocable: invocable, **opts)
26
26
  end
27
27
 
28
28
  private
@@ -45,17 +45,19 @@ module Yaso
45
45
 
46
46
  def build_wrapper(&block)
47
47
  wrapper_class = Class.new { extend Stepable }
48
+ build_wrapper_methods(wrapper_class, @klass)
48
49
  wrapper_class.instance_exec(&block)
49
- build_wrapper_call(wrapper_class, @klass)
50
50
  wrapper_class
51
51
  end
52
52
 
53
- def build_wrapper_call(wrapper_class, service_class)
53
+ def build_wrapper_methods(wrapper_class, service_class)
54
54
  wrapper_class.define_singleton_method(:call) do |context, instance|
55
- @entry ||= Logic::Classic.call(service_class, steps)
55
+ @entry ||= service_class.flow.call(service_class, steps)
56
56
  step = @entry
57
- step = step.call(context, instance) while step
58
- context
57
+ success = true
58
+ step, success = step.call(context, instance) while step
59
+ instance.success = success
60
+ instance
59
61
  end
60
62
  end
61
63
  end
@@ -4,15 +4,8 @@ module Yaso
4
4
  module Logic
5
5
  class Switch < Base
6
6
  def call(context, instance)
7
- context.success = true
8
- switch_case = @invokable.call(context, instance) || raise(UnhandledSwitchCaseError, instance.class)
9
-
10
- if Invokable.call(switch_case).last.call(context, instance)
11
- @next_step
12
- else
13
- context.success = false
14
- @failure
15
- end
7
+ switch_case = @invocable.call(context, instance) || raise(UnhandledSwitchCaseError, instance.class)
8
+ Invocable.call(switch_case).last.call(context, instance) ? [@next_step, true] : [@failure, false]
16
9
  end
17
10
  end
18
11
  end
@@ -9,13 +9,8 @@ module Yaso
9
9
  end
10
10
 
11
11
  def call(context, instance)
12
- context.success = true
13
- if @invokable.call(context, instance) { @wrapper.call(context, instance).success? }
14
- @next_step
15
- else
16
- context.success = false
17
- @failure
18
- end
12
+ result = @invocable.call(context, instance) { @wrapper.call(context, instance).success? }
13
+ result ? [@next_step, true] : [@failure, false]
19
14
  end
20
15
  end
21
16
  end
data/lib/yaso/logic.rb CHANGED
@@ -8,7 +8,13 @@ require_relative 'logic/wrap'
8
8
  require_relative 'logic/switch'
9
9
  require_relative 'logic/step_builder'
10
10
  require_relative 'logic/classic'
11
+ require_relative 'logic/rollback'
11
12
 
12
13
  module Yaso
13
- module Logic; end
14
+ module Logic
15
+ FLOWS = {
16
+ classic: Logic::Classic,
17
+ rollback: Logic::Rollback
18
+ }.freeze
19
+ end
14
20
  end
data/lib/yaso/service.rb CHANGED
@@ -4,13 +4,54 @@ module Yaso
4
4
  class Service
5
5
  extend Stepable
6
6
 
7
- def self.call(context = {})
8
- context = context.is_a?(Context) ? context : Context.new(context)
9
- @entry ||= Logic::Classic.call(self, steps)
10
- step = @entry
11
- instance = new
12
- step = step.call(context, instance) while step
13
- context
7
+ attr_writer :success
8
+
9
+ def initialize(context)
10
+ @context = context
11
+ @success = true
12
+ end
13
+
14
+ def [](key)
15
+ @context[key]
16
+ end
17
+
18
+ def []=(key, value)
19
+ @context[key] = value
20
+ end
21
+
22
+ def success?
23
+ @success
24
+ end
25
+
26
+ def failure?
27
+ !@success
28
+ end
29
+
30
+ def to_h
31
+ @context.dup
32
+ end
33
+
34
+ def inspect
35
+ "Result:#{self.class} successful: #{@success}, context: #{@context}"
36
+ end
37
+
38
+ class << self
39
+ def call(context = {})
40
+ @entry ||= flow.call(self, steps)
41
+ step = @entry
42
+ instance = new(context)
43
+ success = true
44
+ step, success = step.call(context, instance) while step
45
+ instance.success = success
46
+ instance
47
+ end
48
+
49
+ def flow(name = nil)
50
+ @flow ||= Logic::FLOWS[:classic] if self == Yaso::Service
51
+ return @flow || Yaso::Service.flow if name.nil?
52
+
53
+ @flow = Logic::FLOWS[name] || raise(UnknownFlowError.new(self, name))
54
+ end
14
55
  end
15
56
  end
16
57
  end
data/lib/yaso/stepable.rb CHANGED
@@ -6,15 +6,22 @@ module Yaso
6
6
  @steps ||= []
7
7
  end
8
8
 
9
- %i[step pass failure wrap switch].each do |category|
10
- define_method(category) do |object, options = {}, &block|
11
- raise InvalidFirstStepError, category if category == :failure && steps.empty?
12
-
9
+ %i[step pass wrap switch].each do |category|
10
+ define_method(category) do |object, **options, &block|
13
11
  steps << {
14
12
  object: object, category: category, fast: options.delete(:fast), on_success: options.delete(:on_success),
15
13
  on_failure: options.delete(:on_failure), options: options, block: block, name: options.delete(:name)
16
14
  }
17
15
  end
18
16
  end
17
+
18
+ def failure(object, **options, &block)
19
+ raise InvalidFirstStepError, :failure if flow == Logic::Classic && steps.empty?
20
+
21
+ steps << {
22
+ object: object, category: :failure, fast: options.delete(:fast), on_success: options.delete(:on_success),
23
+ on_failure: options.delete(:on_failure), options: options, block: block, name: options.delete(:name)
24
+ }
25
+ end
19
26
  end
20
27
  end
data/lib/yaso/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Yaso
4
- VERSION = '1.1.0'
4
+ VERSION = '1.3.0'
5
5
  end
data/lib/yaso.rb CHANGED
@@ -2,8 +2,7 @@
2
2
 
3
3
  require_relative 'yaso/version'
4
4
  require_relative 'yaso/errors'
5
- require_relative 'yaso/context'
6
- require_relative 'yaso/invokable'
5
+ require_relative 'yaso/invocable'
7
6
  require_relative 'yaso/stepable'
8
7
  require_relative 'yaso/logic'
9
8
  require_relative 'yaso/service'
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: yaso
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.0
4
+ version: 1.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Artem Shevchenko
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-08-25 00:00:00.000000000 Z
11
+ date: 2022-09-19 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: ffaker
@@ -197,6 +197,7 @@ files:
197
197
  - benchmark/shared/decouplio_service.rb
198
198
  - benchmark/shared/interactor_service.rb
199
199
  - benchmark/shared/pure_service.rb
200
+ - benchmark/shared/simple_command_service.rb
200
201
  - benchmark/shared/trailblazer_service.rb
201
202
  - benchmark/shared/yaso_service.rb
202
203
  - benchmark/step/active_interaction.rb
@@ -204,18 +205,22 @@ files:
204
205
  - benchmark/step/decouplio.rb
205
206
  - benchmark/step/interactor.rb
206
207
  - benchmark/step/pure.rb
208
+ - benchmark/step/simple_command.rb
207
209
  - benchmark/step/trailblazer.rb
208
210
  - benchmark/step/yaso.rb
211
+ - docker-compose.yml
212
+ - docker/Dockerfile
213
+ - docker/entrypoint.sh
209
214
  - lefthook.yml
210
215
  - lib/yaso.rb
211
- - lib/yaso/context.rb
212
216
  - lib/yaso/errors.rb
213
- - lib/yaso/invokable.rb
217
+ - lib/yaso/invocable.rb
214
218
  - lib/yaso/logic.rb
215
219
  - lib/yaso/logic/base.rb
216
220
  - lib/yaso/logic/classic.rb
217
221
  - lib/yaso/logic/failure.rb
218
222
  - lib/yaso/logic/pass.rb
223
+ - lib/yaso/logic/rollback.rb
219
224
  - lib/yaso/logic/step.rb
220
225
  - lib/yaso/logic/step_builder.rb
221
226
  - lib/yaso/logic/switch.rb
data/lib/yaso/context.rb DELETED
@@ -1,33 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Yaso
4
- class Context
5
- attr_writer :success
6
- attr_reader :data
7
-
8
- def initialize(kwargs)
9
- @success = true
10
- @data = kwargs
11
- end
12
-
13
- def [](key)
14
- @data[key]
15
- end
16
-
17
- def []=(key, value)
18
- @data[key] = value
19
- end
20
-
21
- def to_h
22
- @data.dup
23
- end
24
-
25
- def success?
26
- @success
27
- end
28
-
29
- def failure?
30
- !@success
31
- end
32
- end
33
- end
@@ -1,37 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Yaso
4
- class Invokable
5
- METHOD = :method
6
- CALLABLE = :callable
7
- YASO = :yaso
8
-
9
- class << self
10
- def call(object, options: {}, **)
11
- type = object_type(object)
12
- invokable = case type
13
- when YASO then proc { |context, _| object.call(context.clone).success? }
14
- when CALLABLE then proc { |context, _, &block| object.call(context, **options, &block) }
15
- else method_invokable(object)
16
- end
17
- [type, invokable]
18
- end
19
-
20
- private
21
-
22
- def object_type(object)
23
- return Invokable::METHOD unless object.is_a?(Class)
24
-
25
- object < ::Yaso::Service ? Invokable::YASO : Invokable::CALLABLE
26
- end
27
-
28
- def method_invokable(object)
29
- instance_eval <<-RUBY, __FILE__, __LINE__ + 1
30
- proc { |context, instance, &block| # proc { |context, instance, &block|
31
- instance.#{object}(context, **context.data, &block) # instance.<method_name>(context, **context.data, &block)
32
- } # }
33
- RUBY
34
- end
35
- end
36
- end
37
- end