@@ -126,6 +126,81 @@ def test_rand
126126 assert_send_type "(Range[Float]) -> Float" , Kernel , :rand , 0.0 ...10.0
127127 assert_send_type "(Range[Float]) -> nil" , Kernel , :rand , 0.0 ...0.0
128128 end
129+
130+ def test_trace_var
131+ tracer = BlankSlate . new
132+ def tracer . call ( new ) nil end
133+
134+ with_interned '$__TEST_TRACE_VAR' do |name |
135+ assert_send_type '(interned, String) -> nil' ,
136+ Kernel , :trace_var , name , '1'
137+ assert_send_type '(interned, ::Kernel::_Tracer) -> nil' ,
138+ Kernel , :trace_var , name , tracer
139+ assert_send_type '(interned) { (any) -> void } -> nil' ,
140+ Kernel , :trace_var , name do |x | 0 end
141+
142+ # `Kernel.trace_var` doesn't actually check the type of its second argument,
143+ # but instead defers until the global is actually assigned. To ensure that
144+ # our signatures are correct, we assign the global here (which, if our
145+ # signatures are incorrect, will raise an exception)
146+ $__TEST_TRACE_VAR = 1
147+
148+ # Acts the same as `untrace_var`, so this performs the untracing for us.
149+ assert_send_type '(interned, nil) -> Array[String | ::Kernel::_Tracer]' ,
150+ Kernel , :trace_var , name , nil
151+ end
152+ ensure
153+ # Just in case an exception stopped it, we don't want to continue tracing.
154+ # We do `defined?` as `untrace_var :$some_undefined_global` fails
155+ untrace_var :$__TEST_TRACE_VAR if defined? $__TEST_TRACE_VAR
156+ end
157+
158+ def test_untrace_var
159+ tracer = BlankSlate . new
160+ def tracer . call ( new ) nil end
161+
162+ with_interned '$__TEST_UNTRACE_VAR' do |name |
163+ # No argument yields all traces
164+ trace_var :$__TEST_UNTRACE_VAR , '"string"'
165+ trace_var :$__TEST_UNTRACE_VAR do "proc" end
166+ trace_var :$__TEST_UNTRACE_VAR , tracer
167+ assert_send_type '(interned) -> Array[String | ::Kernel::_Tracer]' ,
168+ Kernel , :untrace_var , name
169+
170+ # `nil` also yields all traces
171+ trace_var :$__TEST_UNTRACE_VAR , '"string"'
172+ trace_var :$__TEST_UNTRACE_VAR do "proc" end
173+ trace_var :$__TEST_UNTRACE_VAR , tracer
174+ assert_send_type '(interned, nil) -> Array[String | ::Kernel::_Tracer]' ,
175+ Kernel , :untrace_var , name , nil
176+
177+ # Passing a String in yields the string if they're the same, or `nil`
178+ string = '"string"'
179+ trace_var :$__TEST_UNTRACE_VAR , string
180+ assert_send_type '(interned, String) -> [String]' ,
181+ Kernel , :untrace_var , name , string
182+ assert_send_type '(interned, String) -> nil' ,
183+ Kernel , :untrace_var , name , 'not a trace'
184+
185+ # Passing a `tracer` yields the tracer if it's set, or `nil` otherwise
186+ trace_var :$__TEST_UNTRACE_VAR , tracer
187+ assert_send_type '[T < ::Kernel::_Tracer] (interned, T) -> [T]' ,
188+ Kernel , :untrace_var , name , tracer
189+ assert_send_type '[T < ::Kernel::_Tracer] (interned, T) -> nil' ,
190+ Kernel , :untrace_var , name , tracer
191+
192+ # Anything else is `nil`
193+ with_untyped do |trace |
194+ next if nil == trace
195+ assert_send_type '(interned, untyped) -> nil' ,
196+ Kernel , :untrace_var , name , trace
197+ end
198+ end
199+ ensure
200+ # Just in case an exception stopped it, we don't want to continue tracing.
201+ # We do `defined?` as `untrace_var :$some_undefined_global` fails
202+ untrace_var :$__TEST_UNTRACE_VAR if defined? $__TEST_UNTRACE_VAR
203+ end
129204end
130205
131206class KernelInstanceTest < Test ::Unit ::TestCase
0 commit comments