Repository
odoo/odoo · module folder
Module version
1.2
Category
Sales/Sales
Folder size
12.94 MB
License
LGPL-3
Application
No
Auto-installable
No
Website
None
Last tracking update
2026-08-17 10:14:40
Authors
Odoo S.A.
Maintainers
Odoo S.A.
Committers
Xavier Morel, Raphael Collet, Thibault Delavallée, odoo, Odoo Translation Bot, Aaron Bohy, Arnold Moyaux, Julien Castiaux, Victor Feyens, Andrea Grazioso (agr-odoo), Sébastien Theys, svs-odoo, Achraf (abz), Rémy Voet (ryv), Tiffany Chang (tic), Gorash, Mathieu Duckerts-Antoine, Pierre Paridans, William Braeckman, Miquel Raïch, Ahmad Khanalizadeh, Víctor Martínez, JF Aubert, Aurelien van Delft (avd), Hubert Van De Walle, Valentin Chevalier, Renaud Thiry, niyasraphy, David, alsh-odoo, Adrien Widart (awt), Maximilien (malb), Victor Piryns (pivi), Mahamadasif Ansari, Gauthier Wala (gawa), Andrew Gavgavian, Levi Siuzdak (sile), Dylan Kiss (dyki), Valeriya(vchu), tanghulu0608, Anita (anko), SilvioC2C, Nguyễn Đại Dương, Sarah Bellefroid, Arnaud Sibille, omra-odoo, stefanorigano (SRI), Adam Heinz, Louis (loti), reka-odoo, kcv-odoo, odoostan, dere-odoo, Lina (liew), manv-afk, Patricia Daloze (pda), Xavier Luyckx (xlu), yagp-odoo, Sanchit Gupta, Mohammad Abdulmoneim, Stéphane Diez, Aungkokolin1997, gteboul, sabr, Julien Schwanen, Victor Miguel Armenta Carrillo, sben-odoo, Arthur Nanson, Christopher Maloney (cmal), David Van Droogenbroeck (DROD), Mohammad Abdulmoneim (abdu), djameltouati, khsr-odoo, Pierre Lamotte (pila), wt, Michaël Mattiello, kasm, Shrey Mehta, Carmine, Mahdi Alijani (malj), MaximeNoirhomme, chha-odoo, bona-odoo, Vincent Sevestre, plha-odoo, Krzysztof Magusiak (krma), kkuj-odoo, nipl-odoo, kukor-odoo, krip-odoo, bhna-odoo, temo-odoo, mohannedah, agbr-odoo, Lulu Grimalkin (lugr), rare-odoo, felin-odoo, igbe, Quentin Colla (qucol), path-odoo, Waleed Elgamal, Amr Elkhatieb, Nisarg (nipl), hossamelgendy1, Samiul Hoque, Merlin Guillaume, Mazen, srap-odoo, saurabh, Nguyen Nguyen (ngtpn), Stephane Vanmeerhaeghe (stva), Youssef (abyo), ELCO, Przemysław Duryło, chpa-odoo, panj-odoo, Oussema Heni, Krishna Patel, Mathias Mathy, jeanschoenlaub, Abhishek Yadav
Odoo dependencies
odoo/odoo:
- web
- bus
- uom
Python dependencies
None
System dependencies
None
Required by
account, barcodes_generator_product, base_global_discount, commission_oca, contract, edi_product_oca, event_product, helpdesk_product, hotel_housekeeping, hotel_restaurant, l10n_br_fiscal, l10n_mx_cfdi, l10n_mx_cfdi_account_addenda_audi, loyalty, maintenance_product, mrp, partner_pricelist_search, partner_supplierinfo_smartbutton, pim, pms_base, product_attribute_archive, product_attribute_set, product_attribute_value_avoid_auto_fill, product_category_active, product_category_code, product_category_type, product_category_uom, product_class, product_code_mandatory, product_code_unique, product_company_default, product_customerinfo, product_dimension, product_harmonized_system, product_logistics_uom, product_manufacturer, product_operating_unit, product_origin, product_pack, product_pricelist_simulation, product_pricelist_supplierinfo, product_sale_team, product_secondary_unit, product_sequence, product_set, product_state, product_supplierinfo_indirect_cost, product_usability, product_variant_attribute_tax, product_variant_configurator, product_variant_default_code, project_task_product, quality_control_oca, sale_partner_company_group, stock, storage_image_product, storage_media_product, tms_product
Description
This is the base module for managing products and pricelists in Odoo.
========================================================================

Products support variants, different pricing methods, vendors information,
make to stock/order, different units of measure, packaging and properties.

Pricelists support:
-------------------
    * Multiple-level of discount (by product, category, quantities)
    * Compute price based on different criteria:
        * Other pricelist
        * Cost price
        * List price
        * Vendor price

Pricelists preferences by product and/or partners.

Print product labels with barcode.
    

Code Analysis

