日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

[NewLife.XCode]实体类详解

發(fā)布時(shí)間:2023/12/4 编程问答 32 豆豆
生活随笔 收集整理的這篇文章主要介紹了 [NewLife.XCode]实体类详解 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

NewLife.XCode是一個(gè)有10多年歷史的開源數(shù)據(jù)中間件,由新生命團(tuán)隊(duì)(2002~2019)開發(fā)完成并維護(hù)至今,以下簡(jiǎn)稱XCode。

整個(gè)系列教程會(huì)大量結(jié)合示例代碼和運(yùn)行日志來進(jìn)行深入分析,蘊(yùn)含多年開發(fā)經(jīng)驗(yàn)于其中。

開源地址:https://github.com/NewLifeX/X?(求star, 620+)

?

回到目錄

生成實(shí)體類

上一章《數(shù)據(jù)模型》講到模型文件Model.xml和腳本Build.tt,(nuget安裝NewLife.XCode后即可擁有)。

把Build.tt和Model.xml(可改名)放在同一個(gè)目錄,在Build.tt上右鍵“運(yùn)行自定義工具”,“顯示所有文件”,即可看到生成的實(shí)體類文件。

**如果運(yùn)行Build.tt出錯(cuò),可能是因?yàn)檎也坏絏Code.dll文件,可以先編譯一次項(xiàng)目,讓XCode.dll生成到項(xiàng)目輸出目錄即可

我們來試試以下模型(拷貝到Model.xml里面):

<?xml version="1.0" encoding="utf-8"?>
<Tables Version="9.9.6940.24706" NameSpace="NewLife.School.Entity" ConnName="School" BaseClass="Entity" Output="">
<Table Name="Class" TableName="xxx_class" Description="班級(jí)" DbType="SqlServer">
<Columns>
<Column Name="ID" DataType="Int32" Identity="True" PrimaryKey="True" Description="編號(hào)" />
<Column Name="Name" ColumnName="xxx_Nameyyy" DataType="String" Master="True" Description="名稱" />
<Column Name="CreateUser" DataType="String" Description="創(chuàng)建者" />
<Column Name="CreateUserID" DataType="Int32" Description="創(chuàng)建者" />
<Column Name="CreateTime" DataType="DateTime" Description="創(chuàng)建時(shí)間" />
<Column Name="CreateIP" DataType="String" Description="創(chuàng)建地址" />
<Column Name="UpdateUser" DataType="String" Description="更新者" />
<Column Name="UpdateUserID" DataType="Int32" Description="更新者" />
<Column Name="UpdateTime" DataType="DateTime" Description="更新時(shí)間" />
<Column Name="UpdateIP" DataType="String" Description="更新地址" />
<Column Name="Remark" DataType="String" Length="200" Description="備注" />
</Columns>
</Table>
<Table Name="Student" Description="學(xué)生" DbType="SqlServer">
<Columns>
<Column Name="ID" DataType="Int32" Identity="True" PrimaryKey="True" Description="編號(hào)" />
<Column Name="ClassID" DataType="Int32" Description="班級(jí)" />
<Column Name="Name" DataType="String" Master="True" Description="名稱" />
<Column Name="Sex" DataType="Int32" Description="性別" Type="XCode.Membership.SexKinds" />
<Column Name="Age" DataType="Int32" Description="年齡" />
<Column Name="Mobile" DataType="String" Description="手機(jī)" />
<Column Name="Address" DataType="String" Description="地址" />
<Column Name="CreateUserID" DataType="Int32" Description="創(chuàng)建者" />
<Column Name="CreateTime" DataType="DateTime" Description="創(chuàng)建時(shí)間" />
<Column Name="CreateIP" DataType="String" Description="創(chuàng)建地址" />
<Column Name="UpdateUserID" DataType="Int32" Description="更新者" />
<Column Name="UpdateTime" DataType="DateTime" Description="更新時(shí)間" />
<Column Name="UpdateIP" DataType="String" Description="更新地址" />
<Column Name="Remark" DataType="String" Length="200" Description="備注" />
</Columns>
<Indexes>
<Index Columns="ClassID" />
</Indexes>
</Table>
</Tables>

運(yùn)行build.tt后

每個(gè)模型表,生成了四個(gè)實(shí)體類文件,選中它們并包含到項(xiàng)目中。

其中Biz常稱之為業(yè)務(wù)類,多次build.tt生成不覆蓋;

