diff options
author | Araq <rumpf_a@web.de> | 2012-11-18 05:12:32 -0800 |
---|---|---|
committer | Araq <rumpf_a@web.de> | 2012-11-18 05:12:32 -0800 |
commit | a56418b7164b0f93146c597e1862fee91e61eb76 (patch) | |
tree | bbae2b5be6db25b543135076562ce64a04967efa | |
parent | 02d074882380c5ff149193368a0c1db7962e28d2 (diff) | |
parent | 2e7967886e8e43ac768da9b04dd2d73b61b45fa1 (diff) | |
download | Nim-a56418b7164b0f93146c597e1862fee91e61eb76.tar.gz |
Merge pull request #253 from gradha/pr_reduce_todo_code_repetition
Reduces code repetition through helper procs and templates.
-rw-r--r-- | examples/cross_todo/nimrod_commandline/nimtodo.nim | 142 |
1 files changed, 63 insertions, 79 deletions
diff --git a/examples/cross_todo/nimrod_commandline/nimtodo.nim b/examples/cross_todo/nimrod_commandline/nimtodo.nim index 0579027c5..1067177c3 100644 --- a/examples/cross_todo/nimrod_commandline/nimtodo.nim +++ b/examples/cross_todo/nimrod_commandline/nimtodo.nim @@ -59,6 +59,48 @@ proc initDefaults(params: var TParamConfig) = params.addText = @[] +proc abort(message: string, value: int) = + # Simple wrapper to abort also displaying the help to the user. + stdout.write(USAGE) + quit(message, value) + + +template parseTodoIdAndSetCommand(newCommand: TCommand): stmt = + ## Helper to parse a big todo identifier into todoId and set command. + try: + let numChars = val.parseBiggestInt(newId) + if numChars < 1: raise newException(EInvalidValue, "Empty string?") + result.command = newCommand + result.todoId = newId + except EOverflow: + raise newException(EInvalidValue, "Value $1 too big" % val) + + +template verifySingleCommand(actions: stmt): stmt = + ## Helper to make sure only one command has been specified so far. + if specifiedCommand: + abort("Only one command can be specified at a time! (extra:$1)" % [key], 2) + else: + actions + specifiedCommand = true + + +proc parsePlusMinus(val: string, debugText: string): bool = + ## Helper to process a plus or minus character from the commandline. + ## + ## Pass the string to parse and the type of parameter for debug errors. + ## The processed parameter will be returned as true for a '+' and false for a + ## '-'. The proc aborts with a debug message if the passed parameter doesn't + ## contain one of those values. + case val + of "+": + return true + of "-": + return false + else: + abort("$1 parameter should be + or - but was '$2'." % [debugText, val], 4) + + proc parseCmdLine(): TParamConfig = ## Parses the commandline. ## @@ -84,127 +126,69 @@ proc parseCmdLine(): TParamConfig = if specifiedCommand and cmdAdd == result.command: result.addText.add(key) else: - stdout.write(USAGE) - quit("Argument ($1) detected without add command." % [key], 1) + abort("Argument ($1) detected without add command." % [key], 1) of cmdLongOption, cmdShortOption: case normalize(key) of "help", "h": stdout.write(USAGE) quit(0) of "a": - if specifiedCommand: - stdout.write(USAGE) - quit("Only one command can be specified at a time! ($1)" % [val], 2) - else: + verifySingleCommand: result.command = cmdAdd result.addPriority = val.parseInt - specifiedCommand = true of "c": - if specifiedCommand: - stdout.write(USAGE) - quit("Only one command can be specified at a time! ($1)" % [val], 2) - else: - result.command = cmdCheck - let numChars = string(val).parseBiggestInt(newId) - if numChars < 1: raise newException(EInvalidValue, "Empty string?") - result.todoId = newId - specifiedCommand = true + verifySingleCommand: + parseTodoIdAndSetCommand(cmdCheck) of "u": - if specifiedCommand: - stdout.write(USAGE) - quit("Only one command can be specified at a time! ($1)" % [val], 2) - else: - result.command = cmdUncheck - let numChars = val.parseBiggestInt(newId) - if numChars < 1: raise newException(EInvalidValue, "Empty string?") - result.todoId = newId - specifiedCommand = true + verifySingleCommand: + parseTodoIdAndSetCommand cmdUncheck of "d": - if specifiedCommand: - stdout.write(USAGE) - quit("Only one command can be specified at a time! ($1)" % [val], 2) - else: + verifySingleCommand: if "all" == val: result.command = cmdNuke else: - result.command = cmdDelete - let numChars = val.parseBiggestInt(newId) - if numChars < 1: - raise newException(EInvalidValue, "Empty string?") - result.todoId = newId - specifiedCommand = true + parseTodoIdAndSetCommand cmdDelete of "g": - if specifiedCommand: - stdout.write(USAGE) - quit("Only one command can be specified at a time! ($1)" % [val], 2) - else: + verifySingleCommand: if val.len > 0: - stdout.write(USAGE) - quit("Unexpected value '$1' for switch l." % [val], 3) + abort("Unexpected value '$1' for switch l." % [val], 3) result.command = cmdGenerate - specifiedCommand = true of "l": - if specifiedCommand: - stdout.write(USAGE) - quit("Only one command can be specified at a time! ($1)" % [val], 2) - else: + verifySingleCommand: if val.len > 0: - stdout.write(USAGE) - quit("Unexpected value '$1' for switch l." % [val], 3) + abort("Unexpected value '$1' for switch l." % [val], 3) result.command = cmdList - specifiedCommand = true of "p": usesListParams = true - case val - of "+": - result.listParams.priorityAscending = true - of "-": - result.listParams.priorityAscending = false - else: - stdout.write(USAGE) - quit("Priority parameter ($1) should be + or |." % [val], 4) + result.listParams.priorityAscending = parsePlusMinus(val, "Priority") of "m": usesListParams = true - case val - of "+": - result.listParams.dateAscending = true - of "-": - result.listParams.dateAscending = false - else: - stdout.write(USAGE) - quit("Date parameter ($1) should be + or |." % [val], 4) + result.listParams.dateAscending = parsePlusMinus(val, "Date") of "t": usesListParams = true if val.len > 0: - stdout.write(USAGE) - quit("Unexpected value '$1' for switch t." % [val], 5) + abort("Unexpected value '$1' for switch t." % [val], 5) result.listParams.showChecked = true of "z": usesListParams = true if val.len > 0: - stdout.write(USAGE) - quit("Unexpected value '$1' for switch z." % [val], 5) + abort("Unexpected value '$1' for switch z." % [val], 5) result.listParams.showUnchecked = false else: - stdout.write(USAGE) - quit("Unexpected option '$1'." % [key], 6) + abort("Unexpected option '$1'." % [key], 6) of cmdEnd: break except EInvalidValue: - stdout.write(USAGE) - quit("Invalid int value '$1' for parameter '$2'." % [val, key], 7) + abort("Invalid integer value '$1' for parameter '$2'." % [val, key], 7) if not specifiedCommand: - stdout.write(USAGE) - quit("Didn't specify any command.", 8) + abort("Didn't specify any command.", 8) if cmdAdd == result.command and result.addText.len < 1: - stdout.write(USAGE) - quit("Used the add command, but provided no text/description.", 9) + abort("Used the add command, but provided no text/description.", 9) if usesListParams and cmdList != result.command: - stdout.write(USAGE) - quit("Used list options, but didn't specify the list command.", 10) + abort("Used list options, but didn't specify the list command.", 10) proc generateDatabaseRows(conn: TDbConn) = |