Views touched (75)
XML IDNameModelTypeStatus
attribute_tree_view product.attribute.list product.attribute list New
inherits_website_sale_country_group_form res.country.group.form.inherit.product res.country.group form Inherits base.view_country_group_form
product.product_combo_view_form product.combo.form product.combo form New
product.product_combo_view_tree product.combo.list product.combo list New
product_attribute_search product.attribute.view.search product.attribute search New
product_attribute_value_list product.attribute.value.list product.attribute.value list New
product_attribute_view_form product.attribute.form product.attribute form New
product_category_form_view product.category.form product.category form New
product_category_list_view product.category.list product.category list New
product_category_search_view product.category.search product.category search New
product_document_form product.document.form product.document form New
product_document_kanban product.document.kanban product.document kanban New
product_document_list product.document.list product.document list New
product_document_search product.document.search product.document search New
product_kanban_view Product Kanban product.product kanban New
product_label_layout_form product.label.layout.form product.label.layout form New
product_normal_form_view product.product.form product.product form Inherits product.product_template_form_view
product_pricelist_item_form_view product.pricelist.item.form product.pricelist.item form New
product_pricelist_item_product_product_form_view product.pricelist.item.product.product.form.inherit product.pricelist.item form Inherits product.product_pricelist_item_product_template_form_view
product_pricelist_item_product_template_form_view product.pricelist.item.product.template.form.inherit product.pricelist.item form Inherits product.product_pricelist_item_form_view
product_pricelist_item_tree_view product.pricelist.item.list product.pricelist.item list New
product_pricelist_item_tree_view_from_product product.pricelist.item.list product.pricelist.item list New
product_pricelist_item_view_search product.pricelist.item.search product.pricelist.item search New
product_pricelist_view product.pricelist.form product.pricelist form New
product_pricelist_view_kanban product.pricelist.kanban product.pricelist kanban New
product_pricelist_view_search product.pricelist.search product.pricelist search New
product_pricelist_view_tree product.pricelist.list product.pricelist list New
product_product_tree_view product.product.list product.product list New
product_product_view_activity product.product.activity product.product activity New
product_product_view_form_normalized product.product.view.form.normalized product.product form New
product_product_view_tree_tag product.product.view.list.tag product.product list New
product_search_form_view product.product.search product.product search Inherits product.product_template_search_view
product_supplierinfo_form_view product.supplierinfo.form.view product.supplierinfo form New
product_supplierinfo_search_view product.supplierinfo.search.view product.supplierinfo search New
product_supplierinfo_tree_view product.supplierinfo.list.view product.supplierinfo list New
product_supplierinfo_view_kanban product.supplierinfo.kanban product.supplierinfo kanban New
product_tag_form_view product.tag.form product.tag form New
product_tag_tree_view product.tag.list product.tag list New
product_template_attribute_line_form product.template.attribute.line.form product.template.attribute.line form New
product_template_attribute_line_view_tree product.template.attribute.line.view.list product.template.attribute.line list New
product_template_attribute_value_view_form product.template.attribute.value.view.form. product.template.attribute.value form New
product_template_attribute_value_view_search product.template.attribute.value search New
product_template_attribute_value_view_tree product.template.attribute.value.view.list product.template.attribute.value list New
product_template_form_view product.template.common.form product.template form New
product_template_kanban_view Product.template.product.kanban product.template kanban New
product_template_list_view_purchasable product.template.list.purchasable product.template list Inherits product.product_template_tree_view
product_template_list_view_sellable product.template.list.sellable product.template list Inherits product.product_template_tree_view
product_template_only_form_view product.template.product.form product.template form Inherits product.product_template_form_view
product_template_search_view product.template.search product.template search New
product_template_tree_view product.template.product.list product.template list New
product_template_view_activity product.template.activity product.template activity New
product_template_view_tree_tag product.template.view.list.tag product.template list New
product_uom_list_view product.uom.list product.uom list New
product_variant_easy_edit_view product.product.view.form.easy product.product form New
product_view_kanban_catalog product.view.kanban.catalog product.product kanban New
product_view_search_catalog product.view.search.catalog product.product search New
report_packagingbarcode report_packagingbarcode ir.ui.view qweb New
report_pricelist report_pricelist ir.ui.view qweb New
report_pricelist_page report_pricelist_page ir.ui.view qweb New
report_productlabel report_productlabel ir.ui.view qweb New
report_productlabel_dymo report_productlabel_dymo ir.ui.view qweb New
report_producttemplatelabel2x7 report_producttemplatelabel2x7 ir.ui.view qweb New
report_producttemplatelabel4x12 report_producttemplatelabel4x12 ir.ui.view qweb New
report_producttemplatelabel4x12noprice report_producttemplatelabel4x12noprice ir.ui.view qweb New
report_producttemplatelabel4x7 report_producttemplatelabel4x7 ir.ui.view qweb New
report_producttemplatelabel_dymo report_producttemplatelabel_dymo ir.ui.view qweb New
report_simple_label2x7 report_simple_label2x7 ir.ui.view qweb New
report_simple_label4x12 report_simple_label4x12 ir.ui.view qweb New
report_simple_label4x12_no_price report_simple_label4x12_no_price ir.ui.view qweb New
report_simple_label4x7 report_simple_label4x7 ir.ui.view qweb New
report_simple_label_dymo report_simple_label_dymo ir.ui.view qweb New
res_config_settings_view_form res.config.settings.view.form.inherit.product res.config.settings form Inherits base_setup.res_config_settings_view_form
uom_uom_form_view_inherit uom.uom.form.inherit uom.uom form Inherits uom.product_uom_form_view
update_product_attribute_value_form update.product.attribute.value.form update.product.attribute.value form New
view_partner_property_form res.partner.product.property.form.inherit res.partner form Inherits base.view_partner_form
HTTP endpoints (4)
Route(s)HandlerAuthTypeMethodsFlags
/product/catalog/order_lines_info ProductCatalogController.product_catalog_get_order_lines_info user jsonrpc ALL
/product/catalog/update_order_line_info ProductCatalogController.product_catalog_update_order_line_info user jsonrpc ALL
/product/document/upload ProductDocumentController.upload_document user http POST
/product/export/pricelist/ ProductPricelistExportController.export_pricelist user http ALL
Models touched (33)

New fields (0)

No new fields.

Public methods (1)
  • create(self, vals_list)
    @api.model_create_multi
    Create product.document for attachments added in products chatters

New fields (10)
  • active Boolean
    default=True help='If unchecked, it will allow you to hide the attribute without removing it.'
  • attribute_line_ids One2many → product.template.attribute.line
    comodel_name='product.template.attribute.line' inverse_name='attribute_id' string='Lines'
  • create_variant Selection
    default='always' help='- Instantly: All possible variants are created as soon as the attribute and its values are added to a product.\n - Dynamically: Each variant is created only when its corresponding attributes and values are added to a sales order.\n - Never: Variants are never created for the attribute.\n Note: this cannot be changed once the attribute is used on a product.' required=True selection=[('always', 'Instantly'), ('dynamic', 'Dynamically'), ('no_variant', 'Never')] string='Variant Creation'
  • display_type Selection
    default='radio' help='The display type used in the Product Configurator.' required=True selection=[('radio', 'Radio'), ('pills', 'Pills'), ('select', 'Select'), ('color', 'Color'), ('multi', 'Multi-checkbox'), ('image', 'Image')]
  • name Char
    required=True string='Attribute' translate=True
  • number_related_products Integer
    compute='_compute_number_related_products'
  • product_tmpl_ids Many2many → product.template
    comodel_name='product.template' compute='_compute_products' store=True string='Related Products'
  • sequence Integer
    default=20 help='Determine the display order' index=True string='Sequence'
  • template_value_ids One2many → product.template.attribute.value
    comodel_name='product.template.attribute.value' inverse_name='attribute_id' string='Template Values'
  • value_ids One2many → product.attribute.value
    comodel_name='product.attribute.value' copy=True inverse_name='attribute_id' string='Values'
