Skip to content

Commit d431d1c

Browse files
committed
WIP: keep getting more and more of Expression parsing working with the new CST/AST node setup
1 parent 97dca84 commit d431d1c

File tree

13 files changed

+609
-355
lines changed

13 files changed

+609
-355
lines changed

lib/plume.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ module Plume
1111
autoload :Token, "plume/ast/token"
1212

1313
autoload :BinaryExpression, "plume/ast/binary_expression"
14+
autoload :ParentheticalExpression, "plume/ast/parenthetical_expression"
1415
autoload :Blob, "plume/ast/blob"
1516
autoload :CaseCondition, "plume/ast/case_condition"
1617
autoload :CaseExpression, "plume/ast/case_expression"
@@ -81,6 +82,7 @@ module Plume
8182
autoload :UnionCompoundOperator, "plume/ast/union_compound_operator"
8283
autoload :UniqueColumnConstraint, "plume/ast/unique_column_constraint"
8384
autoload :UniqueTableConstraint, "plume/ast/unique_table_constraint"
85+
autoload :LiteralExpression, "plume/ast/literal_expression"
8486
autoload :Variable, "plume/ast/variable"
8587
autoload :WithoutRowidTableOption, "plume/ast/without_rowid_table_option"
8688

lib/plume/ast/binary_expression.rb

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -61,8 +61,8 @@ def after_initialize()
6161
end
6262
end
6363

64-
def operator = @operator || TOKEN_TO_OPERATOR[operator_tk_tok]
65-
def left = @left || left_tk_val
66-
def right = @right || right_tk_val
64+
def operator = (@operator == LiteralNil) ? TOKEN_TO_OPERATOR[operator_tk_tok] : @operator
65+
def left = (@left == LiteralNil) ? left_tk_val : @left
66+
def right = (@right == LiteralNil) ? right_tk_val : @right
6767
end
6868
end

lib/plume/ast/column_name.rb

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,8 @@ class ColumnName < Node
1515
def self.new(*, column:, **) = super
1616
def self.concrete(*, column_tk:, **) = super
1717

18-
def schema = @schema || schema_tk_val
19-
def table = @table || table_tk_val
20-
def column = @column || column_tk_val
18+
def schema = (@schema == LiteralNil) ? schema_tk_val : @schema
19+
def table = (@table == LiteralNil) ? table_tk_val : @table
20+
def column = (@column == LiteralNil) ? column_tk_val : @column
2121
end
2222
end

lib/plume/ast/expression.rb

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ module Plume
1818
RaiseExpression,
1919
FunctionReference,
2020
SignedExpression,
21+
LiteralExpression,
2122
)
2223
},
2324
)
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
# frozen_string_literal: true
2+
3+
module Plume
4+
class LiteralExpression < Node
5+
token :value_tk # required
6+
7+
attr :value, _Void # required
8+
9+
def self.new(*, value:, **) = super
10+
def self.concrete(*, **) = super
11+
12+
# Parser may pass either tokens or attributes, so
13+
# require none in `concrete` signature but ensure presence here.
14+
def after_initialize()
15+
if @value == LiteralNil && @value_tk == LiteralNil
16+
raise ArgumentError.new("missing either: :value, :value_tk")
17+
end
18+
end
19+
20+
def value
21+
v = (@value == LiteralNil) ? value_tk_val : @value
22+
case v
23+
when LiteralNil then nil
24+
when LiteralFalse then false
25+
else v
26+
end
27+
end
28+
end
29+
end

lib/plume/ast/literal_false.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,4 +2,6 @@
22

33
module Plume
44
LiteralFalse = Object.new
5+
def LiteralFalse.inspect = "<LiteralFalse>"
6+
LiteralFalse.freeze
57
end

lib/plume/ast/literal_nil.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,4 +2,6 @@
22

33
module Plume
44
LiteralNil = Object.new
5+
def LiteralNil.inspect = "<LiteralNil>"
6+
LiteralNil.freeze
57
end

lib/plume/ast/node.rb

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -43,12 +43,12 @@ def self.concrete(*, full_source:, **)
4343
end
4444

4545
def self.attr(name, type, **kw)
46-
prop name, _Nilable(type), reader: false, **kw
46+
prop name, _Union(type, LiteralNil, nil), reader: false, default: LiteralNil, **kw
4747
inspectable name
4848
end
4949

5050
def self.token(name, **kw)
51-
prop name, _Nilable(Token), reader: false, **kw
51+
prop name, _Union(Token, LiteralNil, nil), reader: false, default: LiteralNil, **kw
5252

5353
# Define methods for accessing token properties, like the original source text, parsed value, and location.
5454
# The token reader method is simply the parsed value of the token.
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
# frozen_string_literal: true
2+
3+
module Plume
4+
class ParentheticalExpression < Node
5+
token :value_lp
6+
token :value_tk # required
7+
token :value_rp
8+
9+
attr :value, _Void # required
10+
11+
def self.new(*, value:, **) = super
12+
def self.concrete(*, **) = super
13+
14+
# Parser may pass either tokens or attributes, so
15+
# require none in `concrete` signature but ensure presence here.
16+
def after_initialize()
17+
if @value == LiteralNil && @value_tk == LiteralNil
18+
raise ArgumentError.new("missing either: :value, :value_tk")
19+
end
20+
end
21+
22+
def value
23+
v = (@value == LiteralNil) ? value_tk_val : @value
24+
case v
25+
when LiteralNil then nil
26+
when LiteralFalse then false
27+
when LiteralExpression then v.value
28+
else v
29+
end
30+
end
31+
end
32+
end

lib/plume/ast/token.rb

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -133,9 +133,9 @@ def string_literal(str, tup)
133133

134134
def blob_literal(str, tup)
135135
src = source(str, tup)
136-
bytesize = value.bytesize
136+
bytesize = src.bytesize
137137
# trim the leading /x'/i and trailing /'/ then decode the hexadecimal string
138-
[value.byteslice(2, bytesize - 3)].pack("H*")
138+
[src.byteslice(2, bytesize - 3)].pack("H*")
139139
end
140140

141141
def identifier(str, tup)

0 commit comments

Comments
 (0)