예제 #1
0
파일: config.py 프로젝트: coopengo/proteus
    def __call__(self, *args):
        from trytond.cache import Cache
        from trytond.transaction import Transaction
        from trytond.rpc import RPC

        if self._name in self._object.__rpc__:
            rpc = self._object.__rpc__[self._name]
        elif self._name in getattr(self._object, '_buttons', {}):
            rpc = RPC(readonly=False, instantiate=0)
        else:
            raise TypeError('%s is not callable' % self._name)

        with Transaction().start(self._config.database_name,
                self._config.user, readonly=rpc.readonly) as transaction:
            Cache.clean(self._config.database_name)
            args, kwargs, transaction.context, transaction.timestamp = \
                rpc.convert(self._object, *args)
            meth = getattr(self._object, self._name)
            if not hasattr(meth, 'im_self') or meth.im_self:
                result = rpc.result(meth(*args, **kwargs))
            else:
                assert rpc.instantiate == 0
                inst = args.pop(0)
                if hasattr(inst, self._name):
                    result = rpc.result(meth(inst, *args, **kwargs))
                else:
                    result = [rpc.result(meth(i, *args, **kwargs))
                        for i in inst]
            if not rpc.readonly:
                transaction.commit()
            Cache.resets(self._config.database_name)
        return result
예제 #2
0
 def __setup__(cls):
     super(User, cls).__setup__()
     cls.__rpc__.update({
             'get_preferences': RPC(check_access=False),
             'set_preferences': RPC(
                 readonly=False, check_access=False, fresh_session=True),
             'get_preferences_fields_view': RPC(check_access=False),
             })
     table = cls.__table__()
     cls._sql_constraints += [
         ('login_key', Unique(table, table.login),
             'You can not have two users with the same login!')
     ]
     cls._buttons.update({
             'reset_password': {
                 'invisible': ~Eval('email', True) | (not _has_password),
                 },
             })
     cls._preferences_fields = [
         'name',
         'password',
         'email',
         'signature',
         'menu',
         'pyson_menu',
         'actions',
         'status_bar',
         'warnings',
         'applications',
     ]
     cls._context_fields = [
         'language',
         'language_direction',
         'groups',
     ]
     cls._order.insert(0, ('name', 'ASC'))
예제 #3
0
 def __setup__(cls):
     super(ShipmentOut, cls).__setup__()
     # There can be cases when people might want to use a different
     # shipment carrier at any state except `done`.
     cls.carrier.states = STATES
     cls._error_messages.update({
         'mailclass_missing':
         'Select a mailclass to ship using Endicia [USPS].',
         'error_label':
         'Error in generating label "%s"',
         'tracking_number_already_present':
         'Tracking Number is already present for this shipment.',
         'invalid_state':
         'Labels can only be generated when the '
         'shipment is in Packed or Done states only',
         'wrong_carrier':
         'Carrier for selected shipment is not Endicia',
     })
     cls.__rpc__.update({
         'make_endicia_labels':
         RPC(readonly=False, instantiate=0),
         'get_endicia_shipping_cost':
         RPC(readonly=False, instantiate=0),
     })
예제 #4
0
    def test_check_access(self):
        "Test check_access"
        rpc_no_access = RPC(check_access=False)
        self.assertEqual(rpc_no_access.convert(None, {}), ([], {}, {}, None))

        rpc_with_access = RPC(check_access=True)
        self.assertEqual(rpc_with_access.convert(None, {}),
                         ([], {}, {
                             '_check_access': True
                         }, None))
예제 #5
0
 def __setup__(cls):
     super(PatientPrescriptionOrder, cls).__setup__()
     cls._buttons.update({
         'generate_prescription': {
             'invisible': Equal(Eval('state'), 'validated'),
         },
         'create_prescription': {
             'invisible':
             Or(Equal(Eval('state'), 'done'),
                Equal(Eval('state'), 'validated'))
         },
     })
     ''' Allow calling the set_signature method via RPC '''
     cls.__rpc__.update({
         'set_signature': RPC(readonly=False),
     })