Public methods (3)
  • action_archive(self)
  • action_open_product_template_attribute_lines(self)
    @api.readonly
  • write(self, vals)
    Override to make sure attribute type can't be changed if it's used on a product template. This is important to prevent because changing the type would make existing combinations invalid without recomputing them, and recomputing them might take too long and we don't want to change products without the user knowing about it.

New fields (3)
  • custom_product_template_attribute_value_id Many2one → product.template.attribute.value
    comodel_name='product.template.attribute.value' ondelete='restrict' required=True string='Attribute Value'
  • custom_value Char
    string='Custom Value'
  • name Char
    compute='_compute_name' string='Name'
Public methods (0)

No public methods.

New fields (13)
  • active Boolean
    default=True
  • attribute_id Many2one → product.attribute
    comodel_name='product.attribute' help='The attribute cannot be changed once the value is used on at least one product.' index=True ondelete='cascade' required=True string='Attribute'
  • color Integer
    default=_get_default_color string='Color Index'
  • default_extra_price Float
  • default_extra_price_changed Boolean
    compute='_compute_default_extra_price_changed'
  • display_type Selection
    related='attribute_id.display_type'
  • html_color Char
    help="Here you can set a specific HTML color index (e.g. #ff0000) to display the color if the attribute type is 'Color'." string='Color'
  • image Image
    help='You can upload an image that will be used as the color of the attribute value.' max_height=70 max_width=70 string='Image'
  • is_custom Boolean
    help='Allow customers to set their own value' string='Free text'
  • is_used_on_products Boolean
    compute='_compute_is_used_on_products' string='Used on Products'
  • name Char
    required=True string='Value' translate=True
  • pav_attribute_line_ids Many2many → product.template.attribute.line
    comodel_name='product.template.attribute.line' copy=False relation='product_attribute_value_product_template_attribute_line_rel' string='Lines'
  • sequence Integer
    help='Determine the display order' index=True string='Sequence'
Public methods (5)
  • action_add_to_products(self)
    @api.readonly
  • action_update_prices(self)
    @api.readonly
  • check_is_used_on_products(self)
  • unlink(self)
  • write(self, vals)

New fields (0)

No new fields.

Public methods (1)
  • action_add_from_catalog(self)
    @api.readonly

New fields (7)
  • child_id One2many → product.category
    args: 'product.category', 'parent_id', 'Child Categories'
  • complete_name Char
    compute='_compute_complete_name' recursive=True store=True args: 'Complete Name'
  • name Char
    index='trigram' required=True args: 'Name'
  • parent_id Many2one → product.category
    index=True ondelete='cascade' args: 'product.category', 'Parent Category'
  • parent_path Char
    index=True
  • product_count Integer
    compute='_compute_product_count' help='The number of products under this category (Does not consider the children categories)' args: '# Products'
  • product_properties_definition PropertiesDefinition
    args: 'Product Properties'
Public methods (2)
  • copy_data(self, default=None)
  • name_create(self, name)
    @api.model

New fields (7)
  • base_price Float
    compute='_compute_base_price' help='The minimum price among the products in this combo. This value will be used to prorate the price of this combo with respect to the other combos in a combo product. This heuristic ensures that whatever product the user chooses in a combo, it will always be the same price.' min_display_digits='Product Price' string='Combo Price'
  • combo_item_count Integer
    compute='_compute_combo_item_count' string='Product Count'
  • combo_item_ids One2many → product.combo.item
    comodel_name='product.combo.item' copy=True inverse_name='combo_id'
  • company_id Many2one → res.company
    comodel_name='res.company' index=True string='Company'
  • currency_id Many2one → res.currency
    comodel_name='res.currency' compute='_compute_currency_id'
  • name Char
    required=True string='Name'
  • sequence Integer
    copy=False default=10
Public methods (0)

No public methods.

New fields (6)
  • combo_id Many2one → product.combo
    comodel_name='product.combo' index=True ondelete='cascade' required=True
  • company_id Many2one
    precompute=True related='combo_id.company_id' store=True
  • currency_id Many2one → res.currency
    comodel_name='res.currency' related='product_id.currency_id'
  • extra_price Float
    default=0.0 min_display_digits='Product Price' string='Extra Price'
  • lst_price Float
    min_display_digits='Product Price' related='product_id.lst_price' string='Original Price'
  • product_id Many2one → product.product
    check_company=True comodel_name='product.product' domain=[('type', '!=', 'combo')] ondelete='restrict' required=True string='Options'
Public methods (0)

No public methods.

New fields (3)
  • active Boolean
    default=True
  • ir_attachment_id Many2one → ir.attachment
    ondelete='cascade' required=True string='Related attachment' args: 'ir.attachment'
  • sequence Integer
    default=10
Public methods (3)
  • copy_data(self, default=None)
  • create(self, vals_list)
    @api.model_create_multi
  • unlink(self)

New fields (8)
  • columns Integer
    compute='_compute_dimensions'
  • custom_quantity Integer
    default=1 required=True args: 'Copies'
  • extra_html Html
    default='' args: 'Extra Content'
  • pricelist_id Many2one → product.pricelist
    string='Pricelist' args: 'product.pricelist'
  • print_format Selection
    default='2x7xprice' required=True string='Format' args: [('dymo', 'Dymo'), ('2x7xprice', '2 x 7 with price'), ('4x7xprice', '4 x 7 with price'), ('4x12', '4 x 12'), ('4x12xprice', '4 x 12 with price')]
  • product_ids Many2many → product.product
    args: 'product.product'
  • product_tmpl_ids Many2many → product.template
    args: 'product.template'
  • rows Integer
    compute='_compute_dimensions'
