1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150
|
# Name: plugin.py
# Purpose: Pluggable component support
# Author: Roman Rolinsky <rolinsky@femagsoft.com>
# Created: 31.05.2007
# RCS-ID: $Id: plugin.py 69876 2011-11-30 15:46:26Z ROL $
'''
Functions for loading plugins.
'''
import os, sys, glob
from xml.dom import minidom
from globals import *
from presenter import Manager
import component
import meta
def load_plugins_from_dirs():
'''Load plugins from XRCEDPATH directories.'''
dirs = os.getenv('XRCEDPATH')
if dirs:
for dir in dirs.split(':'):
if os.path.isdir(dir):
load_plugins(dir)
def load_plugins(dir):
'''Load plugins from C{dir}.'''
sys_path = sys.path
cwd = os.getcwd()
dir = os.path.abspath(os.path.normpath(dir))
TRACE('* load_plugins from %s' % dir)
os.chdir(dir)
sys.path = [dir] + sys_path
try: # try/finally shield
ff_py = glob.glob('[!_]*.py')
for f in ff_py:
name = os.path.splitext(f)[0]
TRACE('* __import__ %s', name)
try:
__import__(name, globals(), locals(), ['*'])
except ImportError:
logger.exception('importing %s failed', name)
ff_crx = glob.glob('*.crx')
for crx in ff_crx:
TRACE('* load_crx %s', crx)
try:
load_crx(crx)
except:
logger.exception('parsing CRX file %s failed', crx)
dirs = glob.glob('*/')
for dir in dirs:
if os.path.isfile(os.path.join(dir, '__init__.py')):
TRACE('* import __init__.py in %s', dir)
try:
__import__(dir, globals(), locals(), ['*'])
except ImportError:
logger.exception('importing __init__.py failed')
finally:
sys.path = sys_path
os.chdir(cwd)
def load_crx(filename):
'''Load components defined in a manifest file.'''
dom = minidom.parse(filename)
for node in dom.documentElement.childNodes:
if node.nodeType == node.ELEMENT_NODE and node.tagName == 'component':
create_component(node)
def create_component(node):
'''Create component from a manifest data.
@param node: DOM C{Element} object containing component manifest data.
'''
klass = node.getAttribute('class')
name = node.getAttribute('name')
TRACE('create_component %s', name)
comp = getattr(meta, klass)
compClass = getattr(component, comp.klass) # get component class
attributesIn = comp.getAttribute(node, 'attributes')
# Process attr:klass pairs
attributes = []
specials = {}
for a in attributesIn:
i = a.find(':')
if i != -1:
a,kl = a[:i],a[i+1:]
specials[a] = getattr(component, kl)
attributes.append(a)
attParamsIn = comp.getAttribute(node, 'params')
# Process attr:param_class pairs
params = {}
for a in attParamsIn:
i = a.find(':')
if i != -1:
a,kl = a[:i],a[i+1:]
params[a] = getattr(component.params, kl)
groups = comp.getAttribute(node, 'groups')
styles = comp.getAttribute(node, 'styles')
events = comp.getAttribute(node, 'events')
c = compClass(name, groups, attributes, specials=specials, params=params, events=events)
c.hasName = bool(comp.getAttribute(node, 'has-name'))
c.addStyles(*styles)
Manager.register(c)
menu = comp.getAttribute(node, 'menu')
label = comp.getAttribute(node, 'label')
if menu and label:
try:
index = int(comp.getAttribute(node, 'index'))
except:
index = 1000
help = comp.getAttribute(node, 'help')
Manager.setMenu(c, menu, label, help, index)
panel = comp.getAttribute(node, 'panel')
if panel:
try:
pos = map(int, comp.getAttribute(node, 'pos').split(','))
except:
pos = component.DEFAULT_POS
try:
span = map(int, comp.getAttribute(node, 'span').split(','))
except:
span = (1, 1)
Manager.setTool(c, panel, pos=pos, span=span)
dlName = comp.getAttribute(node, 'DL')
if dlName:
TRACE('Loading dynamic library: %s', dlName)
if not g._CFuncPtr:
try:
import ctypes
g._CFuncPtr = ctypes._CFuncPtr
except:
print 'import ctypes module failed'
if g._CFuncPtr:
dl = ctypes.CDLL(dlName)
try:
Manager.addXmlHandler(dl.AddXmlHandlers)
except:
logger.exception('DL registration failed')
module = comp.getAttribute(node, 'module')
handler = comp.getAttribute(node, 'handler')
if module and handler:
TRACE('importing handler %s from %s', handler, module)
try:
mod = __import__(module, globals(), locals(), [handler])
Manager.addXmlHandler(getattr(mod, handler))
except ImportError:
logger.exception("can't import handler module")
except AttributeError:
logger.exception("can't find handler class")
|