Odoo (odooc v0.2.0)

Library to access Odoo JSON-RPC API from Elixir.

Provides the following methods for interacting with Odoo:

  • login
  • search
  • search_read
  • read
  • read_group
  • create
  • write
  • delete
  • execute

Link to this section Summary

Functions

  • Create objects
  • Return {:ok, new_object_id} or {:error, message}

Example

  iex> {:ok, product_id} = Odoo.create(
    odoo, "product.product", [name: "mi mega producto3"])
{:ok, 63}

You can specify the context language to create the object in the desired language.

  • Delete objects by id

### Example

Execute a method on a model (call to api odoo).

  • Login in Odoo and set session_id for future calls

Params (required)

  • user: string Odoo user
  • password: string Odoo password
  • database: string Odoo database
  • url: string Odoo url, http or https

Example

iex> {:ok, odoo} = Odoo.login(
  "admin", "admin", "mydatabasename", "https://mydatabasename.odoo.com")
{:ok,
%Odoo.Session{
  cookie: "session_id=c8e544d0b305920adgsfdfdsa7b0cfe; Expires=Fri, 06-May-2022 23:16:12 GMT; Max-Age=7776000; HttpOnly; Path=/",
  database: "mydatabasename",
  password: "admin",
  url: "https://mydatabasename.odoo.com",
  user: "admin",
  user_context: %{"lang" => "en_US", "tz" => "Asia/Calcutta", "uid" => 2}
}}

Pagination over results in search_read (call to api odoo)

Get previous page results (call to api odoo)

  • Read objects by id
  • Return {:ok, objects_list} or {:error, message}

Example

iex> {:ok, product} = Odoo.read(
odoo, "product.product", [63], [fields: ["name", "categ_id"]])

{:ok,
%Odoo.Result{
  data: [
    %{"id" => 63, "name" => "mi mega producto3", "categ_id" => [1, "All"]}
  ],
  model: "product.product",
  opts: [fields: ["name", "categ_id"]]
}}
  • Read and group objects

### Params

  • Search by domain. Return single id or id list.

Params

  • Arguments in keyword list format.

Example

  • Search and read with default options (limit, domain, fields, offset and order)

{:ok, res} = Odoo.search_read(odoo, "res.partner")

  • Update objects by id

Example

iex> {:ok, result}=Odoo.write odoo, "product.product", [63], [name: "Mega Pro 3"]
{:ok,
%Odoo.Result{
 data: true,
 model: "product.product",
 opts: [name: "Mega Pro 3"]
}}

Example adding a many2many value to an odoo object:

category_to_link_id = 9
{:ok, result} = Odoo.write(
    odoo,
    "res.partner",
    partner_ids,
    [category_id: [[4, category_to_link_id]] ])

Link to this section Types

Link to this type

odoo_fields()

Specs

odoo_fields() :: keyword()

Specs

option() ::
  {:limit, non_neg_integer()}
  | {:offset, non_neg_integer()}
  | {:order, String.t()}
  | {:fields, [String.t(), ...]}
  | {:domain, [list(), ...]}
Link to this type

option_valid_for_read()

Specs

option_valid_for_read() :: {:fields, [String.t(), ...]}
Link to this type

option_valid_for_read_group()

Specs

option_valid_for_read_group() ::
  {:domain, [list(), ...]}
  | {:fields, [String.t(), ...]}
  | {:groupby, [String.t(), ...]}
  | {:limit, non_neg_integer()}
  | {:lazy, bool()}
Link to this type

option_valid_for_search()

Specs

option_valid_for_search() ::
  {:limit, non_neg_integer()}
  | {:offset, non_neg_integer()}
  | {:order, String.t()}
  | {:domain, [list(), ...]}

Link to this section Functions

Link to this function

create(odoo, model, opts \\ [])

Specs

create(
  %Odoo.Session{
    cookie: term(),
    database: term(),
    password: term(),
    url: term(),
    user: term(),
    user_context: term()
  },
  String.t(),
  [odoo_fields()]
) :: {:ok, integer()} | {:error, String.t()}
  • Create objects
  • Return {:ok, new_object_id} or {:error, message}

