conformist 0.0.3 → 0.1.0
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.
- data/{CHANGELOG.markdown → CHANGELOG.md} +10 -0
- data/README.md +299 -0
- data/Rakefile +5 -17
- data/conformist.gemspec +19 -11
- data/lib/conformist.rb +17 -19
- data/lib/conformist/base.rb +2 -47
- data/lib/conformist/builder.rb +10 -0
- data/lib/conformist/column.rb +14 -17
- data/lib/conformist/hash_struct.rb +33 -0
- data/lib/conformist/schema.rb +66 -0
- data/lib/conformist/version.rb +1 -1
- data/test/helper.rb +2 -11
- data/test/schemas/acma.rb +15 -0
- data/test/{definitions → schemas}/fcc.rb +2 -4
- data/test/unit/conformist/base_test.rb +9 -0
- data/test/unit/conformist/builder_test.rb +12 -0
- data/test/{conformist → unit/conformist}/column_test.rb +4 -0
- data/test/unit/conformist/hash_struct_test.rb +48 -0
- data/test/unit/conformist/schema_test.rb +74 -0
- data/test/unit/conformist_test.rb +20 -0
- data/test/unit/integration_test.rb +72 -0
- metadata +66 -74
- data/README.markdown +0 -157
- data/lib/conformist/row.rb +0 -26
- data/test/conformist/base_test.rb +0 -49
- data/test/conformist/conformist_test.rb +0 -21
- data/test/conformist/row_test.rb +0 -21
- data/test/definitions/acma.rb +0 -24
metadata
CHANGED
@@ -1,120 +1,112 @@
|
|
1
|
-
--- !ruby/object:Gem::Specification
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
2
|
name: conformist
|
3
|
-
version: !ruby/object:Gem::Version
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.0
|
4
5
|
prerelease:
|
5
|
-
version: 0.0.3
|
6
6
|
platform: ruby
|
7
|
-
authors:
|
7
|
+
authors:
|
8
8
|
- Tate Johnson
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
dependencies:
|
16
|
-
- !ruby/object:Gem::Dependency
|
12
|
+
date: 2012-01-05 00:00:00.000000000 Z
|
13
|
+
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
17
15
|
name: rake
|
18
|
-
requirement: &
|
16
|
+
requirement: &70203800707960 !ruby/object:Gem::Requirement
|
19
17
|
none: false
|
20
|
-
requirements:
|
21
|
-
- -
|
22
|
-
- !ruby/object:Gem::Version
|
23
|
-
version: 0
|
18
|
+
requirements:
|
19
|
+
- - ! '>='
|
20
|
+
- !ruby/object:Gem::Version
|
21
|
+
version: '0'
|
24
22
|
type: :development
|
25
23
|
prerelease: false
|
26
|
-
version_requirements: *
|
27
|
-
- !ruby/object:Gem::Dependency
|
24
|
+
version_requirements: *70203800707960
|
25
|
+
- !ruby/object:Gem::Dependency
|
28
26
|
name: minitest
|
29
|
-
requirement: &
|
27
|
+
requirement: &70203800707420 !ruby/object:Gem::Requirement
|
30
28
|
none: false
|
31
|
-
requirements:
|
32
|
-
- -
|
33
|
-
- !ruby/object:Gem::Version
|
34
|
-
version:
|
29
|
+
requirements:
|
30
|
+
- - ! '>='
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: '0'
|
35
33
|
type: :development
|
36
34
|
prerelease: false
|
37
|
-
version_requirements: *
|
38
|
-
|
39
|
-
|
40
|
-
requirement: &id003 !ruby/object:Gem::Requirement
|
41
|
-
none: false
|
42
|
-
requirements:
|
43
|
-
- - ~>
|
44
|
-
- !ruby/object:Gem::Version
|
45
|
-
version: 1.5.4
|
46
|
-
type: :runtime
|
47
|
-
prerelease: false
|
48
|
-
version_requirements: *id003
|
49
|
-
description: Conformist lets you bend CSVs to your will. Let multiple, different input files conform to a single interface without rewriting your parser each time.
|
50
|
-
email:
|
35
|
+
version_requirements: *70203800707420
|
36
|
+
description: Stop using array indexing and start using declarative schemas.
|
37
|
+
email:
|
51
38
|
- tate@tatey.com
|
52
39
|
executables: []
|
53
|
-
|
54
40
|
extensions: []
|
55
|
-
|
56
41
|
extra_rdoc_files: []
|
57
|
-
|
58
|
-
files:
|
42
|
+
files:
|
59
43
|
- .gitignore
|
60
|
-
- CHANGELOG.
|
44
|
+
- CHANGELOG.md
|
61
45
|
- Gemfile
|
62
46
|
- LICENSE
|
63
|
-
- README.
|
47
|
+
- README.md
|
64
48
|
- Rakefile
|
65
49
|
- conformist.gemspec
|
66
50
|
- lib/conformist.rb
|
67
51
|
- lib/conformist/base.rb
|
52
|
+
- lib/conformist/builder.rb
|
68
53
|
- lib/conformist/column.rb
|
69
|
-
- lib/conformist/
|
54
|
+
- lib/conformist/hash_struct.rb
|
55
|
+
- lib/conformist/schema.rb
|
70
56
|
- lib/conformist/version.rb
|
71
|
-
- test/conformist/base_test.rb
|
72
|
-
- test/conformist/column_test.rb
|
73
|
-
- test/conformist/conformist_test.rb
|
74
|
-
- test/conformist/row_test.rb
|
75
|
-
- test/definitions/acma.rb
|
76
|
-
- test/definitions/fcc.rb
|
77
57
|
- test/fixtures/acma.csv
|
78
58
|
- test/fixtures/fcc.txt
|
79
59
|
- test/helper.rb
|
80
|
-
|
60
|
+
- test/schemas/acma.rb
|
61
|
+
- test/schemas/fcc.rb
|
62
|
+
- test/unit/conformist/base_test.rb
|
63
|
+
- test/unit/conformist/builder_test.rb
|
64
|
+
- test/unit/conformist/column_test.rb
|
65
|
+
- test/unit/conformist/hash_struct_test.rb
|
66
|
+
- test/unit/conformist/schema_test.rb
|
67
|
+
- test/unit/conformist_test.rb
|
68
|
+
- test/unit/integration_test.rb
|
81
69
|
homepage: https://github.com/tatey/conformist
|
82
70
|
licenses: []
|
83
|
-
|
84
|
-
|
71
|
+
post_install_message: ! "********************************************************************************\n\n
|
72
|
+
\ Upgrading from <= 0.0.3? You should be aware of breaking changes. See\n https://github.com/tatey/conformist
|
73
|
+
and skip to \"Upgrading from 0.0.3 to \n 0.1.0\" to learn more. Conformist will
|
74
|
+
raise helpful messages where necessary.\n\n********************************************************************************
|
75
|
+
\ \n"
|
85
76
|
rdoc_options: []
|
86
|
-
|
87
|
-
require_paths:
|
77
|
+
require_paths:
|
88
78
|
- lib
|
89
|
-
required_ruby_version: !ruby/object:Gem::Requirement
|
79
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
90
80
|
none: false
|
91
|
-
requirements:
|
92
|
-
- -
|
93
|
-
- !ruby/object:Gem::Version
|
81
|
+
requirements:
|
82
|
+
- - ! '>='
|
83
|
+
- !ruby/object:Gem::Version
|
94
84
|
version: 1.8.7
|
95
|
-
required_rubygems_version: !ruby/object:Gem::Requirement
|
85
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
96
86
|
none: false
|
97
|
-
requirements:
|
98
|
-
- -
|
99
|
-
- !ruby/object:Gem::Version
|
100
|
-
|
101
|
-
segments:
|
87
|
+
requirements:
|
88
|
+
- - ! '>='
|
89
|
+
- !ruby/object:Gem::Version
|
90
|
+
version: '0'
|
91
|
+
segments:
|
102
92
|
- 0
|
103
|
-
|
93
|
+
hash: -4117022895684605404
|
104
94
|
requirements: []
|
105
|
-
|
106
95
|
rubyforge_project: conformist
|
107
|
-
rubygems_version: 1.
|
96
|
+
rubygems_version: 1.8.11
|
108
97
|
signing_key:
|
109
98
|
specification_version: 3
|
110
|
-
summary:
|
111
|
-
test_files:
|
112
|
-
- test/conformist/base_test.rb
|
113
|
-
- test/conformist/column_test.rb
|
114
|
-
- test/conformist/conformist_test.rb
|
115
|
-
- test/conformist/row_test.rb
|
116
|
-
- test/definitions/acma.rb
|
117
|
-
- test/definitions/fcc.rb
|
99
|
+
summary: Bend CSVs to your will.
|
100
|
+
test_files:
|
118
101
|
- test/fixtures/acma.csv
|
119
102
|
- test/fixtures/fcc.txt
|
120
103
|
- test/helper.rb
|
104
|
+
- test/schemas/acma.rb
|
105
|
+
- test/schemas/fcc.rb
|
106
|
+
- test/unit/conformist/base_test.rb
|
107
|
+
- test/unit/conformist/builder_test.rb
|
108
|
+
- test/unit/conformist/column_test.rb
|
109
|
+
- test/unit/conformist/hash_struct_test.rb
|
110
|
+
- test/unit/conformist/schema_test.rb
|
111
|
+
- test/unit/conformist_test.rb
|
112
|
+
- test/unit/integration_test.rb
|
data/README.markdown
DELETED
@@ -1,157 +0,0 @@
|
|
1
|
-
# Conformist
|
2
|
-
|
3
|
-
Conformist lets you bend CSVs to your will. Let multiple, different input files conform to a single interface without rewriting your parser each time.
|
4
|
-
|
5
|
-
Motivation for this project came from the desire to simplify importing data from various government organisations into [Antenna Mate](http://antennamate.com). The data from each government was similar, but had completely different formatting. Some pieces of data needed preprocessing while others simply needed to be concatenated together. I did not want to write a new parser for each new government organisation. Instead, I created Conformist.
|
6
|
-
|
7
|
-
## Installation
|
8
|
-
|
9
|
-
Conformist is available from rubygems.org.
|
10
|
-
|
11
|
-
``` sh
|
12
|
-
$ gem install conformist
|
13
|
-
```
|
14
|
-
|
15
|
-
## Usage
|
16
|
-
|
17
|
-
You create a Ruby class, mix-in `Conformist::Base` and declare how an input file should map to a single interface.
|
18
|
-
|
19
|
-
``` ruby
|
20
|
-
require 'conformist'
|
21
|
-
|
22
|
-
class Citizen1
|
23
|
-
include Conformist::Base
|
24
|
-
|
25
|
-
column :name, 0, 1
|
26
|
-
column :city, 2 do |value|
|
27
|
-
value.upcase
|
28
|
-
end
|
29
|
-
end
|
30
|
-
|
31
|
-
class Citizen2
|
32
|
-
include Conformist::Base
|
33
|
-
|
34
|
-
column :name, 0
|
35
|
-
column :city, 1
|
36
|
-
end
|
37
|
-
```
|
38
|
-
|
39
|
-
Load up your definitions and enumerate over each row in the input file.
|
40
|
-
|
41
|
-
``` ruby
|
42
|
-
Conformist.foreach Citizen1.load('citizens1.csv'), Citizen2.load('citizens2.csv') do |row|
|
43
|
-
Citizen.create! row
|
44
|
-
end
|
45
|
-
```
|
46
|
-
|
47
|
-
Each object passed into the block will be a hash. Perfect for passing to a model to save into a datastore (Or whatever tickles your fancy).
|
48
|
-
|
49
|
-
### Option
|
50
|
-
|
51
|
-
Conformist uses CSV (Formally FasterCSV) to perform the heavy lifting. You can declare options that should be passed to CSV at runtime. It is safe to call `option` multiple times.
|
52
|
-
|
53
|
-
``` ruby
|
54
|
-
option :col_sep => ','
|
55
|
-
option :quote_char => '"'
|
56
|
-
```
|
57
|
-
|
58
|
-
### One Column
|
59
|
-
|
60
|
-
Maps the first column in the input file to the `:first_name` key-value pair. Indexing starts at zero.
|
61
|
-
|
62
|
-
``` ruby
|
63
|
-
column :first_name, 0
|
64
|
-
```
|
65
|
-
|
66
|
-
### Many Columns
|
67
|
-
|
68
|
-
Maps the first and second columns in the input file to the `:name` key-value pair and implicitly concatenates the values.
|
69
|
-
|
70
|
-
``` ruby
|
71
|
-
column :name, 0, 1
|
72
|
-
```
|
73
|
-
|
74
|
-
Indexing is completely arbitrary and you can map any combination.
|
75
|
-
|
76
|
-
``` ruby
|
77
|
-
column :name_and_city 0, 2
|
78
|
-
```
|
79
|
-
|
80
|
-
### Preprocessing
|
81
|
-
|
82
|
-
Sometimes you will want to manipulate values before they're conformed. You can pass a block and get access to the values. The return value of the expression becomes the conformed output.
|
83
|
-
|
84
|
-
``` ruby
|
85
|
-
column :name, 0, 1 do |values|
|
86
|
-
values.map { |v| v.upcase } * ' '
|
87
|
-
end
|
88
|
-
```
|
89
|
-
|
90
|
-
Works with one column too. Instead of getting an array of strings, you get one string.
|
91
|
-
|
92
|
-
``` ruby
|
93
|
-
column :first_name, 0 do |value|
|
94
|
-
value.upcase
|
95
|
-
end
|
96
|
-
```
|
97
|
-
|
98
|
-
### Virtual Columns
|
99
|
-
|
100
|
-
Declare a column you want included in the conformed output that is not based on the input file. This is useful when you need to set values based on the conformist definition.
|
101
|
-
|
102
|
-
``` ruby
|
103
|
-
column :day do
|
104
|
-
1
|
105
|
-
end
|
106
|
-
```
|
107
|
-
|
108
|
-
### Inheritance
|
109
|
-
|
110
|
-
Inheriting from a class which mixes in Conformist::Base gives you access to all of the superclasses' columns.
|
111
|
-
|
112
|
-
``` ruby
|
113
|
-
class Citizen
|
114
|
-
include Conformist::Base
|
115
|
-
|
116
|
-
column :name, 0, 1
|
117
|
-
end
|
118
|
-
|
119
|
-
class Adult < Citizen
|
120
|
-
column :category do
|
121
|
-
'Adult'
|
122
|
-
end
|
123
|
-
end
|
124
|
-
|
125
|
-
class Child < Citizen
|
126
|
-
column :category do
|
127
|
-
'Child'
|
128
|
-
end
|
129
|
-
end
|
130
|
-
|
131
|
-
Adult.load('adults.csv').foreach do |row|
|
132
|
-
row # => {:name => 'Tate Johnson', :category => 'Adult}
|
133
|
-
end
|
134
|
-
```
|
135
|
-
## Example
|
136
|
-
|
137
|
-
* https://gist.github.com/949576
|
138
|
-
|
139
|
-
## Compatibility
|
140
|
-
|
141
|
-
* 1.9.2-p180
|
142
|
-
* 1.8.7-p334
|
143
|
-
* jruby-1.6.1
|
144
|
-
|
145
|
-
## Contributing
|
146
|
-
|
147
|
-
Patches welcome!
|
148
|
-
|
149
|
-
1. Fork the repository
|
150
|
-
2. Create a topic branch
|
151
|
-
3. Write tests and make changes
|
152
|
-
4. Make sure the tests pass by running `rake`
|
153
|
-
5. Push and send a pull request on GitHub
|
154
|
-
|
155
|
-
## Copyright
|
156
|
-
|
157
|
-
Copyright © 2011 Tate Johnson. Conformist is released under the MIT license. See LICENSE for details.
|
data/lib/conformist/row.rb
DELETED
@@ -1,26 +0,0 @@
|
|
1
|
-
module Conformist
|
2
|
-
class Row
|
3
|
-
attr_reader :columns, :row
|
4
|
-
|
5
|
-
def initialize columns, row
|
6
|
-
@columns, @row = columns, row
|
7
|
-
end
|
8
|
-
|
9
|
-
# Extracts key-value pairs for each column in the row. Will implicitly
|
10
|
-
# join an array into a string.
|
11
|
-
#
|
12
|
-
# Example:
|
13
|
-
#
|
14
|
-
# row = Row.new columns, csv_row
|
15
|
-
# row.to_hash # => {:first => 'Hello', :second => 'World'}
|
16
|
-
#
|
17
|
-
# Returns conformed hash.
|
18
|
-
def to_hash
|
19
|
-
columns.inject({}) do |attributes, column|
|
20
|
-
values = column.values_in row
|
21
|
-
values = values.join if values.respond_to? :join
|
22
|
-
attributes.merge column.name => values
|
23
|
-
end
|
24
|
-
end
|
25
|
-
end
|
26
|
-
end
|
@@ -1,49 +0,0 @@
|
|
1
|
-
require 'helper'
|
2
|
-
|
3
|
-
class BaseTest < MiniTest::Unit::TestCase
|
4
|
-
def setup
|
5
|
-
@class = Class.new.tap { |klass| klass.send :include, Conformist::Base }
|
6
|
-
end
|
7
|
-
|
8
|
-
def test_option
|
9
|
-
@class.option :a => 1
|
10
|
-
@class.option :b => 2
|
11
|
-
assert_equal({:a => 1, :b => 2}, @class.options)
|
12
|
-
end
|
13
|
-
|
14
|
-
def test_column
|
15
|
-
@class.column :a, 0
|
16
|
-
@class.column :b, 1
|
17
|
-
assert_equal 2, @class.columns.size
|
18
|
-
assert_instance_of Conformist::Column, @class.columns[rand(2)]
|
19
|
-
end
|
20
|
-
|
21
|
-
def test_columns_inherit_from_superclass
|
22
|
-
subclass = Class.new @class
|
23
|
-
@class.column :a, 0
|
24
|
-
@class.column :b, 1
|
25
|
-
assert_equal @class.columns, subclass.columns
|
26
|
-
subclass.column :c, 2
|
27
|
-
subclass.column :d, 3
|
28
|
-
refute_equal @class.columns, subclass.columns
|
29
|
-
end
|
30
|
-
|
31
|
-
def test_load
|
32
|
-
instance = @class.load 'file'
|
33
|
-
assert_equal 'file', instance.path
|
34
|
-
assert_instance_of @class, instance
|
35
|
-
end
|
36
|
-
|
37
|
-
def test_foreach
|
38
|
-
rows = [
|
39
|
-
{:name => "CRAFERS", :callsign => "ABS2", :latitude => "34 58 49S"},
|
40
|
-
{:name => "CRAFERS", :callsign => "SAS7", :latitude => "34 58 57S"},
|
41
|
-
{:name => "CRAFERS", :callsign => "NWS9", :latitude => "34 59 02S"},
|
42
|
-
{:name => "CRAFERS", :callsign => "ADS10", :latitude => "34 59 02S"},
|
43
|
-
{:name => "CRAFERS", :callsign => "ADS10", :latitude => "34 58 57S"}
|
44
|
-
]
|
45
|
-
ACMA.load(fixture('acma.csv')).foreach do |row|
|
46
|
-
assert_equal rows.shift, row
|
47
|
-
end
|
48
|
-
end
|
49
|
-
end
|
@@ -1,21 +0,0 @@
|
|
1
|
-
require 'helper'
|
2
|
-
|
3
|
-
class ConformistTest < MiniTest::Unit::TestCase
|
4
|
-
def test_foreach
|
5
|
-
rows = [
|
6
|
-
{:name => "CRAFERS", :callsign => "ABS2", :latitude => "34 58 49S", :signtal_type => "digital"},
|
7
|
-
{:name => "CRAFERS", :callsign => "SAS7", :latitude => "34 58 57S", :signtal_type => "digital"},
|
8
|
-
{:name => "CRAFERS", :callsign => "NWS9", :latitude => "34 59 02S", :signtal_type => "digital"},
|
9
|
-
{:name => "CRAFERS", :callsign => "ADS10", :latitude => "34 59 02S", :signtal_type => "digital"},
|
10
|
-
{:name => "CRAFERS", :callsign => "ADS10", :latitude => "34 58 57S", :signtal_type => "digital"},
|
11
|
-
{:name => "LOS ANGELES, CA", :callsign => "KVTU-LP", :latitude => "34 11 13.90 N", :signtal_type => "digital"},
|
12
|
-
{:name => "BAKERSFIELD, CA", :callsign => "NEW", :latitude => "35 12 6.00 N", :signtal_type => "digital"},
|
13
|
-
{:name => "YUCA VALLEY, CA", :callsign => "NEW", :latitude => "34 9 10.10 N", :signtal_type => "digital"},
|
14
|
-
{:name => "SACRAMENTO, CA", :callsign => "KCSO-LD", :latitude => "38 7 10.00 N", :signtal_type => "digital"},
|
15
|
-
{:name => "LOS ANGELES, CA", :callsign => "KVTU-LP", :latitude => "34 13 38.00 N", :signtal_type => "digital"}
|
16
|
-
]
|
17
|
-
Conformist.foreach ACMA::Digital.load(fixture('acma.csv')), FCC.load(fixture('fcc.txt')) do |row|
|
18
|
-
assert_equal rows.shift, row
|
19
|
-
end
|
20
|
-
end
|
21
|
-
end
|
data/test/conformist/row_test.rb
DELETED
@@ -1,21 +0,0 @@
|
|
1
|
-
require 'helper'
|
2
|
-
|
3
|
-
class RowTest < MiniTest::Unit::TestCase
|
4
|
-
def test_to_hash_should_join_array
|
5
|
-
column = Conformist::Column.new(:foo, 0, 1, 2)
|
6
|
-
row = Conformist::Row.new [column], stub_row
|
7
|
-
assert_equal({:foo => 'abc'}, row.to_hash)
|
8
|
-
end
|
9
|
-
|
10
|
-
def test_to_hash_should_not_join_string
|
11
|
-
column = Conformist::Column.new(:foo, 0, 1, 2) { |values| values.join('-').upcase }
|
12
|
-
row = Conformist::Row.new [column], stub_row
|
13
|
-
assert_equal({:foo => 'A-B-C'}, row.to_hash)
|
14
|
-
end
|
15
|
-
|
16
|
-
def test_to_hash_with_many_columns
|
17
|
-
columns = Conformist::Column.new(:foo, 0), Conformist::Column.new(:bar, 1, 2, 3)
|
18
|
-
row = Conformist::Row.new columns, stub_row
|
19
|
-
assert_equal({:foo => 'a', :bar => 'bcd'}, row.to_hash)
|
20
|
-
end
|
21
|
-
end
|