Public methods (1)
  • process(self)

New fields (7)
  • active Boolean
    default=True help='If unchecked, it will allow you to hide the pricelist without removing it.' string='Active'
  • company_id Many2one → res.company
    comodel_name='res.company' default=<expr> tracking=5
  • country_group_ids Many2many → res.country.group
    column1='pricelist_id' column2='res_country_group_id' comodel_name='res.country.group' relation='res_country_group_pricelist_rel' string='Country Groups' tracking=10
  • currency_id Many2one → res.currency
    comodel_name='res.currency' default=_default_currency_id required=True tracking=1
  • item_ids One2many → product.pricelist.item
    comodel_name='product.pricelist.item' copy=True domain=<expr> inverse_name='pricelist_id' string='Pricelist Rules'
  • name Char
    required=True string='Pricelist Name' translate=True
  • sequence Integer
    default=16
Public methods (4)
  • action_open_pricelist_report(self)
    @api.readonly
  • copy_data(self, default=None)
  • get_import_templates(self)
    @api.model
  • write(self, vals)

New fields (28)
  • applied_on Selection
    default='3_global' help='Pricelist Item applicable on selected option' required=True selection=[('3_global', 'All Products'), ('2_product_category', 'Product Category'), ('1_product', 'Product'), ('0_product_variant', 'Product Variant')] string='Apply On'
  • base Selection
    default='list_price' help='Base price for computation.\nSales Price: The base price will be the Sales Price.\nCost Price: The base price will be the cost price.\nOther Pricelist: Computation of the base price based on another Pricelist.' required=True selection=[('list_price', 'Sales Price'), ('standard_price', 'Cost'), ('pricelist', 'Other Pricelist')] string='Based on'
  • base_pricelist_id Many2one → product.pricelist
    check_company=True args: 'product.pricelist', 'Other Pricelist'
  • categ_id Many2one → product.category
    comodel_name='product.category' help='Specify a product category if this rule only applies to products belonging to this category or its children categories. Keep empty otherwise.' ondelete='cascade' string='Category'
  • company_id Many2one → res.company
    comodel_name='res.company' compute='_compute_company_id' store=True
  • compute_price Selection
    default='fixed' help='Use the discount rules and activate the discount settings in order to show discount to customer.' index=True required=True selection=[('percentage', 'Discount'), ('formula', 'Formula'), ('fixed', 'Fixed Price')]
  • currency_id Many2one → res.currency
    comodel_name='res.currency' compute='_compute_currency_id' store=True
  • date_end Datetime
    help='Ending datetime for the pricelist item validation\nThe displayed value depends on the timezone set in your preferences.' string='End Date'
  • date_start Datetime
    help='Starting datetime for the pricelist item validation\nThe displayed value depends on the timezone set in your preferences.' string='Start Date'
  • display_applied_on Selection
    default='1_product' help='Pricelist Item applicable on selected option' required=True selection=[('1_product', 'Product'), ('2_product_category', 'Category')]
  • fixed_price Float
    min_display_digits='Product Price' string='Fixed Price'
  • is_pricelist_required Boolean
    compute='_compute_is_pricelist_required'
  • min_quantity Float
    default=0 digits='Product Unit' help='For the rule to apply, bought/sold quantity must be greater than or equal to the minimum quantity specified in this field.\nExpressed in the default unit of measure of the product.' string='Min. Quantity'
  • name Char
    compute='_compute_name' help='Explicit rule name for this pricelist line.' string='Name'
  • percent_price Float
    help='You can apply a mark-up by setting a negative discount.' string='Percentage Price'
  • price Char
    compute='_compute_price_label' help='Explicit rule name for this pricelist line.' string='Price'
  • price_discount Float
    default=0 digits=(16, 2) help='You can apply a mark-up by setting a negative discount.' string='Price Discount'
  • price_markup Float
    compute='_compute_price_markup' digits=(16, 2) help='You can apply a mark-up on the cost' inverse='_inverse_price_markup' store=True string='Markup'
  • price_max_margin Float
    help='Specify the maximum amount of margin over the base price.' min_display_digits='Product Price' string='Max. Price Margin'
  • price_min_margin Float
    help='Specify the minimum amount of margin over the base price.' min_display_digits='Product Price' string='Min. Price Margin'
  • price_round Float
    help='Sets the price so that it is a multiple of this value.\nRounding is applied after the discount and before the surcharge.\nTo have prices that end in 9.99, round off to 10.00 and set an extra at -0.01' min_display_digits='Product Price' string='Price Rounding'
  • price_surcharge Float
    help='Specify the fixed amount to add or subtract (if negative) to the amount calculated with the discount.' min_display_digits='Product Price' string='Extra Fee'
  • pricelist_id Many2one → product.pricelist
    comodel_name='product.pricelist' default=_default_pricelist_id index=True ondelete='cascade' required=False string='Pricelist'
  • product_id Many2one → product.product
    check_company=True comodel_name='product.product' domain="[('product_tmpl_id', '=', product_tmpl_id)]" help='Specify a product if this rule only applies to one product. Keep empty otherwise.' index='btree_not_null' ondelete='cascade' string='Variant'
  • product_tmpl_id Many2one → product.template
    check_company=True comodel_name='product.template' help='Specify a template if this rule only applies to one product template. Keep empty otherwise.' index='btree_not_null' ondelete='cascade' string='Product'
  • product_uom_name Char
    related='product_tmpl_id.uom_name'
  • product_variant_count Integer
    related='product_tmpl_id.product_variant_count'
  • rule_tip Char
    compute='_compute_rule_tip'
Public methods (2)
  • create(self, vals_list)
    @api.model_create_multi
  • write(self, vals)

