Skip to content

Instantly share code, notes, and snippets.

@baweaver
Created December 27, 2018 05:11
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save baweaver/89934ed8ba6e3a8a207db84e542dd512 to your computer and use it in GitHub Desktop.
Save baweaver/89934ed8ba6e3a8a207db84e542dd512 to your computer and use it in GitHub Desktop.
Experimental version of Sf, pre-release
class Sf
attr_reader :operations
OPERATORS = %i(+ - * / % < > <= >= == && & || |)
INSTANCE_OP = -> name {
-> method_name, *args, **kwargs, &fn {
@operations.push(method_name: name, args: args, kwargs: kwargs, fn: fn)
self
}
}
CLASS_OP = -> name {
-> method_name, *args, **kwargs, &fn {
self.new([method_name: name, args: args, kwargs: kwargs, fn: fn])
}
}
OPERATORS.each do |op|
self.define_method(op, &INSTANCE_OP[op])
singleton_class.define_method(op, &CLASS_OP[op])
end
def method_missing(method_name, *args, **kwargs, &fn)
@operations.push(method_name: method_name, args: args, kwargs: kwargs, fn: fn)
self
end
def self.method_missing(method_name, *args, **kwargs, &fn)
CLASS_OP[method_name].call(*args, **kwargs, &fn)
end
def initialize(operations)
@operations = operations
end
def to_proc
-> object { call(object) }
end
def call(object)
@operations.reduce(object) { |obj, method_name:, args:, kwargs:, fn:|
if kwargs.empty?
obj.public_send(method_name, *args, &fn)
else
obj.public_send(method_name, *args, **kwargs, &fn)
end
}
end
def ===(object)
call(object)
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment