typeprof 0.8.0 → 0.11.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/Gemfile.lock +6 -5
- data/doc/demo.md +1 -1
- data/doc/todo.md +133 -0
- data/lib/typeprof/analyzer.rb +177 -76
- data/lib/typeprof/arguments.rb +2 -0
- data/lib/typeprof/block.rb +40 -2
- data/lib/typeprof/builtin.rb +279 -111
- data/lib/typeprof/cli.rb +5 -0
- data/lib/typeprof/config.rb +15 -1
- data/lib/typeprof/container-type.rb +5 -4
- data/lib/typeprof/export.rb +115 -70
- data/lib/typeprof/import.rb +71 -33
- data/lib/typeprof/iseq.rb +46 -11
- data/lib/typeprof/method.rb +42 -21
- data/lib/typeprof/type.rb +93 -15
- data/lib/typeprof/version.rb +1 -1
- data/smoke/alias.rb +4 -4
- data/smoke/alias2.rb +6 -4
- data/smoke/any1.rb +1 -1
- data/smoke/any2.rb +2 -2
- data/smoke/arguments.rb +2 -2
- data/smoke/arguments2.rb +10 -10
- data/smoke/array-each.rb +1 -1
- data/smoke/array-each2.rb +1 -1
- data/smoke/array-each3.rb +1 -1
- data/smoke/array-ltlt.rb +1 -1
- data/smoke/array-ltlt2.rb +1 -1
- data/smoke/array-map.rb +1 -1
- data/smoke/array-map2.rb +1 -1
- data/smoke/array-map3.rb +3 -3
- data/smoke/array-mul.rb +2 -2
- data/smoke/array-plus1.rb +1 -1
- data/smoke/array-plus2.rb +3 -2
- data/smoke/array-pop.rb +1 -1
- data/smoke/array-range-aref.rb +11 -11
- data/smoke/array-replace.rb +1 -1
- data/smoke/array-s-aref.rb +1 -1
- data/smoke/array1.rb +5 -5
- data/smoke/array10.rb +1 -1
- data/smoke/array11.rb +1 -1
- data/smoke/array12.rb +3 -3
- data/smoke/array13.rb +4 -4
- data/smoke/array14.rb +1 -1
- data/smoke/array15.rb +16 -0
- data/smoke/array2.rb +3 -3
- data/smoke/array3.rb +5 -4
- data/smoke/array4.rb +1 -1
- data/smoke/array5.rb +1 -1
- data/smoke/array6.rb +3 -2
- data/smoke/array7.rb +1 -1
- data/smoke/array8.rb +1 -1
- data/smoke/array9.rb +1 -1
- data/smoke/attr-module.rb +27 -0
- data/smoke/attr-vis.rb +43 -0
- data/smoke/attr-vis.rbs +4 -0
- data/smoke/attr.rb +5 -5
- data/smoke/autoload.rb +1 -1
- data/smoke/backtrace.rb +3 -3
- data/smoke/block-ambiguous.rb +8 -8
- data/smoke/block-args1-rest.rb +12 -11
- data/smoke/block-args1.rb +10 -10
- data/smoke/block-args2-rest.rb +12 -11
- data/smoke/block-args2.rb +10 -10
- data/smoke/block-args3-rest.rb +14 -13
- data/smoke/block-args3.rb +12 -12
- data/smoke/block-blockarg.rb +4 -4
- data/smoke/block-kwarg.rb +10 -10
- data/smoke/block1.rb +1 -1
- data/smoke/block10.rb +1 -1
- data/smoke/block11.rb +5 -5
- data/smoke/block12.rb +2 -2
- data/smoke/block14.rb +2 -2
- data/smoke/block2.rb +1 -1
- data/smoke/block3.rb +3 -3
- data/smoke/block4.rb +2 -2
- data/smoke/block5.rb +3 -2
- data/smoke/block6.rb +2 -2
- data/smoke/block7.rb +1 -1
- data/smoke/block8.rb +3 -3
- data/smoke/block9.rb +1 -1
- data/smoke/block_given.rb +37 -0
- data/smoke/blown.rb +1 -1
- data/smoke/break1.rb +2 -2
- data/smoke/break2.rb +1 -1
- data/smoke/break3.rb +13 -0
- data/smoke/case.rb +1 -1
- data/smoke/case2.rb +1 -1
- data/smoke/case3.rb +17 -0
- data/smoke/class-hierarchy.rb +5 -5
- data/smoke/class-hierarchy2.rb +3 -3
- data/smoke/class-new.rb +15 -0
- data/smoke/class_instance_var.rb +1 -1
- data/smoke/class_method.rb +2 -2
- data/smoke/class_method2.rb +2 -2
- data/smoke/class_method3.rb +2 -2
- data/smoke/constant1.rb +6 -6
- data/smoke/constant2.rb +5 -4
- data/smoke/constant3.rb +1 -1
- data/smoke/constant4.rb +1 -1
- data/smoke/context-sensitive1.rb +1 -1
- data/smoke/cvar.rb +6 -5
- data/smoke/cvar2.rb +2 -2
- data/smoke/define_method.rb +2 -2
- data/smoke/define_method2.rb +2 -2
- data/smoke/define_method3.rb +14 -0
- data/smoke/define_method3.rbs +3 -0
- data/smoke/define_method4.rb +15 -0
- data/smoke/define_method4.rbs +3 -0
- data/smoke/define_method5.rb +12 -0
- data/smoke/define_method6.rb +19 -0
- data/smoke/demo.rb +6 -6
- data/smoke/demo1.rb +1 -1
- data/smoke/demo10.rb +2 -2
- data/smoke/demo11.rb +1 -1
- data/smoke/demo2.rb +1 -1
- data/smoke/demo3.rb +1 -1
- data/smoke/demo4.rb +3 -3
- data/smoke/demo5.rb +1 -1
- data/smoke/demo6.rb +4 -3
- data/smoke/demo7.rb +1 -1
- data/smoke/demo8.rb +2 -2
- data/smoke/demo9.rb +3 -2
- data/smoke/dummy-execution1.rb +2 -2
- data/smoke/dummy-execution2.rb +2 -2
- data/smoke/dummy_element.rb +14 -0
- data/smoke/ensure1.rb +2 -2
- data/smoke/enum_for.rb +15 -0
- data/smoke/enum_for2.rb +17 -0
- data/smoke/enumerator.rb +2 -2
- data/smoke/expandarray1.rb +1 -1
- data/smoke/expandarray2.rb +1 -1
- data/smoke/fib.rb +2 -2
- data/smoke/flip-flop.rb +28 -0
- data/smoke/flow1.rb +1 -1
- data/smoke/flow10.rb +17 -0
- data/smoke/flow2.rb +1 -1
- data/smoke/flow3.rb +1 -1
- data/smoke/flow5.rb +1 -1
- data/smoke/flow6.rb +1 -1
- data/smoke/flow7.rb +1 -1
- data/smoke/flow8.rb +1 -1
- data/smoke/flow9.rb +12 -0
- data/smoke/freeze.rb +1 -1
- data/smoke/function.rb +2 -2
- data/smoke/gvar.rb +2 -2
- data/smoke/gvar2.rb +3 -3
- data/smoke/hash-bot.rb +12 -0
- data/smoke/hash-fetch.rb +3 -3
- data/smoke/hash-merge-bang.rb +1 -1
- data/smoke/hash1.rb +2 -2
- data/smoke/hash2.rb +1 -1
- data/smoke/hash3.rb +1 -1
- data/smoke/hash4.rb +1 -1
- data/smoke/hash5.rb +1 -1
- data/smoke/inheritance.rb +4 -4
- data/smoke/inheritance2.rb +2 -2
- data/smoke/initialize.rb +6 -5
- data/smoke/instance_eval.rb +2 -2
- data/smoke/instance_eval2.rb +10 -0
- data/smoke/instance_eval3.rb +25 -0
- data/smoke/int_times.rb +1 -1
- data/smoke/integer.rb +1 -1
- data/smoke/ivar.rb +5 -4
- data/smoke/ivar2.rb +4 -4
- data/smoke/ivar3.rb +4 -3
- data/smoke/ivar4.rb +21 -0
- data/smoke/kernel-class.rb +1 -1
- data/smoke/keyword1.rb +1 -1
- data/smoke/keyword2.rb +1 -1
- data/smoke/keyword3.rb +1 -1
- data/smoke/keyword4.rb +1 -1
- data/smoke/keyword5.rb +1 -1
- data/smoke/kwrest.rb +3 -2
- data/smoke/kwsplat1.rb +4 -4
- data/smoke/kwsplat2.rb +1 -1
- data/smoke/lit-complex.rb +10 -0
- data/smoke/lit-encoding.rb +10 -0
- data/smoke/manual-rbs.rb +5 -4
- data/smoke/manual-rbs2.rb +1 -1
- data/smoke/manual-rbs3.rb +3 -2
- data/smoke/masgn1.rb +1 -1
- data/smoke/masgn2.rb +2 -2
- data/smoke/masgn3.rb +1 -1
- data/smoke/method_in_branch.rb +3 -3
- data/smoke/method_missing.rb +5 -4
- data/smoke/module1.rb +2 -2
- data/smoke/module2.rb +1 -1
- data/smoke/module3.rb +3 -3
- data/smoke/module4.rb +3 -2
- data/smoke/module5.rb +17 -0
- data/smoke/module6.rb +40 -0
- data/smoke/module_function1.rb +4 -3
- data/smoke/module_function2.rb +4 -3
- data/smoke/multiple-include.rb +2 -1
- data/smoke/multiple-superclass.rb +1 -1
- data/smoke/next1.rb +2 -2
- data/smoke/next2.rb +1 -1
- data/smoke/object-send1.rb +3 -3
- data/smoke/object-send2.rb +10 -0
- data/smoke/object-send3.rb +18 -0
- data/smoke/once.rb +1 -1
- data/smoke/optional1.rb +1 -1
- data/smoke/optional2.rb +1 -1
- data/smoke/optional3.rb +1 -1
- data/smoke/parameterizedd-self.rb +3 -2
- data/smoke/parameterizedd-self2.rb +1 -1
- data/smoke/pathname1.rb +1 -1
- data/smoke/pathname2.rb +1 -1
- data/smoke/pattern-match1.rb +1 -1
- data/smoke/pattern-match2.rb +1 -1
- data/smoke/prepend1.rb +33 -0
- data/smoke/prepend2.rb +10 -0
- data/smoke/prepend2.rbs +9 -0
- data/smoke/primitive_method.rb +19 -0
- data/smoke/printf.rb +2 -2
- data/smoke/proc.rb +2 -2
- data/smoke/proc2.rb +1 -1
- data/smoke/proc3.rb +1 -1
- data/smoke/proc4.rb +1 -1
- data/smoke/proc5.rb +19 -0
- data/smoke/public.rb +38 -0
- data/smoke/range.rb +1 -1
- data/smoke/rbs-alias.rb +1 -1
- data/smoke/rbs-attr.rb +5 -5
- data/smoke/rbs-attr2.rb +1 -1
- data/smoke/rbs-extend.rb +1 -1
- data/smoke/rbs-interface.rb +4 -4
- data/smoke/rbs-module.rb +26 -0
- data/smoke/rbs-module.rbs +4 -0
- data/smoke/rbs-opt-and-rest.rb +10 -0
- data/smoke/rbs-opt-and-rest.rbs +3 -0
- data/smoke/rbs-proc1.rb +1 -1
- data/smoke/rbs-proc2.rb +2 -2
- data/smoke/rbs-proc3.rb +1 -1
- data/smoke/rbs-record.rb +2 -2
- data/smoke/rbs-tyvar.rb +2 -2
- data/smoke/rbs-tyvar2.rb +2 -2
- data/smoke/rbs-tyvar3.rb +2 -2
- data/smoke/rbs-tyvar4.rb +4 -3
- data/smoke/rbs-tyvar5.rb +1 -1
- data/smoke/rbs-tyvar6.rb +3 -3
- data/smoke/rbs-tyvar7.rb +1 -1
- data/smoke/rbs-vars.rb +6 -6
- data/smoke/redo1.rb +2 -2
- data/smoke/redo2.rb +2 -2
- data/smoke/req-keyword.rb +1 -1
- data/smoke/rescue1.rb +2 -2
- data/smoke/rescue2.rb +2 -2
- data/smoke/rescue3.rb +20 -0
- data/smoke/rescue4.rb +17 -0
- data/smoke/respond_to.rb +1 -1
- data/smoke/rest-farg.rb +1 -1
- data/smoke/rest1.rb +2 -2
- data/smoke/rest2.rb +1 -1
- data/smoke/rest3.rb +6 -6
- data/smoke/rest4.rb +2 -2
- data/smoke/rest5.rb +1 -1
- data/smoke/rest6.rb +1 -1
- data/smoke/retry1.rb +2 -2
- data/smoke/return.rb +1 -1
- data/smoke/simple.rb +12 -0
- data/smoke/singleton_method.rb +1 -1
- data/smoke/step.rb +3 -3
- data/smoke/string-split.rb +1 -1
- data/smoke/struct-keyword_init.rb +10 -0
- data/smoke/struct.rb +1 -1
- data/smoke/struct2.rb +4 -4
- data/smoke/struct3.rb +2 -2
- data/smoke/struct4.rb +7 -0
- data/smoke/struct5.rb +16 -0
- data/smoke/struct6.rb +15 -0
- data/smoke/struct7.rb +17 -0
- data/smoke/stub-keyword.rb +10 -0
- data/smoke/super1.rb +4 -4
- data/smoke/super2.rb +1 -1
- data/smoke/super3.rb +4 -3
- data/smoke/super4.rb +7 -5
- data/smoke/super5.rb +6 -4
- data/smoke/svar1.rb +1 -1
- data/smoke/symbol-proc-attr.rb +22 -0
- data/smoke/symbol-proc-attr2.rb +15 -0
- data/smoke/symbol-proc-bot.rb +13 -0
- data/smoke/symbol-proc.rb +3 -3
- data/smoke/tap1.rb +2 -2
- data/smoke/toplevel.rb +1 -1
- data/smoke/two-map.rb +2 -2
- data/smoke/type_var.rb +3 -3
- data/smoke/typed_method.rb +1 -1
- data/smoke/uninitialize-var.rb +1 -1
- data/smoke/union-recv.rb +2 -2
- data/smoke/user-demo.rb +3 -3
- data/smoke/wrong-extend.rb +3 -2
- data/smoke/wrong-include.rb +3 -2
- data/smoke/wrong-include2.rb +17 -0
- data/typeprof.gemspec +1 -1
- metadata +59 -6
- data/tools/stackprof-wrapper.rb +0 -10
data/lib/typeprof/cli.rb
CHANGED
@@ -20,6 +20,7 @@ module TypeProf
|
|
20
20
|
options = {}
|
21
21
|
dir_filter = nil
|
22
22
|
gem_rbs_features = []
|
23
|
+
gem_repo_dirs = []
|
23
24
|
show_version = false
|
24
25
|
max_sec = max_iter = nil
|
25
26
|
|
@@ -31,6 +32,7 @@ module TypeProf
|
|
31
32
|
opt.on("--version", "Display typeprof version") { show_version = true }
|
32
33
|
opt.on("-I DIR", "Add DIR to the load/require path") {|v| $LOAD_PATH << v }
|
33
34
|
opt.on("-r FEATURE", "Require RBS of the FEATURE gem") {|v| gem_rbs_features << v }
|
35
|
+
opt.on("--repo DIR", "Add DIR to the RBS repository") {|v| gem_repo_dirs << v }
|
34
36
|
|
35
37
|
opt.separator ""
|
36
38
|
opt.separator "Analysis output options:"
|
@@ -48,6 +50,8 @@ module TypeProf
|
|
48
50
|
end
|
49
51
|
opt.on("--[no-]show-errors", "Display possible errors found during the analysis") {|v| options[:show_errors] = v }
|
50
52
|
opt.on("--[no-]show-untyped", "Display \"Foo | untyped\" instead of \"Foo\"") {|v| options[:show_untyped] = v }
|
53
|
+
opt.on("--[no-]show-parameter-names", "Display parameter names for methods") {|v| options[:show_parameter_names] = v }
|
54
|
+
opt.on("--[no-]show-source-locations", "Display definition source locations for methods") {|v| options[:show_source_locations] = v }
|
51
55
|
|
52
56
|
opt.separator ""
|
53
57
|
opt.separator "Analysis limit options:"
|
@@ -85,6 +89,7 @@ module TypeProf
|
|
85
89
|
rbs_files: rbs_files,
|
86
90
|
output: output,
|
87
91
|
gem_rbs_features: gem_rbs_features,
|
92
|
+
gem_repo_dirs: gem_repo_dirs,
|
88
93
|
verbose: verbose,
|
89
94
|
dir_filter: dir_filter,
|
90
95
|
max_sec: max_sec,
|
data/lib/typeprof/config.rb
CHANGED
@@ -6,6 +6,7 @@ module TypeProf
|
|
6
6
|
:rbs_files,
|
7
7
|
:output,
|
8
8
|
:gem_rbs_features,
|
9
|
+
:gem_repo_dirs,
|
9
10
|
:verbose,
|
10
11
|
:dir_filter,
|
11
12
|
:max_iter,
|
@@ -14,10 +15,18 @@ module TypeProf
|
|
14
15
|
keyword_init: true
|
15
16
|
)
|
16
17
|
|
18
|
+
class TypeProfError < StandardError
|
19
|
+
def report(output)
|
20
|
+
output.puts "# Analysis Error"
|
21
|
+
output.puts message
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
17
25
|
class ConfigData
|
18
26
|
def initialize(**opt)
|
19
27
|
opt[:output] ||= $stdout
|
20
28
|
opt[:gem_rbs_features] ||= []
|
29
|
+
opt[:gem_repo_dirs] ||= []
|
21
30
|
opt[:dir_filter] ||= DEFAULT_DIR_FILTER
|
22
31
|
opt[:verbose] ||= 0
|
23
32
|
opt[:options] ||= {}
|
@@ -25,6 +34,8 @@ module TypeProf
|
|
25
34
|
show_indicator: true,
|
26
35
|
show_untyped: false,
|
27
36
|
show_errors: false,
|
37
|
+
show_parameter_names: true,
|
38
|
+
show_source_locations: false,
|
28
39
|
stub_execution: true,
|
29
40
|
type_depth_limit: 5,
|
30
41
|
stackprof: nil,
|
@@ -69,7 +80,7 @@ module TypeProf
|
|
69
80
|
|
70
81
|
prologue_ctx = Context.new(nil, nil, nil)
|
71
82
|
prologue_ep = ExecutionPoint.new(prologue_ctx, -1, nil)
|
72
|
-
prologue_env = Env.new(StaticEnv.new(
|
83
|
+
prologue_env = Env.new(StaticEnv.new(Type.bot, Type.nil, false, true), [], [], Utils::HashWrapper.new({}))
|
73
84
|
|
74
85
|
Config.rb_files.each do |rb|
|
75
86
|
if rb.is_a?(Array) # [String name, String content]
|
@@ -100,6 +111,9 @@ module TypeProf
|
|
100
111
|
end
|
101
112
|
end
|
102
113
|
|
114
|
+
rescue TypeProfError => exc
|
115
|
+
exc.report(Config.output)
|
116
|
+
|
103
117
|
ensure
|
104
118
|
if Config.options[:stackprof] && defined?(StackProf)
|
105
119
|
StackProf.stop
|
@@ -208,10 +208,6 @@ module TypeProf
|
|
208
208
|
@base_type = base_type
|
209
209
|
end
|
210
210
|
|
211
|
-
def self.dummy_elements
|
212
|
-
Elements.new([], Type.any)
|
213
|
-
end
|
214
|
-
|
215
211
|
attr_reader :elems, :base_type
|
216
212
|
|
217
213
|
def inspect
|
@@ -264,6 +260,10 @@ module TypeProf
|
|
264
260
|
@lead_tys, @rest_ty = lead_tys, rest_ty
|
265
261
|
end
|
266
262
|
|
263
|
+
def self.dummy_elements
|
264
|
+
Elements.new([], Type.any)
|
265
|
+
end
|
266
|
+
|
267
267
|
attr_reader :lead_tys, :rest_ty
|
268
268
|
|
269
269
|
def to_local_type(id, base_ty)
|
@@ -796,6 +796,7 @@ module TypeProf
|
|
796
796
|
class Local < ContainerType
|
797
797
|
def initialize(kind, id, base_type)
|
798
798
|
@kind = kind
|
799
|
+
raise if @kind != Cell && @kind != Array && @kind != Hash
|
799
800
|
@id = id
|
800
801
|
raise unless base_type
|
801
802
|
@base_type = base_type
|
data/lib/typeprof/export.rb
CHANGED
@@ -72,7 +72,7 @@ module TypeProf
|
|
72
72
|
gvars.dump.each do |gvar_name, entry|
|
73
73
|
next if entry.type == Type.bot
|
74
74
|
s = entry.rbs_declared ? "#" : ""
|
75
|
-
output.puts s + "#{ gvar_name }
|
75
|
+
output.puts s + "#{ gvar_name }: #{ entry.type.screen_name(scratch) }"
|
76
76
|
end
|
77
77
|
output.puts
|
78
78
|
end
|
@@ -105,19 +105,20 @@ module TypeProf
|
|
105
105
|
consts[name] = ty.screen_name(@scratch)
|
106
106
|
end
|
107
107
|
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
108
|
+
modules = class_def.modules.to_h do |kind, mods|
|
109
|
+
mods = mods.to_h do |singleton, mods|
|
110
|
+
mods = mods.filter_map do |mod_def, _type_args, absolute_paths|
|
111
|
+
next if absolute_paths.all? {|path| !path || Config.check_dir_filter(path) == :exclude }
|
112
|
+
Type::Instance.new(mod_def.klass_obj).screen_name(@scratch)
|
113
|
+
end
|
114
|
+
[singleton, mods]
|
115
|
+
end
|
116
|
+
[kind, mods]
|
116
117
|
end
|
117
118
|
|
118
|
-
|
119
|
-
|
120
|
-
|
119
|
+
visibilities = {}
|
120
|
+
source_locations = {}
|
121
|
+
methods = {}
|
121
122
|
ivars = class_def.ivars.dump
|
122
123
|
cvars = class_def.cvars.dump
|
123
124
|
|
@@ -135,29 +136,47 @@ module TypeProf
|
|
135
136
|
method_name = ctx.mid
|
136
137
|
method_name = "self.#{ method_name }" if singleton
|
137
138
|
|
138
|
-
|
139
|
-
|
140
|
-
|
139
|
+
key = [:iseq, method_name]
|
140
|
+
visibilities[key] ||= mdef.pub_meth
|
141
|
+
source_locations[key] ||= ctx.iseq.source_location(0)
|
142
|
+
(methods[key] ||= []) << @scratch.show_method_signature(ctx)
|
143
|
+
end
|
144
|
+
when AliasMethodDef
|
145
|
+
alias_name, orig_name = mid, mdef.orig_mid
|
146
|
+
if singleton
|
147
|
+
alias_name = "self.#{ alias_name }"
|
148
|
+
orig_name = "self.#{ orig_name }"
|
141
149
|
end
|
150
|
+
key = [:alias, alias_name]
|
151
|
+
visibilities[key] ||= mdef.pub_meth
|
152
|
+
source_locations[key] ||= mdef.def_ep&.source_location
|
153
|
+
methods[key] = orig_name
|
142
154
|
when AttrMethodDef
|
143
|
-
next if !mdef.
|
155
|
+
next if !mdef.def_ep
|
156
|
+
absolute_path = mdef.def_ep.ctx.iseq.absolute_path
|
157
|
+
next if !absolute_path || Config.check_dir_filter(absolute_path) == :exclude
|
144
158
|
mid = mid.to_s[0..-2].to_sym if mid.to_s.end_with?("=")
|
145
159
|
method_name = mid
|
146
160
|
method_name = "self.#{ mid }" if singleton
|
147
161
|
method_name = [method_name, :"@#{ mid }" != mdef.ivar]
|
148
|
-
|
149
|
-
|
150
|
-
|
162
|
+
key = [:attr, method_name]
|
163
|
+
visibilities[key] ||= mdef.pub_meth
|
164
|
+
source_locations[key] ||= mdef.def_ep.source_location
|
165
|
+
if methods[key]
|
166
|
+
if methods[key][0] != mdef.kind
|
167
|
+
methods[key][0] = :accessor
|
151
168
|
end
|
152
169
|
else
|
153
170
|
entry = ivars[[singleton, mdef.ivar]]
|
154
171
|
ty = entry ? entry.type : Type.any
|
155
|
-
|
172
|
+
methods[key] = [mdef.kind, ty.screen_name(@scratch)]
|
156
173
|
end
|
157
174
|
when TypedMethodDef
|
158
175
|
if mdef.rbs_source
|
159
176
|
method_name, sigs = mdef.rbs_source
|
160
|
-
|
177
|
+
key = [:rbs, method_name]
|
178
|
+
methods[key] = sigs
|
179
|
+
visibilities[key] ||= mdef.pub_meth
|
161
180
|
end
|
162
181
|
end
|
163
182
|
end
|
@@ -168,7 +187,7 @@ module TypeProf
|
|
168
187
|
ty = entry.type
|
169
188
|
next unless var.to_s.start_with?("@")
|
170
189
|
var = "self.#{ var }" if singleton
|
171
|
-
next if
|
190
|
+
next if methods[[:attr, [singleton ? "self.#{ var.to_s[1..] }" : var.to_s[1..].to_sym, false]]]
|
172
191
|
next if entry.rbs_declared
|
173
192
|
[var, ty.screen_name(@scratch)]
|
174
193
|
end.compact
|
@@ -180,7 +199,9 @@ module TypeProf
|
|
180
199
|
end.compact
|
181
200
|
|
182
201
|
if !class_def.absolute_path || Config.check_dir_filter(class_def.absolute_path) == :exclude
|
183
|
-
|
202
|
+
if methods.keys.all? {|type,| type == :rbs }
|
203
|
+
return nil if consts.empty? && modules[:before][true].empty? && modules[:before][false].empty? && modules[:after][true].empty? && modules[:after][false].empty? && ivars.empty? && cvars.empty? && inner_classes.empty?
|
204
|
+
end
|
184
205
|
end
|
185
206
|
|
186
207
|
@scratch.namespace = nil
|
@@ -190,18 +211,17 @@ module TypeProf
|
|
190
211
|
name: class_def.name,
|
191
212
|
superclass: superclass,
|
192
213
|
consts: consts,
|
193
|
-
|
194
|
-
extended_mods: extended_mods,
|
214
|
+
modules: modules,
|
195
215
|
ivars: ivars,
|
196
216
|
cvars: cvars,
|
197
|
-
|
198
|
-
|
199
|
-
|
217
|
+
methods: methods,
|
218
|
+
visibilities: visibilities,
|
219
|
+
source_locations: source_locations,
|
200
220
|
inner_classes: inner_classes,
|
201
221
|
)
|
202
222
|
end
|
203
223
|
|
204
|
-
ClassData = Struct.new(:kind, :name, :superclass, :consts, :
|
224
|
+
ClassData = Struct.new(:kind, :name, :superclass, :consts, :modules, :ivars, :cvars, :methods, :visibilities, :source_locations, :inner_classes, keyword_init: true)
|
205
225
|
|
206
226
|
def show(stat_eps, output)
|
207
227
|
# make the class hierarchy
|
@@ -218,7 +238,16 @@ module TypeProf
|
|
218
238
|
|
219
239
|
output.puts "# Classes" # and Modules
|
220
240
|
|
221
|
-
|
241
|
+
prev_nil = true
|
242
|
+
show_class_hierarchy(0, hierarchy).each do |line|
|
243
|
+
if line == nil
|
244
|
+
output.puts line unless prev_nil
|
245
|
+
prev_nil = true
|
246
|
+
else
|
247
|
+
output.puts line
|
248
|
+
prev_nil = false
|
249
|
+
end
|
250
|
+
end
|
222
251
|
|
223
252
|
if ENV["TP_STAT"]
|
224
253
|
output.puts ""
|
@@ -246,13 +275,13 @@ module TypeProf
|
|
246
275
|
end.compact
|
247
276
|
end
|
248
277
|
|
249
|
-
def show_class_hierarchy(depth, hierarchy
|
278
|
+
def show_class_hierarchy(depth, hierarchy)
|
279
|
+
lines = []
|
250
280
|
hierarchy.each do |class_data|
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
show_class_data(depth, class_data, output)
|
281
|
+
lines << nil
|
282
|
+
lines.concat show_class_data(depth, class_data)
|
255
283
|
end
|
284
|
+
lines
|
256
285
|
end
|
257
286
|
|
258
287
|
def show_const(namespace, path)
|
@@ -262,53 +291,69 @@ module TypeProf
|
|
262
291
|
path[i..].join("::")
|
263
292
|
end
|
264
293
|
|
265
|
-
def show_class_data(depth, class_data
|
294
|
+
def show_class_data(depth, class_data)
|
266
295
|
indent = " " * depth
|
267
296
|
name = class_data.name.last
|
268
297
|
superclass = " < " + class_data.superclass if class_data.superclass
|
269
|
-
|
270
|
-
|
298
|
+
first_line = indent + "#{ class_data.kind } #{ name }#{ superclass }"
|
299
|
+
lines = []
|
271
300
|
class_data.consts.each do |name, ty|
|
272
|
-
|
273
|
-
first = false
|
274
|
-
end
|
275
|
-
class_data.included_mods.sort.each do |mod|
|
276
|
-
output.puts indent + " include #{ mod }"
|
277
|
-
first = false
|
301
|
+
lines << (indent + " #{ name }: #{ ty }")
|
278
302
|
end
|
279
|
-
class_data.
|
280
|
-
|
281
|
-
|
303
|
+
class_data.modules.each do |kind, mods|
|
304
|
+
mods.each do |singleton, mods|
|
305
|
+
case
|
306
|
+
when kind == :before && singleton then directive = nil
|
307
|
+
when kind == :before && !singleton then directive = "prepend"
|
308
|
+
when kind == :after && singleton then directive = "extend"
|
309
|
+
when kind == :after && !singleton then directive = "include"
|
310
|
+
end
|
311
|
+
mods.each do |mod|
|
312
|
+
lines << (indent + " #{ directive } #{ mod }") if directive
|
313
|
+
end
|
314
|
+
end
|
282
315
|
end
|
283
316
|
class_data.ivars.each do |var, ty|
|
284
|
-
|
285
|
-
first = false
|
317
|
+
lines << (indent + " #{ var }: #{ ty }") unless var.start_with?("_")
|
286
318
|
end
|
287
319
|
class_data.cvars.each do |var, ty|
|
288
|
-
|
289
|
-
first = false
|
320
|
+
lines << (indent + " #{ var }: #{ ty }")
|
290
321
|
end
|
291
|
-
|
292
|
-
|
293
|
-
|
294
|
-
|
295
|
-
|
296
|
-
|
297
|
-
|
298
|
-
|
299
|
-
|
300
|
-
|
301
|
-
|
302
|
-
|
303
|
-
|
304
|
-
|
305
|
-
|
322
|
+
lines << nil
|
323
|
+
prev_vis = true
|
324
|
+
class_data.methods.each do |key, arg|
|
325
|
+
vis = class_data.visibilities[key]
|
326
|
+
if prev_vis != vis
|
327
|
+
lines << nil
|
328
|
+
lines << (indent + " #{ vis ? "public" : "private" }")
|
329
|
+
prev_vis = vis
|
330
|
+
end
|
331
|
+
source_location = class_data.source_locations[key]
|
332
|
+
if Config.options[:show_source_locations] && source_location
|
333
|
+
lines << nil
|
334
|
+
lines << (indent + " # #{ source_location }")
|
335
|
+
end
|
336
|
+
type, (method_name, hidden) = key
|
337
|
+
case type
|
338
|
+
when :attr
|
339
|
+
kind, ty = *arg
|
340
|
+
lines << (indent + " attr_#{ kind } #{ method_name }#{ hidden ? "()" : "" }: #{ ty }")
|
341
|
+
when :rbs
|
342
|
+
sigs = arg.sort.join("\n" + indent + "#" + " " * (method_name.size + 5) + "| ")
|
343
|
+
lines << (indent + "# def #{ method_name }: #{ sigs }")
|
344
|
+
when :iseq
|
345
|
+
sigs = arg.sort.join("\n" + indent + " " * (method_name.size + 6) + "| ")
|
346
|
+
lines << (indent + " def #{ method_name }: #{ sigs }")
|
347
|
+
when :alias
|
348
|
+
orig_name = arg
|
349
|
+
lines << (indent + " alias #{ method_name } #{ orig_name }")
|
306
350
|
end
|
307
|
-
output.puts indent + " def #{ method_name } : #{ sigs }"
|
308
|
-
first = false
|
309
351
|
end
|
310
|
-
show_class_hierarchy(depth + 1, class_data.inner_classes
|
311
|
-
|
352
|
+
lines.concat show_class_hierarchy(depth + 1, class_data.inner_classes)
|
353
|
+
lines.shift until lines.empty? || lines.first
|
354
|
+
lines.pop until lines.empty? || lines.last
|
355
|
+
lines.unshift first_line
|
356
|
+
lines << (indent + "end")
|
312
357
|
end
|
313
358
|
end
|
314
359
|
end
|
data/lib/typeprof/import.rb
CHANGED
@@ -3,6 +3,10 @@ require "rbs"
|
|
3
3
|
module TypeProf
|
4
4
|
class RBSReader
|
5
5
|
def initialize
|
6
|
+
@repo = RBS::Repository.new
|
7
|
+
Config.gem_repo_dirs.each do |dir|
|
8
|
+
@repo.add(Pathname(dir))
|
9
|
+
end
|
6
10
|
@env, @builtin_env_json = RBSReader.get_builtin_env
|
7
11
|
end
|
8
12
|
|
@@ -11,7 +15,7 @@ module TypeProf
|
|
11
15
|
unless @builtin_env
|
12
16
|
@builtin_env = RBS::Environment.new
|
13
17
|
|
14
|
-
loader = RBS::EnvironmentLoader.new
|
18
|
+
loader = RBS::EnvironmentLoader.new(repository: @repo)
|
15
19
|
new_decls = loader.load(env: @builtin_env).map {|decl,| decl }
|
16
20
|
@builtin_env_json = load_rbs(@builtin_env, new_decls)
|
17
21
|
end
|
@@ -24,14 +28,21 @@ module TypeProf
|
|
24
28
|
end
|
25
29
|
|
26
30
|
def load_library(lib)
|
27
|
-
loader = RBS::EnvironmentLoader.new(core_root: nil)
|
31
|
+
loader = RBS::EnvironmentLoader.new(core_root: nil, repository: @repo)
|
28
32
|
loader.add(library: lib)
|
33
|
+
|
34
|
+
case lib
|
35
|
+
when "yaml"
|
36
|
+
loader.add(library: "pstore")
|
37
|
+
loader.add(library: "dbm")
|
38
|
+
end
|
39
|
+
|
29
40
|
new_decls = loader.load(env: @env).map {|decl,| decl }
|
30
41
|
RBSReader.load_rbs(@env, new_decls)
|
31
42
|
end
|
32
43
|
|
33
44
|
def load_path(path)
|
34
|
-
loader = RBS::EnvironmentLoader.new(core_root: nil)
|
45
|
+
loader = RBS::EnvironmentLoader.new(core_root: nil, repository: @repo)
|
35
46
|
loader.add(path: path)
|
36
47
|
new_decls = loader.load(env: @env).map {|decl,| decl }
|
37
48
|
RBSReader.load_rbs(@env, new_decls)
|
@@ -109,13 +120,13 @@ module TypeProf
|
|
109
120
|
end
|
110
121
|
|
111
122
|
type_params = nil
|
112
|
-
|
113
|
-
extended_modules = []
|
123
|
+
modules = { include: [], extend: [], prepend: [] }
|
114
124
|
methods = {}
|
115
125
|
attr_methods = {}
|
116
126
|
ivars = {}
|
117
127
|
cvars = {}
|
118
128
|
rbs_sources = {}
|
129
|
+
visibility = true
|
119
130
|
|
120
131
|
decls.each do |decl|
|
121
132
|
decl = decl.decl
|
@@ -136,7 +147,7 @@ module TypeProf
|
|
136
147
|
end
|
137
148
|
end
|
138
149
|
|
139
|
-
method_def = conv_method_def(method_types)
|
150
|
+
method_def = conv_method_def(method_types, visibility)
|
140
151
|
rbs_source = [(member.kind == :singleton ? "self." : "") + member.name.to_s, member.types.map {|type| type.location.source }]
|
141
152
|
if member.instance?
|
142
153
|
methods[[false, name]] = method_def
|
@@ -148,13 +159,13 @@ module TypeProf
|
|
148
159
|
end
|
149
160
|
when RBS::AST::Members::AttrReader
|
150
161
|
ty = conv_type(member.type)
|
151
|
-
attr_methods[[false, member.name]] = attr_method_def(:reader, member.name, ty)
|
162
|
+
attr_methods[[false, member.name]] = attr_method_def(:reader, member.name, ty, visibility)
|
152
163
|
when RBS::AST::Members::AttrWriter
|
153
164
|
ty = conv_type(member.type)
|
154
|
-
attr_methods[[false, member.name]] = attr_method_def(:writer, member.name, ty)
|
165
|
+
attr_methods[[false, member.name]] = attr_method_def(:writer, member.name, ty, visibility)
|
155
166
|
when RBS::AST::Members::AttrAccessor
|
156
167
|
ty = conv_type(member.type)
|
157
|
-
attr_methods[[false, member.name]] = attr_method_def(:accessor, member.name, ty)
|
168
|
+
attr_methods[[false, member.name]] = attr_method_def(:accessor, member.name, ty, visibility)
|
158
169
|
when RBS::AST::Members::Alias
|
159
170
|
# XXX: an alias to attr methods?
|
160
171
|
if member.instance?
|
@@ -171,7 +182,7 @@ module TypeProf
|
|
171
182
|
if name.kind == :class
|
172
183
|
mod = conv_type_name(name)
|
173
184
|
type_args = member.args.map {|type| conv_type(type) }
|
174
|
-
|
185
|
+
modules[:include] << [mod, type_args]
|
175
186
|
else
|
176
187
|
# including an interface is not supported yet
|
177
188
|
end
|
@@ -181,7 +192,17 @@ module TypeProf
|
|
181
192
|
if name.kind == :class
|
182
193
|
mod = conv_type_name(name)
|
183
194
|
type_args = member.args.map {|type| conv_type(type) }
|
184
|
-
|
195
|
+
modules[:extend] << [mod, type_args]
|
196
|
+
else
|
197
|
+
# extending a module with an interface is not supported yet
|
198
|
+
end
|
199
|
+
|
200
|
+
when RBS::AST::Members::Prepend
|
201
|
+
name = member.name
|
202
|
+
if name.kind == :class
|
203
|
+
mod = conv_type_name(name)
|
204
|
+
type_args = member.args.map {|type| conv_type(type) }
|
205
|
+
modules[:prepend] << [mod, type_args]
|
185
206
|
else
|
186
207
|
# extending a module with an interface is not supported yet
|
187
208
|
end
|
@@ -191,7 +212,10 @@ module TypeProf
|
|
191
212
|
when RBS::AST::Members::ClassVariable
|
192
213
|
cvars[member.name] = conv_type(member.type)
|
193
214
|
|
194
|
-
when RBS::AST::Members::Public
|
215
|
+
when RBS::AST::Members::Public
|
216
|
+
visibility = true
|
217
|
+
when RBS::AST::Members::Private
|
218
|
+
visibility = false
|
195
219
|
|
196
220
|
# The following declarations are ignoreable because they are handled in other level
|
197
221
|
when RBS::AST::Declarations::Constant
|
@@ -209,8 +233,7 @@ module TypeProf
|
|
209
233
|
type_params: type_params,
|
210
234
|
superclass: superclass,
|
211
235
|
members: {
|
212
|
-
|
213
|
-
extended_modules: extended_modules,
|
236
|
+
modules: modules,
|
214
237
|
methods: methods,
|
215
238
|
attr_methods: attr_methods,
|
216
239
|
ivars: ivars,
|
@@ -263,8 +286,11 @@ module TypeProf
|
|
263
286
|
end
|
264
287
|
return if decl.name == RBS::BuiltinNames::BasicObject.name
|
265
288
|
return if decl.name == name
|
266
|
-
@all_env.class_decls[name]
|
267
|
-
|
289
|
+
decls = @all_env.class_decls[name]
|
290
|
+
if decls
|
291
|
+
decls.decls.each do |decl|
|
292
|
+
each_reference(decl.decl, &blk)
|
293
|
+
end
|
268
294
|
end
|
269
295
|
end
|
270
296
|
|
@@ -287,10 +313,14 @@ module TypeProf
|
|
287
313
|
return RBS::BuiltinNames::Object.name, []
|
288
314
|
end
|
289
315
|
|
290
|
-
def conv_method_def(rbs_method_types)
|
291
|
-
rbs_method_types.map do |method_type|
|
316
|
+
def conv_method_def(rbs_method_types, visibility)
|
317
|
+
sig_rets = rbs_method_types.map do |method_type|
|
292
318
|
conv_func(method_type.type_params, method_type.type, method_type.block)
|
293
319
|
end
|
320
|
+
{
|
321
|
+
sig_rets: sig_rets,
|
322
|
+
visibility: visibility,
|
323
|
+
}
|
294
324
|
end
|
295
325
|
|
296
326
|
def conv_func(type_params, func, block)
|
@@ -320,11 +350,12 @@ module TypeProf
|
|
320
350
|
}
|
321
351
|
end
|
322
352
|
|
323
|
-
def attr_method_def(kind, name, ty)
|
353
|
+
def attr_method_def(kind, name, ty, visibility)
|
324
354
|
{
|
325
355
|
kind: kind,
|
326
356
|
ivar: name,
|
327
357
|
ty: ty,
|
358
|
+
visibility: visibility,
|
328
359
|
}
|
329
360
|
end
|
330
361
|
|
@@ -438,6 +469,8 @@ module TypeProf
|
|
438
469
|
json = scratch.rbs_reader.load_library(feature)
|
439
470
|
rescue RBS::EnvironmentLoader::UnknownLibraryError
|
440
471
|
return nil
|
472
|
+
rescue RBS::DuplicatedDeclarationError
|
473
|
+
return true
|
441
474
|
end
|
442
475
|
# need cache?
|
443
476
|
Import.new(scratch, json).import
|
@@ -490,22 +523,25 @@ module TypeProf
|
|
490
523
|
|
491
524
|
classes.each do |klass, superclass_type_args, members|
|
492
525
|
@scratch.add_superclass_type_args!(klass, superclass_type_args&.map {|ty| conv_type(ty) })
|
493
|
-
|
494
|
-
extended_modules = members[:extended_modules]
|
526
|
+
modules = members[:modules]
|
495
527
|
methods = members[:methods]
|
496
528
|
attr_methods = members[:attr_methods]
|
497
529
|
ivars = members[:ivars]
|
498
530
|
cvars = members[:cvars]
|
499
531
|
rbs_sources = members[:rbs_sources]
|
500
532
|
|
501
|
-
|
502
|
-
|
503
|
-
|
504
|
-
|
505
|
-
|
506
|
-
|
507
|
-
|
508
|
-
|
533
|
+
modules.each do |kind, mods|
|
534
|
+
mods.each do |mod, type_args|
|
535
|
+
type_args = type_args&.map {|ty| conv_type(ty) }
|
536
|
+
case kind
|
537
|
+
when :include
|
538
|
+
@scratch.mix_module(:after, klass, path_to_klass(mod), type_args, false, nil)
|
539
|
+
when :extend
|
540
|
+
@scratch.mix_module(:after, klass, path_to_klass(mod), type_args, true, nil)
|
541
|
+
when :prepend
|
542
|
+
@scratch.mix_module(:before, klass, path_to_klass(mod), type_args, false, nil)
|
543
|
+
end
|
544
|
+
end
|
509
545
|
end
|
510
546
|
|
511
547
|
methods.each do |(singleton, method_name), mdef|
|
@@ -518,7 +554,7 @@ module TypeProf
|
|
518
554
|
kind = mdef[:kind]
|
519
555
|
ivar = mdef[:ivar]
|
520
556
|
ty = conv_type(mdef[:ty]).remove_type_vars
|
521
|
-
@scratch.add_attr_method(klass,
|
557
|
+
@scratch.add_attr_method(klass, ivar, :"@#{ ivar }", kind, mdef[:visibility], nil)
|
522
558
|
@scratch.add_ivar_write!(Type::Instance.new(klass), :"@#{ ivar }", ty, nil)
|
523
559
|
end
|
524
560
|
|
@@ -548,11 +584,11 @@ module TypeProf
|
|
548
584
|
end
|
549
585
|
|
550
586
|
def conv_method_def(method_name, mdef, rbs_source)
|
551
|
-
sig_rets = mdef.flat_map do |sig_ret|
|
587
|
+
sig_rets = mdef[:sig_rets].flat_map do |sig_ret|
|
552
588
|
conv_func(sig_ret)
|
553
589
|
end
|
554
590
|
|
555
|
-
TypedMethodDef.new(sig_rets, rbs_source)
|
591
|
+
TypedMethodDef.new(sig_rets, rbs_source, mdef[:visibility])
|
556
592
|
end
|
557
593
|
|
558
594
|
def conv_func(sig_ret)
|
@@ -652,7 +688,9 @@ module TypeProf
|
|
652
688
|
klass = Type::Builtin[:obj]
|
653
689
|
path.each do |name|
|
654
690
|
klass = @scratch.get_constant(klass, name)
|
655
|
-
|
691
|
+
if klass == Type.any
|
692
|
+
raise TypeProfError.new("A constant `#{ path.join("::") }' is used but not defined in RBS")
|
693
|
+
end
|
656
694
|
end
|
657
695
|
klass
|
658
696
|
end
|