Permalink
Browse files

Add `load_python_object` to load a python object using a qualified name.

- Import the function from the hyde project (`hyde.loader`)
- Import the tests
- Update version and changelog
  • Loading branch information...
lakshmivyas committed Mar 8, 2013
1 parent ef9d9a1 commit 57c022c5196e153145cf5124c4b2e9fa8442ad00
Showing with 116 additions and 5 deletions.
  1. +6 −1 CHANGELOG.rst
  2. +2 −2 README.rst
  3. +53 −0 commando/tests/test_loader.py
  4. +53 −0 commando/util.py
  5. +2 −2 setup.py
View
@@ -1,3 +1,8 @@
+Version 0.3.2a
+--------------
+
+- Add `load_python_object` to load a python object using a qualified name.
+
Version 0.3.1a
--------------
@@ -10,7 +15,7 @@ Version 0.3a
Thanks to `Julien Danjou`_ :
-- Add support for nested sub commands.
+- Add support for nested sub commands.
{0e26a6fe2571accb78d26318ab1b8dc65636d2b0}. (Pull #7)
Version 0.2.1a
View
@@ -2,13 +2,13 @@
commando - argparse in style
============================
-**Version 0.3.1a**
+**Version 0.3.2a**
A simple wrapper for ``argparse`` that allows commands and arguments
to be defined declaratively using decorators. Note that this does
not support all the features of ``argparse`` yet.
-Commando also bundles a few utilities that are useful when building
+Commando also bundles a few utilities that are useful when building
command line applications.
Example
@@ -0,0 +1,53 @@
+# -*- coding: utf-8 -*-
+"""
+Use nose
+`$ pip install nose`
+`$ nosetests`
+"""
+
+from commando.util import CommandoLoaderException, load_python_object
+from nose.tools import raises
+import os
+
+from fswrap import File
+
+
+def test_can_load_locals():
+
+ file_class = load_python_object('fswrap.File')
+ assert file_class
+
+ f = file_class(__file__)
+ assert f
+
+ assert f.name == os.path.basename(__file__)
+
+
+def test_can_load_from_python_path():
+
+ markdown = load_python_object('markdown.markdown')
+ assert markdown
+
+ assert "<h3>h3</h3>" == markdown("### h3")
+
+def test_can_load_module_without_dot():
+
+ yaml = load_python_object('yaml')
+
+ abc = yaml.load("""
+ d: efg
+ l: mno
+ """)
+
+ assert abc['d'] == 'efg'
+ assert abc['l'] == 'mno'
+
+@raises(CommandoLoaderException)
+def test_exception_raised_for_invalid_module():
+ load_python_object("junk.junk.junk")
+ assert False
+
+@raises(CommandoLoaderException)
+def test_exception_raised_for_invalid_object():
+ load_python_object("markdown.junk")
+ assert False
View
@@ -7,6 +7,49 @@
from logging import NullHandler
from subprocess import check_call, check_output, Popen
+class CommandoLoaderException(Exception): pass
+
+def load_python_object(name):
+ """
+ Loads a python module from string
+ """
+ logger = getLoggerWithNullHandler('commando.load_python_object')
+ (module_name, _, object_name) = name.rpartition(".")
+ if module_name == '':
+ (module_name, object_name) = (object_name, module_name)
+ try:
+ logger.debug('Loading module [%s]' % module_name)
+ module = __import__(module_name)
+ except ImportError:
+ raise CommandoLoaderException(
+ "Module [%s] cannot be loaded." % module_name)
+
+ if object_name == '':
+ return module
+
+ try:
+ module = sys.modules[module_name]
+ except KeyError:
+ raise CommandoLoaderException(
+ "Error occured when loading module [%s]" % module_name)
+
+ try:
+ logger.debug('Getting object [%s] from module [%s]' %
+ (object_name, module_name))
+ return getattr(module, object_name)
+ except AttributeError:
+ raise CommandoLoaderException(
+ "Cannot load object [%s]. "
+ "Module [%s] does not contain object [%s]. "
+ "Please fix the configuration or "
+ "ensure that the module is installed properly" %
+ (
+ name,
+ module_name,
+ object_name
+ )
+ )
+
class ShellCommand(object):
"""
@@ -120,3 +163,13 @@ def format(self, record):
return message + RESET_SEQ
logging.ColorFormatter = ColorFormatter
+
+
+__all__ = [
+ 'CommandoLoaderException',
+ 'load_python_object',
+ 'ShellCommand',
+ 'ColorFormatter',
+ 'getLoggerWithNullHandler',
+ 'getLoggerWithConsoleHandler'
+ ]
View
@@ -13,7 +13,7 @@
description='A declarative interface to argparse with additional utilities',
long_description=long_description,
- version='0.3.1a',
+ version='0.3.2a',
author='Lakshmi Vyas',
author_email='lakshmi.vyas@gmail.com',
@@ -22,7 +22,7 @@
packages=['commando'],
requires=['python (>= 2.7)'],
provides=['commando'],
- test_requires=['nose', 'mock'],
+ test_requires=['nose', 'mock', 'fswrap', 'markdown', 'yaml'],
license='MIT',

0 comments on commit 57c022c

Please sign in to comment.