light-service-ext 0.1.9 → 0.1.11
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 +4 -4
- data/README.md +5 -2
- data/lib/light-service-ext/application_action.rb +22 -0
- data/lib/light-service-ext/application_context.rb +7 -1
- data/lib/light-service-ext/around_action_execute_extension.rb +7 -0
- data/lib/light-service-ext/record_actions.rb +11 -6
- data/lib/light-service-ext/version.rb +1 -1
- data/lib/light-service-ext/with_error_handler.rb +1 -1
- data/light-service-ext.gemspec +1 -1
- data/spec/light-service-ext/application_action_spec.rb +49 -15
- data/spec/light-service-ext/application_context_spec.rb +16 -0
- metadata +3 -5
- data/spec/light-service-ext/around_action_execute_extension_spec.rb +0 -56
    
        checksums.yaml
    CHANGED
    
    | @@ -1,7 +1,7 @@ | |
| 1 1 | 
             
            ---
         | 
| 2 2 | 
             
            SHA256:
         | 
| 3 | 
            -
              metadata.gz:  | 
| 4 | 
            -
              data.tar.gz:  | 
| 3 | 
            +
              metadata.gz: ce41945d8919b3cef73709b2a43f77621fb19019d35f22b6719de3d4c4af7948
         | 
| 4 | 
            +
              data.tar.gz: 1f899858676cc260d26d381a4d2c8dbb19688b3aedd666d5e3380c164bf6f495
         | 
| 5 5 | 
             
            SHA512:
         | 
| 6 | 
            -
              metadata.gz:  | 
| 7 | 
            -
              data.tar.gz:  | 
| 6 | 
            +
              metadata.gz: 7a60af56510f4c620b78d97f2609c668b69fd595e6ed6f1acd50056a963ffd9a499e8843ff0147c533f184901f3e636d2e397bfc536b7eeb68af0ec19f970dee
         | 
| 7 | 
            +
              data.tar.gz: e0c0bcb40521c6ea56cec36a555f1ffc6ebb11b7942b4709d616e7ce75ddb34aa79132f4396602cdacb534338e72d7f37a8e62b51f0609ad636fbae5564a18fb
         | 
    
        data/README.md
    CHANGED
    
    | @@ -173,12 +173,14 @@ end | |
| 173 173 | 
             
              - `LightServiceExt::Status::INCOMPLETE`
         | 
| 174 174 | 
             
            - `:last_failed_context` ~ copy of context that failed e.g. with `errors` field present
         | 
| 175 175 | 
             
            - `internal_only` ~ includes the likes of raised error summary and should never be passed to endpoint responses
         | 
| 176 | 
            +
            - `meta` ~ used to store any additional information that could be helpful especially for debugging purposes.
         | 
| 176 177 | 
             
            Example
         | 
| 177 178 |  | 
| 178 179 | 
             
            ````ruby
         | 
| 179 180 | 
             
            input = { order: order }
         | 
| 180 181 | 
             
            overrides = {} # optionally override `params`, `errors` and `allow_raise_on_failure`
         | 
| 181 | 
            -
             | 
| 182 | 
            +
            meta = { current_user_id: 12345, request_id: some-unique-request-id, impersonator_id: 54321 }
         | 
| 183 | 
            +
            LightServiceExt::ApplicationContext.make_with_defaults(input, overrides, meta: meta)
         | 
| 182 184 |  | 
| 183 185 | 
             
            # => { input: { order: order },
         | 
| 184 186 | 
             
            #      errors: { email: ['not found'] },
         | 
| @@ -190,7 +192,8 @@ LightServiceExt::ApplicationContext.make_with_defaults(input, overrides) | |
| 190 192 | 
             
            #      api_responses: [ { user_id: 1, status: 'ACTIVE' } ],
         | 
| 191 193 | 
             
            #      last_failed_context: {input: { order: order }, params: {}, ...},
         | 
| 192 194 | 
             
            #      allow_raise_on_failure: true,
         | 
| 193 | 
            -
            #      internal_only: { error_info: ErrorInfoInstance }
         | 
| 195 | 
            +
            #      internal_only: { error_info: ErrorInfoInstance },
         | 
| 196 | 
            +
            #     meta: { current_user_id: 12345, request_id: some-unique-request-id, impersonator_id: 54321 }
         | 
| 194 197 | 
             
            #    }
         | 
