轉載請註明原文地址:http://www.javashuo.com/article/p-eosipssa-kz.htmlhtml
一:繼承數據庫
在不改變底層對象的時候添加新的功能——這是經過繼承機制來實現的,做爲在現有對象之上的修改層,這些修改能夠發生在全部級別:模型,視圖和業務邏輯。不是直接修改現有模塊,而是建立一個新模塊以添加預期的修改。api
1:擴展模型安全
Odoo 模型存在 Python 的模塊以外, 在中間註冊表那裏。對於這個註冊表,能夠經過模型的方法使用self.env[<model name>]進入。 例如, 經過res.partner 模型獲取對象的引用, 代碼書寫以下 self.env['res.partner']。數據結構
添加字段:dom
# -*- coding: utf-8 -*- from odoo import models, fields, api class Sub(models.Model): _inherit = 'Root' //經過_inherit屬性來繼承父模型 newCol=fields.XX.... //在下面添加新字段便可。
修改現有字段:ide
爲了改變現有字段的屬性,只需再次定義該字段,須要修改的屬性顯式重寫便可,會保留未修改的全部其餘未在此處明確使用的字段的屬性。函數
添加方法:學習
添加新方法很簡單:只需在繼承類中聲明新的函數。測試
修改方法:
擴展或更改現有邏輯,能夠經過聲明具備徹底相同名稱的方法來覆蓋相應的方法。
新方法將替換前一個方法,它能夠只是擴展繼承類的代碼,使用Python的super()方法來調用父方法。而後,能夠在調用super()方法以前和以後,在原有邏輯周圍添加新邏輯。
擴展模型的幾種方式:
1)類繼承:擴展類中沒有_name屬性,由於它繼承了父類的_name。對現有模型的擴展, 添加新功能,都將添加到現有模型中,不會建立新模型。 所以,在odoo中,根據_name惟一肯定這個模型時找到的就是擴展後的類。(如上面添加字段是類繼承)
2)原型繼承:咱們想使用具備不一樣於父模型的值的_name屬性,咱們將得到一個新模型重用來自繼承的特性,可是具備本身的數據庫表和數據。其實就是把繼承的類的功能特性拷貝衣服給新的模型使用,並不改變被繼承模型。
複製意味着被繼承的方法和字段也將在繼承模型中可用。 對於字段,這意味着它們也將被建立並存儲在目標模型的數據庫表中。 原始(繼承)和新(繼承)模型的數據記錄保持不相關。 只有定義是共享的。
3)代理繼承(委託繼承):使用_inherits屬性,它容許一個模型以透明的方式包含其餘模型。經過字典映射繼承模型與字段的關係,並關聯它們。(至關於成員變量:引用一個外部的類對象賦值給這個模型的一個成員,可是對象的值是保存在被引用的類的數據庫表中的。可是在當前類經過成員修改了變量值的,則會同步到被引用的類的數據庫表中)
優勢是不須要在幾個表之間重複數據結構,例如地址。 任何須要包含地址的新模型均可以將其委派給嵌入式合做夥伴模型。 若是在合做夥伴地址字段中引入了修改,則這些修改會當即提供給嵌入它的全部模型!
2:擴展視圖
表單,列表和搜索視圖是使用arch XML結構定義的。 要擴展視圖,咱們須要一種方法來修改這個XML。 這意味着須要定位XML中的元素位置,而後在這些位置引入修改。
對於XML,在其中定位元素的最好方法是使用XPath表達式。若是XPath表達式匹配到多個元素,只有第一個元素會被修改。 所以,表達式應該使用獨特的屬性以使其指定儘量具體。 使用name屬性是確保咱們找到擴展點的確切xml元素的最簡單方法。 所以,在咱們的視圖XML元素上定義name屬性是很重要的。
Xpath表達式的格式:expr="//標籤名[@屬性]='屬性值'":找到屬性=屬性值的標籤位置。
下面是一個寫在arch中的實如今is_done字段以前添加date_deadline字段的具體例子:
<xpath expr="//field[@name]='is_done'" position="before"> //expr屬性值的意思是:找到<filed name="is_done"/>的標籤 <field name="date_deadline" /> </xpath>
Odoo爲此提供了快捷符號,所以大多數時候咱們能夠徹底避免XPath語法。 咱們僅使用要定位的元素的特定屬性及定位類型相關信息就能夠了。
<field name="is_done" position="before"> <field name="date_deadline" /> </field>
若是字段在同一視圖中屢次出現,則應始終使用XPath語法。
position屬性是可選的:
after:將內容添加到父元素之中,匹配的節點以後。 before:添加內容在匹配節點以前。 inside(默認值):匹配節點內的追加內容。 replace:替換匹配的節點。若是使用空內容,它將刪除該匹配的元素。 attributes:修改匹配元素的XML屬性。在元素內容使用<attribute name =「attr-name」>實現給屬性name設置新屬性值attr-name。
1)擴展表單視圖
<record id="view_form_模塊名_inherited" model="ir.ui.view"> <field name="name">模塊名_extension</field> <field name="model">模塊.數據模型</field> <field name="inherit_id" ref="模塊_模型.被繼承的form表單name屬性"/> <field name="arch" type="xml"> //在arch中進行擴展操做:定位—>插入/修改 <field name="定位標籤位置" position="在標籤的哪裏進行擴展"> <field ......> //擴展內容 </field> </field> </record>
2)擴展列表視圖
<record id="view_tree_模型名_inherited" model="ir.ui.view"> <field name="name">模型名 extension</field> <field name="model">模塊.模型</field> <field name="inherit_id" ref="被繼承的tree視圖name名"/> <field name="arch" type="xml">//在arch中進行擴展 <field name="定位標籤名" position="擴展位置"> <field ....進行擴展 /> </field> </field> </record>
3)擴展搜索視圖
<record id="view_filter_模型名_inherited" model="ir.ui.view"> <field name="name"> extension</field> <field name="model">模型名</field> <field name="inherit_id" ref="被繼承的filter視圖名"/> <field name="arch" type="xml"> //下面進行定位、擴展舉例 <field name="name" position="after"> <filter name="filter_my_tasks" string="My Tasks" domain="[('user_id','in',[uid,False])]" /> </field> </field> </record>
4)修改記錄
對於記錄:
<record id="x" model="y">
數據記錄加載時,實際上對模型y執行了create或update操做︰ 若是記錄x不存在,則建立它; 不然,更新原來對應的值。
修改菜單項:
< ! — — 修改菜單項--> <record id="菜單視圖id" model="ir.ui.menu"> //進行修改 </record>
修改action_window:
<record model="ir.actions.act_window" id="action菜單id"> //進行修改 </record>
二:模塊數據
1:列表數據的導出
數據導出是tree視圖的標準功能,不涉及編碼。
只需在列表視圖左側複選框勾選須要導出的記錄,而後點擊列表上方「動做」下拉列表,選擇「導出」。
在導出對話框中選擇須要導出的列、導出的格式(通常選擇CSV,勾選 導入兼容導出),而後點擊「導出到文件」便可。
2:導入數據
在面板點擊「導入」按鈕,選擇文件後載入。而後點擊「驗證」,檢查文件內容的格式合法性,若是正常,則點擊「導入」便可。
3:模塊數據
模塊使用數據文件,將其配置加載到數據庫,能夠經過CSV和XML文件完成。爲了完整性,也可使用YAML文件格式,可是它不多用於加載數據。
一個附加的限制是文件名必須與要加載數據的模型的名稱匹配,這樣系統才能夠推斷應該將數據導入相應的模型。
數據CSV文件的常見用法是加載到ir.model.access模型中的安全定義。
4:演示數據
一個模塊在安裝時,儘可能事先定義一些演示數據,方便在安裝後進行測試使用。
演示數據咱們放在data目錄下,命名爲 xx.xx.csv或者xx.xx.xml
而後在manifest文件中的data屬性進行配置。
5:XML
noupdate:重複數據加載時,將重寫上次運行中加載的記錄。 這意味着升級一個模塊將覆蓋在數據庫內可能已經進行的任何手動更改。此從新導入行爲是默認值,但能夠更改,以便在升級模塊時,某些數據文件記錄保持不變。 這是經過<odoo>或元素的noupdate =「1」屬性完成的。 這些記錄將在安裝addon模塊時建立,但在後續模塊升級中不會對其進行任何操做。
XML中定義記錄:
每一個<record>元素有兩個基本屬性id和model,而且包含爲每列分配值的<field>元素。如前所述,id屬性對應於記錄的外部標識符,而且模型屬性對應於要寫入記錄的目標模型。
設置字段值的幾種方式以下:
1:<record>元素定義數據記錄幷包含<field>元素以設置每一個字段的值,field元素的name屬性標識要寫入的字段,要寫入的值是元素內容:字段的開始和結束標記之間的文本。
2:定義字段值的更精細的替代方法是eval屬性:它評估一個Python表達式並將結果值分配給字段。
<field name="date_deadline" eval="(datetime.now() + timedelta(-1)).strftime('%Y-%m-%d')" />
3:<field>元素還有一個ref屬性,用於使用外部標識符設置many-to-one字段的值。
<field name="user_id" ref="base.user_demo" />
XML中觸發函數:
能夠經過<function>元素,在其加載過程當中執行方法。這能夠用來創建演示和測試數據。
<function model="數據模型" name="數據模型中的方法" eval="參數" />
另外一方式是觸發工做流:
<workflow model="模型" ref="工做流實例" action="工做流信號:觸發工做流" />