New fields (37)
  • active Boolean
    default=True help='If unchecked, it will allow you to hide the product without removing it.' args: 'Active'
  • additional_product_tag_ids Many2many → product.tag
    comodel_name='product.tag' domain="[('id', 'not in', product_tag_ids)]" relation='product_tag_product_product_rel' string='Variant Tags'
  • all_product_tag_ids Many2many → product.tag
    compute='_compute_all_product_tag_ids' search='_search_all_product_tag_ids' args: 'product.tag'
  • barcode Char
    copy=False help='International Article Number used for product identification.' index='btree_not_null' args: 'Barcode'
  • can_image_1024_be_zoomed Boolean
    compute='_compute_can_image_1024_be_zoomed' args: 'Can Image 1024 be zoomed'
  • can_image_variant_1024_be_zoomed Boolean
    compute='_compute_can_image_variant_1024_be_zoomed' store=True args: 'Can Variant Image 1024 be zoomed'
  • code Char
    compute='_compute_product_code' args: 'Reference'
  • combination_indices Char
    compute='_compute_combination_indices' index=True store=True
  • default_code Char
    index=True args: 'Internal Reference'
  • image_1024 Image
    compute='_compute_image_1024' args: 'Image 1024'
  • image_128 Image
    compute='_compute_image_128' args: 'Image 128'
  • image_1920 Image
    compute='_compute_image_1920' inverse='_set_image_1920' args: 'Image'
  • image_256 Image
    compute='_compute_image_256' args: 'Image 256'
  • image_512 Image
    compute='_compute_image_512' args: 'Image 512'
  • image_variant_1024 Image
    max_height=1024 max_width=1024 related='image_variant_1920' store=True args: 'Variant Image 1024'
  • image_variant_128 Image
    max_height=128 max_width=128 related='image_variant_1920' store=True args: 'Variant Image 128'
  • image_variant_1920 Image
    max_height=1920 max_width=1920 args: 'Variant Image'
  • image_variant_256 Image
    max_height=256 max_width=256 related='image_variant_1920' store=True args: 'Variant Image 256'
  • image_variant_512 Image
    max_height=512 max_width=512 related='image_variant_1920' store=True args: 'Variant Image 512'
  • import_attribute_values Char
    compute='_compute_import_attribute_values' copy=False inverse='_inverse_import_attribute_values' store=False string='Product Values'
  • is_favorite Boolean
    readonly=False related='product_tmpl_id.is_favorite' store=True
  • is_in_selected_section_of_order Boolean
    search='_search_is_in_selected_section_of_order'
  • is_product_variant Boolean
    compute='_compute_is_product_variant'
  • lst_price Float
    compute='_compute_product_lst_price' help="The sale price is managed from the product template. Click on the 'Configure Variants' button to set the extra attribute prices." inverse='_set_product_lst_price' min_display_digits='Product Price' args: 'Sales\xa0Price'
  • partner_ref Char
    compute='_compute_partner_ref' args: 'Customer Ref'
  • price_extra Float
    compute='_compute_product_price_extra' help='This is the sum of the extra price of all attributes' min_display_digits='Product Price' args: 'Variant Price Extra'
  • pricelist_rule_ids One2many → product.pricelist.item
    comodel_name='product.pricelist.item' compute='_compute_pricelist_rule_ids' inverse='_inverse_pricelist_rule_ids' inverse_name='product_id' readonly=False string='Pricelist Rules'
  • product_document_count Integer
    compute='_compute_product_document_count' string='Documents Count'
  • product_document_ids One2many → product.document
    comodel_name='product.document' domain=<expr> inverse_name='res_id' string='Documents'
  • product_template_attribute_value_ids Many2many → product.template.attribute.value
    ondelete='restrict' relation='product_variant_combination' string='Attribute Values' args: 'product.template.attribute.value'
  • product_template_variant_value_ids Many2many → product.template.attribute.value
    domain=[('attribute_line_id.value_count', '>', 1)] ondelete='restrict' relation='product_variant_combination' string='Variant Values' args: 'product.template.attribute.value'
  • product_tmpl_id Many2one → product.template
    bypass_search_access=True index=True ondelete='cascade' required=True args: 'product.template', 'Product Template'
  • product_uom_ids One2many → product.uom
    store=True args: 'product.uom', 'product_id', 'Unit Barcode'
  • standard_price Float
    company_dependent=True groups='base.group_user' help='Value of the product (automatically computed in AVCO).\n Used to value the product when the purchase cost is not known (e.g. inventory adjustment).\n Used to compute margins on sale orders.' min_display_digits='Product Price' args: 'Cost'
  • volume Float
    digits='Volume' args: 'Volume'
  • weight Float
    digits='Stock Weight' args: 'Weight'
  • write_date Datetime
    compute='_compute_write_date' store=True
