You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 

106 lines
3.7 KiB

  1. """Command line client functionality"""
  2. import nilmdb.client
  3. from nilmdb.utils.printf import *
  4. from nilmdb.utils import datetime_tz
  5. import nilmdb.utils.time
  6. import sys
  7. import os
  8. import argparse
  9. from argparse import ArgumentDefaultsHelpFormatter as def_form
  10. # Valid subcommands. Defined in separate files just to break
  11. # things up -- they're still called with Cmdline as self.
  12. subcommands = [ "help", "info", "create", "list", "metadata",
  13. "insert", "extract", "remove", "destroy",
  14. "intervals", "rename" ]
  15. # Import the subcommand modules
  16. subcmd_mods = {}
  17. for cmd in subcommands:
  18. subcmd_mods[cmd] = __import__("nilmdb.cmdline." + cmd, fromlist = [ cmd ])
  19. class JimArgumentParser(argparse.ArgumentParser):
  20. def error(self, message):
  21. self.print_usage(sys.stderr)
  22. self.exit(2, sprintf("error: %s\n", message))
  23. class Cmdline(object):
  24. def __init__(self, argv = None):
  25. self.argv = argv or sys.argv[1:]
  26. self.client = None
  27. self.def_url = os.environ.get("NILMDB_URL", "http://localhost:12380")
  28. self.subcmd = {}
  29. def arg_time(self, toparse):
  30. """Parse a time string argument"""
  31. try:
  32. return nilmdb.utils.time.parse_time(toparse).totimestamp()
  33. except ValueError as e:
  34. raise argparse.ArgumentTypeError(sprintf("%s \"%s\"",
  35. str(e), toparse))
  36. def parser_setup(self):
  37. self.parser = JimArgumentParser(add_help = False,
  38. formatter_class = def_form)
  39. group = self.parser.add_argument_group("General options")
  40. group.add_argument("-h", "--help", action='help',
  41. help='show this help message and exit')
  42. group.add_argument("-V", "--version", action="version",
  43. version = nilmdb.__version__)
  44. group = self.parser.add_argument_group("Server")
  45. group.add_argument("-u", "--url", action="store",
  46. default=self.def_url,
  47. help="NilmDB server URL (default: %(default)s)")
  48. sub = self.parser.add_subparsers(
  49. title="Commands", dest="command",
  50. description="Use 'help command' or 'command --help' for more "
  51. "details on a particular command.")
  52. # Set up subcommands (defined in separate files)
  53. for cmd in subcommands:
  54. self.subcmd[cmd] = subcmd_mods[cmd].setup(self, sub)
  55. def die(self, formatstr, *args):
  56. fprintf(sys.stderr, formatstr + "\n", *args)
  57. if self.client:
  58. self.client.close()
  59. sys.exit(-1)
  60. def run(self):
  61. # Clear cached timezone, so that we can pick up timezone changes
  62. # while running this from the test suite.
  63. datetime_tz._localtz = None
  64. # Run parser
  65. self.parser_setup()
  66. self.args = self.parser.parse_args(self.argv)
  67. # Run arg verify handler if there is one
  68. if "verify" in self.args:
  69. self.args.verify(self)
  70. self.client = nilmdb.client.Client(self.args.url)
  71. # Make a test connection to make sure things work,
  72. # unless the particular command requests that we don't.
  73. if "no_test_connect" not in self.args:
  74. try:
  75. server_version = self.client.version()
  76. except nilmdb.client.Error as e:
  77. self.die("error connecting to server: %s", str(e))
  78. # Now dispatch client request to appropriate function. Parser
  79. # should have ensured that we don't have any unknown commands
  80. # here.
  81. retval = self.args.handler(self) or 0
  82. self.client.close()
  83. sys.exit(retval)