[ADD] rpc: Go examples
Examples rely on `kolo/xmlrpc` as well as on the standard library package `log` to panic on error, matching snippets in other languages (which tend to raise exceptions). As with other languages, only the RPC interaction is spelled out. closes odoo/documentation#5064 Signed-off-by: Xavier Morel (xmo) <xmo@odoo.com>
This commit is contained in:
parent
7ce5a5afe4
commit
0a65b0872d
@ -72,6 +72,15 @@ If you already have an Odoo server installed, you can just use its parameters.
|
||||
username = "admin",
|
||||
password = <insert password for your admin user (default: admin)>;
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var (
|
||||
url = <insert server URL>
|
||||
db = <insert database name>
|
||||
username = "admin"
|
||||
password = <insert password for your admin user (default: admin)>
|
||||
)
|
||||
|
||||
.. _api/external_api/keys:
|
||||
|
||||
API Keys
|
||||
@ -180,6 +189,27 @@ database:
|
||||
The examples do not include imports as these imports couldn't be
|
||||
pasted in the code.
|
||||
|
||||
.. group-tab:: Go
|
||||
|
||||
.. code-block:: go
|
||||
|
||||
client, err := xmlrpc.NewClient("https://demo.odoo.com/start", nil)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
info := map[string]string{}
|
||||
client.Call("start", nil, &info)
|
||||
url = info["host"].(string)
|
||||
db = info["database"].(string)
|
||||
username = info["user"].(string)
|
||||
password = info["password"].(string)
|
||||
|
||||
.. note::
|
||||
These examples use the `github.com/kolo/xmlrpc library <https://github.com/kolo/xmlrpc>`_.
|
||||
|
||||
The examples do not include imports as these imports couldn't be
|
||||
pasted in the code.
|
||||
|
||||
Logging in
|
||||
----------
|
||||
|
||||
@ -217,6 +247,17 @@ the login.
|
||||
common_config.setServerURL(new URL(String.format("%s/xmlrpc/2/common", url)));
|
||||
client.execute(common_config, "version", emptyList());
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
client, err := xmlrpc.NewClient(fmt.Sprintf("%s/xmlrpc/2/common", url), nil)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
common := map[string]any{}
|
||||
if err := client.Call("version", nil, &common); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -247,6 +288,16 @@ Result:
|
||||
|
||||
int uid = (int)client.execute(common_config, "authenticate", asList(db, username, password, emptyMap()));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var uid int64
|
||||
if err := client.Call("authenticate", []any{
|
||||
db, username, password,
|
||||
map[string]any{},
|
||||
}, &uid); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
.. _api/external_api/calling_methods:
|
||||
|
||||
Calling methods
|
||||
@ -303,6 +354,22 @@ Each call to ``execute_kw`` takes the following parameters:
|
||||
new HashMap() {{ put("raise_exception", false); }}
|
||||
));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
models, err := xmlrpc.NewClient(fmt.Sprintf("%s/xmlrpc/2/object", url), nil)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
var result bool
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "check_access_rights",
|
||||
[]string{"read"},
|
||||
map[string]bool{"raise_exception": false},
|
||||
}, &result); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -345,6 +412,19 @@ database identifiers of all records matching the filter.
|
||||
asList("is_company", "=", true)))
|
||||
)));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var records []int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "search",
|
||||
[]any{[]any{
|
||||
[]any{"is_company", "=", true},
|
||||
}},
|
||||
}, &records); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -384,6 +464,20 @@ available to only retrieve a subset of all matched records.
|
||||
new HashMap() {{ put("offset", 10); put("limit", 5); }}
|
||||
)));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var records []int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "search",
|
||||
[]any{[]any{
|
||||
[]any{"is_company", "=", true},
|
||||
}},
|
||||
map[string]int64{"offset": 10, "limit": 5},
|
||||
}, &records); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -424,6 +518,19 @@ only the number of records matching the query. It takes the same
|
||||
asList("is_company", "=", true)))
|
||||
));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var counter int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "search_count",
|
||||
[]any{[]any{
|
||||
[]any{"is_company", "=", true},
|
||||
}},
|
||||
}, &counter); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -488,6 +595,30 @@ which tends to be a huge amount.
|
||||
// count the number of fields fetched by default
|
||||
record.size();
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var ids []int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "search",
|
||||
[]any{[]any{
|
||||
[]any{"is_company", "=", true},
|
||||
}},
|
||||
map[string]int64{"limit": 1},
|
||||
}, &ids); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
var records []any
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "read",
|
||||
ids,
|
||||
}, &records); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
// count the number of fields fetched by default
|
||||
count := len(records)
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -521,6 +652,20 @@ which tends to be a huge amount.
|
||||
}}
|
||||
)));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var recordFields []map[string]any
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "read",
|
||||
ids,
|
||||
map[string][]string{
|
||||
"fields": {"name", "country_id", "comment"},
|
||||
},
|
||||
}, &recordFields); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -569,6 +714,20 @@ updating a record).
|
||||
}}
|
||||
));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
recordFields := map[string]string{}
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "fields_get",
|
||||
[]any{},
|
||||
map[string][]string{
|
||||
"attributes": {"string", "help", "type"},
|
||||
},
|
||||
}, &recordFields); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -652,6 +811,23 @@ if that list is not provided it will fetch all fields of matched records).
|
||||
}}
|
||||
)));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var recordFields []map[string]any
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "search_read",
|
||||
[]any{[]any{
|
||||
[]any{"is_company", "=", true},
|
||||
}},
|
||||
map[string]any{
|
||||
"fields": []string{"name", "country_id", "comment"},
|
||||
"limit": 5,
|
||||
},
|
||||
}, &recordFields); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -723,6 +899,19 @@ set through the mapping argument, the default value will be used.
|
||||
asList(new HashMap() {{ put("name", "New Partner"); }})
|
||||
));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var id int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "create",
|
||||
[]map[string]string{
|
||||
{"name": "New Partner"},
|
||||
},
|
||||
}, &id); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -792,6 +981,31 @@ a record).
|
||||
asList(asList(id))
|
||||
)));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var result bool
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "write",
|
||||
[]any{
|
||||
[]int64{id},
|
||||
map[string]string{"name": "Newer partner"},
|
||||
},
|
||||
}, &result); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
// get record name after having changed it
|
||||
var record []any
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "name_get",
|
||||
[]any{
|
||||
[]int64{id},
|
||||
},
|
||||
}, &record); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -841,6 +1055,30 @@ Records can be deleted in bulk by providing their ids to
|
||||
asList(asList(asList("id", "=", 78)))
|
||||
)));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var result bool
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "unlink",
|
||||
[]any{
|
||||
[]int64{id},
|
||||
},
|
||||
}, &result); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
// check if the deleted record is still in the database
|
||||
var record []any
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"res.partner", "search",
|
||||
[]any{[]any{
|
||||
[]any{"id", "=", id},
|
||||
}},
|
||||
}, &record); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -953,6 +1191,34 @@ Provides information about Odoo models via its various fields.
|
||||
}}
|
||||
));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var id int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"ir.model", "create",
|
||||
[]map[string]string{
|
||||
{
|
||||
"name": "Custom Model",
|
||||
"model": "x_custom_model",
|
||||
"state": "manual",
|
||||
},
|
||||
},
|
||||
}, &id); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
recordFields := map[string]string{}
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"x_custom_model", "fields_get",
|
||||
[]any{},
|
||||
map[string][]string{
|
||||
"attributes": {"string", "help", "type"},
|
||||
},
|
||||
}, &recordFields); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
@ -1118,6 +1384,57 @@ custom fields without using Python code.
|
||||
asList(asList(record_id))
|
||||
));
|
||||
|
||||
.. code-tab:: go
|
||||
|
||||
var id int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"ir.model", "create",
|
||||
[]map[string]string{
|
||||
{
|
||||
"name": "Custom Model",
|
||||
"model": "x_custom",
|
||||
"state": "manual",
|
||||
},
|
||||
},
|
||||
}, &id); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
var fieldId int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"ir.model.fields", "create",
|
||||
[]map[string]any{
|
||||
{
|
||||
"model_id": id,
|
||||
"name": "x_name",
|
||||
"ttype": "char",
|
||||
"state": "manual",
|
||||
"required": true,
|
||||
},
|
||||
},
|
||||
}, &fieldId); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
var recordId int64
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"x_custom", "create",
|
||||
[]map[string]string{
|
||||
{"x_name": "test record"},
|
||||
},
|
||||
}, &recordId); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
var recordFields []map[string]any
|
||||
if err := models.Call("execute_kw", []any{
|
||||
db, uid, password,
|
||||
"x_custom", "read",
|
||||
[][]int64{{recordId}},
|
||||
}, recordFields); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
Result:
|
||||
|
||||
.. code-block:: json
|
||||
|
Loading…
Reference in New Issue
Block a user