parlour 6.0.1 → 7.0.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.
- checksums.yaml +4 -4
- data/.parlour +4 -2
- data/CHANGELOG.md +18 -0
- data/exe/parlour +2 -3
- data/lib/parlour/conflict_resolver.rb +18 -14
- data/lib/parlour/debugging.rb +29 -16
- data/lib/parlour/mixin/searchable.rb +54 -0
- data/lib/parlour/rbi_generator/arbitrary.rb +3 -6
- data/lib/parlour/rbi_generator/attribute.rb +9 -0
- data/lib/parlour/rbi_generator/class_namespace.rb +6 -7
- data/lib/parlour/rbi_generator/constant.rb +3 -6
- data/lib/parlour/rbi_generator/enum_class_namespace.rb +7 -0
- data/lib/parlour/rbi_generator/extend.rb +5 -8
- data/lib/parlour/rbi_generator/include.rb +5 -8
- data/lib/parlour/rbi_generator/method.rb +15 -10
- data/lib/parlour/rbi_generator/module_namespace.rb +7 -9
- data/lib/parlour/rbi_generator/namespace.rb +10 -10
- data/lib/parlour/rbi_generator/parameter.rb +12 -0
- data/lib/parlour/rbi_generator/rbi_object.rb +0 -5
- data/lib/parlour/rbi_generator/struct_class_namespace.rb +7 -0
- data/lib/parlour/rbi_generator/type_alias.rb +5 -8
- data/lib/parlour/rbi_generator.rb +1 -16
- data/lib/parlour/rbs_generator/arbitrary.rb +3 -6
- data/lib/parlour/rbs_generator/attribute.rb +8 -0
- data/lib/parlour/rbs_generator/class_namespace.rb +5 -9
- data/lib/parlour/rbs_generator/constant.rb +3 -6
- data/lib/parlour/rbs_generator/extend.rb +3 -6
- data/lib/parlour/rbs_generator/include.rb +3 -6
- data/lib/parlour/rbs_generator/interface_namespace.rb +5 -5
- data/lib/parlour/rbs_generator/method.rb +6 -7
- data/lib/parlour/rbs_generator/method_signature.rb +13 -0
- data/lib/parlour/rbs_generator/module_namespace.rb +5 -6
- data/lib/parlour/rbs_generator/namespace.rb +8 -8
- data/lib/parlour/rbs_generator/rbs_object.rb +0 -5
- data/lib/parlour/rbs_generator/type_alias.rb +3 -6
- data/lib/parlour/type_loader.rb +6 -1
- data/lib/parlour/type_parser.rb +2 -2
- data/lib/parlour/typed_object.rb +88 -3
- data/lib/parlour/version.rb +1 -1
- data/lib/parlour.rb +2 -0
- metadata +4 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: cc5c6c8baabe95bbc999a4143264b1dad8b84260bdc156d2a35526244322db2f
|
4
|
+
data.tar.gz: 580430b0cfe37f80b60f9dd47f8673f4d1d973e6ef6abca44efa299355d19fed
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ae2fd0263a3d955ff7904a28e69bf16eb21b413bda3e71be42636e0829e730a33ee0eb477712fc45dffbce948de3a4c3d6ae6e19147e21b114cd58fe93679676
|
7
|
+
data.tar.gz: 549cd5f91736b8aa5c1f5e1ebaa69fd2d8e4e9f905f1d4aa9ed799677e2d2367a573548d6a9ea220f3c6c6dbf268cc2679c8d0e26516c52224574563974070b6
|
data/.parlour
CHANGED
data/CHANGELOG.md
CHANGED
@@ -3,6 +3,24 @@ All notable changes to this project will be documented in this file.
|
|
3
3
|
|
4
4
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
|
5
5
|
|
6
|
+
## [7.0.0] - 2022-04-18
|
7
|
+
### Added
|
8
|
+
- `#describe` now uses a new, clearer format.
|
9
|
+
- Added `#describe_tree`, which produces `#describe` output for a node and all
|
10
|
+
of its children.
|
11
|
+
- Added `#find` and `#find_all` for retrieving a node's children based on
|
12
|
+
criteria.
|
13
|
+
|
14
|
+
### Changed
|
15
|
+
- Parlour now uses the new block-based `type_member` syntax internally.
|
16
|
+
**Potentially breaking** if you pin an older version of Sorbet which doesn't
|
17
|
+
support this syntax!
|
18
|
+
- Improved error message when unable to retrieve the file table from Sorbet.
|
19
|
+
- `#inspect` and `#to_s` now call `#describe`.
|
20
|
+
|
21
|
+
## Fixed
|
22
|
+
- Fixed some incorrect YARD documentation tags.
|
23
|
+
|
6
24
|
## [6.0.1] - 2021-02-28
|
7
25
|
### Changed
|
8
26
|
- Disabled runtime type checking for `TypedObject#name`, resulting in a
|
data/exe/parlour
CHANGED
@@ -11,9 +11,8 @@ program :description, 'An RBI generator and plugin system'
|
|
11
11
|
|
12
12
|
default_command :run
|
13
13
|
command :run do |c|
|
14
|
-
|
15
|
-
c.
|
16
|
-
c.description = 'Generates an RBI file from your .parlour file'
|
14
|
+
c.syntax = 'parlour run'
|
15
|
+
c.description = 'Generates a signature file from your .parlour file'
|
17
16
|
|
18
17
|
c.action do |args, options|
|
19
18
|
working_dir = Dir.pwd
|
@@ -7,6 +7,10 @@ module Parlour
|
|
7
7
|
class ConflictResolver
|
8
8
|
extend T::Sig
|
9
9
|
|
10
|
+
def initialize
|
11
|
+
@debugging_tree = Debugging::Tree.new(colour: true)
|
12
|
+
end
|
13
|
+
|
10
14
|
sig do
|
11
15
|
params(
|
12
16
|
namespace: RbiGenerator::Namespace,
|
@@ -41,7 +45,7 @@ module Parlour
|
|
41
45
|
# will be kept, or nil to keep none of them.
|
42
46
|
# @return [void]
|
43
47
|
def resolve_conflicts(namespace, &resolver)
|
44
|
-
Debugging.debug_puts(self,
|
48
|
+
Debugging.debug_puts(self, @debugging_tree.begin("Resolving conflicts for #{namespace.name}..."))
|
45
49
|
|
46
50
|
# Check for multiple definitions with the same name
|
47
51
|
# (Special case here: writer attributes get an "=" appended to their name)
|
@@ -54,10 +58,10 @@ module Parlour
|
|
54
58
|
end
|
55
59
|
|
56
60
|
grouped_by_name_children.each do |name, children|
|
57
|
-
Debugging.debug_puts(self,
|
61
|
+
Debugging.debug_puts(self, @debugging_tree.begin("Checking children named #{name}..."))
|
58
62
|
|
59
63
|
if children.length > 1
|
60
|
-
Debugging.debug_puts(self,
|
64
|
+
Debugging.debug_puts(self, @debugging_tree.here("Possible conflict between #{children.length} objects"))
|
61
65
|
|
62
66
|
# Special case: do we have two methods, one of which is a class method
|
63
67
|
# and the other isn't? If so, do nothing - this is fine
|
@@ -65,7 +69,7 @@ module Parlour
|
|
65
69
|
children.all? { |c| c.is_a?(RbiGenerator::Method) } &&
|
66
70
|
children.count { |c| T.cast(c, RbiGenerator::Method).class_method } == 1
|
67
71
|
|
68
|
-
Debugging.debug_puts(self,
|
72
|
+
Debugging.debug_puts(self, @debugging_tree.end("One is an instance method and one is a class method; no resolution required"))
|
69
73
|
next
|
70
74
|
end
|
71
75
|
|
@@ -80,7 +84,7 @@ module Parlour
|
|
80
84
|
end
|
81
85
|
deduplicate_mixins_of_name(namespace, name)
|
82
86
|
|
83
|
-
Debugging.debug_puts(self,
|
87
|
+
Debugging.debug_puts(self, @debugging_tree.end("Includes/extends do not conflict with namespaces; no resolution required"))
|
84
88
|
next
|
85
89
|
end
|
86
90
|
|
@@ -90,13 +94,13 @@ module Parlour
|
|
90
94
|
children.all? { |c| c.is_a?(RbiGenerator::Attribute) } &&
|
91
95
|
children.count { |c| T.cast(c, RbiGenerator::Attribute).class_attribute } == 1
|
92
96
|
|
93
|
-
Debugging.debug_puts(self,
|
97
|
+
Debugging.debug_puts(self, @debugging_tree.end("One is an instance attribute and one is a class attribute; no resolution required"))
|
94
98
|
next
|
95
99
|
end
|
96
100
|
|
97
101
|
# Optimization for Special case: are they all clearly equal? If so, remove all but one
|
98
102
|
if all_eql?(children)
|
99
|
-
Debugging.debug_puts(self,
|
103
|
+
Debugging.debug_puts(self, @debugging_tree.end("All children are identical"))
|
100
104
|
|
101
105
|
# All of the children are the same, so this deletes all of them
|
102
106
|
namespace.children.delete(T.must(children.first))
|
@@ -116,7 +120,7 @@ module Parlour
|
|
116
120
|
# and get the strategy to use
|
117
121
|
strategy = merge_strategy(children)
|
118
122
|
unless strategy
|
119
|
-
Debugging.debug_puts(self,
|
123
|
+
Debugging.debug_puts(self, @debugging_tree.end("Children are unmergeable types; requesting manual resolution"))
|
120
124
|
# The types aren't the same, so ask the resolver what to do, and
|
121
125
|
# insert that (if not nil)
|
122
126
|
choice = resolver.call("Different kinds of definition for the same name", children)
|
@@ -135,7 +139,7 @@ module Parlour
|
|
135
139
|
# a single method
|
136
140
|
if non_namespaces.length != 0
|
137
141
|
unless non_namespaces.length == 1 && RbiGenerator::Method === non_namespaces.first
|
138
|
-
Debugging.debug_puts(self,
|
142
|
+
Debugging.debug_puts(self, @debugging_tree.end("Non-namespace item in a differing namespace conflict is not a single method; requesting manual resolution"))
|
139
143
|
# The types aren't the same, so ask the resolver what to do, and
|
140
144
|
# insert that (if not nil)
|
141
145
|
choice = resolver.call("Non-namespace item in a differing namespace conflict is not a single method", non_namespaces)
|
@@ -167,29 +171,29 @@ module Parlour
|
|
167
171
|
# Can the children merge themselves automatically? If so, let them
|
168
172
|
first, rest = T.must(first), T.must(rest)
|
169
173
|
if T.must(first).mergeable?(T.must(rest))
|
170
|
-
Debugging.debug_puts(self,
|
174
|
+
Debugging.debug_puts(self, @debugging_tree.end("Children are all mergeable; resolving automatically"))
|
171
175
|
first.merge_into_self(rest)
|
172
176
|
namespace.children << first
|
173
177
|
next
|
174
178
|
end
|
175
179
|
|
176
180
|
# I give up! Let it be resolved manually somehow
|
177
|
-
Debugging.debug_puts(self,
|
181
|
+
Debugging.debug_puts(self, @debugging_tree.end("Unable to resolve automatically; requesting manual resolution"))
|
178
182
|
choice = resolver.call("Can't automatically resolve", children)
|
179
183
|
namespace.children << choice if choice
|
180
184
|
else
|
181
|
-
Debugging.debug_puts(self,
|
185
|
+
Debugging.debug_puts(self, @debugging_tree.end("No conflicts"))
|
182
186
|
end
|
183
187
|
end
|
184
188
|
|
185
|
-
Debugging.debug_puts(self,
|
189
|
+
Debugging.debug_puts(self, @debugging_tree.here("Resolving children..."))
|
186
190
|
|
187
191
|
# Recurse to child namespaces
|
188
192
|
namespace.children.each do |child|
|
189
193
|
resolve_conflicts(child, &resolver) if RbiGenerator::Namespace === child
|
190
194
|
end
|
191
195
|
|
192
|
-
Debugging.debug_puts(self,
|
196
|
+
Debugging.debug_puts(self, @debugging_tree.end("All children done"))
|
193
197
|
end
|
194
198
|
|
195
199
|
private
|
data/lib/parlour/debugging.rb
CHANGED
@@ -17,7 +17,7 @@ module Parlour
|
|
17
17
|
@debug_mode = value
|
18
18
|
end
|
19
19
|
|
20
|
-
# Whether debug messages sent by {
|
20
|
+
# Whether debug messages sent by {.debug_puts} should be printed.
|
21
21
|
# Defaults to true if the PARLOUR_DEBUG environment variable is set.
|
22
22
|
# @return [Boolean] True if debug messages will be printed, false otherwise.
|
23
23
|
sig { returns(T::Boolean) }
|
@@ -25,11 +25,11 @@ module Parlour
|
|
25
25
|
@debug_mode
|
26
26
|
end
|
27
27
|
|
28
|
-
# Prints a message with a debugging prefix to STDOUT if {
|
28
|
+
# Prints a message with a debugging prefix to STDOUT if {.debug_mode?} is
|
29
29
|
# true.
|
30
|
-
# @
|
30
|
+
# @param [Object] object The object which is printing this debug message.
|
31
31
|
# Callers should pass +self+.
|
32
|
-
# @
|
32
|
+
# @param [String] message The message to print. It should not contain
|
33
33
|
# newlines.
|
34
34
|
# @return [void]
|
35
35
|
sig { params(object: T.untyped, message: String).void }
|
@@ -45,7 +45,7 @@ module Parlour
|
|
45
45
|
# "conflict resolver". If the object type is unknown, this returns its class
|
46
46
|
# name.
|
47
47
|
# @param [Object] object The object to convert.
|
48
|
-
# @return [String] A string describing the object for {
|
48
|
+
# @return [String] A string describing the object for {.debug_puts}.
|
49
49
|
sig { params(object: T.untyped).returns(String) }
|
50
50
|
def self.name_for_debug_caller(object)
|
51
51
|
case object
|
@@ -63,24 +63,32 @@ module Parlour
|
|
63
63
|
|
64
64
|
# A module for generating a globally-consistent, nicely-formatted tree of
|
65
65
|
# output using Unicode block characters.
|
66
|
-
|
66
|
+
class Tree
|
67
67
|
extend T::Sig
|
68
68
|
|
69
69
|
# The number of spaces to indent each layer of the tree by. Should be at
|
70
70
|
# least 1.
|
71
71
|
INDENT_SPACES = 2
|
72
72
|
|
73
|
-
#
|
74
|
-
|
73
|
+
# Whether to colour output or not.
|
74
|
+
sig { returns(T::Boolean) }
|
75
|
+
attr_reader :colour
|
76
|
+
|
77
|
+
sig { params(colour: T::Boolean).void }
|
78
|
+
def initialize(colour: false)
|
79
|
+
@colour = colour
|
80
|
+
@indent_level = 0
|
81
|
+
end
|
75
82
|
|
76
83
|
# Returns a new heading, and then decents the tree one level into it.
|
77
84
|
# (That is, future output will go under the new heading.)
|
78
85
|
# @param [String] message The heading.
|
79
86
|
# @return [String] The line of this tree which should be printed.
|
80
87
|
sig { params(message: String).returns(String) }
|
81
|
-
def
|
82
|
-
result = line_prefix + '├' + text_prefix +
|
83
|
-
|
88
|
+
def begin(message)
|
89
|
+
result = line_prefix + '├' + text_prefix +
|
90
|
+
(colour ? Rainbow(message).green.bright.bold : message)
|
91
|
+
indent!(1)
|
84
92
|
result
|
85
93
|
end
|
86
94
|
|
@@ -88,7 +96,7 @@ module Parlour
|
|
88
96
|
# @param [String] message The element.
|
89
97
|
# @return [String] The line of this tree which should be printed.
|
90
98
|
sig { params(message: String).returns(String) }
|
91
|
-
def
|
99
|
+
def here(message)
|
92
100
|
line_prefix + '├' + text_prefix + message
|
93
101
|
end
|
94
102
|
|
@@ -97,16 +105,16 @@ module Parlour
|
|
97
105
|
# @param [String] message The element.
|
98
106
|
# @return [String] The line of this tree which should be printed.
|
99
107
|
sig { params(message: String).returns(String) }
|
100
|
-
def
|
108
|
+
def end(message)
|
101
109
|
result = line_prefix + '└' + text_prefix + message
|
102
|
-
|
110
|
+
indent!(-1)
|
103
111
|
result
|
104
112
|
end
|
105
113
|
|
106
114
|
# The prefix which should be printed before anything else on this line of
|
107
115
|
# the tree, based on the current indent level.
|
108
116
|
# @return [String]
|
109
|
-
def
|
117
|
+
def line_prefix
|
110
118
|
@indent_level.times.map { '│' + ' ' * INDENT_SPACES }.join
|
111
119
|
end
|
112
120
|
|
@@ -114,9 +122,14 @@ module Parlour
|
|
114
122
|
# the current element and its text, based on the specified number of
|
115
123
|
# spaces to use for indents.
|
116
124
|
# @return [String]
|
117
|
-
def
|
125
|
+
def text_prefix
|
118
126
|
'─' * (INDENT_SPACES - 1) + " "
|
119
127
|
end
|
128
|
+
|
129
|
+
# Modifies the current indent level by the given offset.
|
130
|
+
def indent!(offset)
|
131
|
+
@indent_level = [0, @indent_level + offset].max
|
132
|
+
end
|
120
133
|
end
|
121
134
|
end
|
122
135
|
end
|
@@ -0,0 +1,54 @@
|
|
1
|
+
# typed: true
|
2
|
+
|
3
|
+
module Parlour
|
4
|
+
module Mixin
|
5
|
+
# Extends a particular type system's Namespace class to provide searchable
|
6
|
+
# children.
|
7
|
+
module Searchable
|
8
|
+
extend T::Sig
|
9
|
+
extend T::Generic
|
10
|
+
|
11
|
+
Child = type_member
|
12
|
+
|
13
|
+
abstract!
|
14
|
+
|
15
|
+
sig { abstract.returns(T::Array[Child]) }
|
16
|
+
def children; end
|
17
|
+
|
18
|
+
sig { params(name: T.nilable(String), type: T.nilable(Class)).returns(Child) }
|
19
|
+
# Finds the first child matching the given predicates.
|
20
|
+
#
|
21
|
+
# @param [String, nil] name The name of the child to filter on, or nil.
|
22
|
+
# @param [Class, nil] type The type of the child to filter on, or nil. The
|
23
|
+
# type is compared using #is_a?.
|
24
|
+
def find(name: nil, type: nil)
|
25
|
+
T.unsafe(children).find { |c| searchable_child_matches(c, name, type) }
|
26
|
+
end
|
27
|
+
|
28
|
+
sig { params(name: T.nilable(String), type: T.nilable(Class)).returns(T::Array[Child]) }
|
29
|
+
# Finds the first child matching the given predicates.
|
30
|
+
#
|
31
|
+
# @param [String, nil] name The name of the child to filter on, or nil.
|
32
|
+
# @param [Class, nil] type The type of the child to filter on, or nil. The
|
33
|
+
# type is compared using #is_a?.
|
34
|
+
def find_all(name: nil, type: nil)
|
35
|
+
T.unsafe(children).select { |c| searchable_child_matches(c, name, type) }
|
36
|
+
end
|
37
|
+
|
38
|
+
private
|
39
|
+
|
40
|
+
sig do
|
41
|
+
params(
|
42
|
+
child: Child,
|
43
|
+
name: T.nilable(String),
|
44
|
+
type: T.nilable(Class)
|
45
|
+
)
|
46
|
+
.returns(T::Boolean)
|
47
|
+
end
|
48
|
+
def searchable_child_matches(child, name, type)
|
49
|
+
(name.nil? ? true : child.name == name) \
|
50
|
+
&& (type.nil? ? true : child.is_a?(type))
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
@@ -80,12 +80,9 @@ module Parlour
|
|
80
80
|
raise 'arbitrary code is never mergeable'
|
81
81
|
end
|
82
82
|
|
83
|
-
sig { override.returns(String) }
|
84
|
-
|
85
|
-
|
86
|
-
# @return [String]
|
87
|
-
def describe
|
88
|
-
"Arbitrary code (#{code})"
|
83
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
84
|
+
def describe_attrs
|
85
|
+
[:code]
|
89
86
|
end
|
90
87
|
|
91
88
|
sig { override.void }
|
@@ -78,6 +78,15 @@ module Parlour
|
|
78
78
|
@type = TypeParser.parse_single_type(@type) if String === @type
|
79
79
|
end
|
80
80
|
|
81
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
82
|
+
def describe_attrs
|
83
|
+
[
|
84
|
+
:kind,
|
85
|
+
{type: type}, # avoid quotes
|
86
|
+
:class_attribute
|
87
|
+
]
|
88
|
+
end
|
89
|
+
|
81
90
|
private
|
82
91
|
|
83
92
|
sig do
|
@@ -5,6 +5,8 @@ module Parlour
|
|
5
5
|
class ClassNamespace < Namespace
|
6
6
|
extend T::Sig
|
7
7
|
|
8
|
+
Child = type_member {{ fixed: RbiObject }}
|
9
|
+
|
8
10
|
sig do
|
9
11
|
params(
|
10
12
|
generator: Generator,
|
@@ -110,13 +112,10 @@ module Parlour
|
|
110
112
|
end
|
111
113
|
end
|
112
114
|
|
113
|
-
sig { override.returns(String) }
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
"Class #{name} - #{"superclass #{superclass}, " if superclass}" +
|
118
|
-
"#{"abstract, " if abstract}#{children.length} children, " +
|
119
|
-
"#{includes.length} includes, #{extends.length} extends"
|
115
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
116
|
+
def describe_attrs
|
117
|
+
(superclass ? [:superclass] : []) \
|
118
|
+
+ [:children, :abstract, :final, :sealed]
|
120
119
|
end
|
121
120
|
|
122
121
|
sig { override.void }
|
@@ -95,12 +95,9 @@ module Parlour
|
|
95
95
|
# We don't need to change anything! We only merge identical constants
|
96
96
|
end
|
97
97
|
|
98
|
-
sig { override.returns(String) }
|
99
|
-
|
100
|
-
|
101
|
-
# @return [String]
|
102
|
-
def describe
|
103
|
-
"Constant (#{name} = #{value})"
|
98
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
99
|
+
def describe_attrs
|
100
|
+
[:value, :eigen_constant]
|
104
101
|
end
|
105
102
|
|
106
103
|
sig { override.void }
|
@@ -5,6 +5,8 @@ module Parlour
|
|
5
5
|
class EnumClassNamespace < ClassNamespace
|
6
6
|
extend T::Sig
|
7
7
|
|
8
|
+
Child = type_member {{ fixed: RbiObject }}
|
9
|
+
|
8
10
|
sig do
|
9
11
|
params(
|
10
12
|
generator: Generator,
|
@@ -114,6 +116,11 @@ module Parlour
|
|
114
116
|
def generalize_from_rbi!
|
115
117
|
super
|
116
118
|
end
|
119
|
+
|
120
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
121
|
+
def describe_attrs
|
122
|
+
super + [{enums: enums.inspect}]
|
123
|
+
end
|
117
124
|
end
|
118
125
|
end
|
119
126
|
end
|
@@ -75,16 +75,13 @@ module Parlour
|
|
75
75
|
# We don't need to change anything! We only merge identical extends
|
76
76
|
end
|
77
77
|
|
78
|
-
sig { override.returns(String) }
|
79
|
-
# Returns a human-readable brief string description of this code.
|
80
|
-
#
|
81
|
-
# @return [String]
|
82
|
-
def describe
|
83
|
-
"Extend (#{name})"
|
84
|
-
end
|
85
|
-
|
86
78
|
sig { override.void }
|
87
79
|
def generalize_from_rbi!; end # Nothing to do
|
80
|
+
|
81
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
82
|
+
def describe_attrs
|
83
|
+
[]
|
84
|
+
end
|
88
85
|
end
|
89
86
|
end
|
90
87
|
end
|
@@ -75,16 +75,13 @@ module Parlour
|
|
75
75
|
# We don't need to change anything! We only merge identical includes
|
76
76
|
end
|
77
77
|
|
78
|
-
sig { override.returns(String) }
|
79
|
-
# Returns a human-readable brief string description of this code.
|
80
|
-
#
|
81
|
-
# @return [String]
|
82
|
-
def describe
|
83
|
-
"Include (#{name})"
|
84
|
-
end
|
85
|
-
|
86
78
|
sig { override.void }
|
87
79
|
def generalize_from_rbi!; end # Nothing to do
|
80
|
+
|
81
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
82
|
+
def describe_attrs
|
83
|
+
[]
|
84
|
+
end
|
88
85
|
end
|
89
86
|
end
|
90
87
|
end
|
@@ -206,16 +206,6 @@ module Parlour
|
|
206
206
|
# We don't need to change anything! We only merge identical methods
|
207
207
|
end
|
208
208
|
|
209
|
-
sig { override.returns(String) }
|
210
|
-
# Returns a human-readable brief string description of this method.
|
211
|
-
#
|
212
|
-
# @return [String]
|
213
|
-
def describe
|
214
|
-
# TODO: more info
|
215
|
-
"Method #{name} - #{parameters.length} parameters, " +
|
216
|
-
" returns #{return_type}"
|
217
|
-
end
|
218
|
-
|
219
209
|
sig { override.void }
|
220
210
|
def generalize_from_rbi!
|
221
211
|
@return_type = TypeParser.parse_single_type(@return_type) if String === @return_type
|
@@ -223,6 +213,21 @@ module Parlour
|
|
223
213
|
parameters.each(&:generalize_from_rbi!)
|
224
214
|
end
|
225
215
|
|
216
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
217
|
+
def describe_attrs
|
218
|
+
(type_parameters.any? ? [{ type_parameters: type_parameters.join(", ")}] : []) \
|
219
|
+
+ [
|
220
|
+
{parameters: "(#{parameters.map(&:describe_in_method).join(", ")})"},
|
221
|
+
{return_type: return_type || '(void)'}, # avoid quotes
|
222
|
+
:class_method,
|
223
|
+
:abstract,
|
224
|
+
:implementation,
|
225
|
+
:override,
|
226
|
+
:overridable,
|
227
|
+
:final,
|
228
|
+
]
|
229
|
+
end
|
230
|
+
|
226
231
|
private
|
227
232
|
|
228
233
|
sig do
|
@@ -5,6 +5,8 @@ module Parlour
|
|
5
5
|
class ModuleNamespace < Namespace
|
6
6
|
extend T::Sig
|
7
7
|
|
8
|
+
Child = type_member {{ fixed: RbiObject }}
|
9
|
+
|
8
10
|
sig do
|
9
11
|
params(
|
10
12
|
generator: Generator,
|
@@ -100,19 +102,15 @@ module Parlour
|
|
100
102
|
super
|
101
103
|
end
|
102
104
|
|
103
|
-
sig { override.returns(String) }
|
104
|
-
# Returns a human-readable brief string description of this module.
|
105
|
-
# @return [String]
|
106
|
-
def describe
|
107
|
-
"Module #{name} - #{"interface, " if interface}" +
|
108
|
-
"#{"abstract, " if abstract}#{children.length} " +
|
109
|
-
"children, #{includes.length} includes, #{extends.length} extends"
|
110
|
-
end
|
111
|
-
|
112
105
|
sig { override.void }
|
113
106
|
def generalize_from_rbi!
|
114
107
|
super
|
115
108
|
end
|
109
|
+
|
110
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
111
|
+
def describe_attrs
|
112
|
+
[:children, :abstract, :interface, :final, :sealed]
|
113
|
+
end
|
116
114
|
end
|
117
115
|
end
|
118
116
|
end
|
@@ -5,6 +5,7 @@ module Parlour
|
|
5
5
|
# {RbiGenerator#root}.
|
6
6
|
class Namespace < RbiObject
|
7
7
|
extend T::Sig
|
8
|
+
extend T::Generic
|
8
9
|
|
9
10
|
sig do
|
10
11
|
override.overridable.params(
|
@@ -60,11 +61,14 @@ module Parlour
|
|
60
61
|
# @return [Boolean]
|
61
62
|
attr_reader :sealed
|
62
63
|
|
63
|
-
sig { returns(T::Array[RbiObject]) }
|
64
|
+
sig { override.returns(T::Array[RbiObject]).checked(:never) }
|
64
65
|
# The child {RbiObject} instances inside this namespace.
|
65
66
|
# @return [Array<RbiObject>]
|
66
67
|
attr_reader :children
|
67
68
|
|
69
|
+
include Mixin::Searchable
|
70
|
+
Child = type_member {{ fixed: RbiObject }}
|
71
|
+
|
68
72
|
sig { returns(T::Array[RbiGenerator::Extend]) }
|
69
73
|
# The {RbiGenerator::Extend} objects from {children}.
|
70
74
|
# @return [Array<RbiGenerator::Extend>]
|
@@ -647,20 +651,16 @@ module Parlour
|
|
647
651
|
end
|
648
652
|
end
|
649
653
|
|
650
|
-
sig { override.overridable.returns(String) }
|
651
|
-
# Returns a human-readable brief string description of this namespace.
|
652
|
-
#
|
653
|
-
# @return [String]
|
654
|
-
def describe
|
655
|
-
"Namespace #{name} - #{children.length} children, #{includes.length} " +
|
656
|
-
"includes, #{extends.length} extends, #{constants.length} constants"
|
657
|
-
end
|
658
|
-
|
659
654
|
sig { override.void }
|
660
655
|
def generalize_from_rbi!
|
661
656
|
children.each(&:generalize_from_rbi!)
|
662
657
|
end
|
663
658
|
|
659
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
660
|
+
def describe_attrs
|
661
|
+
[:children, :final, :sealed]
|
662
|
+
end
|
663
|
+
|
664
664
|
private
|
665
665
|
|
666
666
|
sig do
|
@@ -134,6 +134,18 @@ module Parlour
|
|
134
134
|
def generalize_from_rbi!
|
135
135
|
@type = TypeParser.parse_single_type(@type) if String === @type
|
136
136
|
end
|
137
|
+
|
138
|
+
sig { returns(String) }
|
139
|
+
def describe_in_method
|
140
|
+
t = type
|
141
|
+
t = t.is_a?(String) ? t : t.describe
|
142
|
+
|
143
|
+
if default
|
144
|
+
"#{name}: #{t} = #{default}"
|
145
|
+
else
|
146
|
+
"#{name}: #{t}"
|
147
|
+
end
|
148
|
+
end
|
137
149
|
end
|
138
150
|
end
|
139
151
|
end
|
@@ -69,11 +69,6 @@ module Parlour
|
|
69
69
|
# @return [void]
|
70
70
|
def merge_into_self(others); end
|
71
71
|
|
72
|
-
sig { override.overridable.returns(String) }
|
73
|
-
def describe
|
74
|
-
'RBI object'
|
75
|
-
end
|
76
|
-
|
77
72
|
sig { abstract.void }
|
78
73
|
# Assuming that the types throughout this object and its children have
|
79
74
|
# been specified as RBI-style types, generalises them into type instances
|
@@ -6,6 +6,8 @@ module Parlour
|
|
6
6
|
class StructClassNamespace < ClassNamespace
|
7
7
|
extend T::Sig
|
8
8
|
|
9
|
+
Child = type_member {{ fixed: RbiObject }}
|
10
|
+
|
9
11
|
sig do
|
10
12
|
params(
|
11
13
|
generator: Generator,
|
@@ -107,6 +109,11 @@ module Parlour
|
|
107
109
|
|
108
110
|
props.each(&:generalize_from_rbi!)
|
109
111
|
end
|
112
|
+
|
113
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
114
|
+
def describe_attrs
|
115
|
+
super + [{props: "(#{props.map(&:name)})"}]
|
116
|
+
end
|
110
117
|
end
|
111
118
|
end
|
112
119
|
end
|
@@ -84,18 +84,15 @@ module Parlour
|
|
84
84
|
# We don't need to change anything! We only merge identical type alias
|
85
85
|
end
|
86
86
|
|
87
|
-
sig { override.returns(String) }
|
88
|
-
# Returns a human-readable brief string description of this code.
|
89
|
-
#
|
90
|
-
# @return [String]
|
91
|
-
def describe
|
92
|
-
"Type Alias (#{name} = #{type})"
|
93
|
-
end
|
94
|
-
|
95
87
|
sig { override.void }
|
96
88
|
def generalize_from_rbi!
|
97
89
|
@type = TypeParser.parse_single_type(@type) if String === @type
|
98
90
|
end
|
91
|
+
|
92
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
93
|
+
def describe_attrs
|
94
|
+
[{type: type}] # avoid quotes
|
95
|
+
end
|
99
96
|
end
|
100
97
|
end
|
101
98
|
end
|
@@ -21,22 +21,7 @@ module Parlour
|
|
21
21
|
#
|
22
22
|
# @return [String] The generated RBI file
|
23
23
|
def rbi(strictness = 'strong')
|
24
|
-
#
|
25
|
-
# Absolutely remove this later on
|
26
|
-
if ENV['PARLOUR_CONVERT_TO_RBS']
|
27
|
-
# Perform conversion
|
28
|
-
root.generalize_from_rbi!
|
29
|
-
rbs_gen = Parlour::RbsGenerator.new
|
30
|
-
converter = Parlour::Conversion::RbiToRbs.new(rbs_gen)
|
31
|
-
root.children.each do |child|
|
32
|
-
converter.convert_object(child, rbs_gen.root)
|
33
|
-
end
|
34
|
-
|
35
|
-
# Write the final RBS
|
36
|
-
rbs_gen.rbs
|
37
|
-
else
|
38
|
-
"# typed: #{strictness}\n" + root.generate_rbi(0, options).join("\n") + "\n"
|
39
|
-
end
|
24
|
+
"# typed: #{strictness}\n" + root.generate_rbi(0, options).join("\n") + "\n"
|
40
25
|
end
|
41
26
|
end
|
42
27
|
end
|
@@ -80,12 +80,9 @@ module Parlour
|
|
80
80
|
raise 'arbitrary code is never mergeable'
|
81
81
|
end
|
82
82
|
|
83
|
-
sig { override.returns(String) }
|
84
|
-
|
85
|
-
|
86
|
-
# @return [String]
|
87
|
-
def describe
|
88
|
-
"Arbitrary code (#{code})"
|
83
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
84
|
+
def describe_attrs
|
85
|
+
[:code]
|
89
86
|
end
|
90
87
|
end
|
91
88
|
end
|
@@ -77,6 +77,14 @@ module Parlour
|
|
77
77
|
super(other) && Attribute === other && kind == other.kind
|
78
78
|
)
|
79
79
|
end
|
80
|
+
|
81
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
82
|
+
def describe_attrs
|
83
|
+
[
|
84
|
+
:kind,
|
85
|
+
:class_attribute
|
86
|
+
]
|
87
|
+
end
|
80
88
|
end
|
81
89
|
end
|
82
90
|
end
|
@@ -5,6 +5,8 @@ module Parlour
|
|
5
5
|
class ClassNamespace < Namespace
|
6
6
|
extend T::Sig
|
7
7
|
|
8
|
+
Child = type_member {{ fixed: RbsObject }}
|
9
|
+
|
8
10
|
sig do
|
9
11
|
params(
|
10
12
|
generator: Generator,
|
@@ -18,10 +20,8 @@ module Parlour
|
|
18
20
|
#
|
19
21
|
# @param generator [RbsGenerator] The current RbsGenerator.
|
20
22
|
# @param name [String] The name of this class.
|
21
|
-
# @param final [Boolean] Whether this namespace is final.
|
22
23
|
# @param superclass [String, nil] The superclass of this class, or nil if it doesn't
|
23
24
|
# have one.
|
24
|
-
# @param abstract [Boolean] A boolean indicating whether this class is abstract.
|
25
25
|
# @param block A block which the new instance yields itself to.
|
26
26
|
# @return [void]
|
27
27
|
def initialize(generator, name, superclass, &block)
|
@@ -93,13 +93,9 @@ module Parlour
|
|
93
93
|
end
|
94
94
|
end
|
95
95
|
|
96
|
-
sig { override.returns(String) }
|
97
|
-
|
98
|
-
|
99
|
-
def describe
|
100
|
-
"Class #{name} - #{"superclass #{superclass}, " if superclass}" +
|
101
|
-
"#{children.length} children, " +
|
102
|
-
"#{includes.length} includes, #{extends.length} extends"
|
96
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
97
|
+
def describe_attrs
|
98
|
+
(superclass ? [:superclass] : []) + [:children]
|
103
99
|
end
|
104
100
|
end
|
105
101
|
end
|
@@ -83,12 +83,9 @@ module Parlour
|
|
83
83
|
# We don't need to change anything! We only merge identical constants
|
84
84
|
end
|
85
85
|
|
86
|
-
sig { override.returns(String) }
|
87
|
-
|
88
|
-
|
89
|
-
# @return [String]
|
90
|
-
def describe
|
91
|
-
"Constant (#{name} = #{type})"
|
86
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
87
|
+
def describe_attrs
|
88
|
+
[{type: type}] # avoid quotes
|
92
89
|
end
|
93
90
|
end
|
94
91
|
end
|
@@ -80,12 +80,9 @@ module Parlour
|
|
80
80
|
# We don't need to change anything! We only merge identical extends
|
81
81
|
end
|
82
82
|
|
83
|
-
sig { override.returns(String) }
|
84
|
-
|
85
|
-
|
86
|
-
# @return [String]
|
87
|
-
def describe
|
88
|
-
"Extend (#{@type})"
|
83
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
84
|
+
def describe_attrs
|
85
|
+
[{type: type}] # avoid quotes
|
89
86
|
end
|
90
87
|
end
|
91
88
|
end
|
@@ -80,12 +80,9 @@ module Parlour
|
|
80
80
|
# We don't need to change anything! We only merge identical includes
|
81
81
|
end
|
82
82
|
|
83
|
-
sig { override.returns(String) }
|
84
|
-
|
85
|
-
|
86
|
-
# @return [String]
|
87
|
-
def describe
|
88
|
-
"Include (#{@type})"
|
83
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
84
|
+
def describe_attrs
|
85
|
+
[{type: type}] # avoid quotes
|
89
86
|
end
|
90
87
|
end
|
91
88
|
end
|
@@ -5,6 +5,8 @@ module Parlour
|
|
5
5
|
class InterfaceNamespace < Namespace
|
6
6
|
extend T::Sig
|
7
7
|
|
8
|
+
Child = type_member {{ fixed: RbsObject }}
|
9
|
+
|
8
10
|
sig do
|
9
11
|
override.params(
|
10
12
|
indent_level: Integer,
|
@@ -23,11 +25,9 @@ module Parlour
|
|
23
25
|
lines << options.indented(indent_level, "end")
|
24
26
|
end
|
25
27
|
|
26
|
-
sig { override.returns(String) }
|
27
|
-
|
28
|
-
|
29
|
-
def describe
|
30
|
-
"Interface #{name} - #{children.length}"
|
28
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
29
|
+
def describe_attrs
|
30
|
+
[:children]
|
31
31
|
end
|
32
32
|
end
|
33
33
|
end
|
@@ -133,13 +133,12 @@ module Parlour
|
|
133
133
|
# TODO: merge signatures of different definitions
|
134
134
|
end
|
135
135
|
|
136
|
-
sig { override.returns(String) }
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
|
142
|
-
"Method #{name} - #{signatures.length} signatures"
|
136
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
137
|
+
def describe_attrs
|
138
|
+
[
|
139
|
+
{signatures: "(#{signatures.map(&:describe_in_method).join(", ")})"},
|
140
|
+
:class_method,
|
141
|
+
]
|
143
142
|
end
|
144
143
|
end
|
145
144
|
end
|
@@ -99,6 +99,19 @@ module Parlour
|
|
99
99
|
|
100
100
|
generated_params
|
101
101
|
end
|
102
|
+
|
103
|
+
sig { returns(String) }
|
104
|
+
def describe_in_method
|
105
|
+
# RBS is terse enough that just describing using the RBS is probably
|
106
|
+
# fine. (Unfortunately, this doesn't allow any differentiation between
|
107
|
+
# string types and Parlour::Types types.)
|
108
|
+
# (#describe is supposed to be one line, but this will break if you
|
109
|
+
# have than 10000 parameters. Honestly, if you do have more than 10000
|
110
|
+
# parameters, you deserve this...)
|
111
|
+
generate_rbs(Parlour::Options.new(
|
112
|
+
break_params: 10000, tab_size: 2, sort_namespaces: false
|
113
|
+
)).join("\n")
|
114
|
+
end
|
102
115
|
end
|
103
116
|
end
|
104
117
|
end
|
@@ -5,6 +5,8 @@ module Parlour
|
|
5
5
|
class ModuleNamespace < Namespace
|
6
6
|
extend T::Sig
|
7
7
|
|
8
|
+
Child = type_member {{ fixed: RbsObject }}
|
9
|
+
|
8
10
|
sig do
|
9
11
|
override.params(
|
10
12
|
indent_level: Integer,
|
@@ -23,12 +25,9 @@ module Parlour
|
|
23
25
|
lines << options.indented(indent_level, "end")
|
24
26
|
end
|
25
27
|
|
26
|
-
sig { override.returns(String) }
|
27
|
-
|
28
|
-
|
29
|
-
def describe
|
30
|
-
"Module #{name} - #{children.length} " +
|
31
|
-
"children, #{includes.length} includes, #{extends.length} extends"
|
28
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
29
|
+
def describe_attrs
|
30
|
+
[:children]
|
32
31
|
end
|
33
32
|
end
|
34
33
|
end
|
@@ -5,6 +5,7 @@ module Parlour
|
|
5
5
|
# {RbsGenerator#root}.
|
6
6
|
class Namespace < RbsObject
|
7
7
|
extend T::Sig
|
8
|
+
extend T::Generic
|
8
9
|
|
9
10
|
sig do
|
10
11
|
override.overridable.params(
|
@@ -45,11 +46,14 @@ module Parlour
|
|
45
46
|
yield_self(&block) if block
|
46
47
|
end
|
47
48
|
|
48
|
-
sig { returns(T::Array[RbsObject]) }
|
49
|
+
sig { override.returns(T::Array[RbsObject]).checked(:never) }
|
49
50
|
# The child {RbsObject} instances inside this namespace.
|
50
51
|
# @return [Array<RbsObject>]
|
51
52
|
attr_reader :children
|
52
53
|
|
54
|
+
include Mixin::Searchable
|
55
|
+
Child = type_member {{ fixed: RbsObject }}
|
56
|
+
|
53
57
|
sig { returns(T::Array[RbsGenerator::Extend]) }
|
54
58
|
# The {RbsGenerator::Extend} objects from {children}.
|
55
59
|
# @return [Array<RbsGenerator::Extend>]
|
@@ -517,13 +521,9 @@ module Parlour
|
|
517
521
|
end
|
518
522
|
end
|
519
523
|
|
520
|
-
sig { override.
|
521
|
-
|
522
|
-
|
523
|
-
# @return [String]
|
524
|
-
def describe
|
525
|
-
"Namespace #{name} - #{children.length} children, #{includes.length} " +
|
526
|
-
"includes, #{extends.length} extends, #{constants.length} constants"
|
524
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
525
|
+
def describe_attrs
|
526
|
+
[:children]
|
527
527
|
end
|
528
528
|
|
529
529
|
private
|
@@ -68,11 +68,6 @@ module Parlour
|
|
68
68
|
# @param others [Array<RbsGenerator::RbsObject>] An array of other {RbsObject} instances.
|
69
69
|
# @return [void]
|
70
70
|
def merge_into_self(others); end
|
71
|
-
|
72
|
-
sig { overridable.override.returns(String) }
|
73
|
-
def describe
|
74
|
-
'RBS object'
|
75
|
-
end
|
76
71
|
end
|
77
72
|
end
|
78
73
|
end
|
@@ -84,12 +84,9 @@ module Parlour
|
|
84
84
|
# We don't need to change anything! We only merge identical type alias
|
85
85
|
end
|
86
86
|
|
87
|
-
sig { override.returns(String) }
|
88
|
-
|
89
|
-
|
90
|
-
# @return [String]
|
91
|
-
def describe
|
92
|
-
"Type Alias (#{name} = #{type})"
|
87
|
+
sig { override.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
88
|
+
def describe_attrs
|
89
|
+
[{type: type}] # avoid quotes
|
93
90
|
end
|
94
91
|
end
|
95
92
|
end
|
data/lib/parlour/type_loader.rb
CHANGED
@@ -60,7 +60,12 @@ module Parlour
|
|
60
60
|
chdir: root
|
61
61
|
)
|
62
62
|
|
63
|
-
|
63
|
+
stdout = T.must(stdout.read)
|
64
|
+
if stdout == ''
|
65
|
+
raise 'unable to get Sorbet file table; the project may be empty or not have Sorbet initialised'
|
66
|
+
end
|
67
|
+
|
68
|
+
file_table_hash = JSON.parse(stdout)
|
64
69
|
file_table_entries = file_table_hash['files']
|
65
70
|
|
66
71
|
namespaces = T.let([], T::Array[Parlour::RbiGenerator::Namespace])
|
data/lib/parlour/type_parser.rb
CHANGED
@@ -361,8 +361,8 @@ module Parlour
|
|
361
361
|
# (block (send (const nil :T) :type_alias) (args) (type_to_alias))
|
362
362
|
if body.type == :block &&
|
363
363
|
body.to_a[0].type == :send &&
|
364
|
-
body.to_a[0].to_a[0]
|
365
|
-
body.to_a[0].to_a[0]
|
364
|
+
body.to_a[0].to_a[0]&.type == :const &&
|
365
|
+
body.to_a[0].to_a[0]&.to_a == [nil, :T] &&
|
366
366
|
body.to_a[0].to_a[1] == :type_alias
|
367
367
|
|
368
368
|
[Parlour::RbiGenerator::TypeAlias.new(
|
data/lib/parlour/typed_object.rb
CHANGED
@@ -57,16 +57,101 @@ module Parlour
|
|
57
57
|
|
58
58
|
alias_method :add_comments, :add_comment
|
59
59
|
|
60
|
-
sig {
|
60
|
+
sig { returns(String) }
|
61
61
|
# Returns a human-readable brief string description of this object. This
|
62
62
|
# is displayed during manual conflict resolution with the +parlour+ CLI.
|
63
63
|
#
|
64
|
-
# @abstract
|
65
64
|
# @return [String]
|
66
|
-
def describe
|
65
|
+
def describe
|
66
|
+
if is_a?(RbiGenerator::RbiObject)
|
67
|
+
type_system = 'RBI'
|
68
|
+
elsif is_a?(RbsGenerator::RbsObject)
|
69
|
+
type_system = 'RBS'
|
70
|
+
else
|
71
|
+
raise 'unknown type system'
|
72
|
+
end
|
73
|
+
|
74
|
+
attr_strings = describe_attrs.map do |a|
|
75
|
+
case a
|
76
|
+
when Symbol
|
77
|
+
key = a
|
78
|
+
value = send(a)
|
79
|
+
|
80
|
+
case value
|
81
|
+
when Array, Hash
|
82
|
+
value = value.length
|
83
|
+
next nil if value == 0
|
84
|
+
when String
|
85
|
+
value = value.inspect
|
86
|
+
when Parlour::Types::Type
|
87
|
+
value = value.describe
|
88
|
+
when true
|
89
|
+
next key
|
90
|
+
when false
|
91
|
+
next nil
|
92
|
+
end
|
93
|
+
when Hash
|
94
|
+
raise 'describe_attrs Hash must have one key' unless a.length == 1
|
95
|
+
|
96
|
+
key = a.keys[0]
|
97
|
+
value = a.values[0]
|
98
|
+
end
|
99
|
+
|
100
|
+
"#{key}=#{value}"
|
101
|
+
end.compact
|
102
|
+
|
103
|
+
class_name = T.must(self.class.name).split('::').last
|
104
|
+
if attr_strings.empty?
|
105
|
+
"<#{type_system}:#{class_name}:#{name}>"
|
106
|
+
else
|
107
|
+
"<#{type_system}:#{class_name}:#{name} #{attr_strings.join(" ")}>"
|
108
|
+
end
|
109
|
+
end
|
110
|
+
|
111
|
+
sig { params(tree: T.nilable(Debugging::Tree)).returns(String) }
|
112
|
+
# Returns a human-readable multi-line string description of this object and
|
113
|
+
# its children recursively.
|
114
|
+
#
|
115
|
+
# @return [String]
|
116
|
+
def describe_tree(tree: nil)
|
117
|
+
if tree.nil?
|
118
|
+
tree = Debugging::Tree.new
|
119
|
+
result = "#{describe}\n"
|
120
|
+
else
|
121
|
+
result = ""
|
122
|
+
end
|
123
|
+
|
124
|
+
if is_a?(RbiGenerator::Namespace) || is_a?(RbsGenerator::Namespace)
|
125
|
+
children.each do |child|
|
126
|
+
result += "#{tree.begin(child.describe)}\n"
|
127
|
+
result += child.describe_tree(tree: tree)
|
128
|
+
tree.indent!(-1)
|
129
|
+
end
|
130
|
+
else
|
131
|
+
"#{describe}\n"
|
132
|
+
end
|
133
|
+
|
134
|
+
result
|
135
|
+
end
|
136
|
+
|
137
|
+
alias inspect describe
|
138
|
+
alias to_s describe
|
67
139
|
|
68
140
|
protected
|
69
141
|
|
142
|
+
sig { abstract.returns(T::Array[T.any(Symbol, T::Hash[Symbol, String])]) }
|
143
|
+
# The attributes for an instance of this object which should be included in
|
144
|
+
# its string form generated by +#describe+.
|
145
|
+
# For each element in the returned array:
|
146
|
+
# - If it is a symbol, this symbol will be called on +self+ and the
|
147
|
+
# returned object will be dynamically converted into a string.
|
148
|
+
# - If it is a hash, it must be of the format { Symbol => String }. The
|
149
|
+
# given string will be used instead of calling the symbol.
|
150
|
+
#
|
151
|
+
# @abstract
|
152
|
+
# @return [<Symbol, String>]
|
153
|
+
def describe_attrs; end
|
154
|
+
|
70
155
|
sig do
|
71
156
|
params(
|
72
157
|
indent_level: Integer,
|
data/lib/parlour/version.rb
CHANGED
data/lib/parlour.rb
CHANGED
@@ -14,6 +14,8 @@ require 'parlour/types'
|
|
14
14
|
require 'parlour/options'
|
15
15
|
require 'parlour/typed_object'
|
16
16
|
require 'parlour/generator'
|
17
|
+
require 'parlour/mixin/searchable'
|
18
|
+
|
17
19
|
require 'parlour/rbi_generator/parameter'
|
18
20
|
require 'parlour/rbi_generator/rbi_object'
|
19
21
|
require 'parlour/rbi_generator/type_alias'
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: parlour
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 7.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Aaron Christiansen
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2022-04-18 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: sorbet-runtime
|
@@ -181,6 +181,7 @@ files:
|
|
181
181
|
- lib/parlour/detached_rbs_generator.rb
|
182
182
|
- lib/parlour/generator.rb
|
183
183
|
- lib/parlour/kernel_hack.rb
|
184
|
+
- lib/parlour/mixin/searchable.rb
|
184
185
|
- lib/parlour/options.rb
|
185
186
|
- lib/parlour/parse_error.rb
|
186
187
|
- lib/parlour/plugin.rb
|
@@ -242,7 +243,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
242
243
|
- !ruby/object:Gem::Version
|
243
244
|
version: '0'
|
244
245
|
requirements: []
|
245
|
-
rubygems_version: 3.2.
|
246
|
+
rubygems_version: 3.2.22
|
246
247
|
signing_key:
|
247
248
|
specification_version: 4
|
248
249
|
summary: A type information generator, merger and parser for Sorbet and Ruby 3/Steep
|