Giter Site home page Giter Site logo

evil-struct's Introduction

Evil::Struct

Nested structure with type constraints, based on the dry-initializer DSL.

Sponsored by Evil Martians

Gem Version Build Status Dependency Status Inline docs

Installation

Add this line to your application's Gemfile:

gem 'evil-struct'

And then execute:

$ bundle

Or install it yourself as:

$ gem install evil-struct

Synopsis

The structure is like dry-struct except for it controls optional attributes and default values aside of type constraints.

Its DSL is taken from dry-initializer. Its method attribute is just an alias for option.

require "evil-struct"
require "dry-types"

class Product < Evil::Struct
  attribute :title
  attribute :price,    Dry::Types["coercible.float"]
  attribute :quantity, Dry::Types["coercible.int"], default: proc { 0 }

  # shared options
  attributes optional: true do
    attribute :subtitle
    attribute :description
  end
end

# Accepts both symbolic and string keys.
# Class methods `[]`, `call`, and `load` are just aliases for `new`
product = Product[title: "apple", "price" => "10.9", description: "a fruit"]

# Attributes are available via methods or `[]`
product.title       # => "apple"
product[:price]     # => 10.9
product["quantity"] # => 0
product.description # => "a fruit"

# unassigned value differs from `nil`
product.subtitle    # => Dry::Initializer::UNDEFINED

# Raises in case a mandatory value not assigned
Product.new # BOOM! because neither title, nor price are assigned

# Hashifies all attributes except for undefined subtitle
# You can use `dump` as an alias for `to_h`
product.to_h
# => { title: "apple", price: 10.9, description: "a fruit", quantity: 0 }

# The structure is comparable to any object that responds to `#to_h`
product == { title: "apple", price: 10.9, description: "a fruit", quantity: 0 }
# => true

The structure is designed for immutability. That's why it doesn't contain writers (but you can define them by yourself via attr_writer).

Instead of mutating current instance, you can merge another hash to the object via merge or deep_merge.

new_product = product.merge(title: "orange")
new_product.class # => Product
new_product.to_h
# => { title: "orange", price: 10.9, description: "a fruit", quantity: 0 }

# you can merge any object that responds to `to_h` or `to_hash`
other = Product[title: "orange", price: 12]
new_product = product.merge(other)
new_product.to_h
# => { title: "orange", price: 12, description: "a fruit", quantity: 0 }

# merge_deeply (deep_merge) gracefully merge nested hashes or hashified objects
grape = Product.new title: "grape",
                    price: 30,
                    description: { country: "FR", year: 2016, sort: "Merlot" }

new_grape = grape.merge_deeply description: { year: 2017 }
new_grape.to_h
# => {
#      title: "grape",
#      price: 30,
#      description: { country: "FR", year: 2017, sort: "Merlot" }
#     }

Compatibility

Tested under rubies compatible to MRI 2.2+.

Contributing

  • Fork the project
  • Create your feature branch (git checkout -b my-new-feature)
  • Add tests for it
  • Commit your changes (git commit -am '[UPDATE] Add some feature')
  • Push to the branch (git push origin my-new-feature)
  • Create a new Pull Request

License

The gem is available as open source under the terms of the MIT License.

evil-struct's People

Contributors

nepalez avatar

Watchers

 avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.