parseSelection parses user selection string into indices Supports formats: "all", "1", "1,3", "1-3", "1,3-5,7" Note: Input should already be cleaned (no spaces)
(selection string, total int)
| 295 | // Supports formats: "all", "1", "1,3", "1-3", "1,3-5,7" |
| 296 | // Note: Input should already be cleaned (no spaces) |
| 297 | func parseSelection(selection string, total int) ([]int, error) { |
| 298 | // Handle "all" |
| 299 | if strings.ToLower(selection) == "all" { |
| 300 | indices := make([]int, total) |
| 301 | for i := 0; i < total; i++ { |
| 302 | indices[i] = i |
| 303 | } |
| 304 | return indices, nil |
| 305 | } |
| 306 | |
| 307 | var indices []int |
| 308 | seen := make(map[int]bool) |
| 309 | |
| 310 | // Split by comma |
| 311 | parts := strings.Split(selection, ",") |
| 312 | for _, part := range parts { |
| 313 | if part == "" { |
| 314 | continue // Skip empty parts |
| 315 | } |
| 316 | |
| 317 | // Check if it's a range (e.g., "1-3") |
| 318 | if strings.Contains(part, "-") { |
| 319 | rangeParts := strings.Split(part, "-") |
| 320 | if len(rangeParts) != 2 { |
| 321 | return nil, fmt.Errorf("invalid range format: '%s'", part) |
| 322 | } |
| 323 | |
| 324 | start, err := strconv.Atoi(rangeParts[0]) |
| 325 | if err != nil { |
| 326 | return nil, fmt.Errorf("invalid number in range: '%s' (error: %v)", rangeParts[0], err) |
| 327 | } |
| 328 | |
| 329 | end, err := strconv.Atoi(rangeParts[1]) |
| 330 | if err != nil { |
| 331 | return nil, fmt.Errorf("invalid number in range: '%s' (error: %v)", rangeParts[1], err) |
| 332 | } |
| 333 | |
| 334 | if start < 1 || end > total || start > end { |
| 335 | return nil, fmt.Errorf("range %d-%d is out of bounds (valid range: 1-%d)", start, end, total) |
| 336 | } |
| 337 | |
| 338 | for i := start; i <= end; i++ { |
| 339 | idx := i - 1 // Convert to 0-based index |
| 340 | if !seen[idx] { |
| 341 | indices = append(indices, idx) |
| 342 | seen[idx] = true |
| 343 | } |
| 344 | } |
| 345 | } else { |
| 346 | // Single number |
| 347 | num, err := strconv.Atoi(part) |
| 348 | if err != nil { |
| 349 | return nil, fmt.Errorf("invalid number: '%s' (error: %v)", part, err) |
| 350 | } |
| 351 | |
| 352 | if num < 1 || num > total { |
| 353 | return nil, fmt.Errorf("number %d is out of bounds (valid range: 1-%d)", num, total) |
| 354 | } |