permanent_record 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. checksums.yaml +7 -0
  2. data/lib/permanent_record.rb +188 -0
  3. metadata +89 -0
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: adcecb24f1c6611a113103ac06b26e589f321563
4
+ data.tar.gz: 69fe494a2595ab8f74044fcdda83ddd13f162d73
5
+ SHA512:
6
+ metadata.gz: 5498cb313de9b9064ccba63c81490d2910f7b406186a8812a040ada0a34491994726f11cdfa9f010390ba758f60dc17ef2ac7a82082dc489b38c5a48be5d2ec2
7
+ data.tar.gz: 0f94c0aa82601ed43fc81b2c0fb999fe8e364091e95bd2d73cff47bb65a66caad20cdb9279accbc898c59bf25b4e830b12c9cff003ca6ae0d8c7a5444982154b
@@ -0,0 +1,188 @@
1
+ require 'active_model'
2
+ require 'active_support/core_ext/hash'
3
+
4
+ class PermanentRecord
5
+
6
+ # Get goodies for model_name, etc from ActiveModel.
7
+ # This allows normal Rails path helper generation.
8
+ #
9
+ extend ActiveModel::Naming
10
+
11
+ # Constructs a new PermanentRecord instance.
12
+ # Set instance variable and reader based on input hash.
13
+ #
14
+ def initialize attrs={}
15
+ attrs.each do |key, value|
16
+ if valid_attribute? key
17
+ self.instance_variable_set("@#{key}", value)
18
+ self.class.class_eval{attr_reader key}
19
+ end
20
+ end
21
+ end
22
+
23
+ # For working with Rails routing helpers.
24
+ # Override in your PermanentRecord class to adjust URLs.
25
+ #
26
+ def to_param
27
+ self.id
28
+ end
29
+
30
+ # Overrides equality to match ids.
31
+ #
32
+ def == model
33
+ self.id == model.id
34
+ end
35
+
36
+ class << self
37
+ # Returns collection of all PermanentRecord instances.
38
+ #
39
+ # Example:
40
+ # >> Model.all
41
+ # => [@model1, @model2, ...]
42
+ #
43
+ def all
44
+ data.map{|d| self.new(d)}
45
+ end
46
+
47
+ # Find instance given id.
48
+ # Returns instance if found; nil otherwise.
49
+ #
50
+ # Example:
51
+ # >> Model.find(42)
52
+ # => @model
53
+ #
54
+ def find id
55
+ self.find_by_attribute(:id, id)
56
+ end
57
+
58
+ # Find instance given attribute name and expected value.
59
+ # Returns instance if found; nil otherwise.
60
+ #
61
+ # Example:
62
+ # >> Model.find_by_attribute(:bacon, 'chunky')
63
+ # => @model
64
+ #
65
+ def find_by_attribute key, value
66
+ found = data.find{|d| d[key.to_sym].to_s == value.to_s}
67
+ self.new(found) if found
68
+ end
69
+
70
+ # Find instance(s) given hash of attribute key/values.
71
+ # Returns all instances if found; empty array otherwise.
72
+ #
73
+ # Example:
74
+ # >> Model.where(bacon: 'chunky', cats: 'calico')
75
+ # => [@model1, @model2, ...]
76
+ #
77
+ def where *attrs
78
+ keys = attrs.first.keys
79
+ found = data.map{|d| d if d.reject{|key,_| !keys.include?(key)} == attrs.first}
80
+ found.compact.map{|f| self.new(f)}
81
+ end
82
+
83
+ # Oh, just for fun let's metaprogram some method missing!
84
+ # Provides 'find_by_<attr>' finders if you don't like 'where'.
85
+ # Returns instance if found; nil otherwise.
86
+ #
87
+ # Example:
88
+ # >> Model.find_by_bacon('chunky')
89
+ # => @model
90
+ #
91
+ def method_missing(method, *arguments, &block)
92
+ match = method.to_s.match(/^find_by_(.*)$/)
93
+ if match && valid_attribute?($1.to_sym)
94
+ find_by_attribute($1.to_sym, arguments.first)
95
+ else
96
+ super
97
+ end
98
+ end
99
+ end
100
+
101
+ protected
102
+
103
+ # Check if attribute name is valid.
104
+ #
105
+ def valid_attribute? key
106
+ self.class.valid_attribute?(key)
107
+ end
108
+
109
+ class << self
110
+ # Declares source for PermanentRecord class data.
111
+ # PermanentRecord pretty much just wants to source any ol' array of hashes.
112
+ # If not declared, it'll default to a pluralized model name constant.
113
+ # ie: If your model is called MyModel, this'll try and find MY_MODELS.
114
+ #
115
+ # The default example, with NO source defined:
116
+ # class MyModel < PermanentRecord
117
+ # end
118
+ #
119
+ # Example with source constant explicitly defined:
120
+ # class MyModel < PermanentRecord
121
+ # source SOME_CONSTANT
122
+ # end
123
+ #
124
+ # Another example with a source YAML file explicitly defined:
125
+ # class MyModel < PermanentRecord
126
+ # source YAML.load(File.read('path/to/yaml/file.yml'))
127
+ # end
128
+ #
129
+ # I doubt you'd want to define your source as an explicit array of hash,
130
+ # but just to drive home this "any array of hashes" idea here's an example:
131
+ # class MyModel < PermanentRecord
132
+ # source [{eyes: 'blue', hair: 'blonde'}, {eyes: 'brown', hair: 'green'}]
133
+ # end
134
+ #
135
+ def source data=nil
136
+ @_data = format_data data
137
+ end
138
+
139
+ # Retrieve or load raw data.
140
+ #
141
+ def data
142
+ @_data ||= data_from_constant
143
+ end
144
+
145
+ # Auto load data from constant; pluralized model name
146
+ # ie: If your model is called ZooKeeper, this will try and
147
+ # auto load a constant called ZOO_KEEPERS. You can put that
148
+ # constant anywhere you want ... like in the model, or in
149
+ # a constants.rb file, or maybe a zoo_keeprs.rb file.
150
+ #
151
+ def data_from_constant
152
+ data = eval(self.name.to_s.underscore.pluralize.upcase)
153
+ format_data data
154
+ end
155
+
156
+ # Add sequential id to all records.
157
+ # This can be overwritten if an id is specified in the data.
158
+ # CAUTION! If defining your own ids please make sure they're unique!
159
+ #
160
+ def format_data data
161
+ data = data.each_with_index.map{|d, i| {id: i+1}.merge(d)}
162
+ data.each(&:symbolize_keys!)
163
+ end
164
+
165
+ # Retrieve or load model attributes.
166
+ #
167
+ def attributes
168
+ @_attributes ||= attributes_from_data
169
+ end
170
+
171
+ # Find attributes based on first data item keys
172
+ # This might be something worth explicitly stating in an
173
+ # 'attributes' config or something... but for now I'm going
174
+ # with the lazy way out, and we'll just check the first data item.
175
+ # So please be sure to have well formed data!
176
+ #
177
+ def attributes_from_data
178
+ data.first.keys
179
+ end
180
+
181
+ # Check if attribute name is valid.
182
+ #
183
+ def valid_attribute? key
184
+ attributes.include?(key)
185
+ end
186
+ end
187
+
188
+ end
metadata ADDED
@@ -0,0 +1,89 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: permanent_record
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Caleb K Matthiesen
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-10-01 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: activemodel
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '4.1'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '4.1'
27
+ - !ruby/object:Gem::Dependency
28
+ name: activesupport
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '4.1'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '4.1'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rake
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '10.3'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '10.3'
55
+ description: ActiveRecord type READ ONLY data storage for small amounts of simple,
56
+ unchanging data.
57
+ email:
58
+ - c@calebkm.com
59
+ executables: []
60
+ extensions: []
61
+ extra_rdoc_files: []
62
+ files:
63
+ - lib/permanent_record.rb
64
+ homepage: https://github.com/calebkm/permanent_record
65
+ licenses:
66
+ - MIT
67
+ metadata: {}
68
+ post_install_message:
69
+ rdoc_options: []
70
+ require_paths:
71
+ - lib
72
+ required_ruby_version: !ruby/object:Gem::Requirement
73
+ requirements:
74
+ - - ">="
75
+ - !ruby/object:Gem::Version
76
+ version: '0'
77
+ required_rubygems_version: !ruby/object:Gem::Requirement
78
+ requirements:
79
+ - - ">="
80
+ - !ruby/object:Gem::Version
81
+ version: '0'
82
+ requirements: []
83
+ rubyforge_project:
84
+ rubygems_version: 2.2.2
85
+ signing_key:
86
+ specification_version: 4
87
+ summary: Persistent Data without a DB.
88
+ test_files: []
89
+ has_rdoc: