edtf 0.0.8 → 0.0.9

Sign up to get free protection for your applications and to get access to all the features.
data/README.md CHANGED
@@ -21,10 +21,6 @@ EDTF-Ruby parser implements all levels and features of the EDTF specification
21
21
  nested expressions (the parser will not accept some of the more complex
22
22
  examples, though).
23
23
 
24
- The level 2 list extensions (203 and 204) currently return simple Ruby arrays;
25
- therefore, advanced behavior (such as 'earlier' or 'later') is parsed correctly
26
- but not yet exposed by the Ruby API.
27
-
28
24
  EDTF-Ruby has been confirmed to work on the following Ruby implementations:
29
25
  1.9.3, 1.9.2, 1.8.7, Rubinius, and JRuby. Active Support's date extensions
30
26
  are currently listed as a dependency, because of a number of many functional
@@ -39,8 +35,9 @@ You can access parse EDTF strings either using `Date.edtf` or `EDTF.parse`
39
35
  (both methods come with an alternative bang! version, that will raise an error
40
36
  if the string cannot be parsed instead of silently returning nil); if
41
37
  given a valid EDTF string the return value will either be an (extended) `Date`,
42
- `EDTF::Interval` or `Range` (for masked precision strings) instance. Given
43
- a Date, you can print the corresponding EDTF string using the `#edtf` method.
38
+ `EDTF::Interval`, `EDTF::Set`, or `Range` (for masked precision strings)
39
+ instance. Given a Date, you can print the corresponding EDTF string using the
40
+ `#edtf` method.
44
41
 
45
42
  $ [sudo] gem install edtf
46
43
  $ irb
@@ -86,6 +83,21 @@ a Date, you can print the corresponding EDTF string using the `#edtf` method.
86
83
  => true # an open ended interval covers today
87
84
  > Date.edtf("(1999-(02)~-23)?").edtf
88
85
  => "1999?-(02)?~-23?" # when printing, EDTF-Ruby reduces nested parentheses
86
+ > s = Date.edtf('{1667,1668, 1670..1672}')
87
+ > s.include?(Date.edtf('1669'))
88
+ => false
89
+ > s.include?(Date.edtf('1671'))
90
+ => true # the range is enumerated for membership tests
91
+ > s.length
92
+ => 3 # but we're still aware that there were only three elements
93
+ > s.map(&:year)
94
+ => [1667, 1668, 1670, 1671, 1672] # when enumerated there are 5 elements
95
+ > s.earlier?
96
+ => false # the original list was not vague
97
+ > s.earlier! # but we can make it so
98
+ > s.edtf
99
+ => "{..1667, 1668, 1670..1672}"
100
+
89
101
 
90
102
  For additional features take a look at the documentation or the extensive
91
103
  list of rspec examples.
@@ -40,6 +40,7 @@ autoload :Rational, 'rational'
40
40
 
41
41
  require 'forwardable'
42
42
  require 'enumerator'
43
+ require 'set'
43
44
 
44
45
  require 'active_support/core_ext/date/calculations'
45
46
  require 'active_support/core_ext/date_time/calculations'
@@ -56,6 +57,7 @@ require 'edtf/date_time'
56
57
  require 'edtf/epoch'
57
58
  require 'edtf/season'
58
59
  require 'edtf/interval'
60
+ require 'edtf/set'
59
61
  require 'edtf/parser'
60
62
  require 'edtf/extensions'
61
63
 
@@ -0,0 +1,11 @@
1
+
2
+ class Range
3
+
4
+ def edtf
5
+ [
6
+ self.begin.respond_to?(:edtf) ? self.begin.edtf : self.begin.to_s,
7
+ self.end.respond_to?(:edtf) ? self.end.edtf : self.end.to_s
8
+ ].join(exclude_end? ? '...' : '..')
9
+ end
10
+
11
+ end
@@ -219,29 +219,32 @@ rule
219
219
  ;
220
220
 
221
221
 
