diff --git a/bin/addons/__init__.py b/bin/addons/__init__.py index f1d74009ff5..cefd6859e6c 100644 --- a/bin/addons/__init__.py +++ b/bin/addons/__init__.py @@ -45,8 +45,8 @@ logger = netsvc.Logger() opj = os.path.join -_ad = opj(tools.config['root_path'], 'addons') # default addons path (base) -ad = tools.config['addons_path'] # alternate addons path +_ad = os.path.abspath(opj(tools.config['root_path'], 'addons')) # default addons path (base) +ad = os.path.abspath(tools.config['addons_path']) # alternate addons path sys.path.insert(1, _ad) if ad != _ad: @@ -131,10 +131,37 @@ class Node(Singleton): s += '%s`-> %s' % (' ' * depth, c._pprint(depth+1)) return s -def _get_module_path(module): - if os.path.exists(opj(ad, module)): +def get_module_path(module): + """Return the path of the given module. + """ + + if os.path.exists(opj(ad, module)) or os.path.exists(opj(ad, '%s.zip' % module)): return opj(ad, module) - return opj(_ad, module) + + if os.path.exists(opj(_ad, module)) or os.path.exists(opj(_ad, '%s.zip' % module)): + return opj(_ad, module) + + raise IOError, 'Module not found : %s' % module + +def get_module_resource(module, *args): + """Return the full path of a resource of the given module. + + @param module: the module + @param args: the resource path components + + @return: absolute path to the resource + """ + return opj(get_module_path(module), *args) + +def get_modules(): + """Returns the list of module names + """ + + module_list = os.listdir(ad) + module_names = [os.path.basename(m) for m in module_list] + module_list += [m for m in os.listdir(_ad) if m not in module_names] + + return module_list def create_graph(module_list, force=None): if not force: @@ -145,9 +172,9 @@ def create_graph(module_list, force=None): for module in module_list: if module[-4:]=='.zip': module = module[:-4] - mod_path = _get_module_path(module) - terp_file = opj(mod_path, '__terp__.py') - if os.path.isfile(terp_file) or zipfile.is_zipfile(mod_path+'.zip'): + mod_path = get_module_path(module) + terp_file = get_module_resource(module, '__terp__.py') + if os.path.isfile(terp_file) or zipfile.is_zipfile(mod_path): try: info = eval(tools.file_open(terp_file).read()) except: @@ -254,24 +281,20 @@ def load_module_graph(cr, graph, status=None, **kwargs): cr.commit() def register_classes(): - module_list = os.listdir(ad) - module_names = [os.path.basename(m) for m in module_list] - module_list += [m for m in os.listdir(_ad) if m not in module_names] - + module_list = get_modules() for package in create_graph(module_list): m = package.name logger.notifyChannel('init', netsvc.LOG_INFO, 'addon:%s:registering classes' % m) sys.stdout.flush() - mod_path = _get_module_path(m) - if not os.path.isfile(mod_path + '.zip'): + mod_path = get_module_path(m) + if not os.path.isfile(mod_path+'.zip'): # XXX must restrict to only addons paths imp.load_module(m, *imp.find_module(m)) else: import zipimport - mod_path = mod_path + '.zip' try: - zimp = zipimport.zipimporter(mod_path) + zimp = zipimport.zipimporter(mod_path+'.zip') zimp.load_module(m) except zipimport.ZipImportError: logger.notifyChannel('init', netsvc.LOG_ERROR, 'Couldn\'t find module %s' % m) diff --git a/bin/addons/base/ir/ir_actions.py b/bin/addons/base/ir/ir_actions.py index a4a7ae71d1c..50168aac610 100644 --- a/bin/addons/base/ir/ir_actions.py +++ b/bin/addons/base/ir/ir_actions.py @@ -30,6 +30,8 @@ from osv import fields,osv import tools import time +from tools.config import config +import netsvc class actions(osv.osv): _name = 'ir.actions.actions' @@ -306,6 +308,7 @@ class actions_server(osv.osv): # False : Finnished correctly # ACTION_ID : Action to launch def run(self, cr, uid, ids, context={}): + logger = netsvc.Logger() for action in self.browse(cr, uid, ids, context): if action.state=='python': localdict = { @@ -316,11 +319,17 @@ class actions_server(osv.osv): 'cr': cr, 'uid': uid } - print action.code exec action.code in localdict - print localdict.keys() if 'action' in localdict: return localdict['action'] + if action.state == 'email': + user = "%s@yahoo.co.in," % (config['smtp_user']) + subject = action.name + body = action.message + if tools.email_send_attach(user, action.address, subject, body) == True: + logger.notifyChannel('email', netsvc.LOG_INFO, 'Email successfully send to : %s' % (user)) + else: + logger.notifyChannel('email', netsvc.LOG_ERROR, 'Failed to send email to : %s' % (user)) return False actions_server() diff --git a/bin/addons/base/ir/ir_rule.py b/bin/addons/base/ir/ir_rule.py index 093c32981ab..6f76133341d 100644 --- a/bin/addons/base/ir/ir_rule.py +++ b/bin/addons/base/ir/ir_rule.py @@ -205,7 +205,7 @@ class ir_rule(osv.osv): query_global, val_global = _query(clause_global, 'OR') if query_global: if query: - query = '('+query+') AND '+query_global + query = '('+query+') OR '+query_global val.extend(val_global) else: query = query_global diff --git a/bin/addons/base/ir/ir_translation.py b/bin/addons/base/ir/ir_translation.py index 211f9dbaf45..ac87f08d76a 100644 --- a/bin/addons/base/ir/ir_translation.py +++ b/bin/addons/base/ir/ir_translation.py @@ -43,6 +43,7 @@ TRANSLATION_TYPE = [ ('xsl', 'XSL'), ('help', 'Help'), ('code', 'Code'), + ('constraint', 'Constraint'), ] class ir_translation(osv.osv, Cacheable): @@ -138,12 +139,10 @@ class ir_translation(osv.osv, Cacheable): 'and name=%s', (lang, tt, str(name))) res = cr.fetchone() - if res: - self.add((lang, tt, name, source), res[0]) - return res[0] - else: - self.add((lang, tt, name, source), False) - return False + + trad = res and res[0] or '' + self.add((lang, tt, name, source), trad) + return trad def unlink(self, cursor, user, ids, context=None): self.clear() diff --git a/bin/addons/base/module/module.py b/bin/addons/base/module/module.py index 0ebb5d9ab79..1ad9a844ea0 100644 --- a/bin/addons/base/module/module.py +++ b/bin/addons/base/module/module.py @@ -38,9 +38,7 @@ import release import zipimport import wizard - - - +import addons ver_regexp = re.compile("^(\\d+)((\\.\\d+)*)([a-z]?)((_(pre|p|beta|alpha|rc)\\d*)*)(-r(\\d+))?$") suffix_regexp = re.compile("^(alpha|beta|rc|pre|p)(\\d*)$") @@ -199,7 +197,7 @@ class module(osv.osv): def get_module_info(self, name): try: - f = tools.file_open(os.path.join(tools.config['addons_path'], name, '__terp__.py')) + f = tools.file_open(os.path.join(name, '__terp__.py')) data = f.read() info = eval(data) if 'version' in info: @@ -343,18 +341,17 @@ class module(osv.osv): filepath = files[lang] # if filepath does not contain :// we prepend the path of the module if filepath.find('://') == -1: - filepath = os.path.join(tools.config['addons_path'], module['name'], filepath) + filepath = addons.get_module_resource(module['name'], filepath) tools.trans_load(filepath, lang) return True # update the list of available packages def update_list(self, cr, uid, context={}): robj = self.pool.get('ir.module.repository') - adp = tools.config['addons_path'] res = [0, 0] # [update, add] # iterate through installed modules and mark them as being so - for name in os.listdir(adp): + for name in addons.get_modules(): mod_name = name if name[-4:]=='.zip': mod_name=name[:-4] @@ -384,20 +381,19 @@ class module(osv.osv): self._update_category(cr, uid, ids[0], terp.get('category', 'Uncategorized')) continue - terp_file = os.path.join(adp, name, '__terp__.py') - mod_path = os.path.join(adp, name) + terp_file = addons.get_module_resource(name, '__terp__.py') + mod_path = addons.get_module_path(name) if os.path.isdir(mod_path) or os.path.islink(mod_path) or zipfile.is_zipfile(mod_path): terp = self.get_module_info(mod_name) if not terp or not terp.get('installable', True): continue - if not os.path.isfile(os.path.join(adp, mod_name+'.zip')): + if not os.path.isfile(mod_path+'.zip'): import imp # XXX must restrict to only addons paths imp.load_module(name, *imp.find_module(mod_name)) else: import zipimport - mod_path = os.path.join(adp, mod_name+'.zip') - zimp = zipimport.zipimporter(mod_path) + zimp = zipimport.zipimporter(mod_path+'.zip') zimp.load_module(mod_name) id = self.create(cr, uid, { 'name': mod_name, @@ -472,7 +468,6 @@ class module(osv.osv): def download(self, cr, uid, ids, download=True, context=None): res = [] - adp = tools.config['addons_path'] for mod in self.browse(cr, uid, ids, context=context): if not mod.url: continue @@ -486,7 +481,7 @@ class module(osv.osv): if not download: continue zipfile = urllib.urlopen(mod.url).read() - fname = os.path.join(adp, mod.name+'.zip') + fname = addons.get_module_path(mod.name+'.zip') try: fp = file(fname, 'wb') fp.write(zipfile) diff --git a/bin/addons/base/module/module_wizard.xml b/bin/addons/base/module/module_wizard.xml index 2c700b1e616..e6a445e3a86 100644 --- a/bin/addons/base/module/module_wizard.xml +++ b/bin/addons/base/module/module_wizard.xml @@ -27,22 +27,26 @@ wizard.module.lang.export form -
+ - + -