~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/plugin.py

  • Committer: Robert Collins
  • Date: 2005-10-30 00:00:09 UTC
  • mfrom: (1185.16.134)
  • Revision ID: robertc@robertcollins.net-20051030000009-9db99a338a0dfdac
MergeĀ fromĀ Martin.

Show diffs side-by-side

added added

removed removed

Lines of Context:
42
42
import imp
43
43
import os
44
44
import sys
45
 
import types
46
45
 
47
46
import bzrlib
48
47
from bzrlib.config import config_dir
50
49
        log_exception_quietly
51
50
from bzrlib.errors import BzrError
52
51
from bzrlib import plugins
53
 
from bzrlib.osutils import pathjoin
54
 
 
55
 
DEFAULT_PLUGIN_PATH = pathjoin(config_dir(), 'plugins')
56
 
 
 
52
 
 
53
DEFAULT_PLUGIN_PATH = os.path.join(config_dir(), 'plugins')
 
54
 
 
55
all_plugins = []
57
56
_loaded = False
58
57
 
59
58
 
60
 
def all_plugins():
61
 
    """Return a dictionary of the plugins."""
62
 
    result = {}
63
 
    for name, plugin in bzrlib.plugins.__dict__.items():
64
 
        if isinstance(plugin, types.ModuleType):
65
 
            result[name] = plugin
66
 
    return result
67
 
 
68
 
 
69
59
def load_plugins():
70
 
    """Load bzrlib plugins.
 
60
    """Find all python plugins and load them.
 
61
 
 
62
    Loading a plugin means importing it into the python interpreter.
 
63
    The plugin is expected to make calls to register commands when
 
64
    it's loaded (or perhaps access other hooks in future.)
 
65
 
 
66
    A list of plugs is stored in bzrlib.plugin.all_plugins for future
 
67
    reference.
71
68
 
72
69
    The environment variable BZR_PLUGIN_PATH is considered a delimited
73
70
    set of paths to look through. Each entry is searched for *.py
74
71
    files (and whatever other extensions are used in the platform,
75
72
    such as *.pyd).
 
73
    """
76
74
 
77
 
    load_from_dirs() provides the underlying mechanism and is called with
78
 
    the default directory list to provide the normal behaviour.
79
 
    """
80
 
    global _loaded
 
75
    global all_plugins, _loaded
81
76
    if _loaded:
82
77
        # People can make sure plugins are loaded, they just won't be twice
83
78
        return
84
79
        #raise BzrError("plugins already initialized")
85
80
    _loaded = True
86
81
 
87
 
    dirs = os.environ.get('BZR_PLUGIN_PATH', DEFAULT_PLUGIN_PATH).split(os.pathsep)
 
82
    dirs = os.environ.get('BZR_PLUGIN_PATH', DEFAULT_PLUGIN_PATH).split(":")
88
83
    dirs.insert(0, os.path.dirname(plugins.__file__))
89
84
 
90
 
    load_from_dirs(dirs)
91
 
 
92
 
 
93
 
def load_from_dirs(dirs):
94
 
    """Load bzrlib plugins found in each dir in dirs.
95
 
 
96
 
    Loading a plugin means importing it into the python interpreter.
97
 
    The plugin is expected to make calls to register commands when
98
 
    it's loaded (or perhaps access other hooks in future.)
99
 
 
100
 
    Plugins are loaded into bzrlib.plugins.NAME, and can be found there
101
 
    for future reference.
102
 
    """
103
85
    # The problem with imp.get_suffixes() is that it doesn't include
104
86
    # .pyo which is technically valid
105
87
    # It also means that "testmodule.so" will show up as both test and testmodule
109
91
    suffixes.append(('.pyo', 'rb', imp.PY_COMPILED))
110
92
    package_entries = ['__init__.py', '__init__.pyc', '__init__.pyo']
111
93
    for d in dirs:
 
94
        # going through them one by one allows different plugins with the same
 
95
        # filename in different directories in the path
 
96
        mutter('looking for plugins in %s' % d)
112
97
        if not d:
113
98
            continue
114
 
        mutter('looking for plugins in %s', d)
115
99
        plugin_names = set()
116
100
        if not os.path.isdir(d):
117
101
            continue
118
102
        for f in os.listdir(d):
119
 
            path = pathjoin(d, f)
 
103
            path = os.path.join(d, f)
120
104
            if os.path.isdir(path):
121
105
                for entry in package_entries:
122
106
                    # This directory should be a package, and thus added to
123
107
                    # the list
124
 
                    if os.path.isfile(pathjoin(path, entry)):
 
108
                    if os.path.isfile(os.path.join(path, entry)):
125
109
                        break
126
110
                else: # This directory is not a package
127
111
                    continue
134
118
                        break
135
119
                else:
136
120
                    continue
137
 
            if getattr(bzrlib.plugins, f, None):
138
 
                mutter('Plugin name %s already loaded', f)
139
 
            else:
140
 
                mutter('add plugin name %s', f)
141
 
                plugin_names.add(f)
 
121
            mutter('add plugin name %s' % f)
 
122
            plugin_names.add(f)
142
123
 
143
124
        plugin_names = list(plugin_names)
144
125
        plugin_names.sort()
145
126
        for name in plugin_names:
146
127
            try:
147
128
                plugin_info = imp.find_module(name, [d])
148
 
                mutter('load plugin %r', plugin_info)
 
129
                mutter('load plugin %r' % (plugin_info,))
149
130
                try:
150
131
                    plugin = imp.load_module('bzrlib.plugins.' + name,
151
132
                                             *plugin_info)
 
133
                    all_plugins.append(plugin)
152
134
                    setattr(bzrlib.plugins, name, plugin)
153
135
                finally:
154
136
                    if plugin_info[0] is not None:
155
137
                        plugin_info[0].close()
156
138
 
157
139
                mutter('loaded succesfully')
158
 
            except KeyboardInterrupt:
159
 
                raise
160
 
            except Exception, e:
161
 
                ## import pdb; pdb.set_trace()
 
140
            except:
 
141
                ## import pdb
 
142
                ## pdb.set_trace()
162
143
                warning('Unable to load plugin %r from %r' % (name, d))
163
144
                log_exception_quietly()