另一個(gè)稱之為數(shù)據(jù)類,每次build.tt生成均覆蓋;

這里采用了C#的分部類(partial)技術(shù),一個(gè)類由兩個(gè)或多個(gè)類文件組成。

數(shù)據(jù)類包含表名(類名)字段名(屬性)等信息,修改模型文件后,每次生成都會(huì)覆蓋文件。

業(yè)務(wù)類包含其它非表結(jié)構(gòu)信息,供開發(fā)者填寫代碼,所以只有首次生成,而再次生成時(shí)不會(huì)覆蓋。

數(shù)據(jù)類包括一個(gè)接口(如IStudent),以滿足精簡(jiǎn)需要的場(chǎng)合。

數(shù)據(jù)類內(nèi)部還有兩個(gè)內(nèi)嵌類_和__,可用于快速訪問字段信息以及屬性名。

?

回到目錄

實(shí)體靜態(tài)構(gòu)造函數(shù)

XCode是充血模型,因此實(shí)體類除了各個(gè)代表著表結(jié)構(gòu)信息的屬性外,還會(huì)有大量用戶代碼在其中,并且繼承泛型實(shí)體基類(如Entity<User>)。

一個(gè)常見的實(shí)體類構(gòu)造函數(shù)如下:

static User()
{
// 累加字段
var df = Meta.Factory.AdditionalFields;
df.Add(__.Logins);

// 過濾器 UserModule、TimeModule、IPModule
Meta.Modules.Add<UserModule>();
Meta.Modules.Add
<TimeModule>();
Meta.Modules.Add
<IPModule>();

// 單對(duì)象緩存
var sc = Meta.SingleCache;
sc.FindSlaveKeyMethod
= k => Find(__.Name, k);
sc.GetSlaveKeyMethod
= e => e.Name;
}

這里首先介紹一個(gè)最重要的實(shí)體類內(nèi)嵌類Meta,它位于Entity<TEntity>.Meta,記錄著實(shí)體類的一切元數(shù)據(jù),承載著實(shí)體類的一切高級(jí)功能!

?

Meta.Factory.AdditionalFields用于存放累加字段

一般更新語句?update user set Logins=123 where id=1,而把Logins字段設(shè)為累加字段后,將得到?update user set Logins=Logins+33 where id=1?,特別適用于并發(fā)更新同一行記錄的場(chǎng)合。

?

實(shí)體過濾器EntityModule,用于攔截實(shí)體類的添刪改操作,內(nèi)置最常用的3個(gè)過濾器UserModule/TimeModule/IPModule

上一章末尾推薦的8個(gè)常用字段還記得嗎? CreateUser/CreateTime/CreateIP?等,所有CreateAbc將在Insert的時(shí)候攔截賦值,所有UpdateAbc將在Insert和Update的時(shí)候攔截賦值。

UserModule取當(dāng)前登錄用戶,由ManageProvider驅(qū)動(dòng);

TimeModule取當(dāng)前時(shí)間;

IPModule取當(dāng)前訪問IP,由ManageProvider.UserHost提供;

?

緩存配置

單對(duì)象緩存是一個(gè)字典緩存,默認(rèn)以主鍵為key,實(shí)體對(duì)象為value。

單對(duì)象緩存支持第二個(gè)字典,如上,配置Name為第二字典的主鍵,實(shí)體對(duì)象為value。

?

實(shí)體基類

當(dāng)然,實(shí)體類靜態(tài)構(gòu)造函數(shù)還可以用于其它用途,它將會(huì)在使用該實(shí)體類任意方法(包括成員方法和靜態(tài)方法)之前執(zhí)行。

有時(shí)候把一個(gè)系統(tǒng)模塊放到一個(gè)獨(dú)立子目錄里面,獨(dú)享一個(gè)“Abc.xml”模型文件,生成的實(shí)體類在目錄里面,這個(gè)時(shí)候可以讓它們繼承一個(gè)相同的實(shí)體基類(如EntityBase)。

然后在實(shí)體基類EntityBase的靜態(tài)構(gòu)造函數(shù)中寫入這個(gè)模塊所共有的代碼。

?

回到目錄

初始化數(shù)據(jù)

有些數(shù)據(jù)表需要默認(rèn)初始化一些數(shù)據(jù),如類別表、配置表等,便于開發(fā)測(cè)試。

這個(gè)時(shí)候可以重載InitData方法,它會(huì)在實(shí)體類第一次訪問數(shù)據(jù)庫之前執(zhí)行。