Public methods (15)
  • action_archive(self)
  • action_open_documents(self)
    @api.readonly
  • action_open_label_layout(self)
    @api.readonly
  • action_unarchive(self)
  • copy(self, default=None)
    Variants are generated depending on the configuration of attributes and values on the template, so copying them does not make sense. For convenience the template is copied instead and its first variant is returned.
  • create(self, vals_list)
    @api.model_create_multi
  • get_contextual_price(self)
  • get_empty_list_help(self, help_message)
    @api.model
  • get_product_multiline_description_sale(self)
    Compute a multiline description of this product, in the context of sales (do not use for purchases or other display reasons that don't intend to use "description_sale"). It will often be used as the default description of a sale order line referencing this product.
  • load(self, fields, data)
    @api.model
  • name_search(self, name='', domain=None, operator='ilike', limit=100)
    @api.model
  • open_product_template(self)
    Utility method used to add an "Open Template" button in product views
  • unlink(self)
  • view_header_get(self, view_id, view_type)
    @api.model
  • write(self, vals)

New fields (17)
  • company_id Many2one → res.company
    default=<expr> index=1 args: 'res.company', 'Company'
  • currency_id Many2one → res.currency
    default=<expr> required=True args: 'res.currency', 'Currency'
  • date_end Date
    help='End date for this vendor price' args: 'End Date'
  • date_start Date
    help='Start date for this vendor price' args: 'Start Date'
  • delay Integer
    default=1 help='Lead time in days between the confirmation of the purchase order and the receipt of the products in your warehouse. Used by the scheduler for automatic computation of the purchase order planning.' required=True args: 'Lead Time'
  • discount Float
    digits='Discount' readonly=False string='Discount (%)'
  • min_qty Float
    default=0.0 digits='Product Unit' help='The quantity to purchase from this vendor to benefit from the unit price. If a vendor unit is set, quantity should be specified in this unit, otherwise it should be specified in the default unit of the product.' required=True args: 'Quantity'
  • partner_id Many2one → res.partner
    check_company=True ondelete='cascade' required=True args: 'res.partner', 'Vendor'
  • price Float
    default=0.0 help='The price to purchase a product' min_display_digits='Product Price' args: 'Unit Price'
  • price_discounted Float
    compute='_compute_price_discounted' args: 'Discounted Price'
  • product_code Char
    help="This vendor's product code will be used when printing a request for quotation. Keep empty to use the internal one." args: 'Vendor Product Code'
  • product_id Many2one → product.product
    check_company=True compute='_compute_product_id' domain="[('product_tmpl_id', '=', product_tmpl_id)] if product_tmpl_id else []" help='If not set, the vendor price will apply to all variants of this product.' precompute=True readonly=False store=True args: 'product.product', 'Product Variant'
  • product_name Char
    help="This vendor's product name will be used when printing a request for quotation. Keep empty to use the internal one." args: 'Vendor Product Name'
  • product_tmpl_id Many2one → product.template
    check_company=True compute='_compute_product_tmpl_id' index=True ondelete='cascade' precompute=True readonly=False required=True store=True args: 'product.template', 'Product Template'
  • product_uom_id Many2one → uom.uom
    compute='_compute_product_uom_id' precompute=True readonly=False required=True store=True args: 'uom.uom', 'Unit'
  • product_variant_count Integer
    related='product_tmpl_id.product_variant_count' args: 'Variant Count'
  • sequence Integer
    default=1 help='Assigns the priority to the list of product vendor.' args: 'Sequence'
Public methods (3)
  • create(self, vals_list)
    @api.model_create_multi
  • get_import_templates(self)
    @api.model
  • write(self, vals)

New fields (8)
  • color Char
    default='#3C3C3C' string='Color'
  • image Image
    max_height=200 max_width=200 string='Image'
  • name Char
    required=True string='Name' translate=True
  • product_ids Many2many → product.product
    compute='_compute_product_ids' search='_search_product_ids' string='All Product Variants using this Tag' args: 'product.product'
  • product_product_ids Many2many → product.product
    comodel_name='product.product' default=_get_default_variant_id domain="[('attribute_line_ids', '!=', False), ('product_tmpl_id', 'not in', product_template_ids)]" relation='product_tag_product_product_rel' string='Product Variants'
  • product_template_ids Many2many → product.template
    comodel_name='product.template' default=_get_default_template_id relation='product_tag_product_template_rel' string='Product Templates'
  • sequence Integer
    default=10
  • visible_to_customers Boolean
    default=True help='Whether the tag is displayed to customers.' string='Visible to customers'
Public methods (1)
  • copy_data(self, default=None)

New fields (46)
  • active Boolean
    default=True help='If unchecked, it will allow you to hide the product without removing it.' args: 'Active'
  • attribute_line_ids One2many → product.template.attribute.line
    copy=True args: 'product.template.attribute.line', 'product_tmpl_id', 'Product Attributes'
  • barcode Char
    compute='_compute_barcode' inverse='_set_barcode' search='_search_barcode' args: 'Barcode'
  • can_image_1024_be_zoomed Boolean
    compute='_compute_can_image_1024_be_zoomed' store=True args: 'Can Image 1024 be zoomed'
  • categ_id Many2one → product.category
    comodel_name='product.category' group_expand='_read_group_categ_id' string='Product Category' tracking=True
  • color Integer
    args: 'Color Index'
  • combo_ids Many2many → product.combo
    check_company=True comodel_name='product.combo' string='Combo Choices'
  • company_id Many2one → res.company
    index=True args: 'res.company', 'Company'
  • cost_currency_id Many2one → res.currency
    compute='_compute_cost_currency_id' args: 'res.currency', 'Cost Currency'
  • currency_id Many2one → res.currency
    compute='_compute_currency_id' args: 'res.currency', 'Currency'
  • default_code Char
    compute='_compute_default_code' inverse='_set_default_code' store=True args: 'Internal Reference'
  • description Html
    translate=True args: 'Description'
  • description_purchase Text
    translate=True args: 'Purchase Description'
  • description_sale Text
    help='A description of the Product that you want to communicate to your customers. This description will be copied to every Sales Order, Delivery Order and Customer Invoice/Credit Note' translate=True args: 'Sales Description'
  • has_configurable_attributes Boolean
    compute='_compute_has_configurable_attributes' store=True args: 'Is a configurable product'
  • import_attribute_values Char
    compute='_compute_import_attribute_values' copy=False inverse='_inverse_import_attribute_values' store=False string='Product Values'
  • is_dynamically_created Boolean
    compute='_compute_is_dynamically_created' args: 'Is Dynamically Created'
  • is_favorite Boolean
    string='Favorite'
  • is_product_variant Boolean
    compute='_compute_is_product_variant' string='Is a product variant'
  • list_price Float
    default=1.0 help='Price at which the product is sold to customers.' min_display_digits='Product Price' tracking=True args: 'Sales Price'
  • name Char
    index='trigram' required=True translate=True args: 'Name'
  • pricelist_rule_ids One2many → product.pricelist.item
    comodel_name='product.pricelist.item' domain=<expr> inverse_name='product_tmpl_id' string='Pricelist Rules'
  • product_document_count Integer
    compute='_compute_product_document_count' string='Documents Count'
  • product_document_ids One2many → product.document
    comodel_name='product.document' domain=<expr> inverse_name='res_id' string='Documents'
  • product_properties Properties
    copy=True definition='categ_id.product_properties_definition' args: 'Properties'
  • product_tag_ids Many2many → product.tag
    comodel_name='product.tag' relation='product_tag_product_template_rel' string='Tags'
  • product_tooltip Char
    compute='_compute_product_tooltip'
  • product_variant_count Integer
    compute='_compute_product_variant_count' args: '# Product Variants'
  • product_variant_id Many2one → product.product
    compute='_compute_product_variant_id' args: 'product.product', 'Product'
  • product_variant_ids One2many → product.product
    required=True args: 'product.product', 'product_tmpl_id', 'Products'
  • purchase_ok Boolean
    compute='_compute_purchase_ok' default=True readonly=False store=True args: 'Purchase'
  • sale_ok Boolean
    default=True args: 'Sales'
  • seller_ids One2many → product.supplierinfo
    depends_context=('company') args: 'product.supplierinfo', 'product_tmpl_id', 'Vendors'
  • sequence Integer
    default=1 help='Gives the sequence order when displaying a product list' args: 'Sequence'
  • service_tracking Selection
    compute='_compute_service_tracking' default='no' readonly=False required=True selection=[('no', 'Nothing')] store=True string='Create on Order'
  • standard_price Float
    compute='_compute_standard_price' groups='base.group_user' help='Value of the product (automatically computed in AVCO).\n Used to value the product when the purchase cost is not known (e.g. inventory adjustment).\n Used to compute margins on sale orders.' inverse='_set_standard_price' min_display_digits='Product Price' search='_search_standard_price' args: 'Cost'
  • type Selection
    default='consu' help='Goods are tangible materials and merchandise you provide.\nA service is a non-material product you provide.' required=True selection=[('consu', 'Goods'), ('service', 'Service'), ('combo', 'Combo')] string='Product Type'
  • uom_id Many2one → uom.uom
    default=_get_default_uom_id help='Default unit of measure used for all stock operations.' required=True tracking=True args: 'uom.uom', 'Unit'
  • uom_ids Many2many → uom.uom
    domain="[('id', '!=', uom_id)]" help='Additional packagings for this product which can be used for sales' string='Packagings' args: 'uom.uom'
  • uom_name Char
    readonly=True related='uom_id.name' string='Unit Name'
  • valid_product_template_attribute_line_ids Many2many → product.template.attribute.line
    compute='_compute_valid_product_template_attribute_line_ids' string='Valid Product Attribute Lines' args: 'product.template.attribute.line'
  • variant_seller_ids One2many → product.supplierinfo
    args: 'product.supplierinfo', 'product_tmpl_id'
  • volume Float
    compute='_compute_volume' digits='Volume' inverse='_set_volume' store=True args: 'Volume'
  • volume_uom_name Char
    compute='_compute_volume_uom_name' string='Volume unit of measure label'
  • weight Float
    compute='_compute_weight' digits='Stock Weight' inverse='_set_weight' store=True args: 'Weight'
  • weight_uom_name Char
    compute='_compute_weight_uom_name' string='Weight unit of measure label'
Public methods (14)
  • action_open_documents(self)
    @api.readonly
  • action_open_label_layout(self)
  • copy(self, default=None)
  • copy_data(self, default=None)
  • create(self, vals_list)
    @api.model_create_multi
    Store the initial standard price in order to be able to retrieve the cost of a product template for a given date
  • default_get(self, fields)
    @api.model
  • get_contextual_price(self, product=None)
  • get_empty_list_help(self, help_message)
    @api.model
  • get_import_templates(self)
    @api.model
  • get_single_product_variant(self)
    Method used by the product configurator to check if the product is configurable or not. We need to open the product configurator if the product: - is configurable (see has_configurable_attributes) - has optional products (method is extended in sale to return optional products info) Note: self.ensure_one()
  • has_dynamic_attributes(self)
    Return whether this `product.template` has at least one dynamic attribute. :return: True if at least one dynamic attribute, False otherwise :rtype: bool
  • load(self, fields, data)
    @api.model
    Data import for products depends on the presence of variants. If 'import_attribute_values' is present, then the product.template files will be created, followed by the product.product files. Everything is done from the same file. The required fields are always imported; however, other fields are imported when the product.product files are created.
  • name_search(self, name='', domain=None, operator='ilike', limit=100)
    @api.model
  • write(self, vals)

New fields (3)
  • product_template_attribute_value_id Many2one → product.template.attribute.value
    comodel_name='product.template.attribute.value' index=True ondelete='cascade' string='Attribute Value'
  • product_tmpl_id Many2one → product.template
    comodel_name='product.template' index=True ondelete='cascade' required=True string='Product Template'
  • value_ids Many2many → product.template.attribute.value
    comodel_name='product.template.attribute.value' domain="[('product_tmpl_id', '=', product_tmpl_id), ('ptav_active', '=', True)]" relation='product_attr_exclusion_value_ids_rel' string='Attribute Values'
Public methods (3)
  • create(self, vals_list)
    @api.model_create_multi
  • unlink(self)
  • write(self, vals)

New fields (7)
  • active Boolean
    default=True
  • attribute_id Many2one → product.attribute
    comodel_name='product.attribute' index=True ondelete='restrict' required=True string='Attribute'
  • product_template_value_ids One2many → product.template.attribute.value
    comodel_name='product.template.attribute.value' inverse_name='attribute_line_id' string='Product Attribute Values'
  • product_tmpl_id Many2one → product.template
    comodel_name='product.template' index=True ondelete='cascade' required=True string='Product Template'
  • sequence Integer
    default=10 args: 'Sequence'
  • value_count Integer
    compute='_compute_value_count' store=True
  • value_ids Many2many → product.attribute.value
    comodel_name='product.attribute.value' domain="[('attribute_id', '=', attribute_id)]" ondelete='restrict' relation='product_attribute_value_product_template_attribute_line_rel' string='Values'
Public methods (4)
  • action_open_attribute_values(self)
    @api.readonly
  • create(self, vals_list)
    @api.model_create_multi
    Override to: - Activate archived lines having the same configuration (if they exist) instead of creating new lines. - Set up related values and related variants. Reactivating existing lines allows to re-use existing variants when possible, keeping their configuration and avoiding duplication.
  • unlink(self)
    Override to: - Archive the line if unlink is not possible. - Clean up related values and related variants. Archiving is typically needed when the line has values that can't be deleted because they are referenced elsewhere (on a variant that can't be deleted, on a sales order line, ...).
  • write(self, vals)
    Override to: - Add constraints to prevent doing changes that are not supported such as modifying the template or the attribute of existing lines. - Clean up related values and related variants when archiving or when updating `value_ids`.