예제 #6
0
 def __setup__(cls):
     super(Invoice, cls).__setup__()
     cls._buttons.update({
         'pay_using_payment_transaction': {
             'invisible': Or(
                 Eval('state') != 'posted',
                 Eval('type') == 'in',
             ),
             'readonly': ~Eval('groups', []).contains(
                 Id('account', 'group_account')),
         },
     })
     cls.__rpc__.update({
         'capture_and_pay_using_transaction': RPC(
             readonly=False, instantiate=0
         ),
     })
예제 #7
0
 def __setup__(cls):
     super(LabTest, cls).__setup__()
     cls._buttons.update({
         'generate_document': {
             'invisible': Not(Equal(Eval('state'), 'draft')),
         },
         'set_to_draft': {
             'invisible': Not(Equal(Eval('state'), 'done')),
         },
         'sign_document': {
             'invisible': Not(Equal(Eval('state'), 'done')),
         },
     })
     ''' Allow calling the set_signature method via RPC '''
     cls.__rpc__.update({
         'set_signature': RPC(readonly=False),
     })
예제 #8
0
    def test_instantiate_unique(self):
        "Test instantiate unique"
        rpc = RPC(instantiate=0, unique=True)
        obj = Mock()

        rpc.convert(obj, [1, 2], {})
        obj.browse.assert_called_once_with([1, 2])

        obj.reset_mock()

        with self.assertRaises(ValueError):
            rpc.convert(obj, [1, 1], {})
예제 #9
0
 def __setup__(cls):
     super(Module, cls).__setup__()
     table = cls.__table__()
     cls._sql_constraints = [
         ('name_uniq', Unique(table, table.name),
          'The name of the module must be unique!'),
     ]
     cls._order.insert(0, ('name', 'ASC'))
     cls.__rpc__.update({
         'on_write': RPC(instantiate=0),
     })
     cls._error_messages.update({
         'delete_state': ('You can not remove a module that is activated '
                          'or will be activated'),
         'missing_dep':
         'Missing dependencies %s for module "%s"',
         'deactivate_dep': ('Some activated modules depend on the ones '
                            'you are trying to deactivate:'),
     })
     cls._buttons.update({
         'activate': {
             'invisible': Eval('state') != 'not activated',
             'depends': ['state'],
         },
         'activate_cancel': {
             'invisible': Eval('state') != 'to activate',
             'depends': ['state'],
         },
         'deactivate': {
             'invisible': Eval('state') != 'activated',
             'depends': ['state'],
         },
         'deactivate_cancel': {
             'invisible': Eval('state') != 'to remove',
             'depends': ['state'],
         },
         'upgrade': {
             'invisible': Eval('state') != 'activated',
             'depends': ['state'],
         },
         'upgrade_cancel': {
             'invisible': Eval('state') != 'to upgrade',
             'depends': ['state'],
         },
     })
예제 #10
0
    def __setup__(cls):
        super(Service, cls).__setup__()
        cls.__rpc__['getTechnicalService'] = RPC(check_access=False,
                                                 readonly=False)

        cls._error_messages.update({
            'modify_invoice': ('You can not modify service "%s".'),
            'delete_cancel': ('You can not delete service "%s".'),
        })

        cls._transitions |= set((
            ('pending', 'review'),
            ('review', 'ready'),
            ('review', 'without'),
            ('review', 'warranty'),
            ('ready', 'delivered'),
            ('without', 'delivered'),
            ('warranty', 'delivered'),
        ))

        cls._buttons.update({
            'review': {
                'invisible': Eval('state') != ('pending')
            },
            'ready': {
                'invisible':
                Eval('state').in_(['pending', 'ready', 'without', 'delivered'])
            },
            'without': {
                'invisible':
                Eval('state').in_(['pending', 'ready', 'without', 'delivered'])
            },
            'warranty': {
                'invisible':
                ~Eval('garanty', True) | (Eval('state').in_(
                    ['pending', 'ready', 'without', 'delivered']))
            },
            'delivered': {
                'invisible':
                Eval('state').in_(['review', 'pending', 'delivered'])
            },
        })
