summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Crute <mcrute@gmail.com>2010-04-21 00:16:16 -0400
committerMike Crute <mcrute@gmail.com>2010-04-21 00:16:16 -0400
commite74452aabeb77ab8ab8f50a350d77e4d9e6914a2 (patch)
tree08a8bcd262622ded9f2996d1d37c174661df4b63
parent5156d1d7635806a237bdf9857702068290fc6340 (diff)
downloadobalie-e74452aabeb77ab8ab8f50a350d77e4d9e6914a2.tar.bz2
obalie-e74452aabeb77ab8ab8f50a350d77e4d9e6914a2.tar.xz
obalie-e74452aabeb77ab8ab8f50a350d77e4d9e6914a2.zip
Adding basic info command
-rw-r--r--obalie/client.py35
-rw-r--r--obalie/commands/__init__.py47
-rw-r--r--obalie/commands/info.py54
-rw-r--r--obalie/utils.py10
4 files changed, 140 insertions, 6 deletions
diff --git a/obalie/client.py b/obalie/client.py
index d943bb8..cc40122 100644
--- a/obalie/client.py
+++ b/obalie/client.py
@@ -7,6 +7,7 @@ Subversion Client
7@date: April 20, 2010 7@date: April 20, 2010
8""" 8"""
9 9
10from xml.dom import pulldom
10from urlparse import urlparse 11from urlparse import urlparse
11from obalie.commands import load_commands 12from obalie.commands import load_commands
12from obalie.exceptions import UnsupportedCommand 13from obalie.exceptions import UnsupportedCommand
@@ -15,6 +16,10 @@ from obalie.utils import run_command
15 16
16 17
17class Client(object): 18class Client(object):
19 """
20 Subversion client that supports both remote and local subversion
21 repositories.
22 """
18 23
19 @inject_logger 24 @inject_logger
20 def __init__(self, repo_url, trust_server=True, config_dir=None, 25 def __init__(self, repo_url, trust_server=True, config_dir=None,
@@ -24,7 +29,7 @@ class Client(object):
24 self.config_dir = config_dir 29 self.config_dir = config_dir
25 self.trust_server = trust_server 30 self.trust_server = trust_server
26 self.additional_config = config 31 self.additional_config = config
27 self.verbosity = None 32 self._repository_info = None
28 self.commands = {} 33 self.commands = {}
29 34
30 self._unpack_url(repo_url) 35 self._unpack_url(repo_url)
@@ -37,11 +42,17 @@ class Client(object):
37 self.commands = load_commands() 42 self.commands = load_commands()
38 43
39 try: 44 try:
40 cmd = self.commands[name](self) 45 return self.commands[name](self)
41 return cmd
42 except KeyError: 46 except KeyError:
43 raise UnsupportedCommand(name) 47 raise UnsupportedCommand(name)
44 48
49 @property
50 def repository_info(self):
51 if not self._repository_info:
52 self._repository_info = self.info()
53
54 return self._repository_info
55
45 def _unpack_url(self, url): 56 def _unpack_url(self, url):
46 """ 57 """
47 Parses a repository URL and loads its parts into the instance. 58 Parses a repository URL and loads its parts into the instance.
@@ -83,10 +94,22 @@ class Client(object):
83 94
84 return ' '.join(args) 95 return ' '.join(args)
85 96
86 def run_raw_command(self, subcommand, *args): 97 def run_raw_command(self, subcommand, *args, **kwargs):
87 command = [self.command, self._get_svn_args(), subcommand] 98 """
99 Runs a raw subversion command and returns the results.
100 """
101 cmd_args = kwargs.pop('cmd_args', '')
102 command = [self.command, cmd_args, self._get_svn_args(), subcommand]
88 command = ' '.join(command + list(args)) 103 command = ' '.join(command + list(args))
89 104
90 self.logger.debug("Command: %r", command) 105 self.logger.debug("Command: %r", command)
91 106
92 return run_command(command) 107 return run_command(command, **kwargs)
108
109 def get_xml_output(self, subcommand, *args):
110 """
111 Runs a raw command passing the XML flag and returns a pulldom
112 instance ready for use.
113 """
114 output = self.run_raw_command(subcommand, *args, raw_output=True, cmd_args='--xml')
115 return pulldom.parseString(output)
diff --git a/obalie/commands/__init__.py b/obalie/commands/__init__.py
index e69de29..f0e3682 100644
--- a/obalie/commands/__init__.py
+++ b/obalie/commands/__init__.py
@@ -0,0 +1,47 @@
1# vim: set filencoding=utf8
2"""
3Subversion Commands
4
5@author: Mike Crute (mcrute@ag.com)
6@organization: SoftGroup Interactive, Inc.
7@date: April 20, 2010
8"""
9
10
11import os
12import sys
13from obalie.log import inject_logger
14
15
16# Commands are relative to this directory by default
17__dir__ = os.path.dirname(__file__)
18
19
20def load_commands(from_path=__dir__, package=__name__):
21 commands = {}
22
23 for filename in os.listdir(from_path):
24 name = filename[:-len('.py')]
25 import_path = '.'.join([package, name])
26
27 mod = __import__(import_path, globals(), locals(), [name])
28
29 command_catalog = getattr(mod, 'COMMANDS', None)
30 if command_catalog:
31 commands.update(command_catalog)
32 continue
33
34 impl_name = "{0}Command".format(name.capitalize())
35 command_impl = getattr(mod, impl_name, None)
36 if command_impl:
37 commands[name] = command_impl
38
39 return commands
40
41
42class BaseCommand(object):
43
44 @inject_logger
45 def __init__(self, client, logger=None):
46 self.client = client
47 self.logger = logger
diff --git a/obalie/commands/info.py b/obalie/commands/info.py
new file mode 100644
index 0000000..5bd29fd
--- /dev/null
+++ b/obalie/commands/info.py
@@ -0,0 +1,54 @@
1# vim: set filencoding=utf8
2"""
3Subversion Info
4
5@author: Mike Crute (mcrute@ag.com)
6@organization: SoftGroup Interactive, Inc.
7@date: April 20, 2010
8"""
9
10
11import os
12from xml.dom import pulldom
13from obalie.utils import join_url
14from obalie.commands import BaseCommand
15
16
17class RepositoryInfo(object):
18
19 def __init__(self, path=None, root=None, uuid=None, revision=None):
20 self.path = path
21 self.root = root
22 self.uuid = uuid
23 self.revision = revision
24
25 @property
26 def relative_path(self):
27 return self.path[len(self.root):]
28
29
30class InfoCommand(BaseCommand):
31
32 def __call__(self, path='/'):
33 path = join_url(self.client.repo_url, path)
34 self.logger.info('Running info for path: %s', path)
35
36 repo_info = RepositoryInfo()
37
38 xml = self.client.get_xml_output('info', path)
39 for event, node in xml:
40 if event != pulldom.START_ELEMENT:
41 continue
42
43 if node.tagName in ('url', 'root', 'uuid'):
44 xml.expandNode(node)
45
46 if node.tagName == 'url':
47 repo_info.path = node.firstChild.data
48 elif node.tagName == 'root':
49 repo_info.root = node.firstChild.data
50 elif node.tagName == 'uuid':
51 repo_info.uuid = node.firstChild.data
52
53 return repo_info
54
diff --git a/obalie/utils.py b/obalie/utils.py
index dcf476a..2d4be0e 100644
--- a/obalie/utils.py
+++ b/obalie/utils.py
@@ -9,6 +9,7 @@ Miscellaneous Utility Commands
9 9
10 10
11import shlex 11import shlex
12from urlparse import urljoin
12from subprocess import Popen, PIPE 13from subprocess import Popen, PIPE
13from obalie.exceptions import ExecutableError 14from obalie.exceptions import ExecutableError
14 15
@@ -30,3 +31,12 @@ def run_command(command, raw_output=False):
30 return stdout 31 return stdout
31 else: 32 else:
32 return stdout.splitlines(True) 33 return stdout.splitlines(True)
34
35
36def join_url(base, path):
37 """
38 Joins a URL but ignores the leading slash on the path that would
39 otherwise truncate the base part back to the hostname.
40 """
41 path = path.lstrip('/')
42 return urljoin(base, path)