Skip to content

Navigation Menu

Sign in
Sign up

Repository files navigation

Sumaki


Gem Version example workflow Maintainability Test Coverage

Sumaki is a wrapper for structured data like JSON.

Since Sumaki wraps the target data as it is, rather than parsing it using a schema, the original data can be referenced at any time.

This makes it easy to add or modify definitions as needed while checking the target data.

This feature may be useful when there is no document defining the structure of the data, or when the specification is complex and difficult to grasp, and the definition is written little by little starting from the obvious places.

class AnimeList
 include Sumaki::Model
 repeated :anime
 field :name
 class Anime
 include Sumaki::Model
 singular :studio
 field :title
 class Studio
 include Sumaki::Model
 field :name
 end
 end
end
data = {
 name: 'Winter 2023',
 anime: [
 {
 title: 'The Vampire Dies in No Time',
 studio: {
 name: 'MADHOUSE Inc.'
 }
 },
 {
 title: '"Ippon" again!',
 studio: {
 name: 'BAKKEN RECORD'
 }
 }
 ]
}
anime_list = AnimeList.new(data)
anime_list.name #=> 'Winter 2023'
anime_list.anime[0].title #=> 'The Vampire Dies in No Time'
anime_list.anime[0].studio.name #=> 'MADHOUSE Inc.'
anime_list.anime[0].object #=> { title: 'The Vampire Dies in No Time', studio: { name: 'MADHOUSE Inc.' } }

Installation

Install the gem and add to the application's Gemfile by executing:

$ bundle add sumaki

If bundler is not being used to manage dependencies, install the gem by executing:

$ gem install sumaki

Usage

Include Sumaki::Model module in the class that wraps the data, and give the data when creating the instance.

class Anime
 include Sumaki::Model
end
Anime.new({})

Only this does not give access to fields or structured data, so the following declarations need to be added.

Access to the fields

By declaring field, you can access the field.

class Anime
 include Sumaki::Model
 field :title
 field :url
end
# Read the field values
anime = Anime.new({ title: 'The Vampire Dies in No Time', url: 'https://sugushinu-anime.jp/' })
anime.title #=> 'The Vampire Dies in No Time'
anime.url #=> 'https://sugushinu-anime.jp/'
# Write the field value
anime = Anime.new({})
anime.title = 'The Vampire Dies in No Time'
anime.title #=> 'The Vampire Dies in No Time'

If the data contains attributes not declared in the field, it raises no error and is simply ignored.

Type casting

When a type is specified, it will be typecast.

class Character
 include Sumaki::Model
 field :age, :int
end
character = Character.new({ age: '208' })
character.age #=> 208

Types are:

  • :int
  • :float
  • :string
  • :bool
  • :date
  • :datetime

Access to the sub object

By declaring singular, you can access the sub object.

class Book
 include Sumaki::Model
 singular :company
 field :title
 class Company
 include Sumaki::Model
 field :name
 end
end
data = {
 title: 'The Ronaldo Chronicles',
 company: {
 name: 'Autumn Books',
 }
}
# Read from the sub object
book = Book.new(data)
book.company.name #=> 'Autumn Books'
# Build a sub object
book = Book.new({})
book.build_company(name: 'Autumn Books')
book.company #=> #<Book::Company:0x000073a618e31e80 name: "Autumn Books">

Sub object is wrapped with the class inferred from the field name under the original class.

This can be changed by specifying the class to wrap.

class Book
 include Sumaki::Model
 singular :author, class_name: 'Character'
 field :title
 class Character
 include Sumaki::Model
 field :name
 end
end
data = {
 title: 'The Ronaldo Chronicles',
 author: {
 name: 'Ronaldo'
 }
}
book = Book.new(data)
book.author.class #=> Book::Character

Access to the repeated sub objects

By declaring repeated, you can access the repeated sub objects as an Array.

class Company
 include Sumaki::Model
 repeated :member
 field :name
 class Member
 include Sumaki::Model
 field :name
 end
end
data = {
 name: 'The Ronaldo Vampire Hunter Agency',
 member: [
 { name: 'Ronaldo' },
 { name: 'Draluc' },
 { name: 'John' }
 ]
}
# Read from the sub object
company = Company.new(data)
company.member.size #=> 3
company.member[2].name #=> 'John'
# Build a sub object
company = Company.new({})
company.member.build(name: 'John')
company.member[0].name #=> 'John'

The class_name option can also be used to specify the class to wrap.

Access to the parent object

Parent object can be referenced from sub object by #parent method.

class Character
 include Sumaki::Model
 singular :child
 field :name
 class Child
 include Sumaki::Model
 field :name
 end
end
data = {
 name: 'Draus',
 child: {
 name: 'Draluc'
 }
}
character = Character.new(data)
character.child.name #=> 'Draluc'
character.child.parent.name #=> 'Draus'

Enumerations

By declaring enum, You can map a field to the specified value.

class Character
 include Sumaki::Model
 field :name
 enum :type, { vampire: 1, vampire_hunter: 2, familier: 3, editor: 4 }
end
data = {
 name: 'John',
 type: 3
}
# Read the enum
character = Character.new(data)
character.type.name #=> :familier
character.type.familier? #=> true
# Write the enum value
character = Character.new({})
character.type = 1
character.type.name #=> :vampire
character.type = :vampire_hunter
character.type.name #=> :vampire_hunter
character.type.familier!
character.type.name #=> :familier

Development

After checking out the repo, run bin/setup to install dependencies. Then, run rake spec to run the tests. You can also run bin/console for an interactive prompt that will allow you to experiment.

To install this gem onto your local machine, run bundle exec rake install. To release a new version, update the version number in version.rb, and then run bundle exec rake release, which will create a git tag for the version, push git commits and the created tag, and push the .gem file to rubygems.org.

Contributing

Bug reports and pull requests are welcome on GitHub at https://github.com/nowlinuxing/sumaki.

License

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

About

Sumaki is a wrapper for structured data like JSON.

Topics

Resources

Stars

1 star

Watchers

1 watching

Forks

Releases

Packages

Used by

Contributors

Languages

AltStyle によって変換されたページ (->オリジナル) /