| 195 198 | 
             
            ````
         | 
| 196 199 |  | 
| @@ -4,9 +4,31 @@ module LightServiceExt | |
| 4 4 | 
             
              class ApplicationAction
         | 
| 5 5 | 
             
                extend LightService::Action
         | 
| 6 6 |  | 
| 7 | 
            +
             | 
| 7 8 | 
             
                def self.inherited(base)
         | 
| 9 | 
            +
                  base.extend LifecycleMethods
         | 
| 8 10 | 
             
                  base.singleton_class.prepend AroundActionExecuteExtension
         | 
| 9 11 | 
             
                  super
         | 
| 10 12 | 
             
                end
         | 
| 13 | 
            +
             | 
| 14 | 
            +
                module LifecycleMethods
         | 
| 15 | 
            +
                  attr_writer :before_execute_block, :after_execute_block, :after_success_block, :after_failure_block
         | 
| 16 | 
            +
             | 
| 17 | 
            +
                  def before_execute_block
         | 
| 18 | 
            +
                    @before_execute_block ||= ->(_context) {}
         | 
| 19 | 
            +
                  end
         | 
| 20 | 
            +
             | 
| 21 | 
            +
                  def after_execute_block
         | 
| 22 | 
            +
                    @after_execute_block ||= ->(_context) {}
         | 
| 23 | 
            +
                  end
         | 
| 24 | 
            +
             | 
| 25 | 
            +
                  def after_success_block
         | 
| 26 | 
            +
                    @after_success_block ||= ->(_context) {}
         | 
| 27 | 
            +
                  end
         | 
| 28 | 
            +
             | 
| 29 | 
            +
                  def after_failure_block
         | 
| 30 | 
            +
                    @after_failure_block ||= ->(_context) {}
         | 
| 31 | 
            +
                  end
         | 
| 32 | 
            +
                end
         | 
| 11 33 | 
             
              end
         | 
| 12 34 | 
             
            end
         | 
| @@ -25,7 +25,8 @@ module LightServiceExt | |
| 25 25 | 
             
                      api_responses: [],
         | 
| 26 26 | 
             
                      last_failed_context: nil,
         | 
| 27 27 | 
             
                      allow_raise_on_failure: LightServiceExt.config.allow_raise_on_failure?,
         | 
| 28 | 
            -
                      internal_only: {}
         | 
| 28 | 
            +
                      internal_only: {},
         | 
| 29 | 
            +
                      meta: {}
         | 
| 29 30 | 
             
                    }.freeze
         | 
| 30 31 | 
             
                  end
         | 
| 31 32 | 
             
                end
         | 
| @@ -63,6 +64,11 @@ module LightServiceExt | |
| 63 64 | 
             
                  add_attrs_to_ctx(:internal_only, **attrs)
         | 
| 64 65 | 
             
                end
         | 
| 65 66 |  | 
| 67 | 
            +
                def add_meta(**attrs)
         | 
| 68 | 
            +
                  add_attrs_to_ctx(:meta, **attrs)
         | 
| 69 | 
            +
                end
         | 
| 70 | 
            +
             | 
| 71 | 
            +
             | 
| 66 72 | 
             
                def record_raised_error(error)
         | 
| 67 73 | 
             
                  @error_info = ErrorInfo.new(error)
         | 
| 68 74 | 
             
                  error_type = @error_info.type
         | 
| @@ -3,10 +3,17 @@ | |
| 3 3 | 
             
            module LightServiceExt
         | 
| 4 4 | 
             
              module AroundActionExecuteExtension
         | 
| 5 5 | 
             
                def execute(context)
         | 
| 6 | 
            +
                  return context if context.status == Status::COMPLETE
         | 
| 7 | 
            +
                  self.before_execute_block.call(context)
         | 
| 8 | 
            +
             | 
| 6 9 | 
             
                  result = super(context.merge(invoked_action: self))
         | 
| 7 10 |  | 
| 8 11 | 
             
                  context.merge!(result)
         | 
| 9 12 | 
             
                  context.fail! if result.errors.present?
         | 
| 13 | 
            +
             | 
| 14 | 
            +
                  self.after_execute_block.call(context)
         | 
| 15 | 
            +
                  self.after_success_block.call(context) if result.success?
         | 
| 16 | 
            +
                  self.after_failure_block.call(context) if result.failure?
         | 