New fields (15)
  • attribute_id Many2one
    index=True related='attribute_line_id.attribute_id' store=True
  • attribute_line_id Many2one → product.template.attribute.line
    comodel_name='product.template.attribute.line' index=True ondelete='cascade' required=True
  • color Integer
    default=_get_default_color string='Color'
  • currency_id Many2one
    related='attribute_line_id.product_tmpl_id.currency_id'
  • display_type Selection
    related='product_attribute_value_id.display_type'
  • exclude_for One2many → product.template.attribute.exclusion
    comodel_name='product.template.attribute.exclusion' help='Make this attribute value not compatible with other values of the product or some attribute values of optional and accessory products.' inverse_name='product_template_attribute_value_id' string='Exclude for'
  • html_color Char
    related='product_attribute_value_id.html_color' string='HTML Color Index'
  • image Image
    related='product_attribute_value_id.image'
  • is_custom Boolean
    related='product_attribute_value_id.is_custom'
  • name Char
    related='product_attribute_value_id.name' string='Value'
  • price_extra Float
    default=0.0 help='Extra price for the variant with this attribute value on sale price. eg. 200 price extra, 1000 + 200 = 1200.' min_display_digits='Product Price' string='Extra Price'
  • product_attribute_value_id Many2one → product.attribute.value
    comodel_name='product.attribute.value' index=True ondelete='cascade' required=True string='Attribute Value'
  • product_tmpl_id Many2one
    index=True related='attribute_line_id.product_tmpl_id' store=True
  • ptav_active Boolean
    default=True string='Active'
  • ptav_product_variant_ids Many2many → product.product
    comodel_name='product.product' readonly=True relation='product_variant_combination' string='Related Variants'