예제 #11
0
 def __setup__(cls):
     super(Payment, cls).__setup__()
     cls._order.insert(0, ('date', 'DESC'))
     cls._transitions |= set((
         ('draft', 'approved'),
         ('approved', 'processing'),
         ('processing', 'succeeded'),
         ('processing', 'failed'),
         ('approved', 'draft'),
         ('succeeded', 'failed'),
         ('failed', 'succeeded'),
     ))
     cls._buttons.update({
         'draft': {
             'invisible': Eval('state') != 'approved',
             'icon': 'tryton-back',
             'depends': ['state'],
         },
         'approve': {
             'invisible': Eval('state') != 'draft',
             'icon': 'tryton-forward',
             'depends': ['state'],
         },
         'succeed': {
             'invisible': ~Eval('state').in_(['processing', 'failed']),
             'icon': 'tryton-ok',
             'depends': ['state'],
         },
         'fail': {
             'invisible': ~Eval('state').in_(['processing', 'succeeded']),
             'icon': 'tryton-cancel',
             'depends': ['state'],
         },
     })
     cls.__rpc__.update({
         'approve':
         RPC(readonly=False, instantiate=0, fresh_session=True),
     })
예제 #12
0
 def __setup__(cls):
     super(Module, cls).__setup__()
     cls._sql_constraints = [
         ('name_uniq', 'unique (name)',
          'The name of the module must be unique!'),
     ]
     cls._order.insert(0, ('name', 'ASC'))
     cls.__rpc__.update({
         'on_write': RPC(instantiate=0),
     })
     cls._error_messages.update({
         'delete_state': ('You can not remove a module that is installed '
                          'or will be installed'),
         'missing_dep':
         'Missing dependencies %s for module "%s"',
         'uninstall_dep': ('The modules you are trying to uninstall '
                           'depends on installed modules:'),
     })
     cls._buttons.update({
         'install': {
             'invisible': Eval('state') != 'uninstalled',
         },
         'install_cancel': {
             'invisible': Eval('state') != 'to install',
         },
         'uninstall': {
             'invisible': Eval('state') != 'installed',
         },
         'uninstall_cancel': {
             'invisible': Eval('state') != 'to remove',
         },
         'upgrade': {
             'invisible': Eval('state') != 'installed',
         },
         'upgrade_cancel': {
             'invisible': Eval('state') != 'to upgrade',
         },
     })
예제 #13
0
 def __setup__(cls):
     super(Statement, cls).__setup__()
     cls._order[0] = ('id', 'DESC')
     cls._transitions |= set((
             ('draft', 'validated'),
             ('draft', 'cancelled'),
             ('validated', 'posted'),
             ('validated', 'cancelled'),
             ('cancelled', 'draft'),
             ))
     cls._buttons.update({
             'draft': {
                 'invisible': Eval('state') != 'cancelled',
                 'depends': ['state'],
                 },
             'validate_statement': {
                 'invisible': Eval('state') != 'draft',
                 'depends': ['state'],
                 },
             'post': {
                 'invisible': Eval('state') != 'validated',
                 'depends': ['state'],
                 },
             'cancel': {
                 'invisible': ~Eval('state').in_(['draft', 'validated']),
                 'depends': ['state'],
                 },
             'reconcile': {
                 'invisible': Eval('state').in_(['draft', 'cancelled']),
                 'readonly': ~Eval('to_reconcile'),
                 'depends': ['state', 'to_reconcile'],
                 },
             })
     cls.__rpc__.update({
             'post': RPC(
                 readonly=False, instantiate=0, fresh_session=True),
             })
예제 #14
0
 def __setup__(cls):
     super(Module, cls).__setup__()
     table = cls.__table__()
     cls._sql_constraints = [
         ('name_uniq', Unique(table, table.name),
          'The name of the module must be unique!'),
     ]
     cls._order.insert(0, ('name', 'ASC'))
     cls.__rpc__.update({
         'on_write': RPC(instantiate=0),
     })
     cls._buttons.update({
         'activate': {
             'invisible': Eval('state') != 'not activated',
             'depends': ['state'],
         },
         'activate_cancel': {
             'invisible': Eval('state') != 'to activate',
             'depends': ['state'],
         },
         'deactivate': {
             'invisible': Eval('state') != 'activated',
             'depends': ['state'],
         },
         'deactivate_cancel': {
             'invisible': Eval('state') != 'to remove',
             'depends': ['state'],
         },
         'upgrade': {
             'invisible': Eval('state') != 'activated',
             'depends': ['state'],
         },
         'upgrade_cancel': {
             'invisible': Eval('state') != 'to upgrade',
             'depends': ['state'],
         },
     })
