Coverage for src/robotide/spec/iteminfo.py: 82%
304 statements
« prev ^ index » next coverage.py v7.8.0, created at 2025-05-06 10:40 +0100
« prev ^ index » next coverage.py v7.8.0, created at 2025-05-06 10:40 +0100
1# Copyright 2008-2015 Nokia Networks
2# Copyright 2016- Robot Framework Foundation
3#
4# Licensed under the Apache License, Version 2.0 (the "License");
5# you may not use this file except in compliance with the License.
6# You may obtain a copy of the License at
7#
8# http://www.apache.org/licenses/LICENSE-2.0
9#
10# Unless required by applicable law or agreed to in writing, software
11# distributed under the License is distributed on an "AS IS" BASIS,
12# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13# See the License for the specific language governing permissions and
14# limitations under the License.
16import os 1ab
17from functools import total_ordering 1ab
19from .. import utils 1ab
20from ..lib.robot.libdocpkg.htmlwriter import DocToHtml 1ab
23class ItemInfo(object): 1ab
24 """Represents an object that can be displayed by content assistant."""
26 def __init__(self, name, source, details): 1ab
27 """Creates an item info.
29 :Parameters:
30 name
31 Item name. Is shown in the first column of the content assist popup.
32 source
33 Item source. Is shown in the second column of the content assist popup.
34 details
35 Detailed information for item that is shown in the additional popup
36 besides the list that contains content assist values. Will be
37 displayed as HTML.
38 """
39 self.name = name 2a i - ; . cbdbwb9 ! # $ % / m eb| fbgbhbxbf + ` ybzbAbBbN ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p Gbc ibjbkbMbFblbmbCb= k Dbl } j ' w _ nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq t 2b3bM sbtbNb, YbWbZb0bubvbJbObKbPbLbQbIbbbRb
40 self.source = source 2a i - ; . cbdbwb9 ! # $ % / m eb| fbgbhbxbf + ` ybzbAbBbN ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p Gbc ibjbkbMbFblbmbCb= k Dbl } j ' w _ nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq t 2b3bM sbtbNb, YbWbZb0bubvbJbObKbPbLbQbIbbbRb
41 # print(f"DEBUG: iteminfo.py ItemInfo {name=} {source=}")
42 if details is not None: 2a i - ; . cbdbwb9 ! # $ % / m eb| fbgbhbxbf + ` ybzbAbBbN ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p Gbc ibjbkbMbFblbmbCb= k Dbl } j ' w _ nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq t 2b3bM sbtbNb, YbWbZb0bubvbJbObKbPbLbQbIbbbRb
43 self.details = details 1aM
44 self._priority = PRIORITIES.get(self.__class__, PRIORITIES[ItemInfo]) 2a i - ; . cbdbwb9 ! # $ % / m eb| fbgbhbxbf + ` ybzbAbBbN ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p Gbc ibjbkbMbFblbmbCb= k Dbl } j ' w _ nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq t 2b3bM sbtbNb, YbWbZb0bubvbJbObKbPbLbQbIbbbRb
46 @property 1ab
47 def longname(self): 1ab
48 return '%s.%s' % (self.source, self.name) 2a i ; 9 ! # $ % m f ` N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ * v n o p c = k l ' w ? g y z r A s B C x d D @ ( h E F G H I [ L J K : e { q t M
50 def name_begins_with(self, prefix): 1ab
51 return utils.normalize(self.name).startswith(prefix) 1cklgyzrAsBCxdD(hEFGHILJK:eqM
53 def longname_begins_with(self, prefix): 1ab
54 return utils.normalize(self.longname).startswith(prefix) 1clgyzABCxdD(hEFGHILJK:eqM
56 def is_library_keyword(self): 1ab
57 return False 26b
59 def is_user_keyword(self): 1ab
60 return not self.is_library_keyword()
62 @staticmethod 1ab
63 def m_cmp(a, b): 1ab
64 return (a > b) - (a < b) 24b
66 def __cmp__(self, other): 1ab
67 if self._priority == other._priority: 67 ↛ 70line 67 didn't jump to line 70 because the condition on line 67 was always true24b
68 name_cmp = self.m_cmp(self.name.upper(), other.name.upper()) 24b
69 return name_cmp if name_cmp else self.m_cmp(self.source, other.source) 24b
70 return self.m_cmp(self._priority, other._priority)
72 def __eq__(self, other): 1ab
73 return not self.__cmp__(other) if isinstance(other, ItemInfo) else False 24b
75 def __hash__(self): 1ab
76 return hash((self.name, self.source)) 1M
79@total_ordering 1ab
80class VariableInfo(ItemInfo): 1ab
82 def __init__(self, name, value, source): 1ab
83 ItemInfo.__init__(self, name, self._source_name(source), None) 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= k Dbl nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq 2b3bM YbWbZb0b
84 self._original_source = source 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= k Dbl nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq 2b3bM YbWbZb0b
85 self._value = value 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= k Dbl nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq 2b3bM YbWbZb0b
87 @staticmethod 1ab
88 def _source_name(source): 1ab
89 return os.path.basename(source) if source else '' 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= k Dbl nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq 2b3bM YbWbZb0b
91 def name_matches(self, pattern): 1ab
92 normalized = utils.normalize(self._undecorate(pattern)) 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= k Dbl nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq M
93 return utils.normalize(self.name[2:-1]).startswith(normalized) 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= k Dbl nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq M
95 @staticmethod 1ab
96 def _undecorate(pattern): 1ab
97 def get_prefix_length(): 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= k Dbl nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq M
98 if pattern[0] not in ['$', '@', '&']: 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= Dbl nb? g y obz A B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq M
99 return 0 1clgyzABCxdD(hEFGHILJK:eqM
100 elif len(pattern) > 1 and pattern[1] == '{': 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= Dbl nb? ob@ [ pbEbqb{ rb
101 return 2 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= Dbl nb? ob@ [ pbEbqb{ rb
102 else:
103 return 1 1c?@[
104 if not pattern: 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= k Dbl nb? g y obz r A s B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq M
105 return pattern 1krs
106 without_prefix = pattern[get_prefix_length():] 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= Dbl nb? g y obz A B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq M
107 if pattern[-1] == '}': 107 ↛ 108line 107 didn't jump to line 108 because the condition on line 107 was never true2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= Dbl nb? g y obz A B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq M
108 return without_prefix[:-1]
109 else:
110 return without_prefix 2i - . cbdbwb/ m eb| fbgbhbxbf + c FblbmbCb= Dbl nb? g y obz A B C x d D @ ( h E F G H I [ L J K pb: e Ebqb{ rbq M
112 @property 1ab
113 def details(self): 1ab
114 value = self._value 2YbWbZb0b
115 if self.name.startswith('@') and value is None: 2YbWbZb0b
116 value = '[ ]' 2Wb
117 return ('<table>' 2YbWbZb0b
118 '<tr><td><i>Name:</i></td><td>%s</td></tr>'
119 '<tr><td><i>Source:</i></td><td>%s</td></tr>'
120 '<tr><td valign=top><i>Value:</i></td><td>%s</td></tr>'
121 '</table>') % (self.name, self._original_source, str(value))
123 def __eq__(self, other): 1ab
124 if isinstance(other, str): # DEBUG
125 return self.name.lower() == other.lower()
126 return self.name.lower() == other.name.lower()
128 def __hash__(self): 1ab
129 return hash(repr(self)) 2. / = k l ? obr s x @ [ pbEbqbrb
131 def __lt__(self, other): 1ab
132 if isinstance(other, str): # DEBUG 132 ↛ 133line 132 didn't jump to line 133 because the condition on line 132 was never true1=kl?rs@[
133 return self.name.lower() < other.lower()
134 return self.name.lower() < other.name.lower() 1=kl?rs@[
137@total_ordering 1ab
138class ArgumentInfo(VariableInfo): 1ab
140 SOURCE = 'Argument' 1ab
142 def __init__(self, name, value): 1ab
143 VariableInfo.__init__(self, name, value, self.SOURCE) 2lbmbCb= k Dbl nb? g y obz r A s B C x d D @ h E F G H I [ J K pbe qb{ rbq
145 def __eq__(self, other): 1ab
146 if isinstance(other, str):
147 return self.longname.lower() == other.lower()
148 return self.longname.lower() == other.longname.lower()
150 def __hash__(self): 1ab
151 return hash(repr(self)) 2lbmb= k nb? r s @ [ {
153 def __lt__(self, other): 1ab
154 if isinstance(other, str): 154 ↛ 155line 154 didn't jump to line 155 because the condition on line 154 was never true1=k?rs@[{
155 return self.longname.lower() < other.lower()
156 return self.longname.lower() < other.longname.lower() 1=k?rs@[{
159class LocalVariableInfo(VariableInfo): 1ab
161 SOURCE = 'Local variable' 1ab
163 def __init__(self, name): 1ab
164 VariableInfo.__init__(self, name, '', self.SOURCE) 1=kl
167@total_ordering 1ab
168class _KeywordInfo(ItemInfo): 1ab
170 def __init__(self, item): 1ab
171 self.doc = self._doc(item).strip() 2a i ; 9 ! # $ % m f N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p c k l j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb, ubvbbb
172 self.doc_format = "ROBOT" 2a i ; 9 ! # $ % m f N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p c k l j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb, ubvbbb
173 ItemInfo.__init__(self, self._name(item), self._source(item), None) 2a i ; 9 ! # $ % m f N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p c k l j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb, ubvbbb
174 self.shortdoc = self.doc.splitlines()[0] if self.doc else '' 2a i ; 9 ! # $ % m f N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p c k l j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb, ubvbbb
175 self.item = item 2a i ; 9 ! # $ % m f N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p c k l j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb, ubvbbb
177 @property 1ab
178 def arguments(self): 1ab
179 return self._parse_args(self.item) 2a i - SbXb; . TbUbHb1b5b/ f + O P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ v n o c j ' w d e t , bb
181 @property 1ab
182 def details(self): 1ab
183 formatter = DocToHtml(self.doc_format) 2sbtb,
184 return ('<table>' 2sbtb,
185 '<tr><td><i>Name:</i></td><td>%s</td></tr>'
186 '<tr><td><i>Source:</i></td><td>%s <%s></td></tr>'
187 '<tr><td><i>Arguments:</i></td><td>%s</td></tr>'
188 '</table>'
189 '<table>'
190 '<tr><td>%s</td></tr>'
191 '</table>') % (self._name(self.item), self._source(self.item), self._type,
192 self._format_args(self.arguments),
193 formatter(self.doc))
195 @staticmethod 1ab
196 def _format_args(args): 1ab
197 return '[ %s ]' % ' | '.join(args) 2a c j d e sbtb, ubvbbb
199 def __str__(self): 1ab
200 return 'KeywordInfo[name: %s, source: %s, doc: %s]' % (self.name, self.source, self.doc)
202 def _name(self, item): 1ab
203 return item.name 2a i ; 9 ! # $ % m f N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p c k l j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb,
205 def __eq__(self, other): 1ab
206 if isinstance(other, str): # DEBUG 206 ↛ 207line 206 didn't jump to line 207 because the condition on line 206 was never true1c
207 return self.name.lower() == other.lower()
208 return self.name.lower() == other.name.lower() 1c
210 def __hash__(self): 1ab
211 return hash(repr(self)) 1ajwdeqt
213 def __lt__(self, other): 1ab
214 if isinstance(other, str): # DEBUG 214 ↛ 215line 214 didn't jump to line 215 because the condition on line 214 was never true1ajwdeqt
215 return self.name.lower() < other.lower()
216 return self.name.lower() < other.name.lower() 1ajwdeqt
219class _XMLKeywordContent(_KeywordInfo): 1ab
221 def __init__(self, item, source, source_type, doc_format): 1ab
222 self._type = source_type 2a c j d e ubvbbb
223 self._source = lambda x: source 2a c j d e ubvbbb
224 _KeywordInfo.__init__(self, item) 2a c j d e ubvbbb
225 self.args = self._format_args(self._parse_args(item)) 2a c j d e ubvbbb
226 if doc_format in ("TEXT", "ROBOT", "REST", "HTML"): 226 ↛ 227line 226 didn't jump to line 227 because the condition on line 226 was never true2a c j d e ubvbbb
227 self.doc_format = doc_format
228 else:
229 self.doc_format = "ROBOT" 2a c j d e ubvbbb
231 def with_alias(self, alias): 1ab
232 if alias: 232 ↛ 233line 232 didn't jump to line 233 because the condition on line 232 was never true1ajde
233 self.source = alias
234 return self 1ajde
236 def _name(self, node): 1ab
237 return node.get('name') 2a c j d e ubvbbb
239 @staticmethod 1ab
240 def _doc(node): 1ab
241 return node.find('doc').text or '' 2a c j d e ubvbbb
243 @staticmethod 1ab
244 def _parse_args(node): 1ab
245 args_node = node.find('arguments') 2a c j d e ubvbbb
246 return [arg_node.text for arg_node in args_node.findall('arg')] 2a c j d e ubvbbb
248 def is_library_keyword(self): 1ab
249 return True 1t
252@total_ordering 1ab
253class LibraryKeywordInfo(_KeywordInfo): 1ab
254 _type = 'test library' 1ab
255 _library_alias = None 1ab
256 item = None 1ab
258 def __init__(self, name, doc, doc_format, library_name, args): 1ab
259 self._item_name = name 2a i 9 ! # $ % m f ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbObKbPbLbQbIbRb
260 self.doc = doc.strip() 2a i 9 ! # $ % m f ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbObKbPbLbQbIbRb
261 self._item_library_name = library_name 2a i 9 ! # $ % m f ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbObKbPbLbQbIbRb
262 self._args = args 2a i 9 ! # $ % m f ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbObKbPbLbQbIbRb
263 ItemInfo.__init__(self, self._item_name, library_name, None) 2a i 9 ! # $ % m f ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbObKbPbLbQbIbRb
264 self.shortdoc = self.doc.splitlines()[0] if self.doc else '' 2a i 9 ! # $ % m f ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbObKbPbLbQbIbRb
266 if doc_format in ("TEXT", "ROBOT", "REST", "HTML"): 2a i 9 ! # $ % m f ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbObKbPbLbQbIbRb
267 self.doc_format = doc_format 2a p Gbc JbObKbPbLbQb
268 else:
269 self.doc_format = "ROBOT" 2a i 9 ! # $ % m f ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbKbLbIbRb
271 def with_alias(self, alias): 1ab
272 self._library_alias = alias 2a 9 ! # $ % f ybzbAbBbp c j g d ( h e
273 self.source = self._source(self.item) 2a 9 ! # $ % f ybzbAbBbp c j g d ( h e
274 return self 2a 9 ! # $ % f ybzbAbBbp c j g d ( h e
276 def _source(self, item): 1ab
277 _ = item 2a 9 ! # $ % f ybzbAbBbp c j g d ( h e sbtb
278 if self._library_alias: 2a 9 ! # $ % f ybzbAbBbp c j g d ( h e sbtb
279 return self._library_alias 1#$%jgh
280 return self._item_library_name 2a 9 ! f ybzbAbBbp c j g d ( h e sbtb
282 @property 1ab
283 def arguments(self): 1ab
284 return self._args 2a i 7bwb9 ! # $ % m eb| fbgbxb8bf ` ybzbAbBbN O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p Gbc ibjbkbMbk l } j g d ( h e M sbtbJbObKbPbLbQbIbRb
286 def is_library_keyword(self): 1ab
287 return True 27bXb9 ! # $ % eb| fbgb8b` 6b9b
289 def __eq__(self, other): 1ab
290 if isinstance(other, str): # DEBUG 290 ↛ 291line 290 didn't jump to line 291 because the condition on line 290 was never true2a p Gbc Ib
291 return self.name.lower() == other.lower() # and self.__hash__ == other.__hash__
292 return self.name.lower() == other.name.lower() 2a p Gbc Ib
294 def __hash__(self): 1ab
295 return hash(repr(self)) # self.name) # 1a9!#$%fpck}j'w_gyzrAsBCxdD(hEFGHILJKeqt
297 def __lt__(self, other): 1ab
298 if isinstance(other, str): # DEBUG 298 ↛ 299line 298 didn't jump to line 299 because the condition on line 298 was never true1a9!#$%fpckj'wgyzrAsBCxdDhEFGHILJKeqt
299 return self.name.lower() < other.lower()
300 return self.name.lower() < other.name.lower() 1a9!#$%fpckj'wgyzrAsBCxdDhEFGHILJKeqt
302 def _name(self, item): 1ab
303 return self._item_name 2sbtb
306@total_ordering 1ab
307class BlockKeywordInfo(_KeywordInfo): 1ab
308 """ Special Info for FOR and END, documentation and since 5.0,
309 IF, ELSE, ELSEIF, WHILE, TRY, EXCEPT, BREAK, CONTINUE. Since 7.0, VAR.
310 """
311 _type = 'test library' 1ab
312 _library_alias = None 1ab
313 item = None 1ab
315 def __init__(self, name, doc, doc_format='ROBOT', library_name='BuiltIn', 1ab
316 *args):
317 self._item_name = name 2a i m f ` N O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p c ibjbkbk l } g h M
318 self.doc = doc.strip() 2a i m f ` N O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p c ibjbkbk l } g h M
319 self._item_library_name = library_name 2a i m f ` N O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p c ibjbkbk l } g h M
320 self.doc_format = doc_format 2a i m f ` N O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p c ibjbkbk l } g h M
321 self._args = args 2a i m f ` N O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p c ibjbkbk l } g h M
322 ItemInfo.__init__(self, self._item_name, library_name, None) 2a i m f ` N O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p c ibjbkbk l } g h M
323 self.shortdoc = self.doc.splitlines()[0] if self.doc else '' 2a i m f ` N O ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u * v n o p c ibjbkbk l } g h M
325 def with_alias(self, alias): 1ab
326 self._library_alias = alias
327 self.source = self._source(self.item)
328 return self
330 def _source(self, item): 1ab
331 _ = item
332 if self._library_alias:
333 return self._library_alias
334 return self._item_library_name
336 @property 1ab
337 def arguments(self): 1ab
338 return self._args 2cbdbm | hbf + `
340 def is_library_keyword(self): 1ab
341 return True 2cbdbm | hbf +
343 def __eq__(self, other): 1ab
344 if isinstance(other, str): # DEBUG
345 return self.name == other
346 return self.name == other.name # must match Capital case
348 def __hash__(self): 1ab
349 return hash(repr(self)) # self.name) # 1akl}j_rs
351 def __lt__(self, other): 1ab
352 if isinstance(other, str): # DEBUG 352 ↛ 353line 352 didn't jump to line 353 because the condition on line 352 was never true1krs
353 return self.name < other
354 return self.name < other.name 1krs
356 def _name(self, item): 1ab
357 return self._item_name
360class UserKeywordInfo(_KeywordInfo): 1ab
362 @staticmethod 1ab
363 def _source(item): 1ab
364 return os.path.basename(item.source) if item.source else '' 2a i ; 9 ! # $ % m f N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p c k l j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb,
366 @staticmethod 1ab
367 def _doc(item): 1ab
368 return utils.unescape(item.doc.value) 2a i ; 9 ! # $ % m f N ~ abO ) P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ Vb* v n o p c k l j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb,
370 def _parse_args(self, uk): 1ab
371 parsed = [] 2a i - SbXb; . TbUbHb1b5b/ f + O P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ v n o ' w t ,
372 for arg in uk.args.value: 2a i - SbXb; . TbUbHb1b5b/ f + O P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ v n o ' w t ,
373 if self._is_scalar(arg): 2a i - SbXb; . TbUbHb1b/ f + n o ' w t ,
374 parsed.append(self._parse_name_and_default(arg)) 2a i - Sb; . TbUbHb/ f + n o ' w t ,
375 elif self._is_list(arg): 375 ↛ 377line 375 didn't jump to line 377 because the condition on line 375 was always true2XbHb1b,
376 parsed.append(self._parse_vararg(arg)) 2XbHb1b,
377 elif self._is_dict(arg):
378 parsed.append(self._parse_kwarg(arg))
379 return parsed 2a i - SbXb; . TbUbHb1b5b/ f + O P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ v n o ' w t ,
381 @staticmethod 1ab
382 def _is_scalar(arg): 1ab
383 return arg.startswith('$') 2a i - SbXb; . TbUbHb1b/ f + n o ' w t ,
385 def _parse_name_and_default(self, arg): 1ab
386 parts = arg.split('=', 1) 2a i - Sb; . TbUbHb/ f + n o ' w t ,
387 name = self._strip_var_syntax_chars(parts[0]) 2a i - Sb; . TbUbHb/ f + n o ' w t ,
388 if len(parts) == 1: 2a i - Sb; . TbUbHb/ f + n o ' w t ,
389 return name 2a i - Sb; . TbUb/ f + n o ' w t ,
390 return name + '=' + parts[1] 2i - SbTbUbHb,
392 @staticmethod 1ab
393 def _strip_var_syntax_chars(string): 1ab
394 return string[2:-1] 2a i - SbXb; . TbUbHb1b/ f + n o ' w t ,
396 @staticmethod 1ab
397 def _is_list(arg): 1ab
398 return arg.startswith('@') 2XbHb1b,
400 @staticmethod 1ab
401 def _is_dict(arg): 1ab
402 return arg.startswith('&')
404 def _parse_vararg(self, arg): 1ab
405 return '*' + self._strip_var_syntax_chars(arg) 2XbHb1b,
407 def _parse_kwarg(self, arg): 1ab
408 return '**' + self._strip_var_syntax_chars(arg)
411@total_ordering 1ab
412class TestCaseUserKeywordInfo(UserKeywordInfo): 1ab
413 __test__ = False 1ab
414 _type = 'test case file' 1ab
416 @property 1ab
417 def longname(self): 1ab
418 return self.name 2a i ; 9 ! # $ % m N ~ abO P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ * v n o c k l j ' w _ g y z r A s B C x d D h E F G H I L J K e q t
420 def __eq__(self, other): 1ab
421 if isinstance(other, self.__class__): # DEBUG
422 return self.name.lower() == other.name.lower() # and self.__hash__ == other.__hash__
423 else:
424 return False
426 def __hash__(self): 1ab
427 return hash(self.longname) # repr(self)) 2a i ; 9 ! # $ % m N ~ abO P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ * v n o c k l j ' w _ g y z r A s B C x d D h E F G H I L J K e q t
429 def __lt__(self, other): 1ab
430 if isinstance(other, str): # DEBUG 430 ↛ 431line 430 didn't jump to line 431 because the condition on line 430 was never true2a i ; 9 ! # $ % m N ~ abO P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ * v n o c k j ' w _ g y z r A s B C x d D h E F G H I L J K e q t
431 return self.name.lower() < other.lower()
432 return self.name.lower() < other.name.lower() 2a i ; 9 ! # $ % m N ~ abO P Q R S T U V W X Y Z 0 1 2 3 4 5 6 7 8 u ] ^ * v n o c k j ' w _ g y z r A s B C x d D h E F G H I L J K e q t
435@total_ordering 1ab
436class ResourceUserKeywordInfo(UserKeywordInfo): 1ab
437 _type = 'resource file' 1ab
439 @property 1ab
440 def longname(self): 1ab
441 return self.item.parent.parent.rawname + '.' + self.name 2a f N ~ ab) u ] ^ v n o p c j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t Nb
443 def __eq__(self, other): 1ab
444 if isinstance(other, self.__class__): 444 ↛ 447line 444 didn't jump to line 447 because the condition on line 444 was always true1acjw_deqt
445 return self.name.lower() == other.name.lower() 1acjw_deqt
446 else:
447 return False
449 def __hash__(self): 1ab
450 return hash(self.longname) # repr(self)) 2a f N ~ ab) u ] ^ v n o p c j ' w _ g y z r A s B C x d D h E F G H I L J K : e q t
452 def __lt__(self, other): 1ab
453 if isinstance(other, str): # DEBUG 453 ↛ 454line 453 didn't jump to line 454 because the condition on line 453 was never true2a f N ~ ab) u ] ^ v n o p c j ' w _ g y z r A s B C x d D h E F G H I L J K e q t
454 return self.name.lower() < other.lower()
455 return self.name.lower() < other.name.lower() 2a f N ~ ab) u ] ^ v n o p c j ' w _ g y z r A s B C x d D h E F G H I L J K e q t
458PRIORITIES = {ItemInfo: 50, 1ab
459 BlockKeywordInfo: 45,
460 LibraryKeywordInfo: 40,
461 ResourceUserKeywordInfo: 30,
462 TestCaseUserKeywordInfo: 20,
463 VariableInfo: 10,
464 ArgumentInfo: 5,
465 LocalVariableInfo: 5}