222
- choice_list : '[' list ']' { result = val[1] }
222
+ choice_list : '[' list ']' { result = val[1].choice! }
223
223
 
224
224
  inclusive_list : '{' list '}' { result = val[1] }
225
225
 
226
- list : earlier { result = val }
227
- | earlier ',' list_elements ',' later { result = [val[0]] + val[2] + [val[4]] }
228
- | earlier ',' list_elements { result = [val[0]] + val[2] }
229
- | earlier ',' later { result = [val[0]] + [val[2]] }
230
- | list_elements ',' later { result = val[0] + [val[2]] }
231
- | list_elements
232
- | later { result = val }
226
+ list : earlier { result = EDTF::Set.new(val[0]).earlier! }
227
+ | earlier ',' list_elements ',' later { result = EDTF::Set.new([val[0]] + val[2] + [val[4]]).earlier!.later! }
228
+ | earlier ',' list_elements { result = EDTF::Set.new([val[0]] + val[2]).earlier! }
229
+ | earlier ',' later { result = EDTF::Set.new([val[0]] + [val[2]]).earlier!.later! }
230
+ | list_elements ',' later { result = EDTF::Set.new(val[0] + [val[2]]).later! }
231
+ | list_elements { result = EDTF::Set.new(*val[0]) }
232
+ | later { result = EDTF::Set.new(val[0]).later! }
233
233
  ;
234
234
 
235
235
  list_elements : list_element { result = [val[0]].flatten }
236
236
  | list_elements ',' list_element { result = val[0] + [val[2]].flatten }
237
237
  ;
238
-
239
- list_element : date
240
- | partial_uncertain_or_approximate
241
- | unspecified
242
- | consecutives { result = val[0].map { |d| Date.new(*d) } }
238
+
239
+ list_element : atomic
240
+ | consecutives
243
241
  ;
244
242
 
243
+ atomic : date
244
+ | partial_uncertain_or_approximate
245
+ | unspecified
246
+ ;
247
+
245
248
  earlier : DOTS date { result = val[1] }
246
249
 
247
250
  later : year_month_day DOTS { result = Date.new(*val[0]).year_precision! }
@@ -249,9 +252,9 @@ rule
249
252
  | year DOTS { result = Date.new(val[0]).year_precision! }
250
253
  ;
251
254
 
252
- consecutives : year_month_day DOTS year_month_day
253
- | year_month DOTS year_month
254
- | year DOTS year { result = (val[0]..val[2]).to_a.map }
255
+ consecutives : year_month_day DOTS year_month_day { result = (Date.new(val[0]).day_precision! .. Date.new(val[2]).day_precision!) }
256
+ | year_month DOTS year_month { result = (Date.new(val[0]).month_precision! .. Date.new(val[2]).month_precision!) }
257
+ | year DOTS year { result = (Date.new(val[0]).year_precision! .. Date.new(val[2]).year_precision!) }
255
258
  ;
256
259
 
257
260
  partial_unspecified :