| 10 17 | 
             
                  result
         | 
| 11 18 | 
             
                end
         | 
| 12 19 | 
             
              end
         | 
| @@ -6,21 +6,26 @@ module LightServiceExt | |
| 6 6 |  | 
| 7 7 | 
             
                def self.call(context)
         | 
| 8 8 | 
             
                  with_error_handler(ctx: context) do
         | 
| 9 | 
            -
                    result = yield
         | 
| 9 | 
            +
                    result = yield || context
         | 
| 10 10 | 
             
                    return context if outcomes_complete?(ctx: context, result: result)
         | 
| 11 11 |  | 
| 12 | 
            +
                    invoked_action = result.invoked_action
         | 
| 13 | 
            +
                    return context if invoked_action.nil?
         | 
| 14 | 
            +
             | 
| 15 | 
            +
                    context.add_to_successful_actions(invoked_action.name)
         | 
| 16 | 
            +
             | 
| 12 17 | 
             
                    merge_api_responses!(ctx: context, result: result)
         | 
| 18 | 
            +
                    context
         | 
| 13 19 | 
             
                  end
         | 
| 14 20 | 
             
                end
         | 
| 15 21 |  | 
| 16 22 | 
             
                class << self
         | 
| 17 23 | 
             
                  def merge_api_responses!(ctx:, result:)
         | 
| 18 | 
            -
                     | 
| 19 | 
            -
                    return if  | 
| 24 | 
            +
                    api_response = result.current_api_response
         | 
| 25 | 
            +
                    return if api_response.blank?
         | 
| 20 26 |  | 
| 21 | 
            -
                    ctx. | 
| 22 | 
            -
                     | 
| 23 | 
            -
                    ctx
         | 
| 27 | 
            +
                    ctx.add_to_api_responses(api_response)
         | 
| 28 | 
            +
                    nil
         | 
| 24 29 | 
             
                  end
         | 
| 25 30 |  | 
| 26 31 | 
             
                  def outcomes_complete?(ctx:, result:)
         | 
    
        data/light-service-ext.gemspec
    CHANGED
    
    | @@ -16,7 +16,7 @@ Gem::Specification.new do |gem| | |
| 16 16 | 
             
              gem.name = "light-service-ext"
         | 
| 17 17 | 
             
              gem.require_paths = ["lib"]
         | 
| 18 18 | 
             
              gem.version = LightServiceExt::VERSION
         | 
| 19 | 
            -
              gem.required_ruby_version = ">=  | 
| 19 | 
            +
              gem.required_ruby_version = ">= 2.7"
         | 
| 20 20 |  | 
| 21 21 | 
             
              gem.metadata["homepage_uri"] = gem.homepage
         | 
| 22 22 | 
             
              gem.metadata["source_code_uri"] = gem.homepage
         | 
| @@ -1,19 +1,17 @@ | |
| 1 1 | 
             
            module LightServiceExt
         | 
| 2 2 | 
             
              RSpec.describe ApplicationAction do
         | 
| 3 | 
            -
                 | 
| 4 | 
            -
                   | 
| 5 | 
            -
                     | 
| 6 | 
            -
             | 
| 7 | 
            -
             | 
| 3 | 
            +
                let(:fake_action) do
         | 
| 4 | 
            +
                  Class.new(described_class) do
         | 
| 5 | 
            +
                    executed do |context|
         | 
| 6 | 
            +
                      value = context.dig(:input, :callback).call
         | 
| 7 | 
            +
                      context.add_params(value: value)
         | 
| 8 | 
            +
                      context.add_errors!(value: value)
         | 
| 9 | 
            +
                    end
         | 
| 8 10 | 
             
                  end
         | 
| 9 11 | 
             
                end
         | 
| 10 12 |  | 
| 11 13 | 
             
                let(:organizer_class) do
         | 
| 12 | 
            -
                  Class.new(ApplicationOrganizer) do
         | 
| 13 | 
            -
                    def self.steps
         | 
| 14 | 
            -
                      [FakeApplicationAction]
         | 
| 15 | 
            -
                    end
         | 
| 16 | 
            -
                  end
         | 
| 14 | 
            +
                  Class.new(ApplicationOrganizer) do end
         | 
| 17 15 | 
             
                end
         | 
| 18 16 |  | 
| 19 17 | 
             
                let(:value) { 'some-value' }
         | 