這里遇到Meta的第二次用法Meta.Count,該屬性表示當(dāng)前實(shí)體類數(shù)據(jù)表的總行數(shù)。

當(dāng)總行數(shù)在100萬以內(nèi)時(shí),數(shù)字精確等于 select count(*) from table,大于100萬時(shí),將采用特有的快速方法。

Meta.Count帶緩存,擁有極好的性能,可用于粗略(數(shù)值較小時(shí)精確)估算該表總行數(shù)。

?

這里通過Meta.Count來判斷該表是否為空表,然后對(duì)空表插入一些默認(rèn)數(shù)據(jù)。

?

回到目錄

數(shù)據(jù)驗(yàn)證Valid

每個(gè)實(shí)體類在Insert/Update之前,都需要Valid驗(yàn)證數(shù)據(jù) ,參數(shù)isNew以區(qū)分Insert。

Valid常常可用于判斷主要字段的有效性,無效時(shí)強(qiáng)烈推薦拋出參數(shù)類異常,魔方NewLife.Cube表單將可以捕獲并定位。

除此之外,Valid用得更多的功能是在Insert/Update之前修改完善字段數(shù)據(jù),例如上面對(duì)密碼進(jìn)行MD5散列,以及格式化RoleIDs。

這里出現(xiàn)新技術(shù),IsDirty和Dirtys,這是XCode的臟數(shù)據(jù),前者判斷Password字段是否有臟數(shù)據(jù)(Password被賦予跟原來不想等的值),后者清空Password臟數(shù)據(jù)。

臟數(shù)據(jù)是生成Update語句的核心,不臟的字段不會(huì)出現(xiàn)在update set?之中,實(shí)現(xiàn)部分字段更新,后續(xù)有專門章節(jié)講解。

?

回到目錄

重載添刪改

實(shí)體類的添刪改操作都可以重載(Insert/Update/Delete/OnInsert/OnUpdate/OnDelete)

重載后可以做業(yè)務(wù)代碼判斷,也可以級(jí)聯(lián)更新其它表,還可以記錄添刪改操作日志,甚至還可以做假刪除(重載OnDelete然后實(shí)際執(zhí)行OnUpdate)

分為兩組重載,實(shí)際執(zhí)行順序是:Insert=>Valid=>EntityModule=>OnInsert

?

回到目錄

擴(kuò)展屬性

XCode不支持多表關(guān)聯(lián)Join,取而代之的是擴(kuò)展屬性!

擴(kuò)展屬性的意義,用到該屬性時(shí),再去查詢相應(yīng)數(shù)據(jù),一般目標(biāo)表帶有緩存,并且擴(kuò)展屬性Extends也有緩存

一般擴(kuò)展屬性復(fù)雜對(duì)象加上XmlIgnore和ScriptIgnore特性,規(guī)避Xml序列化和Json序列化。

常常還會(huì)加上 AbcName? 這樣的字符串型屬性,頭上的Map特性將在魔方NewLife.Cube展現(xiàn)數(shù)據(jù)時(shí)發(fā)揮極大作用。

__.ClassID表示映射到該字段,在所有顯示ClassID的地方用當(dāng)前屬性ClassName替代;

后面的類名和字段名,表示要關(guān)聯(lián)的目標(biāo)表和字段,在魔方Cube表單中將直接生成下拉選擇;

?

回到目錄

擴(kuò)展查詢

實(shí)際業(yè)務(wù)中經(jīng)常會(huì)用到根據(jù)某一兩個(gè)字段查詢的需求,例如根據(jù)主鍵查詢。

一般我們把查詢返回單個(gè)對(duì)象的方法命名為 FindByAbc,而把返回多個(gè)實(shí)體的方法命名為 FindAllByAbc。

上面的代碼展示了3種查詢方法:

通過Meta.Count判斷,當(dāng)總行數(shù)小于1000時(shí),全部走M(jìn)eta.Cache實(shí)體緩存表達(dá)式搜索,其原理是整表一次性載入內(nèi)存,后續(xù)有專門文章介紹;

FindByID和FindByName,當(dāng)總數(shù)大于1000時(shí),走對(duì)象緩存Meta.SingleCache,按主鍵ID/Name為鍵,緩存實(shí)體對(duì)象;

不常用的FindByMail和FindAllByClassID中,用到了真正的數(shù)據(jù)庫查詢 Find(__.Mail, mail)?和 FindAll(_.ClassID == classid);

默認(rèn)生成的代碼,都帶有實(shí)體緩存和對(duì)象緩存的例子,默認(rèn)情況下,FindByID只需要查一次數(shù)據(jù)并載入內(nèi)存,即可實(shí)現(xiàn)“極速查詢”,后續(xù)每10秒異步更新。

顯然,如果完全不需要用到緩存,直接寫數(shù)據(jù)庫代碼就好了。

?

回到目錄

高級(jí)查詢

?在業(yè)務(wù)實(shí)現(xiàn)中經(jīng)常出現(xiàn)超過兩個(gè)甚至更多查詢條件,這個(gè)時(shí)候我們推薦Search或SearchAbc

XCode的查詢有一套條件表達(dá)式,以WhereExpression為代表,可以動(dòng)態(tài)拼接任意復(fù)雜的where查詢語句。

FindAll常用兩個(gè)參數(shù),第一個(gè)條件,第二個(gè)PageParameter實(shí)現(xiàn)分頁查詢。

?

至此,簡(jiǎn)單羅列了實(shí)體類的主要構(gòu)成,具體各個(gè)構(gòu)成部分都將會(huì)在后面有專題文章介紹。

?

回到目錄

系列教程

NewLife.XCode教程系列[2019版]

  • 增刪改查入門。快速展現(xiàn)用法,代碼配置連接字符串

  • 數(shù)據(jù)模型文件。建立表格字段和索引,名字以及數(shù)據(jù)類型規(guī)范,推薦字段(時(shí)間,用戶,IP)

  • 實(shí)體類詳解。數(shù)據(jù)類業(yè)務(wù)類,泛型基類,接口

  • 功能設(shè)置。連接字符串,調(diào)試開關(guān),SQL日志,慢日志,參數(shù)化,執(zhí)行超時(shí)。代碼與配置文件設(shè)置,連接字符串局部設(shè)置

  • 反向工程。自動(dòng)建立數(shù)據(jù)庫數(shù)據(jù)表

  • 數(shù)據(jù)初始化。InitData寫入初始化數(shù)據(jù)

  • 高級(jí)增刪改。重載攔截,自增字段,Valid驗(yàn)證,實(shí)體模型(時(shí)間,用戶,IP)

  • 臟數(shù)據(jù)。如何產(chǎn)生,怎么利用

  • 增量累加。高并發(fā)統(tǒng)計(jì)

  • 事務(wù)處理。單表和多表,不同連接,多種寫法

  • 擴(kuò)展屬性。多表關(guān)聯(lián),Map映射

  • 高級(jí)查詢。復(fù)雜條件,分頁,自定義擴(kuò)展FieldItem,查總記錄數(shù),查匯總統(tǒng)計(jì)

  • 數(shù)據(jù)層緩存。Sql緩存,更新機(jī)制

  • 實(shí)體緩存。全表整理緩存,更新機(jī)制

  • 對(duì)象緩存。字典緩存,適用用戶等數(shù)據(jù)較多場(chǎng)景。

  • 百億級(jí)性能。字段精煉,索引完備,合理查詢,充分利用緩存

  • 實(shí)體工廠。元數(shù)據(jù),通用處理程序

  • 角色權(quán)限。Membership

  • 導(dǎo)入導(dǎo)出。Xml,Json,二進(jìn)制,網(wǎng)絡(luò)或文件

  • 分表分庫。常見拆分邏輯

  • 高級(jí)統(tǒng)計(jì)。聚合統(tǒng)計(jì),分組統(tǒng)計(jì)

  • 批量寫入。批量插入,批量Upsert,異步保存

  • 實(shí)體隊(duì)列。寫入級(jí)緩存,提升性能。

  • 備份同步。備份數(shù)據(jù),恢復(fù)數(shù)據(jù),同步數(shù)據(jù)

  • 數(shù)據(jù)服務(wù)。提供RPC接口服務(wù),遠(yuǎn)程執(zhí)行查詢,例如SQLite網(wǎng)絡(luò)版

  • 大數(shù)據(jù)分析。ETL抽取,調(diào)度計(jì)算處理,結(jié)果持久化


  • 創(chuàng)作挑戰(zhàn)賽新人創(chuàng)作獎(jiǎng)勵(lì)來咯,堅(jiān)持創(chuàng)作打卡瓜分現(xiàn)金大獎(jiǎng)

    總結(jié)

    以上是生活随笔為你收集整理的[NewLife.XCode]实体类详解的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。