@@ -0,0 +1,79 @@
1
+ module EDTF
2
+
3
+ class Set
4
+ extend Forwardable
5
+
6
+ include Enumerable
7
+ include Comparable
8
+
9
+ def_delegators :@dates, :size, :length, :empty?
10
+ def_delegators :to_a, :include?
11
+
12
+ attr_accessor :choice, :later, :earlier
13
+
14
+
15
+ def initialize(*dates)
16
+ @dates = ::Set.new(dates.flatten)
17
+ @choice, @later, @earlier = false, false, false
18
+ end
19
+
20
+ def initialize_copy(other)
21
+ @set = other.to_set
22
+ end
23
+
24
+ [:choice, :later, :earlier].each do |m|
25
+ define_method("#{m}?") { send(m) }
26
+ define_method("#{m}!") do
27
+ send("#{m}=", true)
28
+ self
29
+ end
30
+ end
31
+
32
+ def <<(date)
33
+ dates << date
34
+ self
35
+ end
36
+
37
+ def each
38
+ if block_given?
39
+ to_a.each(&Proc.new)
40
+ self
41
+ else
42
+ to_enum
43
+ end
44
+ end
45
+
46
+ def edtf
47
+ parenthesize(dates.map { |d| d.respond_to?(:edtf) ? d.edtf : d.to_s }.join(', '))
48
+ end
49
+
50
+ def to_a
51
+ dates.map { |d| Array(d) }.flatten
52
+ end
53
+
54
+ def to_set
55
+ to_a.to_set
56
+ end
57
+
58
+ alias to_s edtf
59
+
60
+ def <=>(other)
61
+ return nil unless other.respond_to?(:to_a)
62
+ to_a <=> other.to_a
63
+ end
64
+
65
+ private
66
+
67
+ attr_reader :dates
68
+
69
+ def parenthesize(string)
70
+ p = choice? ? %w([ ]) : %w({ })
71
+ p[-1,0] = '..' if earlier?
72
+ p[-1,0] = string unless string.empty?
73
+ p[-1,0] = '..' if later?
74
+ p.join
75
+ end
76
+
77
+ end
78
+
79
+ end
@@ -1,3 +1,3 @@
1
1
  module EDTF
2
- VERSION = '0.0.8'.freeze
2
+ VERSION = '0.0.9'.freeze
3
3
  end
@@ -39,7 +39,7 @@ module EDTF
39
39
  end
40
40
 
41
41
  it 'does not include christmas day 2009' do
42
- interval.should_not include(Date.new(2009,12,24))
42
+ interval.should_not be_include(Date.new(2009,12,24))
43
43
  end
44
44
 
45
45
  it 'christmas day 2009 is less than max' do
@@ -51,11 +51,11 @@ module EDTF
51
51
  end
52
52
 
53
53
  it 'covers christmas day 2009' do
54
- interval.should cover(Date.new(2009,12,24))
54
+ interval.should be_cover(Date.new(2009,12,24))
55
55
  end
56
56
 
57
57
  it 'covers 2011-12-31' do
58
- interval.should cover(Date.new(2011,12,31))
58
+ interval.should be_cover(Date.new(2011,12,31))
59
59
  end
60
60
 
61
61
  end
@@ -64,15 +64,15 @@ module EDTF
64
64
  let(:interval) { Date.edtf('2008-08-23/2011-07-01') }
65
65
 
66
66
  it 'includes christmas day 2009' do
67
- interval.should include(Date.new(2009,12,24))
67
+ interval.should be_include(Date.new(2009,12,24))
68
68
  end
69
69
 
70
70
  it 'covers christmas day 2009' do
71
- interval.should cover(Date.new(2009,12,24))
71
+ interval.should be_cover(Date.new(2009,12,24))
72
72
  end
73
73
 
74
74
  it 'does not cover 2011-07-02' do
75
- interval.should_not cover(Date.new(2011,07,02))
75
+ interval.should_not be_cover(Date.new(2011,07,02))
76
76
  end
77
77
  end
78
78
 
@@ -94,15 +94,15 @@ module EDTF
94
94
  end
95
95
 
96
96
  it 'includes christmas day 2009' do
97
- interval.should include(Date.new(2009,12,24))
97
+ interval.should be_include(Date.new(2009,12,24))
98
98
  end
99
99
 
100
100
  it 'covers christmas day 2009' do
101
- interval.should cover(Date.new(2009,12,24))
101
+ interval.should be_cover(Date.new(2009,12,24))
102
102
  end
103
103
 
104
104
  it 'covers 2023-07-02' do
105
- interval.should cover(Date.new(2023,07,02))
105
+ interval.should be_cover(Date.new(2023,07,02))
106
106
  end
107
107
 
108
108
  end