| @@ -22,18 +20,54 @@ module LightServiceExt | |
| 22 20 | 
             
                let(:ctx) do
         | 
| 23 21 | 
             
                  LightService::Testing::ContextFactory
         | 
| 24 22 | 
             
                    .make_from(organizer_class)
         | 
| 25 | 
            -
                    .for( | 
| 23 | 
            +
                    .for(fake_action)
         | 
| 26 24 | 
             
                    .with(callback: callback)
         | 
| 27 25 | 
             
                end
         | 
| 28 26 |  | 
| 29 | 
            -
                subject(: | 
| 30 | 
            -
             | 
| 27 | 
            +
                subject(:executed_ctx) { fake_action.execute(ctx) }
         | 
| 28 | 
            +
             | 
| 29 | 
            +
                before do
         | 
| 30 | 
            +
                  allow(organizer_class).to receive(:steps) { [fake_action] }
         | 
| 31 31 | 
             
                end
         | 
| 32 32 |  | 
| 33 33 | 
             
                it 'adds value returned by callback to params' do
         | 
| 34 | 
            -
                  expect( | 
| 34 | 
            +
                  expect(executed_ctx.keys).to include(:input, :errors, :params)
         | 
| 35 | 
            +
             | 
| 36 | 
            +
                  expect(executed_ctx[:params]).to eql({ value: value })
         | 
| 37 | 
            +
                end
         | 
| 38 | 
            +
             | 
| 39 | 
            +
                describe 'lifecycle callbacks' do
         | 
| 40 | 
            +
                  before do
         | 
| 41 | 
            +
                    allow(fake_action.before_execute_block).to receive(:call)
         | 
| 42 | 
            +
                    allow(fake_action.after_execute_block).to receive(:call)
         | 
| 43 | 
            +
                    allow(fake_action.after_success_block).to receive(:call)
         | 
| 44 | 
            +
                    allow(fake_action.after_failure_block).to receive(:call)
         | 
| 45 | 
            +
                  end
         | 
| 35 46 |  | 
| 36 | 
            -
                   | 
| 47 | 
            +
                  it 'calls appropriate lifecycle callbacks' do
         | 
| 48 | 
            +
                    executed_ctx
         | 
| 49 | 
            +
             | 
| 50 | 
            +
                    expect(fake_action.before_execute_block).to have_received(:call).with(kind_of(ApplicationContext)).at_least(:once)
         | 
| 51 | 
            +
                    expect(fake_action.after_execute_block).to have_received(:call).with(kind_of(ApplicationContext))
         | 
| 52 | 
            +
                    expect(fake_action.after_success_block).not_to have_received(:call).with(kind_of(ApplicationContext))
         | 
| 53 | 
            +
                    expect(fake_action.after_failure_block).to have_received(:call).at_least(:once)
         | 
| 54 | 
            +
                  end
         | 
| 55 | 
            +
             | 
| 56 | 
            +
                  context 'with failure' do
         | 
| 57 | 
            +
                    before do
         | 
| 58 | 
            +
                      allow_any_instance_of(ApplicationContext).to receive(:errors) { {} }
         | 
| 59 | 
            +
                      allow_any_instance_of(ApplicationContext).to receive(:success?) { true }
         | 
| 60 | 
            +
                    end
         | 
| 61 | 
            +
             | 
| 62 | 
            +
                    it 'calls appropriate lifecycle callbacks' do
         | 
| 63 | 
            +
                      executed_ctx
         | 
| 64 | 
            +
             | 
| 65 | 
            +
                      expect(fake_action.before_execute_block).to have_received(:call).with(kind_of(ApplicationContext)).at_least(:once)
         | 
| 66 | 
            +
                      expect(fake_action.after_execute_block).to have_received(:call).with(kind_of(ApplicationContext)).at_least(:once)
         | 
| 67 | 
            +
                      expect(fake_action.after_success_block).to have_received(:call).with(kind_of(ApplicationContext))
         | 
| 68 | 
            +
                      expect(fake_action.after_failure_block).to_not have_received(:call)
         | 
| 69 | 
            +
                    end
         | 
| 70 | 
            +
                  end
         | 
| 37 71 | 
             
                end
         | 
| 38 72 | 
             
              end
         | 
| 39 73 | 
             
            end
         | 
| @@ -325,6 +325,21 @@ module LightServiceExt | |
| 325 325 |  | 
| 326 326 | 
             
                  subject(:ctx_with_defaults) { described_class.make_with_defaults(input, overrides) }
         | 
| 327 327 |  | 
| 328 | 
            +
                  describe '#add_meta' do
         | 
| 329 | 
            +
                    it 'adds meta to context' do
         | 
| 330 | 
            +
                      ctx_with_defaults.add_meta(key => value)
         | 
| 331 | 
            +
                      expect(ctx_with_defaults.meta).to eql(key => value)
         | 
| 332 | 
            +
                    end
         | 
| 333 | 
            +
                  end
         | 
| 334 | 
            +
             | 
| 335 | 
            +
                  context 'with meta as an override' do
         | 
| 336 | 
            +
                    let(:overrides) { { meta: { key: 'some-value' } } }
         | 
| 337 | 
            +
             | 
| 338 | 
            +
                    it 'adds meta to context' do
         | 
| 339 | 
            +
                      expect(ctx_with_defaults.meta).to eql(key => value)
         | 
| 340 | 
            +
                    end
         | 
| 341 | 
            +
                  end
         | 
| 342 | 
            +
             | 
| 328 343 | 
             
                  context 'with non symbolized input keys' do
         | 
| 329 344 | 
             
                    let(:input) { { "key" => 'some-value' } }
         | 
| 330 345 |  | 
| @@ -346,6 +361,7 @@ module LightServiceExt | |
| 346 361 | 
             
                                                                    invoked_action
         | 
| 347 362 | 
             
                                                                    current_api_response
         | 
| 348 363 | 
             
                                                                    last_failed_context
         | 
| 364 | 
            +
                                                                    meta
         | 
| 349 365 | 
             
                                                                  ])
         | 
| 350 366 |  | 
| 351 367 | 
             
                    expect(ctx_with_defaults[:input]).to eql(input)
         | 
    
        metadata
    CHANGED
    
    | @@ -1,14 +1,14 @@ | |
| 1 1 | 
             
            --- !ruby/object:Gem::Specification
         | 
| 2 2 | 
             
            name: light-service-ext
         | 
| 3 3 | 
             
            version: !ruby/object:Gem::Version
         | 
| 4 | 
            -
              version: 0.1. | 
| 4 | 
            +
              version: 0.1.11
         | 
| 5 5 | 
             
            platform: ruby
         | 
| 6 6 | 
             
            authors:
         | 
| 7 7 | 
             
            - Desmond O'Leary
         | 
| 8 8 | 
             
            autorequire:
         | 
| 9 9 | 
             
            bindir: bin
         | 
| 10 10 | 
             
            cert_chain: []
         | 
| 11 | 
            -
            date: 2023-09- | 
| 11 | 
            +
            date: 2023-09-29 00:00:00.000000000 Z
         | 
| 12 12 | 
             
            dependencies:
         | 
| 13 13 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 14 14 | 
             
              name: light-service
         | 
| @@ -205,7 +205,6 @@ files: | |
| 205 205 | 
             
            - spec/light-service-ext/application_orchestrator_spec.rb
         | 
| 206 206 | 
             
            - spec/light-service-ext/application_organizer_spec.rb
         | 
| 207 207 | 
             
            - spec/light-service-ext/application_validator_action_spec.rb
         | 
| 208 | 
            -
            - spec/light-service-ext/around_action_execute_extension_spec.rb
         | 
| 209 208 | 
             
            - spec/light-service-ext/configuration_spec.rb
         | 
| 210 209 | 
             
            - spec/light-service-ext/context_error_spec.rb
         | 
| 211 210 | 
             
            - spec/light-service-ext/error_info_spec.rb
         | 
| @@ -229,7 +228,7 @@ required_ruby_version: !ruby/object:Gem::Requirement | |
| 229 228 | 
             
              requirements:
         | 
| 230 229 | 
             
              - - ">="
         | 
| 231 230 | 
             
                - !ruby/object:Gem::Version
         | 
| 232 | 
            -
                  version: ' | 
| 231 | 
            +
                  version: '2.7'
         | 
| 233 232 | 
             
            required_rubygems_version: !ruby/object:Gem::Requirement
         | 
| 234 233 | 
             
              requirements:
         | 
| 235 234 | 
             
              - - ">="
         | 
| @@ -249,7 +248,6 @@ test_files: | |
| 249 248 | 
             
            - spec/light-service-ext/application_orchestrator_spec.rb
         | 
| 250 249 | 
             
            - spec/light-service-ext/application_organizer_spec.rb
         | 
| 251 250 | 
             
            - spec/light-service-ext/application_validator_action_spec.rb
         | 
| 252 | 
            -
            - spec/light-service-ext/around_action_execute_extension_spec.rb
         | 
| 253 251 | 
             
            - spec/light-service-ext/configuration_spec.rb
         | 
| 254 252 | 
             
            - spec/light-service-ext/context_error_spec.rb
         | 
| 255 253 | 
             
            - spec/light-service-ext/error_info_spec.rb
         | 
| @@ -1,56 +0,0 @@ | |
| 1 | 
            -
            module LightServiceExt
         | 
| 2 | 
            -
              RSpec.describe AroundActionExecuteExtension do
         | 
| 3 | 
            -
                let(:fake_action) do
         | 
| 4 | 
            -
                  Class.new do
         | 
| 5 | 
            -
                    prepend AroundActionExecuteExtension
         | 
| 6 | 
            -
             | 
| 7 | 
            -
                    def execute(_ctx)
         | 
| 8 | 
            -
                      fake_resultant_ctx # HACK: to allow us to control returned value from prepended execute method
         | 
| 9 | 
            -
                    end
         | 
| 10 | 
            -
             | 
| 11 | 
            -
                    def fake_resultant_ctx; end
         | 
| 12 | 
            -
                  end.new
         | 
| 13 | 
            -
                end
         | 
| 14 | 
            -
             | 
| 15 | 
            -
                describe '#execute' do
         | 
| 16 | 
            -
                  let(:input) { { key: 'some-value' } }
         | 
| 17 | 
            -
                  let(:orig_ctx) { ApplicationContext.make_with_defaults }
         | 
| 18 | 
            -
                  let(:errors) { {} }
         | 
| 19 | 
            -
                  let(:frozen_resultant_ctx) do
         | 
| 20 | 
            -
                    ApplicationContext.make_with_defaults.merge({ key: 'some-value', errors: errors }).freeze
         | 
| 21 | 
            -
                  end
         | 
| 22 | 
            -
             | 
| 23 | 
            -
                  subject(:executed_ctx) { fake_action.execute(orig_ctx) }
         | 
| 24 | 
            -
             | 
| 25 | 
            -
                  before do
         | 
| 26 | 
            -
                    allow(fake_action).to receive(:fake_resultant_ctx) { frozen_resultant_ctx }
         | 
| 27 | 
            -
                  end
         | 
| 28 | 
            -
             | 
| 29 | 
            -
                  it 'returns unmodified resultant context' do
         | 
| 30 | 
            -
                    expect(executed_ctx).to eql(frozen_resultant_ctx)
         | 
| 31 | 
            -
                  end
         | 
| 32 | 
            -
             | 
| 33 | 
            -
                  it 'calls underlying prepended execute method' do
         | 
| 34 | 
            -
                    executed_ctx
         | 
| 35 | 
            -
             | 
| 36 | 
            -
                    expect(fake_action).to have_received(:fake_resultant_ctx)
         | 
| 37 | 
            -
                  end
         | 
| 38 | 
            -
             | 
| 39 | 
            -
                  it 'merges key value pairs from underlying execute to original context' do
         | 
| 40 | 
            -
                    executed_ctx
         | 
| 41 | 
            -
             | 
| 42 | 
            -
                    expect(orig_ctx.keys).to include(:key)
         | 
| 43 | 
            -
                  end
         | 
| 44 | 
            -
             | 
| 45 | 
            -
                  context 'with resultant ctx with errors' do
         | 
| 46 | 
            -
                    let(:errors) { { key: 'must be filled' } }
         | 
| 47 | 
            -
             | 
| 48 | 
            -
                    it 'fails original context' do
         | 
| 49 | 
            -
                      executed_ctx
         | 
| 50 | 
            -
             | 
| 51 | 
            -
                      expect(orig_ctx.failure?).to be_truthy
         | 
| 52 | 
            -
                    end
         | 
| 53 | 
            -
                  end
         | 
| 54 | 
            -
                end
         | 
| 55 | 
            -
              end
         | 
| 56 | 
            -
            end
         |