In this post, we will use the new name, Odoo instead of OpenERP but the content and the examples are compatible with OpenERP 5.0, 6.0, 6.1 and 7.0 and of course with Odoo v8.0. There is no need to be worried, I will try to be compatible with the new version.
If you are glad with this content, just inform me via my twitter account.
Usually, when you want to discuss with Odoo in Python, you have several options.
- Based on the HTTP protocol, you have the xmlrpc and jsonrpc protocols.
- Based on the simple socket, you can use the netrpc (there is no documentation for this protocol).
The protocols
xmlrpc (since the beginning of Odoo)
jsonrpc (introduced in OpenERP 7.0)
- introduced in OpenERP 7.0 via the web module
- based on HTTP (virtualhost via nginx)
- need a web session
netrpc (deprecated)
- available for some versions of OpenERP
- use socket and the Pickle module of Python
Imagining that you want to show the users from the database, you can use the following code with the xmlrpclib module of the Standard Library of Python.
#!/usr/bin/env python
from __future__ import print_function
from xmlrpclib import ServerProxy
SERVER = 'http://localhost:8069'
DATABASE = 'demo'
USERNAME = 'admin'
PASSWORD = 'admin'
server = ServerProxy('http://localhost:8069/xmlrpc/common')
user_id = server.login(DATABASE, USERNAME, PASSWORD)
server = ServerProxy('http://localhost:8069/xmlrpc/object')
user_ids = server.execute(
DATABASE, user_id, PASSWORD,
'res.users', 'search', []
)
users = server.execute(
DATABASE, user_id, PASSWORD,
'res.users', 'read', user_ids, []
)
for user in users:
print(user['id'], user['name'])
With the above example, I think it’s not very verbose, the code is very simple. We use the ServerProxy object from the xmlrpclib library and the library does the rest.
But in some cases, for example, if you have a lot of xmlrpc calls, the code starts to be too long and very verbose. And by the way, I think you will not like write a file with one hundred of lines.
Now, we will use the ERPpeek library by Florent Xicluna.
Here is the same example with ERPpeek
#!/usr/bin/env python
from __future__ import print_function
import erppeek
SERVER = 'http://localhost:8069'
DATABASE = 'demo'
USERNAME = 'admin'
PASSWORD = 'admin'
client = erppeek.Client(SERVER, DATABASE, USERNAME, PASSWORD)
proxy = client.model('res.users')
# No need to use the model.search method, the model.browse method accepts a domain
users = proxy.browse([])
for user in users:
print("{user.id} {user.name}".format(user=user))
Interested in this library? Let’s go for this tutorial.
Firstly, you need to install the library. In my case, I prefer to use a virtualenv but you are free to do as you want. The installation will be executed via the pip command (from the python-pip package if you are using debian or ubuntu).
In the case where you want to use a virtualenv.
pip install virtualenv
virtualenv ~/.venvs/erppeek
source ~/.venvs/erppeek/bin/activate
Once your environment is installed, you can install the library with pip.
Install the library
pip install erppeek
After that, you’ll be free to use it via the CLI provided by the library, because this one contains a CLI called erppeek ;-) Or you can use the library via the API and in this tutorial, we will use this option, the API.
List the databases
#!/usr/bin/env python
from __future__ import print_function
import erppeek
SERVER = 'http://localhost:8069'
client = erppeek.Client(server=SERVER)
for database in client.db.list():
print('database: %r' % (database,))
Check if a database exists
#!/usr/bin/env python
from __future__ import print_function
import erppeek
DATABASE = 'demo'
SERVER = 'http://localhost:8069'
client = erppeek.Client(server=SERVER)
database_exists = DATABASE in client.db.list()
if database_exists:
print("Database {} exists".format(DATABASE))
else:
print("Database {} does not exist".format(DATABASE))
Create a database
Firstly, when you start with Odoo, you want to create a new database.
#!/usr/bin/env python
from __future__ import print_function
import erppeek
DATABASE = 'demo'
SERVER = 'http://localhost:8069'
ADMIN_PASSWORD = 'admin'
client = erppeek.Client(server=SERVER)
if not DATABASE in client.db.list():
print("the database does not exist...")
client.create_database(ADMIN_PASSWORD, DATABASE)
Default configuration
erppeek allows you to use a .INI file (erppeek.ini) for the configuration of several environments. By the way, instead of using the erppeek.Client method, and pass the arguments for the connection, you can use the erppeek.Client.from_config method and give the right environment.
[demo]
host = localhost
port = 8069
database = demo
username = admin
password = admin
For example, here is the right code
#!/usr/bin/env python
import erppeek
# if you don't use the configuration file, you need to use the __init__
# method of the Client class
client = erppeek.Client('http://localhost:8069', 'demo', 'admin', 'admin')
# you can use the erppeek.Client.from_config method
client = erppeek.Client.from_config('demo')
List the installed modules
#!/usr/bin/env python
from __future__ import print_function
import erppeek
client = erppeek.Client.from_config('demo')
installed_modules = client.modules(installed=True)
for module in installed_modules['installed']:
print(module)
# or you can use the other code which use the model('ir.module.module')
proxy = client.model('ir.module.module')
installed_modules = proxy.browse([('state', '=', 'installed')])
for module in installed_modules:
print('{:>5} {}'.format(module.name, module.description))
Update the module list
#!/usr/bin/env python
from __future__ import print_function
import erppeek
client = erppeek.Client.from_config('demo')
proxy = client.model('ir.module.module')
proxy.update_list()
Install the CRM module
#!/usr/bin/env python
from __future__ import print_function
import erppeek
client = erppeek.Client.from_config('demo')
modules = client.modules('crm', installed=False)
if 'crm' in modules['uninstalled']:
client.install('crm')
List the models
Here is a part of code which shows how to fetch the list of the models installed in the database.
#!/usr/bin/env python
from __future__ import print_function
import erppeek
client = erppeek.Client.from_config('demo')
proxy = client.model('ir.model')
for model in proxy.browse([]):
print("{model.model} {model.state}".format(model=model))
Show the description of a model
#!/usr/bin/env python
from __future__ import print_function
import erppeek
DEFAULTS = dict(help='', string='Unknown')
client = erppeek.Client.from_config('demo')
user_model = client.model('res.users')
for fname, field in sorted(user_model.fields().items()):
values = dict(DEFAULTS, name=fname, **field)
print("{name:30} {type:10} {string}".format(**values))
Create a new model
In this example, we will see how to create a new model via XML-RPC and add a new field.
#!/usr/bin/env python
from __future__ import print_function
import erppeek
client = erppeek.Client.from_config('demo')
model_proxy = client.model('ir.model')
field_proxy = client.model('ir.model.fields')
values = {
'model': 'x_contact',
'name': 'Contact',
'state': 'manual',
}
# With this instruction, you are going to create the model
# in the database without one line of python code.
model = model_proxy.create(values)
values = {
'name': 'x_firstname',
'ttype': 'char',
'size': 64,
'field_description': 'Firstname',
'model_id': model.id,
'model': model.model,
'domain': '[]',
}
field = field_proxy.create(values)
With this code, you will be able to create a new record with ERPpeek
contact_proxy = client.model('x_contact')
contact_proxy.create({'x_firstname': 'Stephane'})
for contact in contact_proxy.browse([]):
print(contact.x_firstname)
In the second part of this series, I will explain how to create an invoice and print it with the old system (RML) and the new system (Webkit) and a lot of funny stuff ;-)
You can send me your feedback and I will adapt my post with your experience of Erppeek.
Troubleshooting
Connection refused
In this case, just check that your server is running ;-)