1- import functools
21from dataclasses import dataclass , field
32from enum import Enum
43from typing import (
54 TYPE_CHECKING ,
65 Any ,
7- Callable ,
8- Generic ,
96 List ,
107 Optional ,
118 Tuple ,
12- TypeVar ,
13- cast ,
149)
1510
16- from typing_extensions import Concatenate , ParamSpec
17-
1811from robot .parsing .lexer .tokens import Token
1912from robotcode .core .lsp .types import Position , Range
2013
2417if TYPE_CHECKING :
2518 from robotcode .robot .diagnostics .library_doc import KeywordDoc , LibraryDoc
2619
27- _F = TypeVar ("_F" , bound = Callable [..., Any ])
28-
29-
30- _NOT_SET = object ()
31-
32-
33- def single_call (func : _F ) -> _F :
34- result = _NOT_SET
35-
36- def wrapper (self : Any , * args : Any , ** kwargs : Any ) -> Any :
37- nonlocal result
38-
39- if result is _NOT_SET :
40- result = func (self , * args , ** kwargs )
41-
42- return result
43-
44- return cast (_F , wrapper )
45-
4620
47- P = ParamSpec ("P" )
48- R = TypeVar ("R" )
49-
50-
51- class cached_method (Generic [P , R ]): # noqa: N801
52- def __init__ (
53- self , func : Optional [Callable [Concatenate [Any , P ], R ]] = None , * , maxsize : Optional [int ] = None
54- ) -> None :
55- self .func : Optional [Callable [Concatenate [Any , P ], R ]] = func
56- self ._maxsize = maxsize
57- self .cache_name : Optional [str ] = None
58- if func is not None :
59- functools .update_wrapper (self , func )
60-
61- def __set_name__ (self , owner : type , name : str ) -> None :
62- self .cache_name = f"__cached_{ owner .__name__ } _{ name } "
63-
64- def __call__ (self , func : Callable [Concatenate [Any , P ], R ]) -> "cached_method[P, R]" :
65- self .func = func
66- functools .update_wrapper (self , func )
67- return self
68-
69- def __get__ (self , instance : Any , owner : Optional [type ] = None ) -> Callable [P , R ]:
70- cached = instance .__dict__ .get (self .cache_name , _NOT_SET )
71- if cached is _NOT_SET :
72- assert self .func is not None
73-
74- bound_method = self .func .__get__ (instance , owner )
75- cached = functools .lru_cache (maxsize = self ._maxsize )(bound_method )
76- instance .__dict__ [self .cache_name ] = cached
77- return cast (Callable [P , R ], cached )
78-
79-
80- @dataclass
21+ @dataclass (slots = True )
8122class SourceEntity :
8223 line_no : int
8324 col_offset : int
@@ -92,7 +33,6 @@ def range(self) -> Range:
9233 end = Position (line = self .end_line_no - 1 , character = self .end_col_offset ),
9334 )
9435
95- @single_call
9636 def __hash__ (self ) -> int :
9737 return hash (
9838 (
@@ -105,7 +45,7 @@ def __hash__(self) -> int:
10545 )
10646
10747
108- @dataclass
48+ @dataclass ( slots = True )
10949class Import (SourceEntity ):
11050 name : Optional [str ]
11151 name_token : Optional [Token ]
@@ -124,7 +64,7 @@ def range(self) -> Range:
12464 )
12565
12666
127- @dataclass
67+ @dataclass ( slots = True )
12868class LibraryImport (Import ):
12969 args : Tuple [str , ...] = ()
13070 alias : Optional [str ] = None
@@ -143,23 +83,20 @@ def alias_range(self) -> Range:
14383 ),
14484 )
14585
146- @single_call
14786 def __hash__ (self ) -> int :
14887 return hash ((type (self ), self .name , self .args , self .alias ))
14988
15089
151- @dataclass
90+ @dataclass ( slots = True )
15291class ResourceImport (Import ):
153- @single_call
15492 def __hash__ (self ) -> int :
15593 return hash ((type (self ), self .name ))
15694
15795
158- @dataclass
96+ @dataclass ( slots = True )
15997class VariablesImport (Import ):
16098 args : Tuple [str , ...] = ()
16199
162- @single_call
163100 def __hash__ (self ) -> int :
164101 return hash ((type (self ), self .name , self .args ))
165102
@@ -178,7 +115,7 @@ class VariableDefinitionType(Enum):
178115 VARIABLE_NOT_FOUND = "variable not found"
179116
180117
181- @dataclass
118+ @dataclass ( slots = True )
182119class VariableDefinition (SourceEntity ):
183120 name : str
184121 name_token : Optional [Token ] # TODO: this is not needed anymore, but kept for compatibility
@@ -192,17 +129,16 @@ class VariableDefinition(SourceEntity):
192129 value_is_native : bool = field (default = False , compare = False )
193130 value_type : Optional [str ] = field (default = None , compare = False )
194131
195- @functools . cached_property
132+ @property
196133 def matcher (self ) -> VariableMatcher :
197134 return search_variable (self .name )
198135
199- @functools . cached_property
136+ @property
200137 def convertable_name (self ) -> str :
201138 m = self .matcher
202139 value_type = f": { self .value_type } " if self .value_type else ""
203140 return f"{ m .identifier } {{{ m .base .strip ()} { value_type } }}"
204141
205- @single_call
206142 def __hash__ (self ) -> int :
207143 return hash ((self .type , self .name , self .source , self .range ))
208144
@@ -221,82 +157,74 @@ def range(self) -> Range:
221157 )
222158
223159
224- @dataclass
160+ @dataclass ( slots = True )
225161class TestVariableDefinition (VariableDefinition ):
226162 type : VariableDefinitionType = VariableDefinitionType .TEST_VARIABLE
227163
228- @single_call
229164 def __hash__ (self ) -> int :
230165 return hash ((self .type , self .name , self .source , self .range ))
231166
232167
233- @dataclass
168+ @dataclass ( slots = True )
234169class LocalVariableDefinition (VariableDefinition ):
235170 type : VariableDefinitionType = VariableDefinitionType .LOCAL_VARIABLE
236171
237- @single_call
238172 def __hash__ (self ) -> int :
239173 return hash ((self .type , self .name , self .source , self .range ))
240174
241175
242- @dataclass
176+ @dataclass ( slots = True )
243177class GlobalVariableDefinition (VariableDefinition ):
244178 type : VariableDefinitionType = VariableDefinitionType .GLOBAL_VARIABLE
245179
246- @single_call
247180 def __hash__ (self ) -> int :
248181 return hash ((self .type , self .name , self .source , self .range ))
249182
250183
251- @dataclass
184+ @dataclass ( slots = True )
252185class BuiltInVariableDefinition (GlobalVariableDefinition ):
253186 type : VariableDefinitionType = VariableDefinitionType .BUILTIN_VARIABLE
254187 resolvable : bool = True
255188
256- @single_call
257189 def __hash__ (self ) -> int :
258190 return hash ((self .type , self .name , self .source , self .range ))
259191
260192
261- @dataclass
193+ @dataclass ( slots = True )
262194class CommandLineVariableDefinition (GlobalVariableDefinition ):
263195 type : VariableDefinitionType = VariableDefinitionType .COMMAND_LINE_VARIABLE
264196 resolvable : bool = True
265197
266- @single_call
267198 def __hash__ (self ) -> int :
268199 return hash ((self .type , self .name , self .source , self .range ))
269200
270201
271- @dataclass
202+ @dataclass ( slots = True )
272203class ArgumentDefinition (LocalVariableDefinition ):
273204 type : VariableDefinitionType = VariableDefinitionType .ARGUMENT
274205 keyword_doc : Optional ["KeywordDoc" ] = field (default = None , compare = False , metadata = {"nosave" : True })
275206
276- @single_call
277207 def __hash__ (self ) -> int :
278208 return hash ((self .type , self .name , self .source , self .range ))
279209
280210
281- @dataclass
211+ @dataclass ( slots = True )
282212class EmbeddedArgumentDefinition (ArgumentDefinition ):
283213 pattern : Optional [str ] = field (default = None , compare = False )
284214
285- @single_call
286215 def __hash__ (self ) -> int :
287216 return hash ((self .type , self .name , self .source , self .range ))
288217
289218
290- @dataclass
219+ @dataclass ( slots = True )
291220class LibraryArgumentDefinition (ArgumentDefinition ):
292221 type : VariableDefinitionType = VariableDefinitionType .LIBRARY_ARGUMENT
293222
294- @single_call
295223 def __hash__ (self ) -> int :
296224 return hash ((self .type , self .name , self .source , self .range ))
297225
298226
299- @dataclass (frozen = True , eq = False , repr = False )
227+ @dataclass (slots = True , frozen = True , eq = False , repr = False )
300228class NativeValue :
301229 value : Any
302230
@@ -307,39 +235,36 @@ def __str__(self) -> str:
307235 return str (self .value )
308236
309237
310- @dataclass
238+ @dataclass ( slots = True )
311239class ImportedVariableDefinition (VariableDefinition ):
312240 type : VariableDefinitionType = VariableDefinitionType .IMPORTED_VARIABLE
313241 value : Optional [NativeValue ] = field (default = None , compare = False )
314242
315- @single_call
316243 def __hash__ (self ) -> int :
317244 return hash ((self .type , self .name , self .source , self .range ))
318245
319246
320- @dataclass
247+ @dataclass ( slots = True )
321248class EnvironmentVariableDefinition (VariableDefinition ):
322249 type : VariableDefinitionType = VariableDefinitionType .ENVIRONMENT_VARIABLE
323250 resolvable : bool = True
324251
325252 default_value : Any = field (default = None , compare = False )
326253
327- @single_call
328254 def __hash__ (self ) -> int :
329255 return hash ((self .type , self .name , self .source , self .range ))
330256
331257
332- @dataclass
258+ @dataclass ( slots = True )
333259class VariableNotFoundDefinition (VariableDefinition ):
334260 type : VariableDefinitionType = VariableDefinitionType .VARIABLE_NOT_FOUND
335261 resolvable : bool = False
336262
337- @single_call
338263 def __hash__ (self ) -> int :
339264 return hash ((self .type , self .name , self .source , self .range ))
340265
341266
342- @dataclass
267+ @dataclass ( slots = True )
343268class LibraryEntry :
344269 name : str
345270 import_name : str
@@ -358,7 +283,6 @@ def __str__(self) -> str:
358283 result += f" WITH NAME { self .alias } "
359284 return result
360285
361- @single_call
362286 def __hash__ (self ) -> int :
363287 return hash (
364288 (
@@ -374,12 +298,11 @@ def __hash__(self) -> int:
374298 )
375299
376300
377- @dataclass
301+ @dataclass ( slots = True )
378302class ResourceEntry (LibraryEntry ):
379303 imports : List [Import ] = field (default_factory = list , compare = False )
380304 variables : List [VariableDefinition ] = field (default_factory = list , compare = False )
381305
382- @single_call
383306 def __hash__ (self ) -> int :
384307 return hash (
385308 (
@@ -392,11 +315,10 @@ def __hash__(self) -> int:
392315 )
393316
394317
395- @dataclass
318+ @dataclass ( slots = True )
396319class VariablesEntry (LibraryEntry ):
397320 variables : List [ImportedVariableDefinition ] = field (default_factory = list , compare = False )
398321
399- @single_call
400322 def __hash__ (self ) -> int :
401323 return hash (
402324 (
@@ -410,11 +332,10 @@ def __hash__(self) -> int:
410332 )
411333
412334
413- @dataclass
335+ @dataclass ( slots = True )
414336class TestCaseDefinition (SourceEntity ):
415337 name : str
416338
417- @single_call
418339 def __hash__ (self ) -> int :
419340 return hash (
420341 (
@@ -428,11 +349,10 @@ def __hash__(self) -> int:
428349 )
429350
430351
431- @dataclass
352+ @dataclass ( slots = True )
432353class TagDefinition (SourceEntity ):
433354 name : str
434355
435- @single_call
436356 def __hash__ (self ) -> int :
437357 return hash (
438358 (
0 commit comments