@@ -0,0 +1,73 @@
1
+ module EDTF
2
+ describe 'Sets' do
3
+
4
+ describe 'constructor' do
5
+
6
+ it 'creates a new empty set by default' do
7
+ Set.new.should be_empty
8
+ end
9
+
10
+ end
11
+
12
+ describe '#edtf' do
13
+
14
+ it 'returns {} by default' do
15
+ Set.new.edtf.should == '{}'
16
+ end
17
+
18
+ it 'returns [] for empty choice lists' do
19
+ Set.new.choice!.edtf.should == '[]'
20
+ end
21
+
22
+ it 'returns {1984} if the set contains the year 1984' do
23
+ Set.new(Date.edtf('1984')).edtf.should == '{1984}'
24
+ end
25
+
26
+ it 'returns {1984, 1985-10} for the set containing these dates' do
27
+ Set.new(Date.edtf('1984'), Date.new(1984,10).month_precision).edtf.should == '{1984, 1984-10}'
28
+ end
29
+
30
+ it 'returns {..1984, 1985-10} for the set containing these dates and earlier == true' do
31
+ Set.new(Date.edtf('1984'), Date.new(1984,10).month_precision).earlier!.edtf.should == '{..1984, 1984-10}'
32
+ end
33
+
34
+ it 'returns {1984, 1985-10..} for the set containing these dates and later == true' do
35
+ Set.new(Date.edtf('1984'), Date.new(1984,10).month_precision).later!.edtf.should == '{1984, 1984-10..}'
36
+ end
37
+
38
+ it 'returns [1667, 1668, 1670..1672] for the years 1667, 1668 and the interval 1670..1672' do
39
+ s = Set.new.choice!
40
+ s << Date.edtf('1667') << Date.edtf('1668')
41
+ s << (Date.edtf('1670') .. Date.edtf('1672'))
42
+ s.edtf.should == '[1667, 1668, 1670..1672]'
43
+ end
44
+
45
+ end
46
+
47
+ describe 'the set [1667, 1668, 1670..1672]' do
48
+ let(:set) { Set.new(Date.edtf('1667'), Date.edtf('1668'), Date.edtf('1670')..Date.edtf('1672')).choice! }
49
+
50
+ it 'includes the year 1671' do
51
+ set.should include(Date.new(1671).year_precision!)
52
+ end
53
+
54
+ it 'does not include the date 1671-01-01' do
55
+ set.should_not include(Date.new(1671))
56
+ end
57
+
58
+ it 'does not include the year 1669' do
59
+ set.should_not include(Date.new(1669).year_precision!)
60
+ end
61
+
62
+ it 'has a length of 3' do
63
+ set.should have(3).elements
64
+ end
65
+
66
+ it 'maps to the year array [1667, 1668, 1670, 1671, 1672]' do
67
+ set.map(&:year).should == [1667, 1668, 1670, 1671, 1672]
68
+ end
69
+
70
+ end
71
+
72
+ end
73
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: edtf
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.8
4
+ version: 0.0.9
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -13,7 +13,7 @@ date: 2011-11-09 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: activesupport
16
- requirement: &70235877316060 !ruby/object:Gem::Requirement
16
+ requirement: &70355024984460 !ruby/object:Gem::Requirement
17
17
  none: false
18
18
  requirements:
19
19
  - - ~>
@@ -21,10 +21,10 @@ dependencies:
21
21
  version: '3.0'
22
22
  type: :runtime
23
23
  prerelease: false
24
- version_requirements: *70235877316060
24
+ version_requirements: *70355024984460
25
25
  - !ruby/object:Gem::Dependency
26
26
  name: rake
27
- requirement: &70235877525400 !ruby/object:Gem::Requirement
27
+ requirement: &70355024983720 !ruby/object:Gem::Requirement
28
28
  none: false
29
29
  requirements:
30
30
  - - ~>
@@ -32,10 +32,10 @@ dependencies:
32
32
  version: '0.9'
33
33
  type: :development
34
34
  prerelease: false
35
- version_requirements: *70235877525400
35
+ version_requirements: *70355024983720
36
36
  - !ruby/object:Gem::Dependency
37
37
  name: racc
38
- requirement: &70235877523860 !ruby/object:Gem::Requirement
38
+ requirement: &70355024982860 !ruby/object:Gem::Requirement
39
39
  none: false
40
40
  requirements:
41
41
  - - ~>
@@ -43,10 +43,10 @@ dependencies:
43
43
  version: '1.4'
44
44
  type: :development
45
45
  prerelease: false
46
- version_requirements: *70235877523860
46
+ version_requirements: *70355024982860
47
47
  - !ruby/object:Gem::Dependency
48
48
  name: cucumber
49
- requirement: &70235877522840 !ruby/object:Gem::Requirement
49
+ requirement: &70355024981980 !ruby/object:Gem::Requirement
50
50
  none: false
51
51
  requirements:
52
52
  - - ~>
@@ -54,10 +54,10 @@ dependencies:
54
54
  version: '1.0'
55
55
  type: :development
56
56
  prerelease: false
57
- version_requirements: *70235877522840
57
+ version_requirements: *70355024981980
58
58
  - !ruby/object:Gem::Dependency
59
59
  name: rspec
60
- requirement: &70235877521760 !ruby/object:Gem::Requirement
60
+ requirement: &70355024981220 !ruby/object:Gem::Requirement
61
61
  none: false
62
62
  requirements:
63
63
  - - ~>
@@ -65,10 +65,10 @@ dependencies:
65
65
  version: '2.6'
66
66
  type: :development
67
67
  prerelease: false
68
- version_requirements: *70235877521760
68
+ version_requirements: *70355024981220
69
69
  - !ruby/object:Gem::Dependency
70
70
  name: ZenTest
71
- requirement: &70235877521200 !ruby/object:Gem::Requirement
71
+ requirement: &70355024980360 !ruby/object:Gem::Requirement
72
72
  none: false
73
73
  requirements:
74
74
  - - ~>
@@ -76,7 +76,7 @@ dependencies:
76
76
  version: '4.6'
77
77
  type: :development
78
78
  prerelease: false
79
- version_requirements: *70235877521200
79
+ version_requirements: *70355024980360
80
80
  description: A Ruby implementation of the Extended Date/Time Format (EDTF).
81
81
  email:
82
82
  - http://sylvester.keil.or.at
@@ -115,6 +115,7 @@ files:
115
115
  - lib/edtf/interval.rb
116
116
  - lib/edtf/parser.y
117
117
  - lib/edtf/season.rb
118
+ - lib/edtf/set.rb
118
119
  - lib/edtf/uncertainty.rb
119
120
  - lib/edtf/version.rb
120
121
  - spec/edtf/date_spec.rb
@@ -122,6 +123,7 @@ files:
122
123
  - spec/edtf/interval_spec.rb
123
124
  - spec/edtf/parser_spec.rb
124
125
  - spec/edtf/season_spec.rb
126
+ - spec/edtf/set_spec.rb
125
127
  - spec/edtf/uncertainty_spec.rb
126
128
  - spec/spec_helper.rb
127
129
  - lib/edtf/parser.rb
@@ -147,7 +149,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
147
149
  version: '0'
148
150
  segments:
149
151
  - 0
150
- hash: -533372685399765203
152
+ hash: -1918843685167052448
151
153
  required_rubygems_version: !ruby/object:Gem::Requirement
152
154
  none: false
153
155
  requirements:
@@ -156,7 +158,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
156
158
  version: '0'
157
159
  segments:
158
160
  - 0
159
- hash: -533372685399765203
161
+ hash: -1918843685167052448
160
162
  requirements: []
161
163
  rubyforge_project:
162
164
  rubygems_version: 1.8.10
@@ -181,5 +183,6 @@ test_files:
181
183
  - spec/edtf/interval_spec.rb
182
184
  - spec/edtf/parser_spec.rb
183
185
  - spec/edtf/season_spec.rb
186
+ - spec/edtf/set_spec.rb
184
187
  - spec/edtf/uncertainty_spec.rb
185
188
  - spec/spec_helper.rb