tcepsni 0.1.1 → 0.3.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +30 -0
- data/lib/tcepsni/parser.rb +161 -0
- data/lib/tcepsni/vendor/activesupport/ordered_options.rb +28 -0
- data/lib/tcepsni/vendor/ipaddr.rb +20 -0
- data/lib/tcepsni/vendor/pathname.rb +21 -0
- data/lib/tcepsni/vendor/rails/paths/root.rb +37 -0
- data/lib/tcepsni/vendor/string_scanner.rb +35 -0
- data/lib/tcepsni/version.rb +1 -1
- data/lib/tcepsni.rb +5 -140
- data/sig/tcepsni.gen.rbs +72 -18
- data/sig/tcepsni.rbs +44 -12
- metadata +8 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 3c7e2dad3ee934784b32e2263cfd23a6a478ec4d648b7e02f1a02267238296e5
|
4
|
+
data.tar.gz: 5db7c50e53eea93481004efd7d2f359db19fe8099356bfd980564f3b861d52d1
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: fc943477c66e694f76a6711ec01a2f82893c756fe7e30b1f00e8ef82d04c63699899b28252e2d046d148af68195a049bf2ca79b8b90bde359474ac610d9d3804
|
7
|
+
data.tar.gz: 8daf45aa53eb860b306357831c0c86a17d0e847fba6cfa8a051fe932a6d355ccfee936aee3ef48949b05a418013b7e140ce37ff57108ae653f768c97359c2f94
|
data/CHANGELOG.md
CHANGED
@@ -2,6 +2,36 @@
|
|
2
2
|
|
3
3
|
## Unreleased
|
4
4
|
|
5
|
+
## 0.3.0 - 2023-11-18
|
6
|
+
|
7
|
+
### Changed
|
8
|
+
|
9
|
+
- Introduced plugin system.
|
10
|
+
For example, if the source contains `Pathname` objects, use the `vendors` option like `Tcepsni.parse(str, vendors: [::Tcepsni::Vendor::Pathname])`.
|
11
|
+
|
12
|
+
### Removed
|
13
|
+
|
14
|
+
- `Tcepsni::Class#string_scanner?`, `Tcepsni::Class#pathname?`, `Tcepsni::Class#ipaddr?`, `Tcepsni::Class#active_support_ordered_options?`, and `Tcepsni::Class#rails_paths_root?`.
|
15
|
+
|
16
|
+
## 0.2.0 - 2023-10-20
|
17
|
+
|
18
|
+
### Added
|
19
|
+
|
20
|
+
- `Time` support
|
21
|
+
- `Pathname` support
|
22
|
+
- `Encoding` support
|
23
|
+
- `IPAddr` support
|
24
|
+
- `ActiveSupport::OrderedOptions` support
|
25
|
+
- `Rails::Paths::Root` support
|
26
|
+
- `Float` support
|
27
|
+
|
28
|
+
### Fixed
|
29
|
+
|
30
|
+
- Parsing the empty array
|
31
|
+
- Parsing the object with some attributes
|
32
|
+
- Parsing the `nil`, `true`, and `false` literals
|
33
|
+
- Detecting `StringScanner`-like object
|
34
|
+
|
5
35
|
## 0.1.1 - 2023-10-02
|
6
36
|
|
7
37
|
### Changed
|
@@ -0,0 +1,161 @@
|
|
1
|
+
require 'strscan'
|
2
|
+
require 'forwardable'
|
3
|
+
|
4
|
+
module Tcepsni
|
5
|
+
class Parser
|
6
|
+
def initialize(source, vendors:)
|
7
|
+
@scanner = ::StringScanner.new(source)
|
8
|
+
@vendors = vendors.flat_map { |vendor| [*vendor.dependencies, vendor] }.uniq
|
9
|
+
end
|
10
|
+
|
11
|
+
# If it returned nil when failed, it collides with normal nil value.
|
12
|
+
def parse_expression
|
13
|
+
if @scanner.skip(/nil\b/)
|
14
|
+
nil
|
15
|
+
elsif @scanner.skip(/true\b/)
|
16
|
+
true
|
17
|
+
elsif @scanner.skip(/false\b/)
|
18
|
+
false
|
19
|
+
elsif @scanner.skip(':')
|
20
|
+
parse_identifier
|
21
|
+
elsif @scanner.skip('"')
|
22
|
+
parse_string
|
23
|
+
elsif @scanner.skip('[')
|
24
|
+
parse_array
|
25
|
+
elsif @scanner.skip('{')
|
26
|
+
parse_hash
|
27
|
+
elsif @scanner.skip('#<')
|
28
|
+
pos = @scanner.pos
|
29
|
+
@vendors.select { |vendor| vendor.object? }.each do |vendor|
|
30
|
+
begin
|
31
|
+
@scanner.pos = pos
|
32
|
+
return vendor.parse(self)
|
33
|
+
rescue Error
|
34
|
+
next
|
35
|
+
end
|
36
|
+
end
|
37
|
+
@scanner.pos = pos
|
38
|
+
parse_object
|
39
|
+
else
|
40
|
+
if (digits = @scanner.scan(/\d+/))
|
41
|
+
int = Integer(digits)
|
42
|
+
if @scanner.skip('.')
|
43
|
+
int2 = parse_integer
|
44
|
+
Float("#{int}.#{int2}")
|
45
|
+
elsif digits.size == 4 && @scanner.skip(/-(?<month>[01]\d)-(?<day>\d\d) (?<hour>[012]\d):(?<minute>[0-5]\d):(?<second>[0-5]\d) (?<zone>[+-]\d\d\d\d)/)
|
46
|
+
Time.new(Integer(int), @scanner[:month], @scanner[:day],
|
47
|
+
@scanner[:hour], @scanner[:minute], @scanner[:second],
|
48
|
+
@scanner[:zone])
|
49
|
+
else
|
50
|
+
int
|
51
|
+
end
|
52
|
+
else
|
53
|
+
parse_class
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
alias parse parse_expression
|
59
|
+
|
60
|
+
def parse_integer
|
61
|
+
int = @scanner.scan(/\d+/) or raise Error, 'no digits'
|
62
|
+
Integer(int)
|
63
|
+
end
|
64
|
+
|
65
|
+
def parse_identifier
|
66
|
+
id = @scanner.scan(/[A-Za-z_][A-Za-z0-9_]*/) or raise Error, 'no identifier'
|
67
|
+
id.intern
|
68
|
+
end
|
69
|
+
|
70
|
+
def parse_string
|
71
|
+
result = ''
|
72
|
+
until @scanner.eos?
|
73
|
+
if @scanner.skip('"')
|
74
|
+
return result
|
75
|
+
elsif @scanner.skip('\\"')
|
76
|
+
result << '"'
|
77
|
+
else
|
78
|
+
result << @scanner.getch
|
79
|
+
end
|
80
|
+
end
|
81
|
+
result
|
82
|
+
end
|
83
|
+
|
84
|
+
def parse_array
|
85
|
+
result = []
|
86
|
+
until @scanner.eos?
|
87
|
+
result << parse_expression rescue break
|
88
|
+
@scanner.skip(', ') or break
|
89
|
+
end
|
90
|
+
@scanner.skip(']') or raise Error, "no array closer: #{@scanner.inspect}"
|
91
|
+
result
|
92
|
+
end
|
93
|
+
|
94
|
+
def parse_hash
|
95
|
+
result = {}
|
96
|
+
until @scanner.eos?
|
97
|
+
key = parse_expression rescue break
|
98
|
+
@scanner.skip('=>') or raise Error, 'no hash arrow'
|
99
|
+
value = parse_expression
|
100
|
+
result[key] = value
|
101
|
+
@scanner.skip(', ') or break
|
102
|
+
end
|
103
|
+
@scanner.skip('}') or raise Error, 'no hash closer'
|
104
|
+
result
|
105
|
+
end
|
106
|
+
|
107
|
+
def parse_class
|
108
|
+
namespaces = [parse_capitalized_identifier]
|
109
|
+
until @scanner.eos?
|
110
|
+
@scanner.skip('::') or break
|
111
|
+
@scanner.eos? and raise Error, 'incomplete class'
|
112
|
+
namespaces << parse_capitalized_identifier
|
113
|
+
end
|
114
|
+
*namespaces, name = namespaces
|
115
|
+
Tcepsni::Class.new(name: name, namespaces: namespaces)
|
116
|
+
end
|
117
|
+
|
118
|
+
def parse_capitalized_identifier
|
119
|
+
id = @scanner.scan(/[A-Z][A-Za-z0-9_]*/) or raise Error, "no capitalized identifier: #{@scanner.inspect}"
|
120
|
+
id.intern
|
121
|
+
end
|
122
|
+
|
123
|
+
def parse_object
|
124
|
+
klass = parse_class
|
125
|
+
if klass.encoding?
|
126
|
+
@scanner.skip(':') or raise Error, 'no colon separator in encoding object'
|
127
|
+
@scanner.skip(/(?<name>[^>]+)>/) or raise Error, 'invalid encoding name'
|
128
|
+
Encoding.find(@scanner[:name])
|
129
|
+
else
|
130
|
+
memory_reference = parse_memory_reference
|
131
|
+
attributes = parse_attributes
|
132
|
+
Tcepsni::Object.new(klass: klass, memory_reference: memory_reference, attributes: attributes)
|
133
|
+
end
|
134
|
+
end
|
135
|
+
|
136
|
+
def parse_attributes
|
137
|
+
attributes = {}
|
138
|
+
unless @scanner.skip('>')
|
139
|
+
until @scanner.eos?
|
140
|
+
@scanner.skip(' @') or break
|
141
|
+
key = parse_identifier
|
142
|
+
@scanner.skip('=') or raise Error, 'no attribute keyval equal char'
|
143
|
+
attributes[key.intern] = parse_expression
|
144
|
+
unless @scanner.skip(',')
|
145
|
+
@scanner.skip('>') or raise Error, "no object closer: #{@scanner.inspect}"
|
146
|
+
break
|
147
|
+
end
|
148
|
+
end
|
149
|
+
end
|
150
|
+
attributes
|
151
|
+
end
|
152
|
+
|
153
|
+
def parse_memory_reference
|
154
|
+
@scanner.skip(/:(?<memory_reference>0x[0-9a-f]{16})/) or raise Error, "no memory reference: #{@scanner.inspect}"
|
155
|
+
Integer(@scanner[:memory_reference])
|
156
|
+
end
|
157
|
+
|
158
|
+
extend Forwardable
|
159
|
+
def_delegators :@scanner, :skip, :[]
|
160
|
+
end
|
161
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
require 'active_support/ordered_options'
|
2
|
+
|
3
|
+
module Tcepsni
|
4
|
+
module Vendor
|
5
|
+
module ActiveSupport
|
6
|
+
class OrderedOptions
|
7
|
+
def self.parse(parser)
|
8
|
+
parser.skip('ActiveSupport::OrderedOptions {') or raise Error, 'no space between ActiveSupport::OrderedOptions class name and hash opener'
|
9
|
+
hash = parser.parse_hash
|
10
|
+
parser.skip('>') or raise Error, "no ActiveSupport ordered options closer: #{parser.scanner.inspect}"
|
11
|
+
options = ::ActiveSupport::OrderedOptions.new
|
12
|
+
hash.each do |key, val|
|
13
|
+
options[key] = val
|
14
|
+
end
|
15
|
+
options
|
16
|
+
end
|
17
|
+
|
18
|
+
def self.dependencies
|
19
|
+
[]
|
20
|
+
end
|
21
|
+
|
22
|
+
def self.object?
|
23
|
+
true
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require 'ipaddr'
|
2
|
+
|
3
|
+
module Tcepsni
|
4
|
+
module Vendor
|
5
|
+
class IPAddr
|
6
|
+
def self.parse(parser)
|
7
|
+
parser.skip(/IPAddr: IPv[46]:(?<addr>[^>]+)>/) or raise Error, 'invalid IP address format error'
|
8
|
+
::IPAddr.new(parser[:addr])
|
9
|
+
end
|
10
|
+
|
11
|
+
def self.object?
|
12
|
+
true
|
13
|
+
end
|
14
|
+
|
15
|
+
def self.dependencies
|
16
|
+
[]
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
require 'pathname'
|
2
|
+
|
3
|
+
module Tcepsni
|
4
|
+
module Vendor
|
5
|
+
class Pathname
|
6
|
+
def self.parse(parser)
|
7
|
+
parser.skip('Pathname:') or raise Error, 'no colon between Pathname class name and path string'
|
8
|
+
parser.skip(/(?<path>[^>]+)>/) or raise Error, 'invalid path string and closer'
|
9
|
+
::Pathname.new(parser[:path])
|
10
|
+
end
|
11
|
+
|
12
|
+
def self.object?
|
13
|
+
true
|
14
|
+
end
|
15
|
+
|
16
|
+
def self.dependencies
|
17
|
+
[]
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
require 'rails/paths'
|
2
|
+
|
3
|
+
module Tcepsni
|
4
|
+
module Vendor
|
5
|
+
module Rails
|
6
|
+
module Paths
|
7
|
+
class Root
|
8
|
+
attr_reader :memory_reference, :attributes
|
9
|
+
|
10
|
+
def initialize(memory_reference, attributes)
|
11
|
+
@memory_reference = memory_reference
|
12
|
+
@attributes = attributes
|
13
|
+
end
|
14
|
+
|
15
|
+
def self.parse(parser)
|
16
|
+
parser.skip('Rails::Paths::Root') or raise Error, 'this is not Rails::Paths::Root'
|
17
|
+
memory_reference = parser.parse_memory_reference
|
18
|
+
if parser.skip(' ...>')
|
19
|
+
attributes = {}
|
20
|
+
else
|
21
|
+
attributes = parser.parse_attributes
|
22
|
+
end
|
23
|
+
Tcepsni::Vendor::Rails::Paths::Root.new(memory_reference, attributes)
|
24
|
+
end
|
25
|
+
|
26
|
+
def self.object?
|
27
|
+
true
|
28
|
+
end
|
29
|
+
|
30
|
+
def self.dependencies
|
31
|
+
[::Tcepsni::Vendor::Pathname]
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
module Tcepsni
|
2
|
+
module Vendor
|
3
|
+
class StringScanner
|
4
|
+
attr_reader :pos, :total, :scanned, :rest
|
5
|
+
|
6
|
+
def initialize(pos:, total:, scanned:, rest:)
|
7
|
+
@pos = pos
|
8
|
+
@total = total
|
9
|
+
@scanned = scanned
|
10
|
+
@rest = rest
|
11
|
+
end
|
12
|
+
|
13
|
+
def self.parse(parser)
|
14
|
+
parser.skip('StringScanner ') or raise Error, 'no space after string scanner class name'
|
15
|
+
pos = parser.parse_integer
|
16
|
+
parser.skip('/') or raise Error, 'no string scanner progress delimiter slash'
|
17
|
+
total = parser.parse_integer
|
18
|
+
parser.skip(' "') or raise Error, 'no space after string scanner progress'
|
19
|
+
scanned = parser.parse_string
|
20
|
+
parser.skip(' @ "') or raise Error, "no string scanner mark in string: #{parser.scanner.inspect}"
|
21
|
+
rest = parser.parse_string
|
22
|
+
parser.skip('>') or raise Error, 'no string scanner closer'
|
23
|
+
Tcepsni::Vendor::StringScanner.new(pos: pos, total: total, scanned: scanned, rest: rest)
|
24
|
+
end
|
25
|
+
|
26
|
+
def self.dependencies
|
27
|
+
[]
|
28
|
+
end
|
29
|
+
|
30
|
+
def self.object?
|
31
|
+
true
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
data/lib/tcepsni/version.rb
CHANGED
data/lib/tcepsni.rb
CHANGED
@@ -1,135 +1,11 @@
|
|
1
|
-
require 'strscan'
|
2
1
|
require_relative 'tcepsni/version'
|
2
|
+
require_relative 'tcepsni/parser'
|
3
3
|
|
4
4
|
module Tcepsni
|
5
5
|
class Error < StandardError; end
|
6
6
|
|
7
|
-
def self.parse(str)
|
8
|
-
|
9
|
-
parse_expression(scanner)
|
10
|
-
end
|
11
|
-
|
12
|
-
class << self
|
13
|
-
private
|
14
|
-
|
15
|
-
# If it returned nil when failed, it collides with normal nil value.
|
16
|
-
def parse_expression(scanner)
|
17
|
-
if scanner.skip('nil')
|
18
|
-
nil
|
19
|
-
elsif scanner.skip('true')
|
20
|
-
true
|
21
|
-
elsif scanner.skip('false')
|
22
|
-
false
|
23
|
-
elsif scanner.skip(':')
|
24
|
-
parse_identifier(scanner)
|
25
|
-
elsif scanner.skip('"')
|
26
|
-
parse_string(scanner)
|
27
|
-
elsif scanner.skip('[')
|
28
|
-
parse_array(scanner)
|
29
|
-
elsif scanner.skip('{')
|
30
|
-
parse_hash(scanner)
|
31
|
-
elsif scanner.skip('#<')
|
32
|
-
parse_object(scanner)
|
33
|
-
else
|
34
|
-
parse_integer(scanner) or parse_class(scanner)
|
35
|
-
end
|
36
|
-
end
|
37
|
-
|
38
|
-
# Returns nil if it's not integer.
|
39
|
-
# This doesn't raise error for convenience.
|
40
|
-
def parse_integer(scanner)
|
41
|
-
int = scanner.scan(/\d+/) or return
|
42
|
-
Integer(int)
|
43
|
-
end
|
44
|
-
|
45
|
-
def parse_identifier(scanner)
|
46
|
-
id = scanner.scan(/[A-Za-z_][A-Za-z0-9_]*/) or raise Error, 'no identifier'
|
47
|
-
id.intern
|
48
|
-
end
|
49
|
-
|
50
|
-
def parse_string(scanner)
|
51
|
-
result = ''
|
52
|
-
until scanner.eos?
|
53
|
-
if scanner.skip('"')
|
54
|
-
return result
|
55
|
-
elsif scanner.skip('\\"')
|
56
|
-
result << '"'
|
57
|
-
else
|
58
|
-
result << scanner.getch
|
59
|
-
end
|
60
|
-
end
|
61
|
-
result
|
62
|
-
end
|
63
|
-
|
64
|
-
def parse_array(scanner)
|
65
|
-
result = [parse_expression(scanner)]
|
66
|
-
until scanner.eos?
|
67
|
-
scanner.skip(', ') or break
|
68
|
-
scanner.eos? and raise Error, 'incomplete array'
|
69
|
-
result << parse_expression(scanner)
|
70
|
-
end
|
71
|
-
scanner.skip(']') or raise Error, 'no array closer'
|
72
|
-
result
|
73
|
-
end
|
74
|
-
|
75
|
-
def parse_hash(scanner)
|
76
|
-
result = {}
|
77
|
-
until scanner.eos?
|
78
|
-
key = parse_expression(scanner) rescue break
|
79
|
-
scanner.skip('=>') or raise Error, 'no hash arrow'
|
80
|
-
value = parse_expression(scanner)
|
81
|
-
result[key] = value
|
82
|
-
scanner.skip(', ') or break
|
83
|
-
end
|
84
|
-
scanner.skip('}') or raise Error, 'no hash closer'
|
85
|
-
result
|
86
|
-
end
|
87
|
-
|
88
|
-
def parse_class(scanner)
|
89
|
-
namespaces = [parse_capitalized_identifier(scanner)]
|
90
|
-
until scanner.eos?
|
91
|
-
scanner.skip('::') or break
|
92
|
-
scanner.eos? and raise Error, 'incomplete class'
|
93
|
-
namespaces << parse_capitalized_identifier(scanner)
|
94
|
-
end
|
95
|
-
*namespaces, name = namespaces
|
96
|
-
Tcepsni::Class.new(name: name, namespaces: namespaces)
|
97
|
-
end
|
98
|
-
|
99
|
-
def parse_capitalized_identifier(scanner)
|
100
|
-
id = scanner.scan(/[A-Z][A-Za-z0-9_]*/) or raise Error, 'no capitalized identifier'
|
101
|
-
id.intern
|
102
|
-
end
|
103
|
-
|
104
|
-
def parse_object(scanner)
|
105
|
-
klass = parse_class(scanner)
|
106
|
-
if klass.string_scanner?
|
107
|
-
scanner.skip(' ') or raise Error, 'no space after string scanner class name'
|
108
|
-
pos = parse_integer(scanner) or raise Error, 'no string scanner pos'
|
109
|
-
scanner.skip('/') or raise Error, 'no string scanner progress delimiter slash'
|
110
|
-
total = parse_integer(scanner) or raise Error, 'no string scanner total size'
|
111
|
-
scanner.skip(' "') or raise Error, 'no space after string scanner progress'
|
112
|
-
scanned = parse_string(scanner)
|
113
|
-
scanner.skip(' @ "') or raise Error, "no string scanner mark in string: #{scanner.inspect}"
|
114
|
-
rest = parse_string(scanner)
|
115
|
-
scanner.skip('>') or raise Error, 'no string scanner closer'
|
116
|
-
Tcepsni::StringScanner.new(pos: pos, total: total, scanned: scanned, rest: rest)
|
117
|
-
else
|
118
|
-
scanner.skip(/:(?<memory_reference>0x[0-9a-f]{16})/) or raise Error, "no memory reference: #{scanner.inspect}"
|
119
|
-
memory_reference = Integer(scanner[:memory_reference])
|
120
|
-
attributes = {}
|
121
|
-
unless scanner.skip('>')
|
122
|
-
until scanner.eos?
|
123
|
-
scanner.skip(' @') or break
|
124
|
-
key = parse_identifier(scanner)
|
125
|
-
scanner.skip('=') or raise Error, 'no attribute keyval equal char'
|
126
|
-
attributes[key.intern] = parse_expression(scanner)
|
127
|
-
scanner.skip(',') or break
|
128
|
-
end
|
129
|
-
end
|
130
|
-
Tcepsni::Object.new(klass: klass, memory_reference: memory_reference, attributes: attributes)
|
131
|
-
end
|
132
|
-
end
|
7
|
+
def self.parse(str, vendors: [])
|
8
|
+
Parser.new(str, vendors: vendors).parse
|
133
9
|
end
|
134
10
|
|
135
11
|
class Class
|
@@ -140,8 +16,8 @@ module Tcepsni
|
|
140
16
|
@namespaces = namespaces
|
141
17
|
end
|
142
18
|
|
143
|
-
def
|
144
|
-
|
19
|
+
def encoding?
|
20
|
+
@name == :Encoding && @namespaces.empty?
|
145
21
|
end
|
146
22
|
end
|
147
23
|
|
@@ -154,15 +30,4 @@ module Tcepsni
|
|
154
30
|
@memory_reference = memory_reference
|
155
31
|
end
|
156
32
|
end
|
157
|
-
|
158
|
-
class StringScanner
|
159
|
-
attr_reader :pos, :total, :scanned, :rest
|
160
|
-
|
161
|
-
def initialize(pos:, total:, scanned:, rest:)
|
162
|
-
@pos = pos
|
163
|
-
@total = total
|
164
|
-
@scanned = scanned
|
165
|
-
@rest = rest
|
166
|
-
end
|
167
|
-
end
|
168
33
|
end
|
data/sig/tcepsni.gen.rbs
CHANGED
@@ -4,37 +4,91 @@
|
|
4
4
|
module Tcepsni
|
5
5
|
VERSION: String
|
6
6
|
|
7
|
-
# def self.parse: (String str) ->
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
def
|
15
|
-
def
|
16
|
-
|
7
|
+
# def self.parse: (String str) -> untyped
|
8
|
+
|
9
|
+
class Parser
|
10
|
+
extend Forwardable
|
11
|
+
@scanner: StringScanner
|
12
|
+
@vendors: Array[Array[untyped]]
|
13
|
+
|
14
|
+
# def initialize: (String source, vendors: Array[untyped]?) -> void
|
15
|
+
# def parse_expression: -> untyped
|
16
|
+
alias parse parse_expression
|
17
|
+
# def parse_integer: -> Integer
|
18
|
+
# def parse_identifier: -> Symbol
|
19
|
+
# def parse_string: -> String
|
20
|
+
# def parse_array: -> Array[untyped]
|
21
|
+
# def parse_hash: -> Hash[untyped, untyped]
|
22
|
+
# def parse_class: -> Class
|
23
|
+
# def parse_capitalized_identifier: -> Symbol
|
24
|
+
# def parse_object: -> Object
|
25
|
+
# def parse_attributes: -> Hash[Symbol, untyped]
|
26
|
+
# def parse_memory_reference: -> Integer
|
27
|
+
end
|
17
28
|
|
18
29
|
class Class
|
19
30
|
# def initialize: (name: Symbol?, namespaces: Array[Symbol]) -> void
|
20
31
|
# def ==: (Class other) -> bool
|
21
32
|
# def string_scanner?: -> bool
|
33
|
+
# def pathname?: -> bool
|
34
|
+
# def encoding?: -> bool
|
35
|
+
# def ipaddr?: -> bool
|
36
|
+
# def active_support_ordered_options?: -> bool
|
37
|
+
# def rails_paths_root?: -> bool
|
22
38
|
# attr_reader name: Symbol?
|
23
39
|
# attr_reader namespaces: Array[Symbol]
|
24
40
|
end
|
25
41
|
|
26
42
|
class Object
|
27
|
-
# def initialize: (klass: Class, attributes: Hash[Symbol,
|
43
|
+
# def initialize: (klass: Class, attributes: Hash[Symbol, untyped], memory_reference: Integer) -> void
|
28
44
|
# attr_reader klass: Class
|
29
|
-
# attr_reader attributes: Hash[Symbol,
|
45
|
+
# attr_reader attributes: Hash[Symbol, untyped]
|
30
46
|
# attr_reader memory_reference: Integer
|
31
47
|
end
|
32
48
|
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
49
|
+
module Vendor
|
50
|
+
class StringScanner
|
51
|
+
attr_reader pos: untyped
|
52
|
+
attr_reader total: untyped
|
53
|
+
attr_reader scanned: untyped
|
54
|
+
attr_reader rest: untyped
|
55
|
+
def initialize: (pos: untyped, total: untyped, scanned: untyped, rest: untyped) -> void
|
56
|
+
def self.parse: (untyped parser) -> StringScanner
|
57
|
+
def self.dependencies: -> Array[untyped]
|
58
|
+
def self.object?: -> true
|
59
|
+
end
|
60
|
+
|
61
|
+
module Rails
|
62
|
+
module Paths
|
63
|
+
class Root
|
64
|
+
attr_reader memory_reference: untyped
|
65
|
+
attr_reader attributes: Hash[untyped, untyped]
|
66
|
+
def initialize: (untyped memory_reference, Hash[untyped, untyped] attributes) -> void
|
67
|
+
def self.parse: (untyped parser) -> Root
|
68
|
+
def self.object?: -> true
|
69
|
+
def self.dependencies: -> [singleton(Pathname)]
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
|
74
|
+
module ActiveSupport
|
75
|
+
class OrderedOptions
|
76
|
+
def self.parse: (untyped parser) -> untyped
|
77
|
+
def self.dependencies: -> Array[untyped]
|
78
|
+
def self.object?: -> true
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
class IPAddr
|
83
|
+
def self.parse: (untyped parser) -> IPAddr
|
84
|
+
def self.object?: -> true
|
85
|
+
def self.dependencies: -> Array[untyped]
|
86
|
+
end
|
87
|
+
|
88
|
+
class Pathname
|
89
|
+
def self.parse: (untyped parser) -> Pathname
|
90
|
+
def self.object?: -> true
|
91
|
+
def self.dependencies: -> Array[untyped]
|
92
|
+
end
|
39
93
|
end
|
40
94
|
end
|
data/sig/tcepsni.rbs
CHANGED
@@ -4,11 +4,23 @@ module Tcepsni
|
|
4
4
|
class Error < StandardError
|
5
5
|
end
|
6
6
|
|
7
|
-
|
8
|
-
Array[parsed] | Hash[parsed, parsed] |
|
9
|
-
Class | Object | StringScanner
|
7
|
+
def self.parse: (String str) -> untyped
|
10
8
|
|
11
|
-
|
9
|
+
class Parser
|
10
|
+
def initialize: (String source, vendors: Array[untyped]?) -> void
|
11
|
+
def parse_expression: -> untyped
|
12
|
+
alias parse parse_expression
|
13
|
+
def parse_integer: -> Integer
|
14
|
+
def parse_identifier: -> Symbol
|
15
|
+
def parse_string: -> String
|
16
|
+
def parse_array: -> Array[untyped]
|
17
|
+
def parse_hash: -> Hash[untyped, untyped]
|
18
|
+
def parse_class: -> Class
|
19
|
+
def parse_capitalized_identifier: -> Symbol
|
20
|
+
def parse_object: -> Object
|
21
|
+
def parse_attributes: -> Hash[Symbol, untyped]
|
22
|
+
def parse_memory_reference: -> Integer
|
23
|
+
end
|
12
24
|
|
13
25
|
class Class
|
14
26
|
attr_reader name: Symbol
|
@@ -16,20 +28,40 @@ module Tcepsni
|
|
16
28
|
def initialize: (name: Symbol?, namespaces: Array[Symbol]) -> void
|
17
29
|
def ==: (Class other) -> bool
|
18
30
|
def string_scanner?: -> bool
|
31
|
+
def pathname?: -> bool
|
32
|
+
def encoding?: -> bool
|
33
|
+
def ipaddr?: -> bool
|
34
|
+
def active_support_ordered_options?: -> bool
|
35
|
+
def rails_paths_root?: -> bool
|
19
36
|
end
|
20
37
|
|
21
38
|
class Object
|
22
39
|
attr_reader klass: ::Class
|
23
|
-
attr_reader attributes: Hash[Symbol,
|
40
|
+
attr_reader attributes: Hash[Symbol, untyped]
|
24
41
|
attr_reader memory_reference: Integer
|
25
|
-
def initialize: (klass: Class, attributes: Hash[Symbol,
|
42
|
+
def initialize: (klass: Class, attributes: Hash[Symbol, untyped], memory_reference: Integer) -> void
|
26
43
|
end
|
27
44
|
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
45
|
+
module Vendor
|
46
|
+
class StringScanner
|
47
|
+
end
|
48
|
+
|
49
|
+
module Rails
|
50
|
+
module Paths
|
51
|
+
class Root
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
module ActiveSupport
|
57
|
+
class OrderedOptions
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
class IPAddr
|
62
|
+
end
|
63
|
+
|
64
|
+
class Pathname
|
65
|
+
end
|
34
66
|
end
|
35
67
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: tcepsni
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.3.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- gemmaro
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-
|
11
|
+
date: 2023-11-18 00:00:00.000000000 Z
|
12
12
|
dependencies: []
|
13
13
|
description: Tcepsni gem is a parser library for inspected strings of Ruby objects.
|
14
14
|
email:
|
@@ -21,6 +21,12 @@ files:
|
|
21
21
|
- LICENSE.txt
|
22
22
|
- README.md
|
23
23
|
- lib/tcepsni.rb
|
24
|
+
- lib/tcepsni/parser.rb
|
25
|
+
- lib/tcepsni/vendor/activesupport/ordered_options.rb
|
26
|
+
- lib/tcepsni/vendor/ipaddr.rb
|
27
|
+
- lib/tcepsni/vendor/pathname.rb
|
28
|
+
- lib/tcepsni/vendor/rails/paths/root.rb
|
29
|
+
- lib/tcepsni/vendor/string_scanner.rb
|
24
30
|
- lib/tcepsni/version.rb
|
25
31
|
- sig/tcepsni.gen.rbs
|
26
32
|
- sig/tcepsni.rbs
|