예제 #15
0
    def __call__(self, *args, **kwargs):
        from trytond.rpc import RPC
        from trytond.tools import is_instance_method
        from trytond.transaction import Transaction
        from trytond.worker import run_task

        if self._name in self._object.__rpc__:
            rpc = self._object.__rpc__[self._name]
        elif self._name in getattr(self._object, '_buttons', {}):
            rpc = RPC(readonly=False, instantiate=0)
        else:
            raise TypeError('%s is not callable' % self._name)

        with Transaction().start(self._config.database_name,
                                 self._config.user,
                                 readonly=rpc.readonly) as transaction:
            args, kwargs, transaction.context, transaction.timestamp = \
                rpc.convert(self._object, *args, **kwargs)
            meth = getattr(self._object, self._name)
            if (rpc.instantiate is None
                    or not is_instance_method(self._object, self._name)):
                result = rpc.result(meth(*args, **kwargs))
            else:
                assert rpc.instantiate == 0
                inst = args.pop(0)
                if hasattr(inst, self._name):
                    result = rpc.result(meth(inst, *args, **kwargs))
                else:
                    result = [
                        rpc.result(meth(i, *args, **kwargs)) for i in inst
                    ]
            transaction.commit()
        while transaction.tasks:
            task_id = transaction.tasks.pop()
            run_task(self._config.database_name, task_id)
        return result
예제 #16
0
 def __setup__(cls):
     super(ViewTreeState, cls).__setup__()
     cls.__rpc__.update({
         'set': RPC(readonly=False, check_access=False),
         'get': RPC(check_access=False),
     })
예제 #17
0
 def __setup__(cls):
     super(ViewTreeWidth, cls).__setup__()
     cls.__rpc__.update({
         'set_width': RPC(readonly=False),
     })
예제 #18
0
 def __setup__(cls):
     super(DictSchemaMixin, cls).__setup__()
     cls.__rpc__.update({
         'get_keys': RPC(instantiate=0),
     })
예제 #19
0
 def __setup__(cls):
     super(Icon, cls).__setup__()
     cls.__rpc__.update({
         'list_icons': RPC(),
     })
예제 #20
0
파일: export.py 프로젝트: tryton/trytond
 def __setup__(cls):
     super().__setup__()
     cls.__rpc__.update(
         update=RPC(instantiate=0, readonly=False))
예제 #21
0
 def __setup__(cls):
     super(Invoice, cls).__setup__()
     cls.__rpc__.update({
         'render': RPC(instantiate=0),
     })
예제 #22
0
 def test_simple(self):
     "Test simple"
     rpc = RPC(check_access=False)
     self.assertEqual(rpc.convert(None, 'foo', {}), (['foo'], {}, {}, None))
예제 #23
0
 def __setup__(cls):
     super(Report, cls).__setup__()
     cls.__rpc__ = {
         'execute': RPC(),
     }
예제 #24
0
    def __setup__(cls):
        super(ModelView, cls).__setup__()
        cls.__rpc__['fields_view_get'] = RPC()
        cls.__rpc__['view_toolbar_get'] = RPC()
        cls.__rpc__['on_change'] = RPC(instantiate=0)
        cls.__rpc__['on_change_with'] = RPC(instantiate=0)
        cls._buttons = {}

        fields_ = {}
        callables = {}
        for name in dir(cls):
            if name.startswith('__'):
                continue
            attr = getattr(cls, name)
            if isinstance(attr, fields.Field):
                fields_[name] = attr
            elif callable(attr):
                callables[name] = attr

        methods = {
            'depends': collections.defaultdict(set),
            'depend_methods': collections.defaultdict(set),
            'change': collections.defaultdict(set),
        }
        cls.__change_buttons = methods['change']

        def get_callable_attributes(name, method):
            for parent_cls in cls.__mro__:
                parent_meth = getattr(parent_cls, name, None)
                if not parent_meth:
                    continue
                for attr in ['depends', 'depend_methods', 'change']:
                    parent_value = getattr(parent_meth, attr, None)
                    if parent_value:
                        methods[attr][name] |= parent_value

        for name, method in callables.items():
            get_callable_attributes(name, method)

        def setup_field(field_name, field, attribute):
            if attribute == 'selection_change_with':
                if isinstance(getattr(field, 'selection', None), str):
                    function_name = field.selection
                else:
                    return
            else:
                function_name = '%s_%s' % (attribute, field_name)
            if not getattr(cls, function_name, None):
                return

            function = getattr(cls, function_name, None)
            setattr(
                field, attribute,
                getattr(field, attribute) | methods['depends'][function_name])

            meth_names = list(methods['depend_methods'][function_name])
            meth_done = set()
            while meth_names:
                meth_name = meth_names.pop()
                assert callable(getattr(cls, meth_name)), \
                    "%s.%s not callable" % (cls, meth_name)
                setattr(
                    field, attribute,
                    getattr(field, attribute) | methods['depends'][meth_name])
                meth_names += list(methods['depend_methods'][meth_name] -
                                   meth_done)
                meth_done.add(meth_name)

            if (attribute == 'on_change'
                    and not getattr(function, 'on_change', None)):
                # Decorate on_change to always return self
                setattr(cls, function_name, on_change(function))

        for name, field in fields_.items():
            for attribute in [
                    'on_change',
                    'on_change_with',
                    'autocomplete',
                    'selection_change_with',
            ]:
                setup_field(name, field, attribute)
예제 #25
0
파일: modelview.py 프로젝트: tryton/trytond
    def __post_setup__(cls):
        super(ModelView, cls).__post_setup__()

        methods = {
            '_done': set(),
            'depends': collections.defaultdict(set),
            'depend_methods': collections.defaultdict(set),
            'change': collections.defaultdict(set),
        }
        cls.__change_buttons = methods['change']

        def set_methods(name):
            if name in methods['_done']:
                return
            methods['_done'].add(name)
            for parent_cls in cls.__mro__:
                parent_meth = getattr(parent_cls, name, None)
                if not parent_meth:
                    continue
                for attr in ['depends', 'depend_methods', 'change']:
                    if isinstance(parent_meth, property):
                        parent_value = getattr(parent_meth.fget, attr, set())
                        parent_value |= getattr(parent_meth.fset, attr, set())
                    else:
                        parent_value = getattr(parent_meth, attr, set())
                    if parent_value:
                        methods[attr][name] |= parent_value

        def setup_field(field_name, field, attribute):
            if attribute == 'selection_change_with':
                if isinstance(getattr(field, 'selection', None), str):
                    function_name = field.selection
                else:
                    return
            else:
                function_name = '%s_%s' % (attribute, field_name)
            function = getattr(cls, function_name, None)
            if not function:
                return

            set_methods(function_name)
            setattr(field, attribute, methods['depends'][function_name])

            meth_names = list(methods['depend_methods'][function_name])
            meth_done = set()
            while meth_names:
                meth_name = meth_names.pop()
                method = getattr(cls, meth_name)
                assert callable(method) or isinstance(method, property), \
                    "%s.%s not callable or property" % (cls, meth_name)
                set_methods(meth_name)
                setattr(
                    field, attribute,
                    getattr(field, attribute) | methods['depends'][meth_name])
                meth_names += list(methods['depend_methods'][meth_name] -
                                   meth_done)
                meth_done.add(meth_name)

            if (attribute == 'on_change'
                    and not getattr(function, 'on_change', None)):
                # Decorate on_change to always return self
                setattr(cls, function_name, on_change(function))

        for name, field in cls._fields.items():
            for attribute in [
                    'on_change',
                    'on_change_with',
                    'autocomplete',
                    'selection_change_with',
            ]:
                setup_field(name, field, attribute)

        # Update __rpc__
        for field_name, field in cls._fields.items():
            field.set_rpc(cls)

        for button in cls._buttons:
            if not is_instance_method(cls, button):
                cls.__rpc__.setdefault(button,
                                       RPC(readonly=False, instantiate=0))
            else:
                cls.__rpc__.setdefault(
                    button, RPC(instantiate=0, result=on_change_result))

            meth_names = set()
            meth_done = set()
            for parent_cls in cls.__mro__:
                parent_meth = getattr(parent_cls, button, None)
                if not parent_meth:
                    continue
                cls.__change_buttons[button] |= getattr(
                    parent_meth, 'change', set())
                meth_names |= getattr(parent_meth, 'change_methods', set())
            while meth_names:
                meth_name = meth_names.pop()
                method = getattr(cls, meth_name)
                assert callable(method) or isinstance(method, property), \
                    "%s.%s not callable or property" % (cls, meth_name)
                set_methods(meth_name)
                cls.__change_buttons[button] |= methods['depends'][meth_name]
                meth_names |= (methods['depend_methods'][meth_name] -
                               meth_done)
                meth_done.add(meth_name)

        set_methods('on_change_notify')
        cls._on_change_notify_depends = methods['depends']['on_change_notify']
        meth_names = list(methods['depend_methods']['on_change_notify'])
        meth_done = set()
        while meth_names:
            meth_name = meth_names.pop()
            method = getattr(cls, meth_name)
            assert callable(method) or isinstance(method, property), \
                "%s.%s not callable or property" % (cls, meth_name)
            set_methods(meth_name)
            cls._on_change_notify_depends |= methods['depends'][meth_name]
            meth_names += list(methods['depend_methods'][meth_name] -
                               meth_done)
            meth_done.add(meth_name)
예제 #26
0
 def __setup__(cls):
     super(Currency, cls).__setup__()
     cls._order.insert(0, ('code', 'ASC'))
     cls.__rpc__.update({
         'compute': RPC(instantiate=slice(0, 3, 2)),
     })
예제 #27
0
 def test_timestamp(self):
     "Test context timestamp"
     rpc = RPC(check_access=False)
     self.assertEqual(rpc.convert(None, {'_timestamp': 'test'}),
                      ([], {}, {}, 'test'))
예제 #28
0
 def __setup__(cls):
     super(ViewSearch, cls).__setup__()
     cls.__rpc__.update({
         'get_search': RPC(),
     })
예제 #29
0
파일: user.py 프로젝트: zarumaru/trytond
 def __setup__(cls):
     super().__setup__()
     cls.__rpc__.update({
         'renew': RPC(readonly=False),
     })
예제 #30
0
def dispatch(host, port, protocol, database_name, user, session, object_type,
        object_name, method, *args, **kwargs):

    if object_type == 'common':
        if method == 'login':
            try:
                database = Database(database_name).connect()
                cursor = database.cursor()
                cursor.close()
            except Exception:
                return False
            res = security.login(database_name, user, session)
            Cache.clean(database_name)
            logger = logging.getLogger('dispatcher')
            msg = res and 'successful login' or 'bad login or password'
            logger.info('%s \'%s\' from %s:%d using %s on database \'%s\''
                % (msg, user, host, port, protocol, database_name))
            Cache.resets(database_name)
            return res or False
        elif method == 'logout':
            name = security.logout(database_name, user, session)
            logger = logging.getLogger('dispatcher')
            logger.info(('logout \'%s\' from %s:%d '
                    'using %s on database \'%s\'')
                % (name, host, port, protocol, database_name))
            return True
        elif method == 'version':
            return VERSION
        elif method == 'timezone_get':
            return CONFIG['timezone']
        elif method == 'list_lang':
            return [
                ('bg_BG', 'Български'),
                ('ca_ES', 'Català'),
                ('cs_CZ', 'Čeština'),
                ('de_DE', 'Deutsch'),
                ('en_US', 'English'),
                ('es_AR', 'Español (Argentina)'),
                ('es_ES', 'Español (España)'),
                ('es_CO', 'Español (Colombia)'),
                ('fr_FR', 'Français'),
                ('lt_LT', 'Lietuvių'),
                ('nl_NL', 'Nederlands'),
                ('ru_RU', 'Russian'),
            ]
        elif method == 'db_exist':
            try:
                database = Database(*args, **kwargs).connect()
                cursor = database.cursor()
                cursor.close(close=True)
                return True
            except Exception:
                return False
        elif method == 'list':
            if CONFIG['prevent_dblist']:
                raise Exception('AccessDenied')
            database = Database().connect()
            try:
                cursor = database.cursor()
                try:
                    res = database.list(cursor)
                finally:
                    cursor.close(close=True)
            except Exception:
                res = []
            return res
        elif method == 'create':
            return create(*args, **kwargs)
        elif method == 'restore':
            return restore(*args, **kwargs)
        elif method == 'drop':
            return drop(*args, **kwargs)
        elif method == 'dump':
            return dump(*args, **kwargs)
        return
    elif object_type == 'system':
        database = Database(database_name).connect()
        database_list = Pool.database_list()
        pool = Pool(database_name)
        if not database_name in database_list:
            pool.init()
        if method == 'listMethods':
            res = []
            for type in ('model', 'wizard', 'report'):
                for object_name, obj in pool.iterobject(type=type):
                    for method in obj.__rpc__:
                        res.append(type + '.' + object_name + '.' + method)
                    if hasattr(obj, '_buttons'):
                        for button in obj._buttons:
                            res.append(type + '.' + object_name + '.' + button)
            return res
        elif method == 'methodSignature':
            return 'signatures not supported'
        elif method == 'methodHelp':
            res = []
            args_list = args[0].split('.')
            object_type = args_list[0]
            object_name = '.'.join(args_list[1:-1])
            method = args_list[-1]
            obj = pool.get(object_name, type=object_type)
            return pydoc.getdoc(getattr(obj, method))

    for count in range(int(CONFIG['retry']), -1, -1):
        try:
            user = security.check(database_name, user, session)
        except DatabaseOperationalError:
            if count:
                continue
            raise
        break

    Cache.clean(database_name)
    database_list = Pool.database_list()
    pool = Pool(database_name)
    if not database_name in database_list:
        with Transaction().start(database_name, user,
                readonly=True) as transaction:
            pool.init()
    obj = pool.get(object_name, type=object_type)

    if method in obj.__rpc__:
        rpc = obj.__rpc__[method]
    elif method in getattr(obj, '_buttons', {}):
        rpc = RPC(readonly=False, instantiate=0)
    else:
        raise UserError('Calling method %s on %s %s is not allowed!'
            % (method, object_type, object_name))

    for count in range(int(CONFIG['retry']), -1, -1):
        with Transaction().start(database_name, user,
                readonly=rpc.readonly) as transaction:
            try:
                args, kwargs, transaction.context, transaction.timestamp = \
                    rpc.convert(obj, *args, **kwargs)
                meth = getattr(obj, method)
                if not hasattr(meth, 'im_self') or meth.im_self:
                    result = rpc.result(meth(*args, **kwargs))
                else:
                    assert rpc.instantiate == 0
                    inst = args.pop(0)
                    if hasattr(inst, method):
                        result = rpc.result(meth(inst, *args, **kwargs))
                    else:
                        result = [rpc.result(meth(i, *args, **kwargs))
                            for i in inst]
                if not rpc.readonly:
                    transaction.cursor.commit()
            except DatabaseOperationalError, exception:
                transaction.cursor.rollback()
                if count and not rpc.readonly:
                    continue
                raise
            except Exception, exception:
                if CONFIG['verbose'] and not isinstance(exception, (
                            NotLogged, ConcurrencyException, UserError,
                            UserWarning)):
                    tb_s = ''.join(traceback.format_exception(*sys.exc_info()))
                    logger = logging.getLogger('dispatcher')
                    logger.error('Exception calling method %s on '
                        '%s %s from %s@%s:%d/%s:\n'
                        % (method, object_type, object_name, user, host, port,
                            database_name) + tb_s)
                transaction.cursor.rollback()
                raise
예제 #31
0
 def __setup__(cls):
     super(Icon, cls).__setup__()
     cls._order.insert(0, ('sequence', 'ASC'))
     cls.__rpc__.update({
         'list_icons': RPC(),
     })
예제 #32
0
 def __setup__(cls):
     super(DebugModelInstance, cls).__setup__()
     cls._order.insert(0, ('name', 'ASC'))
     cls.__rpc__.update({'refresh': RPC(readonly=False)})
     cls._buttons.update({'open_initial': {}})