Public methods (3)
  • create(self, vals_list)
    @api.model_create_multi
  • unlink(self)
    Override to: - Clean up the variants that use any of the values in self: - Remove the value from the variant if the value belonged to an attribute line with only one value. - Unlink or archive all related variants. - Archive the value if unlink is not possible. Archiving is typically needed when the value is referenced elsewhere (on a variant that can't be deleted, on a sales order line, ...).
  • write(self, vals)

New fields (4)
  • barcode Char
    copy=False index='btree_not_null' required=True
  • company_id Many2one → res.company
    default=<expr> args: 'res.company', 'Company'
  • product_id Many2one → product.product
    index=True ondelete='cascade' required=True args: 'product.product', 'Product'
  • uom_id Many2one → uom.uom
    index=True ondelete='cascade' required=True args: 'uom.uom', 'Unit'
Public methods (0)

No public methods.

New fields (0)

No new fields.

Public methods (1)
  • get_html(self, data)
    @api.readonly@api.model

New fields (0)

No new fields.

Public methods (0)

No public methods.

New fields (0)

No new fields.

Public methods (0)

No public methods.

New fields (0)

No new fields.

Public methods (0)

No public methods.

New fields (0)

No new fields.

Public methods (0)

No public methods.

New fields (0)

No new fields.

Public methods (0)

No public methods.

New fields (0)

No new fields.

Public methods (2)
  • create(self, vals_list)
    @api.model_create_multi
  • write(self, vals)
    Delay the automatic creation of pricelists post-company update. This makes sure that the pricelist(s) automatically created are created with the right currency.

New fields (6)
  • group_product_pricelist Boolean
    implied_group='product.group_product_pricelist' args: 'Pricelists'
  • group_product_variant Boolean
    implied_group='product.group_product_variant' args: 'Variants'
  • group_uom Boolean
    implied_group='uom.group_uom' args: 'Units of Measure & Packagings'
  • module_loyalty Boolean
    args: 'Promotions, Coupons, Gift Card & Loyalty Program'
  • product_volume_volume_in_cubic_feet Selection
    config_parameter='product.volume_in_cubic_feet' default='0' args: [('0', 'Cubic Meters (m³)'), ('1', 'Cubic Feet (ft³)')], 'Volume unit of measure'
  • product_weight_in_lbs Selection
    config_parameter='product.weight_in_lbs' default='0' args: [('0', 'Kilograms (kg)'), ('1', 'Pounds (lb)')], 'Weight unit of measure'
Public methods (1)
  • set_values(self)

New fields (1)
  • pricelist_ids Many2many → product.pricelist
    column1='res_country_group_id' column2='pricelist_id' comodel_name='product.pricelist' relation='res_country_group_pricelist_rel' string='Pricelists'
Public methods (0)

No public methods.

New fields (0)

No new fields.

Public methods (1)
  • write(self, vals)
    Archive pricelist when the linked currency is archived.

New fields (2)
  • property_product_pricelist Many2one → product.pricelist
    comodel_name='product.pricelist' company_dependent=False compute='_compute_product_pricelist' domain=<expr> help='Used for sales to the current partner' inverse='_inverse_product_pricelist' string='Pricelist'
  • specific_property_product_pricelist Many2one → product.pricelist
    comodel_name='product.pricelist' company_dependent=True
Public methods (0)

No public methods.

New fields (1)
  • product_uom_ids One2many → product.uom
    domain=_domain_product_uoms string='Barcodes' args: 'product.uom', 'uom_id'
Public methods (1)
  • action_open_packaging_barcodes(self)

New fields (4)
  • attribute_value_id Many2one → product.attribute.value
    required=True args: 'product.attribute.value'
  • message Char
    compute='_compute_message'
  • mode Selection
    selection=[('add', 'Add to existing products'), ('update_extra_price', 'Update the extra price on existing products')]
  • product_count Integer
    compute='_compute_product_count'
Public methods (1)
  • action_confirm(self)

Loading…

Loading…

Loading…

Loading…

Loading…

Loading…

Loading…

Loading…

Loading…

Loading…

Loading…

Loading…

Loading…