Last active
December 11, 2018 20:23
-
-
Save joegaudet/fc6313fac04a1a056107d940c1cb06f1 to your computer and use it in GitHub Desktop.
Update to the dependency system to support two types of null substitutes, one where the only public interface is call, and one where it is any method. This allows us to more simply test object boundaries.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
module Broadcasters | |
class OrderBroadcaster | |
include Wisper::Publisher | |
include DependencySupport::NullSubstitute | |
def changed(order) | |
// do some stuff | |
end | |
end | |
end |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Basic Inert Class maps args to return values | |
class InertCallable | |
attr_reader :call_history | |
def initialize | |
@return = {} | |
@call_history = [] | |
end | |
def call(*args) | |
@call_history << args | |
@return[args] | |
end | |
def setup(*args, ret) | |
@return[args] = ret | |
end | |
def called_with?(*args) | |
@call_history.include? args | |
end | |
def called_only_with?(*args) | |
@call_history == [args] | |
end | |
end |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class InertNullObject | |
def initialize(parent_klass) | |
@methods = {} | |
@parent_klass = parent_klass | |
end | |
def method_missing(m, *args, &block) | |
raise NoMethodError, "The parent class #{@parent_klass} does not define a #{m} method" unless @parent_klass.method_defined?(m) | |
@methods[m] ||= InertCallable.new | |
args.length > 0 ? @methods[m].(*args) : @methods[m] | |
end | |
end |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
module NullSubstitute | |
def self.included(base) | |
base.extend(ClassMethods) | |
end | |
module ClassMethods | |
def inert | |
InertNullObject.new(self) | |
end | |
end | |
end |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
module Logistics | |
module ArrivalEstimates | |
class UpdateOrder < FoodeeService | |
dependency :find_estimate, Queries::ArrivalEstimates::FindOrCreateByOrder | |
dependency :save_record, Commands::SaveRecord | |
dependency :order_broadcaster, Broadcasters::OrderBroadcaster | |
def call(order, log) | |
estimate = find_estimate.(order.id) | |
estimate.update_estimate(log) | |
save_record.(order) | |
order_broadcaster.changed(order) | |
end | |
end | |
end | |
end |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
require 'test_helper' | |
module Logistics | |
module ArrivalEstimates | |
class UpdateOrderTest < ActiveSupport::TestCase | |
let(:update_order) {Logistics::ArrivalEstimates::UpdateOrder.as_subject} | |
let(:log) {Logistics::ArrivalEstimate::EstimateLog.new(timestamp: Time.current, arrival_estimate: Time.current + 1.hours)} | |
let(:order) {Order.new(id: 1)} | |
let(:estimate) {Logistics::ArrivalEstimate.new(id: 1, order: order)} | |
describe 'updating an order delivery estimate' do | |
context 'when the order is ready to be picked up' do | |
it 'updates the pickup estimate' do | |
order.state = 'driver_confirmed' | |
# Setup | |
update_order.find_estimate.setup(order.id, estimate) | |
update_order.save_record.setup(estimate) | |
# exercise | |
update_order.(order, log) | |
# assert | |
assert estimate.pickup_estimate == log | |
assert update_order.save_record.called_with_only? order | |
assert update_order.order_broadcaster.changed.called_only_with? order | |
end | |
end | |
context 'when the order is ready to be delivered' do | |
it 'updates the estimate' do | |
order.state = 'picked_up' | |
# Setup | |
update_order.find_estimate.setup(order.id, estimate) | |
update_order.save_record.setup(estimate) | |
# exercise | |
update_order.(order, log) | |
# assert | |
assert estimate.delivery_estimate == log | |
assert update_order.save_record.called_with_only? order | |
assert update_order.order_broadcaster.changed.called_only_with? order | |
end | |
end | |
end | |
end | |
end | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment