pgn 0.1.1 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: d868495f784cc03dedf3465023bffe390d7228f5
4
- data.tar.gz: d12ab910e19cac3c20cb2ed965fd460eadc1b657
3
+ metadata.gz: a5c9a8ca0a6c732bd3ec99585b21929c1710976e
4
+ data.tar.gz: ff812fc594259ffa25370d3e35eed074c56a3c41
5
5
  SHA512:
6
- metadata.gz: 790ce8940ab3aa672edb725073847d6c2154335afb9403d71acfdfa835a68658b6d2e2dced3d80f99291cafc361721482ae2f0982bd1221023bd9727b256a710
7
- data.tar.gz: dac60e56ab33829619c706f2e4aab434b1fa4ef61833dd8ff1b1ed6e6547ab95557b72cb371d3462d9dc9cc78995ea73b91da1cb393dfb6717e6add315fcf7e1
6
+ metadata.gz: 05e7faa858c9ee725416c0c87021ac2b3440407b41de732ce6049f446ede8736e039c7f0a8658cba5dced9c6d27a07ad50e0c176e04afbede60cb959c2d267a9
7
+ data.tar.gz: c5d008c3d2d579dd39b3ab76889cf697252d12eac55f5cab69665dd04b2cbc03227de4487325a476a45b1fe9a435e1fb41ad775b456fd5e5b5297fafc4624cbe
@@ -170,7 +170,7 @@ module PGN
170
170
  changes[self.move.destination] = self.move.promotion
171
171
  end
172
172
 
173
- changes.reject! {|key, _| key.nil? }
173
+ changes.reject! {|key, _| key.nil? or key.empty? }
174
174
 
175
175
  changes
176
176
  end
@@ -5,46 +5,48 @@ module PGN
5
5
  # context free grammar.
6
6
  #
7
7
  class Parser < Whittle::Parser
8
- rule(:wsp => /\s+/).skip!
8
+ rule(wsp: /\s+/).skip!
9
9
 
10
- rule("[")
11
- rule("]")
12
- rule("(")
13
- rule(")")
10
+ rule('[')
11
+ rule(']')
12
+ rule('(')
13
+ rule(')')
14
14
 
15
15
  start(:pgn_database)
16
16
 
17
17
  rule(:pgn_database) do |r|
18
18
  r[].as { [] }
19
- r[:pgn_game, :pgn_database].as {|game, database| database << game }
19
+ r[:pgn_game, :pgn_database].as { |game, database| database << game }
20
20
  end
21
21
 
22
22
  rule(:pgn_game) do |r|
23
- r[:tag_section, :movetext_section].as {|tags, moves| {tags: tags, result: moves.pop, moves: moves} }
23
+ r[:tag_section, :movetext_section].as do |tags, moves|
24
+ { tags: tags, result: moves.pop, moves: moves }
25
+ end
24
26
  end
25
27
 
26
28
  rule(:tag_section) do |r|
27
- r[:tag_pair, :tag_section].as {|pair, section| section.merge(pair) }
29
+ r[:tag_pair, :tag_section].as { |pair, section| section.merge(pair) }
28
30
  r[:tag_pair]
29
31
  end
30
32
 
31
33
  rule(:tag_pair) do |r|
32
- r["[", :tag_name, :tag_value, "]"].as {|_, a, b, _| {a => b} }
34
+ r['[', :tag_name, :tag_value, ']'].as { |_, a, b, _| { a => b } }
33
35
  end
34
36
 
35
37
  rule(:tag_value) do |r|
36
- r[:string].as {|value| value[1...-1] }
38
+ r[:string].as { |value| value[1...-1] }
37
39
  end
38
40
 
39
41
  rule(:movetext_section) do |r|
40
- r[:element_sequence, :game_termination].as {|a, b| a.reverse << b }
42
+ r[:element_sequence, :game_termination].as { |a, b| a.reverse << b }
41
43
  end
42
44
 
43
45
  rule(:element_sequence) do |r|
44
- r[:element, :element_sequence].as {|element, sequence| element.nil? ? sequence : sequence << element }
46
+ r[:element, :element_sequence].as do |element, sequence|
47
+ element.nil? ? sequence : sequence << element
48
+ end
45
49
  r[].as { [] }
46
- #r[:recursive_variation, :element_sequence]
47
- #r[:recursive_variation]
48
50
  end
49
51
 
50
52
  rule(:element) do |r|
@@ -56,34 +58,36 @@ module PGN
56
58
  end
57
59
  r[:comment].as { nil }
58
60
  end
59
-
61
+
60
62
  rule(:san_move_annotated) do |r|
61
63
  r[:san_move].as { |move| MoveText.new(move) }
62
- r[:san_move, :comment].as { |move, comment| MoveText.new(move, nil, comment) }
63
- r[:san_move, :numeric_annotation_glyph].as { |move, annotation| MoveText.new(move, annotation) }
64
- r[:san_move, :numeric_annotation_glyph, :comment].as { |move, annotation, comment| MoveText.new(move, annotation, comment) }
64
+ r[:san_move, :comment].as do |move, comment|
65
+ MoveText.new(move, nil, comment)
66
+ end
67
+ r[:san_move, :numeric_annotation_glyph].as do |move, annotation|
68
+ MoveText.new(move, annotation)
69
+ end
70
+ r[:san_move, :numeric_annotation_glyph, :comment].as do |move, annotation, comment|
71
+ MoveText.new(move, annotation, comment)
72
+ end
73
+ r[:san_move, :comment, :numeric_annotation_glyph].as do |move, comment, annotation|
74
+ MoveText.new(move, annotation, comment)
75
+ end
65
76
  end
66
77
 
67
78
  rule(:variation_list) do |r|
68
- r[:variation, :variation_list].as { |variation, sequence| sequence << variation }
69
- r[:variation].as { |v| [v] }
79
+ r[:variation, :variation_list].as do |variation, sequence|
80
+ sequence << variation
81
+ end
82
+ r[:variation].as { |v| [v] }
70
83
  end
71
-
84
+
72
85
  rule(:variation) do |r|
73
- r["(", :element_sequence, ")"].as { |_, sequence, _| sequence }
86
+ r['(', :element_sequence, ')'].as { |_, sequence, _| sequence }
74
87
  end
75
88
 
76
- # rule(:variation_sequence) do |r|
77
- # r[:element, :variation_sequence]
78
- # r[].as { [] }
79
- # end
80
-
81
- #rule(:recursive_variation) do |r|
82
- #r["(", :element_sequence, ")"]
83
- #end
84
-
85
89
  rule(
86
- :string => %r{
90
+ string: /
87
91
  " # beginning of string
88
92
  (
89
93
  [[:print:]&&[^\\"]] | # printing characters except quote and backslash
@@ -91,25 +95,28 @@ module PGN
91
95
  \\" # escaped quotation marks
92
96
  )* # zero or more of the above
93
97
  " # end of string
94
- }x
98
+ /x
95
99
  )
96
100
 
97
101
  rule(
98
- :comment => %r{
99
- \{ # beginning of comment
102
+ comment: /
100
103
  (
101
- [[:print:]&&[^\\\}]] | # printing characters except closing brace and backslash
102
- \n |
103
- \\\\ | # escaped backslashes
104
- \\\}|\\\} | # escaped braces
105
- \n # newlines
106
- )* # zero or more of the above
107
- \} # end of comment
108
- }x
104
+ \{ # beginning of comment
105
+ (
106
+ [[:print:]&&[^\\\{\}]] | # printing characters except brace and backslash
107
+ \n |
108
+ \\\\ | # escaped backslashes
109
+ \\\{|\\\} | # escaped braces
110
+ \n | # newlines
111
+ \g<1> # recursive
112
+ )* # zero or more of the above
113
+ \} # end of comment
114
+ )
115
+ /x
109
116
  )
110
117
 
111
118
  rule(
112
- :game_termination => %r{
119
+ game_termination: %r{
113
120
  1-0 | # white wins
114
121
  0-1 | # black wins
115
122
  1\/2-1\/2 | # draw
@@ -118,14 +125,15 @@ module PGN
118
125
  )
119
126
 
120
127
  rule(
121
- :move_number_indication => %r{
128
+ move_number_indication: /
122
129
  [[:digit:]]+\.* # one or more digits followed by zero or more periods
123
- }x
130
+ /x
124
131
  )
125
132
 
126
133
  rule(
127
- :san_move => %r{
134
+ san_move: %r{
128
135
  (
136
+ -- | # "don't care" move (used in variations)
129
137
  [O0](-[O0]){1,2} | # castling (O-O, O-O-O)
130
138
  [a-h][1-8] | # pawn moves (e4, d7)
131
139
  [BKNQR][a-h1-8]?x?[a-h][1-8] | # major piece moves w/ optional specifier
@@ -144,16 +152,16 @@ module PGN
144
152
  )
145
153
 
146
154
  rule(
147
- :tag_name => %r{
155
+ tag_name: /
148
156
  [A-Za-z0-9_]+ # letters, digits and underscores only
149
- }x
157
+ /x
150
158
  )
151
159
 
152
160
  rule(
153
- :numeric_annotation_glyph => %r{
161
+ numeric_annotation_glyph: /
154
162
  \$\d+ | # dollar sign followed by an integer from 0 to 255
155
163
  [\?!][\?!]? # support the most used annotations directly
156
- }x
164
+ /x
157
165
  )
158
166
  end
159
167
  end
@@ -1,3 +1,3 @@
1
1
  module PGN
2
- VERSION = "0.1.1"
2
+ VERSION = "0.2.0"
3
3
  end
@@ -1,84 +1,84 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe PGN do
4
- describe "parsing a file" do
5
- it "should return a list of games" do
6
- games = PGN.parse(File.read("./examples/immortal_game.pgn"))
4
+ describe '.parse' do
5
+ it 'should return a list of games' do
6
+ games = PGN.parse(File.read('./examples/immortal_game.pgn'))
7
7
  games.length.should == 1
8
8
  game = games.first
9
- game.result.should == "1-0"
10
- game.tags["White"].should == "Adolf Anderssen"
11
- game.moves.last.should == "Be7#"
9
+ game.result.should == '1-0'
10
+ game.tags['White'].should == 'Adolf Anderssen'
11
+ game.moves.last.should == 'Be7#'
12
12
  end
13
- end
14
13
 
15
- context "alternate castling notation" do
16
- describe "parsing a file" do
17
- it "should return a list of games" do
18
- games = PGN.parse(File.read("./spec/pgn_files/alternate_castling.pgn"))
19
- game = games.first
20
- game.tags["White"].should == "Somebody"
21
- game.result.should == "*"
22
- game.moves.last.should == "O-O-O"
23
- end
14
+ it 'should handle alternate castling notation' do
15
+ games = PGN.parse(File.read('./spec/pgn_files/alternate_castling.pgn'))
16
+ game = games.first
17
+ game.tags['White'].should == 'Somebody'
18
+ game.result.should == '*'
19
+ game.moves.last.should == 'O-O-O'
24
20
  end
25
- end
26
21
 
27
- context "annotations" do
28
- describe "parsing a file" do
29
- it "should return a list of games" do
30
- games = PGN.parse(File.read("./spec/pgn_files/annotations.pgn"))
31
- games.each do |game|
32
- game.tags["White"].should == "Fool"
33
- game.result.should == "0-1"
34
- game.moves.last.should == "Qh4#"
35
- end
22
+ it 'should handle annotations' do
23
+ games = PGN.parse(File.read('./spec/pgn_files/annotations.pgn'))
24
+ games.each do |game|
25
+ game.tags['White'].should == 'Fool'
26
+ game.result.should == '0-1'
27
+ game.moves.last.should == 'Qh4#'
36
28
  end
37
29
  end
38
30
 
39
- describe "parsing a file" do
40
- it "should work with comments" do
41
- games = PGN.parse(File.read("./spec/pgn_files/comments.pgn"))
42
- game = games.first
43
- game.tags["White"].should == "Scholar"
44
- game.result.should == "1-0"
45
- game.moves.last.should == "Qxf7#"
46
- end
31
+ it 'should handle comments' do
32
+ games = PGN.parse(File.read('./spec/pgn_files/comments.pgn'))
33
+ game = games.first
34
+ game.tags['White'].should == 'Scholar'
35
+ game.result.should == '1-0'
36
+ game.moves.last.should == 'Qxf7#'
37
+ end
47
38
 
48
- it "should work with multiline comments" do
49
- games = PGN.parse(File.read("./spec/pgn_files/multiline_comments.pgn"))
50
- game = games.first
51
- game.tags["White"].should == "Scholar"
52
- game.result.should == "1-0"
53
- game.moves.last.should == "Qxf7#"
54
- end
39
+ it 'should handle multiline comments' do
40
+ games = PGN.parse(File.read('./spec/pgn_files/multiline_comments.pgn'))
41
+ game = games.first
42
+ game.tags['White'].should == 'Scholar'
43
+ game.result.should == '1-0'
44
+ game.moves.last.should == 'Qxf7#'
55
45
  end
56
46
 
57
- describe "parsing a file" do
58
- it "should return a list of games" do
59
- games = PGN.parse(File.read("./spec/pgn_files/variations.pgn"))
60
- game = games.first
61
- game.tags["Black"].should == "Petrov"
62
- game.result.should == "*"
63
- game.moves.last.should == "Nf6"
64
- end
47
+ it 'should handle nested comments' do
48
+ games = PGN.parse(File.read('./spec/pgn_files/nested_comments.pgn'))
49
+ game = games.first
50
+ game.result.should == '*'
51
+ game.moves.last.should == 'Nf6'
65
52
  end
66
-
67
- describe "parsing a complex file" do
68
- it "should return a list of games" do
69
- games = PGN.parse(File.read("./spec/pgn_files/test.pgn"))
70
- game = games.first
71
- game.tags["Black"].should == "Gelfand, Boris"
72
- game.result.should == "1-0"
73
- game.moves[13].should == "Nfd7"
74
- game.moves[34].should == "f3"
75
- game.moves[35].annotation.should == "$6"
76
- game.moves[35].comment.should == "{Gelfand\ndecide tomar medidas.}"
77
- game.moves[35].variations.size.should == 1
78
- variation = game.moves[35].variations[0]
79
- variation.size.should == 2
80
- variation[0].should == "Nxf3"
81
- end
53
+
54
+ it 'should handle variations' do
55
+ games = PGN.parse(File.read('./spec/pgn_files/variations.pgn'))
56
+ game = games.first
57
+ game.tags['Black'].should == 'Petrov'
58
+ game.result.should == '*'
59
+ game.moves.last.should == 'Nf6'
60
+ end
61
+
62
+ it 'should handle empty variation moves' do
63
+ games = PGN.parse(File.read('./spec/pgn_files/empty_variation_move.pgn'))
64
+ game = games.first
65
+ game.result.should == '*'
66
+ game.moves.last.should == 'Ng5'
67
+ end
68
+
69
+ it 'should handle complex files' do
70
+ games = PGN.parse(File.read('./spec/pgn_files/test.pgn'))
71
+ game = games.first
72
+ game.tags['Black'].should == 'Gelfand, Boris'
73
+ game.result.should == '1-0'
74
+ game.moves[13].should == 'Nfd7'
75
+ game.moves[34].should == 'f3'
76
+ game.moves[35].annotation.should == '$6'
77
+ game.moves[35].comment.should == "{Gelfand\ndecide tomar medidas.}"
78
+ game.moves[35].variations.size.should == 1
79
+ variation = game.moves[35].variations[0]
80
+ variation.size.should == 2
81
+ variation[0].should == 'Nxf3'
82
82
  end
83
83
  end
84
84
  end
@@ -0,0 +1,11 @@
1
+ [White "Somebody"]
2
+ [Black "Somebody Else"]
3
+
4
+ 1. d4 e6 2. c4 d5 3. Nc3 c6 4. Nf3 Nf6 5. Bg5 Nbd7 6. e3 Qa5 7. a3 (7. cxd5
5
+ Nxd5 8. Rc1 {Analyzer's primary variation: 8... Bb4 9. Qd2 e5 10. e4 Nxc3 11.
6
+ bxc3 Ba3 12. Rb1 h6 13. Be3 O-O 14. Bc4 exd4 15. cxd4 Qxd2+ 16. Nxd2 a5 17. O-O
7
+ b5 18. Be2 Rd8 19. d5 cxd5 20. exd5 Nc5 21. Rxb5 Rxd5 {+0.30/21} }) 7... Ne4 8.
8
+ Rc1 Nxg5 9. Nxg5 dxc4 10. Bxc4 Qxg5 11. O-O Nf6 12. Qf3 Qg4 13. Qxg4 Nxg4 14.
9
+ Ne4 Be7 15. b4 O-O 16. Rce1 Nf6 17. Ng5 ({Better is} 17. Nxf6+ gxf6 {-4.08/31}
10
+ (17... Bxf6) (17... gxf6)) (17. Nxf6+) 17... h6 18. Nf3 Ne4 ({Treatening} 18...
11
+ -- 19. Ra1 b5 {-4.05/31}) 19. Bd3 Ng5 *
@@ -0,0 +1,4 @@
1
+ [White "Somebody"]
2
+ [Black "Somebody Else"]
3
+
4
+ 1. e4 e5 2. Nf3 {this {is a} nested {comment}} 2... Nf6 *
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pgn
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.1
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Stacey Touset
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-03-26 00:00:00.000000000 Z
11
+ date: 2017-02-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: whittle
@@ -97,7 +97,9 @@ files:
97
97
  - spec/pgn_files/alternate_castling.pgn
98
98
  - spec/pgn_files/annotations.pgn
99
99
  - spec/pgn_files/comments.pgn
100
+ - spec/pgn_files/empty_variation_move.pgn
100
101
  - spec/pgn_files/multiline_comments.pgn
102
+ - spec/pgn_files/nested_comments.pgn
101
103
  - spec/pgn_files/test.pgn
102
104
  - spec/pgn_files/variations.pgn
103
105
  - spec/position_spec.rb
@@ -133,7 +135,9 @@ test_files:
133
135
  - spec/pgn_files/alternate_castling.pgn
134
136
  - spec/pgn_files/annotations.pgn
135
137
  - spec/pgn_files/comments.pgn
138
+ - spec/pgn_files/empty_variation_move.pgn
136
139
  - spec/pgn_files/multiline_comments.pgn
140
+ - spec/pgn_files/nested_comments.pgn
137
141
  - spec/pgn_files/test.pgn
138
142
  - spec/pgn_files/variations.pgn
139
143
  - spec/position_spec.rb