Skip to content

Commit a694597

Browse files
committed
fix: Handle more marker subtypes in from_line_marker
1 parent a648bba commit a694597

File tree

1 file changed

+39
-40
lines changed

1 file changed

+39
-40
lines changed

src/text_manipulation/range_spec.py

Lines changed: 39 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -174,10 +174,8 @@ def from_line_marker(
174174
assert search_line, "Empty marker"
175175
assert search_term.type == MarkerType.LINE, f"Invalid marker type: {search_term.type}"
176176

177-
matches = {t: [] for t in MATCH_TYPES}
178177

179-
stripped_search = search_line.strip()
180-
normalized_search_line = cls.normalize_line(stripped_search)
178+
matches = {t: [] for t in MATCH_TYPES}
181179

182180
if search_start_index < 0:
183181
search_start_index = 0
@@ -193,81 +191,82 @@ def from_line_marker(
193191
f"must be less than or equal to line count ({len(lines)})"
194192
)
195193

196-
marker_subtype = (search_term.marker_subtype or "").casefold()
194+
marker_subtype = (search_term.marker_subtype or "string").casefold()
197195

196+
# Handle special marker subtypes that don't use normal line matching
198197
match marker_subtype:
199-
case 'number': # Line number relative to search range
200-
relative_index = int(stripped_search) - 1
198+
case 'number': # Match by line number relative to search range
199+
relative_index = search_line - 1
201200
if search_range:
202201
# Make index relative to search range start
203202
index = search_range.start + relative_index
204-
assert 0 <= index <= len(lines), (
205-
f"Line number {stripped_search} out of bounds "
206-
f"(must be in interval [1, {len(lines) + 1}] "
207-
f"relative to context)"
208-
)
203+
if not (0 <= index <= len(lines)):
204+
raise ValueError(
205+
f"Line number {search_line} out of bounds "
206+
f"(must be in interval [1, {len(lines) + 1}] relative to context)"
207+
)
209208
else:
210-
# No context - use absolute file line number
211209
index = relative_index
212-
assert 0 <= index < len(lines), (
213-
f"Line number {stripped_search} out of bounds "
214-
f"(must be in interval [1, {len(lines)}])"
215-
)
210+
if not (0 <= index < len(lines)):
211+
raise ValueError(
212+
f"Line number {search_line} out of bounds "
213+
f"(must be in interval [1, {len(lines)}])"
214+
)
216215
reference_indent = get_line_indent_count_from_lines(lines, index)
217216
index += calc_index_delta_for_relative_position(search_term)
218217
return cls(index, index, reference_indent)
219218

220-
case 'regex':
219+
case 'regex': # Match using regex pattern
221220
try:
222221
pattern = re.compile(search_line)
223222
except re.error as e:
224223
raise ValueError(f"Invalid regex pattern '{search_line}': {e}")
225224

226-
case _:
225+
case _: # Default string matching modes
227226
pattern = None
227+
stripped_search = search_line.strip() if search_line else ""
228+
normalized_search_line = cls.normalize_line(stripped_search)
228229

229-
# Not a line number, so we need to find all line matches
230+
# Find all matching lines based on marker subtype
230231
for i in range(search_start_index, search_end_index):
231232
reference_indent = get_line_indent_count_from_lines(lines, i)
232-
233233
line = lines[i]
234+
stripped_line = line.strip()
235+
normalized_line = cls.normalize_line(line)
236+
234237
match marker_subtype:
238+
case 'empty':
239+
if not line or not stripped_line:
240+
matches['stripped'].append((i, reference_indent))
241+
242+
case 'indent-level':
243+
if reference_indent == search_line: # TODO Calc indent level
244+
matches['exact'].append((i, reference_indent))
235245

236246
case 'regex':
237-
if pattern.search(line) or pattern.search(line.strip()):
247+
if pattern.search(line) or pattern.search(stripped_line):
238248
matches['exact'].append((i, reference_indent))
239249

240250
case 'prefix':
241-
# Check for stripped prefix match
242-
if line.strip().startswith(stripped_search):
251+
if stripped_line.startswith(stripped_search):
243252
matches['exact'].append((i, reference_indent))
244-
# Check for normalized prefix match
245-
elif cls.normalize_line(line).startswith(normalized_search_line):
253+
elif normalized_line.startswith(normalized_search_line):
246254
matches['normalized'].append((i, reference_indent))
247255

248256
case 'suffix':
249-
# Check for stripped suffix match
250-
if line.strip().endswith(stripped_search):
257+
if stripped_line.endswith(stripped_search):
251258
matches['exact'].append((i, reference_indent))
252-
# Check for normalized suffix match
253-
elif cls.normalize_line(line).endswith(normalized_search_line):
259+
elif normalized_line.endswith(normalized_search_line):
254260
matches['normalized'].append((i, reference_indent))
255261

256-
case _:
257-
# Check for exact match
262+
case 'string' | _: # Default string matching
258263
if search_line == line:
259264
matches['exact'].append((i, reference_indent))
260-
261-
# Check for stripped match
262-
elif stripped_search == line.strip():
265+
elif stripped_search == stripped_line:
263266
matches['stripped'].append((i, reference_indent))
264-
265-
# Check for normalized match
266-
elif normalized_search_line == cls.normalize_line(line):
267+
elif normalized_search_line == normalized_line:
267268
matches['normalized'].append((i, reference_indent))
268-
269-
# Dangerous! Last resort!
270-
elif normalized_search_line.casefold() in cls.normalize_line(line).casefold():
269+
elif normalized_search_line.casefold() in normalized_line.casefold():
271270
matches['partial'].append((i, reference_indent))
272271

273272
offset = search_term.offset or 0

0 commit comments

Comments
 (0)