Skip to content

featurist/interfaceable

Repository files navigation

Interfaceable Ruby Gem Version

Impose interfaces on classes and let this gem automatically check that the interface constraints are met.

Installation

Add this line to your application's Gemfile:

gem 'interfaceable'

And then execute:

$ bundle install

Usage

In this example:

module Carrier
  def call(number); end

  def text(number, text); end
end

class Giffgaff
  extend Interfaceable

  implements Carrier
end

An attempt to load this code will result in the following error:

Giffgaff must implement: (Interfaceable::Error)
  - Carrier#text
  - Carrier#call

It will keep failing until Giffgaff defines those methods.

Correctly! E.g.:

class Giffgaff
  def call(number); end

  def text(number, text = ''); end
end

Will fail because of method signature mismatch:

Giffgaff must implement correctly: (Interfaceable::Error)
  - Carrier#text:
    - expected arguments: (req, req)
    - actual arguments: (req, opt=)

Classes may define additional optional or rest arguments.

module Carrier
  def call(number); end

  def text(number, text); end
end

class Giffgaff
  def call(number, *opts); end

  def text(number, text, opt1 = nil, opt2 = nil); end
end

This will not generate any errors since Giffgaff implements the required methods with correct arguments only adding new optional ones.

Rails

Mix in Interfaceable before any of the application code is loaded. For example, in the initializer. For extra peace of mind, you can noop interface checking in production:

# config/initializers/interfaceable.rb
class Class
  if Rails.env.production?
    def implements(*args); end
  else
    include Interfaceable
  end
end

About

Strict interfaces in Ruby

Topics

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published