Created
October 26, 2012 17:40
-
-
Save spllr/3960153 to your computer and use it in GitHub Desktop.
InnoViz SF Database mapper
This file contains 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
#!/usr/bin/env ruby -wKU | |
## | |
# Runtime options | |
# | |
require "optparse" | |
options = { :spec => false } | |
ARGV.options do |opts| | |
opts.banner = "Usage: #{File.basename($PROGRAM_NAME)}" | |
opts.on( "-s", "--[no-]spec", "Run specs") do |v| | |
options[:spec] = v | |
end | |
end.parse! | |
## | |
# Implementation | |
# | |
require "json" | |
module InnoViz | |
module Resource | |
module ClassMethods | |
def resource_name(*args) | |
@resource_name = args[0] unless args.empty? | |
@resource_name.to_s.split(/[ -]/).map { |w| w.capitalize }.join | |
end | |
def slot(name) | |
self.class_eval { attr_accessor name } | |
slots << name | |
end | |
def slots | |
@slots ||= [] | |
end | |
def resource_path | |
resource_name | |
end | |
def resource_slots_path | |
File.join(resource_path, 'slots') | |
end | |
def parse(data) | |
obj = new | |
JSON.parse(data).each do |k,v| | |
obj.send "#{k}=", v | |
end | |
obj | |
end | |
def migrate | |
Dir.mkdir resource_path unless File.exists?(resource_path) | |
Dir.mkdir resource_slots_path unless File.exists?(resource_slots_path) | |
end | |
end | |
module InstanceMethods | |
alias_method :id, :object_id | |
def save | |
File.open("#{id}.json", "w+") { |f| f.write to_json } | |
end | |
def to_json | |
obj = {} | |
self.class.slots.each do |s| | |
obj[s] = send(s) | |
end | |
obj.to_json | |
end | |
end | |
def self.included(receiver) | |
receiver.extend ClassMethods | |
receiver.send :include, InstanceMethods | |
end | |
end | |
end | |
## | |
# Specs | |
# | |
# To run the test: | |
# | |
# %> ruby innovizdb.rb -s | |
# | |
require "minitest/spec" | |
require "minitest/autorun" if options[:spec] | |
describe "InnoViz::Resource" do | |
require "tmpdir" | |
def sandbox | |
Dir.mktmpdir do |dir| | |
Dir.chdir(dir) { yield } | |
end | |
end | |
let(:resource) do | |
Class.new do | |
include InnoViz::Resource | |
resource_name :account | |
slot :name | |
slot :age | |
end | |
end | |
describe ".migrate" do | |
it 'creates the correct folder name' do | |
sandbox do | |
resource.migrate | |
File.directory?('Account').must_equal true | |
end | |
end | |
it 'creates the slots dir' do | |
sandbox do | |
resource.migrate | |
File.directory?('Account/slots').must_equal true | |
end | |
end | |
it 'can be run multiple times' do | |
sandbox do | |
lambda { resource.migrate }.must_be_silent | |
lambda { resource.migrate }.must_be_silent | |
lambda { resource.migrate }.must_be_silent | |
end | |
end | |
end | |
describe "slots" do | |
it 'creates a accesor for each slot' do | |
obj = resource.new | |
obj.must_respond_to :name= | |
obj.must_respond_to :name | |
obj.must_respond_to :age= | |
obj.must_respond_to :age | |
end | |
end | |
describe "#save" do | |
it 'saves the instance to a file using the id as the name' do | |
sandbox do | |
resource.migrate | |
obj = resource.new | |
obj.name = "Emma" | |
obj.age = 21 | |
obj.save | |
File.exists?("#{obj.id}.json").must_equal true | |
end | |
end | |
it 'saves the instance as a json representation' do | |
sandbox do | |
resource.migrate | |
obj = resource.new | |
obj.name = "Emma" | |
obj.age = 21 | |
obj.save | |
File.open("#{obj.id}.json") { |f| | |
the_json = JSON.parse(f.read) | |
the_json["name"].must_equal obj.name | |
the_json["age"].must_equal obj.age | |
} | |
end | |
end | |
end | |
describe ".parse" do | |
it 'can serialize itself from a json representation' do | |
obj = resource.parse(%({ "name": "Pipo", "age": 21 })) | |
obj.name.must_equal "Pipo" | |
obj.age.must_equal 21 | |
end | |
end | |
end | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment