Connector¶
-
class
connector.connector.Binder(connector_env)[source]¶ Bases:
connector.connector.ConnectorUnitFor one record of a model, capable to find an external or internal id, or create the binding (link) between them
This is a default implementation that can be inherited or reimplemented in the connectors.
This implementation assumes that binding models are
_inheritsof the models they are binding.-
bind(external_id, binding_id)[source]¶ Create the link between an external ID and an OpenERP ID
Parameters: - external_id – external id to bind
- binding_id (int) – OpenERP ID to bind
-
to_backend(binding_id, wrap=False)[source]¶ Give the external ID for an OpenERP binding ID
Parameters: - binding_id – OpenERP binding ID for which we want the backend id
- wrap – if False, binding_id is the ID of the binding, if True, binding_id is the ID of the normal record, the method will search the corresponding binding and returns the backend id of the binding
Returns: external ID of the record
-
to_openerp(external_id, unwrap=False)[source]¶ Give the OpenERP ID for an external ID
Parameters: - external_id – external ID for which we want the OpenERP ID
- unwrap – if True, returns the normal record else return the binding record
Returns: a recordset, depending on the value of unwrap, or an empty recordset if the external_id is not mapped
Return type: recordset
-
-
class
connector.connector.ConnectorEnvironment(backend_record, session, model_name)[source]¶ Bases:
objectEnvironment used by the different units for the synchronization.
-
backend¶ Current backend we are working with. Obtained with
backend_record.get_backend().Instance of:
connector.backend.Backend
-
backend_record¶ Browsable record of the backend. The backend is inherited from the model
connector.backendand have at least atypeand aversion.
-
session¶ Current session we are working in. It contains the OpenERP cr, uid and context.
-
model_name¶ Name of the OpenERP model to work with.
-
_propagate_kwargs¶ List of attributes that must be used by
connector.connector.ConnectorEnvironment.create_environment()when a new connector environment is instantiated.
-
classmethod
create_environment(backend_record, session, model, connector_env=None)[source]¶ Create a new environment ConnectorEnvironment.
Parameters: - backend_record (
openerp.models.Model) – browse record of the backend - session (
connector.session.ConnectorSession) – current session (cr, uid, context) - model_name (str) – name of the model
- connector_env (
connector.connector.ConnectorEnvironment) – an existing environment from which the kwargs will be propagated to the new one
- backend_record (
-
env¶
-
get_connector_unit(base_class)[source]¶ Searches and returns an instance of the
ConnectorUnitfor the current model and being a class or subclass ofbase_class.The returned instance is built with
selffor its environment.Parameters: base_class ( connector.connector.ConnectorUnit) –ConnectorUnitto search (class or subclass)
-
model¶
-
pool¶
-
-
class
connector.connector.ConnectorUnit(connector_env)[source]¶ Bases:
objectAbstract class for each piece of the connector:
- Examples:
Or basically any class intended to be registered in a
Backend.-
advisory_lock_or_retry(lock, retry_seconds=1)[source]¶ Acquire a Postgres transactional advisory lock or retry job
When the lock cannot be acquired, it raises a
RetryableJobErrorso the job is retried after nretry_seconds.Usage example:
lock_name = 'import_record({}, {}, {}, {})'.format( self.backend_record._name, self.backend_record.id, self.model._name, self.external_id, ) self.advisory_lock_or_retry(lock_name, retry_seconds=2)
See :func:
openerp.addons.connector.connector.pg_try_advisory_lockfor details.Parameters: - lock – The lock name. Can be anything convertible to a string. It needs to represent what should not be synchronized concurrently, usually the string will contain at least: the action, the backend type, the backend id, the model name, the external id
- retry_seconds – number of seconds after which a job should be retried when the lock cannot be acquired.
-
env¶ Returns the openerp.api.environment
-
localcontext¶ It is there for compatibility.
openerp.tools.translate._()searches for this attribute in the classes do be able to translate the strings.There is no reason to use this attribute for other purposes.
-
classmethod
match(session, model)[source]¶ Returns True if the current class correspond to the searched model.
Parameters: - session (
connector.session.ConnectorSession) – current session - model (str or
openerp.models.Model) – model to match
- session (
-
model¶
-
unit_for(connector_unit_class, model=None)[source]¶ According to the current
ConnectorEnvironment, search and returns an instance of theConnectorUnitfor the current model and being a class or subclass ofconnector_unit_class.If a different
modelis given, a new ConnectorEnvironment is built for this model. The class used for creating the new environment is the same class as in self.connector_env which must beConnectorEnvironmentor a subclass.Parameters: - connector_unit_class (
connector. connector.ConnectorUnit) –ConnectorUnitto search (class or subclass) - model (str) – to give if the
ConnectorUnitis for another model than the current one
- connector_unit_class (
-
class
connector.connector.MetaConnectorUnit(name, bases, attrs)[source]¶ Bases:
typeMetaclass for ConnectorUnit.
Keeps a
_moduleattribute on the classes, the same way OpenERP does it for the Model classes. It is then used to filter them according to the state of the module (installed or not).-
for_model_names¶ Returns the list of models on which a
ConnectorUnitis usableIt is used in
match()when we search the correctConnectorUnitfor a model.
-
-
connector.connector.get_openerp_module(cls_or_func)[source]¶ For a top level function or class, returns the name of the OpenERP module where it lives.
So we will be able to filter them according to the modules installation state.
-
connector.connector.is_module_installed(env, module_name)[source]¶ Check if an Odoo addon is installed.
Parameters: module_name – name of the addon
-
connector.connector.pg_try_advisory_lock(env, lock)[source]¶ Try to acquire a Postgres transactional advisory lock.
The function tries to acquire a lock, returns a boolean indicating if it could be obtained or not. An acquired lock is released at the end of the transaction.
A typical use is to acquire a lock at the beginning of an importer to prevent 2 jobs to do the same import at the same time. Since the record doesn’t exist yet, we can’t put a lock on a record, so we put an advisory lock.
- Example:
- Job 1 imports Partner A
- Job 2 imports Partner B
- Partner A has a category X which happens not to exist yet
- Partner B has a category X which happens not to exist yet
- Job 1 import category X as a dependency
- Job 2 import category X as a dependency
Since both jobs are executed concurrently, they both create a record for category X so we have duplicated records. With this lock:
- Job 1 imports Partner A, it acquires a lock for this partner
- Job 2 imports Partner B, it acquires a lock for this partner
- Partner A has a category X which happens not to exist yet
- Partner B has a category X which happens not to exist yet
- Job 1 import category X as a dependency, it acquires a lock for this category
- Job 2 import category X as a dependency, try to acquire a lock but can’t, Job 2 is retried later, and when it is retried, it sees the category X created by Job 1.
The lock is acquired until the end of the transaction.
Usage example:
lock_name = 'import_record({}, {}, {}, {})'.format( self.backend_record._name, self.backend_record.id, self.model._name, self.external_id, ) if pg_try_advisory_lock(lock_name): # do sync else: raise RetryableJobError('Could not acquire advisory lock', seconds=2, ignore_retry=True)
Parameters: - env – the Odoo Environment
- lock – The lock name. Can be anything convertible to a string. It needs to represents what should not be synchronized concurrently so usually the string will contain at least: the action, the backend type, the backend id, the model name, the external id
:return True/False whether lock was acquired.