Example

  iex> {:ok, product_id} = Odoo.create(
    odoo, "product.product", [name: "mi mega producto3"])
{:ok, 63}

You can specify the context language to create the object in the desired language.

iex(44)> {:ok, result} = Odoo.create(odoo, "product.product", [name: "Product2"], [lang: "en_US"])
{:ok,
%Odoo.Result{data: 185, model: "product.product", opts: [name: "Product2"]}}
Link to this function

delete(odoo, model, object_id)

  • Delete objects by id

### Example

iex(10)> {:ok, result} = Odoo.delete odoo, "product.template", [116]
{:ok, %Odoo.Result{data: true, model: "product.template", opts: 't'}}
    ```
Link to this function

execute(odoo, model, method, args)

Specs

execute(Odoo.Session.t(), String.t(), String.t(), [non_neg_integer()]) ::
  {:ok, %Odoo.Result{data: term(), model: term(), opts: term()}}
  | {:error, String.t()}

Execute a method on a model (call to api odoo).

  • Confirm a sale order with id 3 iex> {:ok, res2} = Odoo.execute(odoo, "sale.order", "action_confirm", [3]) {:ok, %Odoo.Result{data: true, model: "sale.order", opts: [3]}}
Link to this function

login(user, password, database, url)

Specs

login(String.t(), String.t(), String.t(), String.t()) ::
  {:ok,
   %Odoo.Session{
     cookie: term(),
     database: term(),
     password: term(),
     url: term(),
     user: term(),
     user_context: term()
   }}
  | {:error, String.t()}
  • Login in Odoo and set session_id for future calls

Params (required)

  • user: string Odoo user
  • password: string Odoo password
  • database: string Odoo database
  • url: string Odoo url, http or https

Example

iex> {:ok, odoo} = Odoo.login(
  "admin", "admin", "mydatabasename", "https://mydatabasename.odoo.com")
{:ok,
%Odoo.Session{
  cookie: "session_id=c8e544d0b305920adgsfdfdsa7b0cfe; Expires=Fri, 06-May-2022 23:16:12 GMT; Max-Age=7776000; HttpOnly; Path=/",
  database: "mydatabasename",
  password: "admin",
  url: "https://mydatabasename.odoo.com",
  user: "admin",
  user_context: %{"lang" => "en_US", "tz" => "Asia/Calcutta", "uid" => 2}
}}
Link to this function

next(odoo, result)

Pagination over results in search_read (call to api odoo)

Example

iex> {:ok, result} = Odoo.search_read(
  ...>      odoo, "product.product", limit: 5, fields: ["name"], order: "id asc")
  {:ok,
  %Odoo.Result{
    data: [
    %{"id" => 1, "name" => "Restaurant Expenses"},
    %{"id" => 2, "name" => "Hotel Accommodation"},
    %{"id" => 3, "name" => "Virtual Interior Design"},
    %{"id" => 4, "name" => "Virtual Home Staging"},
    %{"id" => 5, "name" => "Office Chair"}
    ],
    model: "product.product",
    opts: [limit: 5, fields: ["name"], order: "id asc"]
}}
iex> {:ok, result2} = Odoo.next(odoo, result)
{:ok,
%Odoo.Result{
  data: [
    %{"id" => 6, "name" => "Office Lamp"},
    %{"id" => 7, "name" => "Office Design Software"},
    %{"id" => 8, "name" => "Desk Combination"},
    %{"id" => 9, "name" => "Customizable Desk"},
    %{"id" => 10, "name" => "Customizable Desk"}
    ],
    model: "product.product",
  opts: [offset: 5, limit: 5, fields: ["name"], order: "id asc"]
}}
Link to this function

prev(odoo, result)

Get previous page results (call to api odoo)

Example

iex> {:ok, odoo} = Odoo.login(
...>    "admin", "admin", "mydatabasename", "https://mydatabasename.odoo.com")
{:ok,
%Odoo.Session{
cookie: "session_id=c8e544d0b305920afgdgsfdfdsa7b0cfe; Expires=Fri, 06-May-2022 23:16:12 GMT; Max-Age=7776000; HttpOnly; Path=/",
database: "mydatabasename",
password: "admin",
url: "https://mydatabasename.odoo.com",
user: "admin",
user_context: %{"lang" => "en_US", "tz" => "Asia/Calcutta", "uid" => 2}
}}
iex> {:ok, result} = Odoo.search_read(
...>      odoo, "product.product", limit: 5, fields: ["name"], order: "id asc")
{:ok,
%Odoo.Result{
data: [
%{"id" => 1, "name" => "Restaurant Expenses"},
%{"id" => 2, "name" => "Hotel Accommodation"},
%{"id" => 3, "name" => "Virtual Interior Design"},
%{"id" => 4, "name" => "Virtual Home Staging"},
%{"id" => 5, "name" => "Office Chair"}
],
model: "product.product",
opts: [limit: 5, fields: ["name"], order: "id asc"]
}}
iex> {:ok, result2} = Odoo.next(odoo, result)
{:ok,
%Odoo.Result{
data: [
%{"id" => 6, "name" => "Office Lamp"},
%{"id" => 7, "name" => "Office Design Software"},
%{"id" => 8, "name" => "Desk Combination"},
%{"id" => 12, "name" => "Customizable Desk"},
%{"id" => 13, "name" => "Customizable Desk"}
],
model: "product.product",
opts: [offset: 5, limit: 5, fields: ["name"], order: "id asc"]
}}
iex> {:ok, result3} = Odoo.prev(odoo, result2)
{:ok,
%Odoo.Result{
data: [
%{"id" => 1, "name" => "Restaurant Expenses"},
%{"id" => 2, "name" => "Hotel Accommodation"},
%{"id" => 3, "name" => "Virtual Interior Design"},
%{"id" => 4, "name" => "Virtual Home Staging"},
%{"id" => 5, "name" => "Office Chair"}
],
model: "product.product",
opts: [offset: 0, limit: 5, fields: ["name"], order: "id asc"]
}}
Link to this function

read(odoo, model, object_id, opts \\ [])

Specs

read(
  %Odoo.Session{
    cookie: term(),
    database: term(),
    password: term(),
    url: term(),
    user: term(),
    user_context: term()
  },
  String.t(),
  [non_neg_integer(), ...],
  [option_valid_for_read()]
) ::
  {:ok, %Odoo.Result{data: term(), model: term(), opts: term()}}
  | {:error, String.t()}
  • Read objects by id
  • Return {:ok, objects_list} or {:error, message}

Example

iex> {:ok, product} = Odoo.read(
odoo, "product.product", [63], [fields: ["name", "categ_id"]])

{:ok,
%Odoo.Result{
  data: [
    %{"id" => 63, "name" => "mi mega producto3", "categ_id" => [1, "All"]}
  ],
  model: "product.product",
  opts: [fields: ["name", "categ_id"]]
}}
Link to this function

read_group(odoo, model, opts \\ [])

Specs

read_group(
  %Odoo.Session{
    cookie: term(),
    database: term(),
    password: term(),
    url: term(),
    user: term(),
    user_context: term()
  },
  String.t(),
  [option_valid_for_read()]
) ::
  {:ok, %Odoo.Result{data: term(), model: term(), opts: term()}}
  | {:error, String.t()}
  • Read and group objects

### Params

  • :fields
  • :domain
  • :groupby
  • :lazy
  • :orderby
  • :offset

Example

iex> {:ok, result} = Odoo.read_group(
odoo, "account.invoice", [
  domain: [["date_invoice", ">=", "2021-11-01"]],
  groupby: ["date_invoice:month"],
  fields: ["number", "partner_id"],
  limit: 2,
  lazy: true])

  {:ok,
   %Odoo.Result{
    data: [
  %{
    "__domain" => [
   "&",
   "&",
   ["date_invoice", ">=", "2022-01-01"],
   ["date_invoice", "<", "2022-02-01"],
   ["date_invoice", ">=", "2021-11-01"]
   ],
   "date_invoice:month" => "enero 2022",
   "date_invoice_count" => 61
   },
   %{
     "__domain" => [
       "&",
       "&",
       ["date_invoice", ">=", "2022-02-01"],
       ["date_invoice", "<", "2022-03-01"],
       ["date_invoice", ">=", "2021-11-01"]
       ],
    "date_invoice:month" => "febrero 2022",
    "date_invoice_count" => 32
  }
  ]}}
Link to this function

search(odoo, model, opts \\ [])

Specs

search(
  %Odoo.Session{
    cookie: term(),
    database: term(),
    password: term(),
    url: term(),
    user: term(),
    user_context: term()
  },
  String.t(),
  [option_valid_for_search()]
) ::
  {:ok, %Odoo.Result{data: term(), model: term(), opts: term()}}
  | {:error, String.t()}
  • Search by domain. Return single id or id list.

Params

  • Arguments in keyword list format.

  • Required opts:

  • domain: list of list

  • Optional arguments

  • limit: int, max number of rows to return from odoo

  • offset: int, offset over the default values to return

Example

iex>  {:ok, partner_ids} = Odoo.search(
odoo, "res.partner",
[ domain:
    [
      ["name", "ilike", "Antonia%"],
      ["customer", "=", true],
      ["create_date",">=","2021-06-01"]
    ],
    limit: 5,
    offset: 10,
    order: "name"
])
{:ok,
  %Odoo.Result{
    data: '[44]',
    model: "res.partner",
    opts: [domain: [["name", "ilike", "Lorraine%"], ["customer", "=", true],
      ["create_date",">=","2021-06-01"]]]
  }}
  • Return one value is a single integer for the id
  • Return more than one value is a list of integers
  • Can also return {:error, message} if the operation fails.
Link to this function

search_read(odoo, model, opts \\ [])

Specs

search_read(
  %Odoo.Session{
    cookie: term(),
    database: term(),
    password: term(),
    url: term(),
    user: term(),
    user_context: term()
  },
  String.t(),
  [option()]
) ::
  {:ok, %Odoo.Result{data: term(), model: term(), opts: term()}}
  | {:error, String.t()}

Example

  • Search and read with default options (limit, domain, fields, offset and order)

{:ok, res} = Odoo.search_read(odoo, "res.partner")

  • Put options to tune the query:
{:ok, partners} = Odoo.search_read(
  odoo,
  "res.partner",
  [
    limit: 1,
    domain: [["name", "ilike", "Antonio"]],
    fields: ["name", "street"],
    offset: 11,
    order: "name asc"])

{:ok,
[
  %{
    "id" => 226,
    "name" => "Antonio Fulanito de tal",
    "street" => "Calle principal 1"
  }
  ]}
  • Search and read active and archived records (by default odoo only return active records)
  {:ok, partners} = Odoo.search_read(
    odoo,
    "res.partner", [
      fields: ["name"],
      offset: 0,
          limit: 10,
          order: "id",
          domain: [["active", "in", [true,false]]]
        ]
        )
        ```
Link to this function

write(odoo, model, object_id, fields \\ [])

Specs

write(
  %Odoo.Session{
    cookie: term(),
    database: term(),
    password: term(),
    url: term(),
    user: term(),
    user_context: term()
  },
  String.t(),
  [non_neg_integer()],
  keyword()
) ::
  {:ok, %Odoo.Result{data: term(), model: term(), opts: term()}}
  | {:error, String.t()}
  • Update objects by id

Example

iex> {:ok, result}=Odoo.write odoo, "product.product", [63], [name: "Mega Pro 3"]
{:ok,
%Odoo.Result{
 data: true,
 model: "product.product",
 opts: [name: "Mega Pro 3"]
}}

Example adding a many2many value to an odoo object:

category_to_link_id = 9
{:ok, result} = Odoo.write(
    odoo,
    "res.partner",
    partner_ids,
    [category_id: [[4, category_to_link_id]] ])