mongodb

MongoDB講義

為0 何要學(xué)習(xí)MongoDB

靈活的數(shù)據(jù)模型

MongoDB的文檔數(shù)據(jù)模型使開(kāi)發(fā)人員和數(shù)據(jù)科學(xué)家能夠輕松地在數(shù)據(jù)庫(kù)中存儲(chǔ)和合并任何結(jié)構(gòu)的數(shù)據(jù),而無(wú)需放棄復(fù)雜的驗(yàn)證規(guī)則來(lái)保障數(shù)據(jù)質(zhì)量。

豐富的編程和查詢模型

MongoDB查詢語(yǔ)言和豐富的二級(jí)索引能使開(kāi)發(fā)人員以多種方式來(lái)構(gòu)建查詢和分析數(shù)據(jù)的應(yīng)用程序菩咨。數(shù)據(jù)可以通過(guò)單鍵捌显,范圍茁彭,文本搜索,圖形和地理空間以及復(fù)雜的管道聚集和MapReduce作業(yè)訪問(wèn)到扶歪,且能以毫秒為單位返回響應(yīng)理肺。

什么是MongoDB

MongoDB是一個(gè)基于分布式文件存儲(chǔ)的數(shù)據(jù)庫(kù)。由C++語(yǔ)言編寫(xiě)善镰。旨在為WEB應(yīng)用提供可擴(kuò)展的高性能數(shù)據(jù)存儲(chǔ)解 決方案妹萨。 MongoDB是一個(gè)介于關(guān)系數(shù)據(jù)庫(kù)和非關(guān)系數(shù)據(jù)庫(kù)之間的產(chǎn)品,是非關(guān)系數(shù)據(jù)庫(kù)當(dāng)中功能最豐富炫欺,最像關(guān)系 數(shù)據(jù)庫(kù)的乎完。它支持的數(shù)據(jù)結(jié)構(gòu)非常松散,是類似json的bson格式品洛,因此可以存儲(chǔ)比較復(fù)雜的數(shù)據(jù)類型树姨。Mongo最大 的特點(diǎn)是它支持的查詢語(yǔ)言非常強(qiáng)大,其語(yǔ)法有點(diǎn)類似于面向?qū)ο蟮牟樵冋Z(yǔ)言桥状,幾乎可以實(shí)現(xiàn)類似關(guān)系數(shù)據(jù)庫(kù)單表查 詢的絕大部分功能娃弓,而且還支持對(duì)數(shù)據(jù)建立索引。

MongoDB使用原理

所謂“面向集合”(Collection-Oriented)岛宦,意思是數(shù)據(jù)被分組存儲(chǔ)在數(shù)據(jù)集中,被稱為一個(gè)集合(Collection)耍缴。每個(gè)集合在數(shù)據(jù)庫(kù)中都有一個(gè)唯一的標(biāo)識(shí)名砾肺,并且可以包含無(wú)限數(shù)目的文檔。集合的概念類似關(guān)系型數(shù)據(jù)庫(kù)(RDBMS)里的表(table)防嗡,不同的是它不需要定義任何模式(schema)变汪。Nytro MegaRAID技術(shù)中的閃存高速緩存算法,能夠快速識(shí)別數(shù)據(jù)庫(kù)內(nèi)大數(shù)據(jù)集中的熱數(shù)據(jù)蚁趁,提供一致的性能改進(jìn)裙盾。模式自由(schema-free),意味著對(duì)于存儲(chǔ)在mongodb數(shù)據(jù)庫(kù)中的文件他嫡,我們不需要知道它的任何結(jié)構(gòu)定義番官。如果需要的話,你完全可以把不同結(jié)構(gòu)的文件存儲(chǔ)在同一個(gè)數(shù)據(jù)庫(kù)里钢属。存儲(chǔ)在集合中的文檔徘熔,被存儲(chǔ)為鍵-值對(duì)的形式。鍵用于唯一標(biāo)識(shí)一個(gè)文檔淆党,為字符串類型酷师,而值則可以是各種復(fù)雜的文件類型讶凉。我們稱這種存儲(chǔ)形式為BSON(Binary Serialized Document Format)。

存儲(chǔ)數(shù)據(jù)圖.png

MongoDB持久化原理

mongodb與mysql不同山孔,mysql的每一次更新操作都會(huì)直接寫(xiě)入硬盤(pán)懂讯,但是mongo不會(huì),做為內(nèi)存型數(shù)據(jù)庫(kù)台颠,數(shù)據(jù)操作會(huì)先寫(xiě)入內(nèi)存褐望,然后再會(huì)持久化到硬盤(pán)中去,那么mongo是如何持久化的呢

mongodb在啟動(dòng)時(shí)蓉媳,專門(mén)初始化一個(gè)線程不斷循環(huán)(除非應(yīng)用crash掉)譬挚,用于在一定時(shí)間周期內(nèi)來(lái)從defer隊(duì)列中獲取要持久化的數(shù)據(jù)并寫(xiě)入到磁盤(pán)的journal(日志)和mongofile(數(shù)據(jù))處,當(dāng)然因?yàn)樗皇窃谟脩籼砑佑涗洉r(shí)就寫(xiě)到磁盤(pán)上酪呻,所以按mongodb開(kāi)發(fā)者說(shuō)减宣,它不會(huì)造成性能上的損耗,因?yàn)榭催^(guò)代碼發(fā)現(xiàn)玩荠,當(dāng)進(jìn)行CUD操作時(shí)漆腌,記錄(Record類型)都被放入到defer隊(duì)列中以供延時(shí)批量(groupcommit)提交寫(xiě)入,但相信其中時(shí)間周期參數(shù)是個(gè)要認(rèn)真考量的參數(shù)阶冈,系統(tǒng)為90毫秒闷尿,如果該值更低的話,可能會(huì)造成頻繁磁盤(pán)操作女坑,過(guò)高又會(huì)造成系統(tǒng)宕機(jī)時(shí)數(shù)據(jù)丟失過(guò)填具。

MongoDB 適用于以下場(chǎng)景

MongoDB 的主要目標(biāo)是在鍵/值存儲(chǔ)方式(提供了高性能和高度伸縮性)和傳統(tǒng)的RDBMS 系統(tǒng)(具有豐富的功能)之間架起

MongoDB的應(yīng)用:

● 網(wǎng)站數(shù)據(jù):Mongo 非常適合實(shí)時(shí)的插入,更新與查詢匆骗,并具備網(wǎng)站實(shí)時(shí)數(shù)據(jù)存儲(chǔ)所需的復(fù)制及高度伸縮性劳景。

● 緩存:由于性能很高,Mongo 也適合作為信息基礎(chǔ)設(shè)施的緩存層碉就。在系統(tǒng)重啟之后盟广,由Mongo 搭建的持久化緩存層可以避免下層的數(shù)據(jù)源過(guò)載。

● 大尺寸瓮钥、低價(jià)值的數(shù)據(jù):使用傳統(tǒng)的關(guān)系型數(shù)據(jù)庫(kù)存儲(chǔ)一些數(shù)據(jù)時(shí)可能會(huì)比較昂貴筋量,在此之前,很多時(shí)候程序員往往會(huì)選擇傳統(tǒng)的文件進(jìn)行存儲(chǔ)碉熄。

● 高伸縮性的場(chǎng)景:Mongo 非常適合由數(shù)十或數(shù)百臺(tái)服務(wù)器組成的數(shù)據(jù)庫(kù)桨武,Mongo 的路線圖中已經(jīng)包含對(duì)MapReduce 引擎的內(nèi)置支持。

● 用于對(duì)象及JSON 數(shù)據(jù)的存儲(chǔ):Mongo 的BSON 數(shù)據(jù)格式非常適合文檔化格式的存儲(chǔ)及查詢锈津。

MongoDB 的使用也會(huì)有一些限制玻募,例如,它不適合于以下幾個(gè)地方一姿。

● 高度事務(wù)性的系統(tǒng):例如七咧,銀行或會(huì)計(jì)系統(tǒng)跃惫。傳統(tǒng)的關(guān)系型數(shù)據(jù)庫(kù)目前還是更適用于需要大量原子性復(fù)雜事務(wù)的應(yīng)用程序。

● 傳統(tǒng)的商業(yè)智能應(yīng)用:針對(duì)特定問(wèn)題的BI 數(shù)據(jù)庫(kù)會(huì)產(chǎn)生高度優(yōu)化的查詢方式艾栋。對(duì)于此類應(yīng)用爆存,數(shù)據(jù)倉(cāng)庫(kù)可能是更合適的選擇。

● 需要SQL 的問(wèn)題蝗砾。

Mongo不適用的場(chǎng)景如下:

要求高度事務(wù)性的系統(tǒng)先较。

傳統(tǒng)的商業(yè)智能應(yīng)用。

復(fù)雜的跨文檔(表)級(jí)聯(lián)查詢悼粮。

如何安裝MongoDB

install_1.jpg
install_2.jpg
install_3.jpg
install_4.jpg
install_5.jpg
install_6.jpg
install_7.jpg
install_8.jpg
install_9.jpg

MongoDB和Redis的區(qū)別

MongoDB 更類似 MySQL闲勺,支持字段索引、游標(biāo)操作扣猫,其優(yōu)勢(shì)在于查詢功能比較強(qiáng)大菜循,擅長(zhǎng)查詢 JSON 數(shù)據(jù),能存儲(chǔ)海量數(shù)據(jù)申尤,但是不支持事務(wù)癌幕。

MongoDB的特點(diǎn)

(1)面向文檔(2)高性能(3)高可用(4)易擴(kuò)展(5)豐富的查詢語(yǔ)言

Redis 是一個(gè)開(kāi)源(BSD許可)的,內(nèi)存中的數(shù)據(jù)結(jié)構(gòu)存儲(chǔ)系統(tǒng)昧穿,它可以用作數(shù)據(jù)庫(kù)勺远、緩存和消息中間件。它支持多種類型的數(shù)據(jù)結(jié)構(gòu)
支持持久化操作时鸵,可以進(jìn)行aof及rdb數(shù)據(jù)持久化到磁盤(pán)胶逢,從而進(jìn)行數(shù)據(jù)備份或數(shù)據(jù)恢復(fù)等操作,較好的防止數(shù)據(jù)丟失的手段饰潜。

Redis和MongoDB的區(qū)別:

    1. 性能

都比較高初坠,性能對(duì)我們來(lái)說(shuō)應(yīng)該都不是瓶頸

總體來(lái)講,TPS方面redis要大于mongodb

    1. 操作的便利性

redis豐富一些囊拜,數(shù)據(jù)操作方面,redis更好一些比搭,較少的網(wǎng)絡(luò)IO次數(shù)

mongodb支持豐富的數(shù)據(jù)表達(dá)冠跷,索引,最類似關(guān)系型數(shù)據(jù)庫(kù)身诺,支持的查詢語(yǔ)言非常豐富

  • 3蜜托、內(nèi)存空間的大小和數(shù)據(jù)量的大小

redis在2.0版本后增加了自己的VM特性,突破物理內(nèi)存的限制霉赡;可以對(duì)key value設(shè)置過(guò)期時(shí)間(類似memcache)

mongoDB適合大數(shù)據(jù)量的存儲(chǔ)橄务,依賴操作系統(tǒng)VM做內(nèi)存管理,吃內(nèi)存也比較厲害穴亏,服務(wù)不要和別的服務(wù)在一起

  • 4蜂挪、可用性(單點(diǎn)問(wèn)題)

對(duì)于單點(diǎn)問(wèn)題重挑,

redis,依賴客戶端來(lái)實(shí)現(xiàn)分布式讀寫(xiě)棠涮;主從復(fù)制時(shí)谬哀,每次從節(jié)點(diǎn)重新連接主節(jié)點(diǎn)都要依賴整個(gè)快照,無(wú)增量復(fù)制,因性能和效率問(wèn)題严肪,所以單點(diǎn)問(wèn)題比較復(fù)雜史煎;不支持自動(dòng)sharding,需要依賴程序設(shè)定一致hash 機(jī)制。

一種替代方案是驳糯,不用redis本身的復(fù)制機(jī)制篇梭,采用自己做主動(dòng)復(fù)制(多份存儲(chǔ)),或者改成增量復(fù)制的方式(需要自己實(shí)現(xiàn))酝枢,一致性問(wèn)題和性能的權(quán)衡

mongoDB支持master-slave,replicaset(內(nèi)部采用paxos選舉算法恬偷,自動(dòng)故障恢復(fù)),auto sharding機(jī)制,對(duì)客戶端屏蔽了故障轉(zhuǎn)移和切分機(jī)制隧枫。

  • 5喉磁、可靠性(持久化)

對(duì)于數(shù)據(jù)持久化和數(shù)據(jù)恢復(fù),

redis支持(快照官脓、AOF):依賴快照進(jìn)行持久化协怒,aof增強(qiáng)了可靠性的同時(shí),對(duì)性能有所影響

MongoDB從1.8版本開(kāi)始采用binlog方式支持持久化的可靠性

  • 6卑笨、數(shù)據(jù)一致性(事務(wù)支持)

redis事務(wù)支持比較弱孕暇,只能保證事務(wù)中的每個(gè)操作連續(xù)執(zhí)行

mongoDB不支持事務(wù)

  • 7、數(shù)據(jù)分析

mongoDB內(nèi)置了數(shù)據(jù)分析的功能(mapreduce),其他不支持

  • 8赤兴、應(yīng)用場(chǎng)景

redis:數(shù)據(jù)量較小的更性能操作和運(yùn)算上

MongoDB:主要解決海量數(shù)據(jù)的訪問(wèn)效率問(wèn)題

MongoDB的語(yǔ)法

數(shù)據(jù)庫(kù)名稱命名規(guī)范

不能是空字符串("")妖滔。

不得含有' '(空格)、.桶良、$座舍、/、\和\0 (空字符)陨帆。

應(yīng)全部小寫(xiě)曲秉。

最多64字節(jié)。

文檔名稱命名規(guī)范

鍵不能含有\(zhòng)0 (空字符)疲牵。這個(gè)字符用來(lái)表示鍵的結(jié)尾承二。

.和$有特別的意義,只有在特定環(huán)境下才能使用纲爸。

以下劃線"_"開(kāi)頭的鍵是保留的(不是嚴(yán)格要求的)亥鸠。

需要注意的是:

文檔中的鍵/值對(duì)是有序的。

文檔中的值不僅可以是在雙引號(hào)里面的字符串,還可以是其他幾種數(shù)據(jù)類型(甚至可以是整個(gè)嵌入的文檔)负蚊。

MongoDB區(qū)分類型和大小寫(xiě)神妹。

MongoDB的文檔不能有重復(fù)的鍵。

文檔的鍵是字符串盖桥。除了少數(shù)例外情況灾螃,鍵可以使用任意UTF-8字符。

集合名稱命名規(guī)范

集合名不能是空字符串""揩徊。

集合名不能含有\(zhòng)0字符(空字符)腰鬼,這個(gè)字符表示集合名的結(jié)尾。

集合名不能以"system."開(kāi)頭塑荒,這是為系統(tǒng)集合保留的前綴熄赡。

用戶創(chuàng)建的集合名字不能含有保留字符。有些驅(qū)動(dòng)程序的確支持在集合名里面包含齿税,這是因?yàn)槟承┫到y(tǒng)生成的集合中包含該字符彼硫。除非你要訪問(wèn)這種系統(tǒng)創(chuàng)建的集合,否則千萬(wàn)不要在名字里出現(xiàn)$凌箕∨±海 

MongoDB的基本操作命令

show dbs: 查詢所有數(shù)據(jù)庫(kù)

1.png

自帶三個(gè)數(shù)據(jù)庫(kù)

admin: 從權(quán)限的角度來(lái)看,這是"root"數(shù)據(jù)庫(kù)牵舱。要是將一個(gè)用戶添加到這個(gè)數(shù)據(jù)庫(kù)串绩,這個(gè)用戶自動(dòng)繼承所有數(shù)據(jù)庫(kù)的權(quán)限。一些特定的服務(wù)器端命令也只能從這個(gè)數(shù)據(jù)庫(kù)運(yùn)行芜壁,比如列出所有的數(shù)據(jù)庫(kù)或者關(guān)閉服務(wù)器礁凡。

local: 這個(gè)數(shù)據(jù)永遠(yuǎn)不會(huì)被復(fù)制,可以用來(lái)存儲(chǔ)限于本地單臺(tái)服務(wù)器的任意集合

config: 當(dāng)Mongo用于分片設(shè)置時(shí)慧妄,config數(shù)據(jù)庫(kù)在內(nèi)部使用顷牌,用于保存分片的相關(guān)信息。

use 數(shù)據(jù)庫(kù)名: 創(chuàng)建并且選中數(shù)據(jù)庫(kù)塞淹,數(shù)據(jù)庫(kù)已經(jīng)存在則直接選中

2.png

db: 查詢當(dāng)前選擇的數(shù)據(jù)庫(kù)

db.createCollection("集合名"): 創(chuàng)建集合

3.png

show collections: 查詢當(dāng)前庫(kù)中的集合

db.集合名.drop(): 刪除集合

4.png

db.dropDatabase(): 刪除當(dāng)前選中的數(shù)據(jù)庫(kù)

5.png

MongoDB支持的常見(jiàn)類型

String(字符串): mongodb中的字符串是UTF-8有效的
Integer(整數(shù)): 存儲(chǔ)數(shù)值窟蓝。整數(shù)可以是32位或64位,具體取決于您的服務(wù)器 
Double(雙精度): 存儲(chǔ)浮點(diǎn)值
Boolean(布爾): 存儲(chǔ)布爾(true/false)值
Arrays(數(shù)組): 將數(shù)組或列表或多個(gè)值存儲(chǔ)到一個(gè)鍵中 
Timestamp(時(shí)間戳): 存儲(chǔ)時(shí)間戳
Date(日期): 以UNIX時(shí)間格式存儲(chǔ)當(dāng)前日期或時(shí)間
Object ID(對(duì)象ID) : 存儲(chǔ)文檔ID
Object(對(duì)象): 嵌入式文檔
Null (空值): 存儲(chǔ)Null值
6.png
7.png
8.png
9.png
10.png

新增操作

當(dāng)操作成功時(shí)饱普,集合會(huì)給文檔生成一個(gè)_id字段运挫,該字段就是文檔的主鍵,也能在插入數(shù)據(jù)時(shí)自己指定該字段的值费彼, 但是不建議這樣做

語(yǔ)法:

db.集合名.insert( 文檔 ) : 往集合中插入文檔(可以是單個(gè)文檔,也可以是多個(gè))

如:

插入單個(gè)文檔

需求:往users集合中插入一個(gè)文檔汛骂,id=1001橡庞,name=hello梯啤,age=18

db.users.insert({"id": NumberLong(1001), "name": "hello", age: NumberInt(18)})

11.png

插入多個(gè)文檔

需求:往users集合中插入兩個(gè)文檔该抒,{id=2堪澎,name=tony,age=20}
{id=3洛巢,name=lili坡贺,age=24}

db.users.insert([{id: 2, name: "tony", age: 20},{id: 3, name: "lili", age: 24}])

12.png

通過(guò)數(shù)組也可以一次性插入多條數(shù)據(jù)。

步驟:

1翘瓮、先創(chuàng)建數(shù)組
2贮折、將數(shù)據(jù)放在數(shù)組中
3、一次 insert 到集合中

如:


var arr = [];
for(var i=1 ; i<=20000 ; i++){
    arr.push({num:i});
}

db.numbers.insert(arr);


db.集合名.insertOne():向指定集合中插入一條文檔數(shù)據(jù)

如:

db.users.insertOne({"date":new Date(),"user":{"id":33,"name":"meinv"}})

db.users.insertOne([{"id":2},{"id":3}])

13.png
db.集合名.insertMany():向指定集合中插入多條文檔數(shù)據(jù)

如:

db.users.insertMany([{"date":new Date(),"user":{"id":89,"name":"yo"}}])

14.png

db.users.insertMany([
{"date":new Date(),"user":{"id":90,"name":"haha"}},
{"date":new Date(),"user":{"id":91,"name":"heihei"}},
{"date":new Date(),"user":{"id":92,"name":"hehe"}}
])

15.png

更新操作

db.集合名.update( 
<query>资盅, 
<update>调榄,
 {
  upsert: <boolean>, 
  multi: <boolean>呵扛, 
  writeConcern: <document>
 }
)

參數(shù)說(shuō)明:

query : update的查詢條件每庆,類似sql
update查詢內(nèi)where后面的。

update : update的對(duì)象和一些更新的操作符(如今穿,inc...)等缤灵,也可以理解為sql update查詢內(nèi)set后面的

upsert : 可選,這個(gè)參數(shù)的意思是蓝晒,如果不存在update的記錄腮出,是否插入objNew,true為插入芝薇,默認(rèn)是 false胚嘲,不插入。

multi : 可選剩燥,mongodb 默認(rèn)是false慢逾,只更新找到的第一條記錄,如果這個(gè)參數(shù)為true灭红,就把按條件查出來(lái)多 條記錄全部更新侣滩。

writeConcern :可選,拋出異常的級(jí)別

db.集合名.update(...):更新集合中的數(shù)據(jù)(一條或者多條)

如:

更新單個(gè)文檔

需求:修改name=tony的文檔信息变擒,把a(bǔ)ge改為19,如果沒(méi)有符合條件的文檔君珠,就不操作,如果有很多符合條件的娇斑,只修改第一個(gè)文檔信息策添。

db.users.update({name:"tony"},{$set:{age:19}},false,false)

31.png

更新多個(gè)文檔

需求:修改users集合中所有符合條件name=tony的文檔信息,把a(bǔ)ge改為22,如果沒(méi)有符合條件的文檔毫缆,就不操作唯竹,如果有很多符合條件的,全部修改

db.users.update({name:"tony"},{$set:{age:22}},false,true)

32.png

針對(duì)更新操作的語(yǔ)法苦丁,我們還有對(duì)應(yīng)的簡(jiǎn)寫(xiě)方式:

只能修改單個(gè)文檔:

db.集合名.updateOne( ... ):更新集合中的一條數(shù)據(jù)

需求:把users集合中符合條件name=tony的文檔浸颓,把文檔中的age修改為30。如果符合條件的文檔有很多,該方法只會(huì)修改第一個(gè)文檔产上。

db.users.updateOne({name: "tony"}, {$set: {age: 30}})

33.png

可以修改多個(gè)文檔:

db.集合名.updateMany( ... ):更新集合中的多條數(shù)據(jù)

需求:把users集合中符合條件name=tony的文檔棵磷,把文檔中的age修改為50。如果符合條件的文檔有很多晋涣,該方法會(huì)修改所有符合條件的文檔仪媒。

db.users.updateMany({name: "tony"}, {$set: {age: 50}})

34.png

刪除操作

    
db.集合名.remove( 
<query>,
{
    justOne: <boolean>谢鹊, 
    writeConcern: <document>
} )

參數(shù)說(shuō)明:

query :(可選)刪除的文檔的條件算吩。

justOne : (可選)如果設(shè)為 true 或 1,則只刪除一個(gè)文檔佃扼,如果不設(shè)置該參數(shù)赌莺,或使用默認(rèn)值 false,則刪除 所有匹配條件的文檔松嘶。

writeConcern :(可選)拋出異常的級(jí)別

db.集合名.remove():根據(jù)條件刪除集合中的數(shù)據(jù)(一條或者多條)

刪除單個(gè)文檔

需求:刪除users集合中id為11的文檔信息

35.png

刪除多個(gè)文檔

需求:刪除users集合中name=tony的文檔信息艘狭。

36.png

只能根據(jù)條件刪除單個(gè)文檔:

db.集合名.deleteOne( ... ):根據(jù)條件只刪除符合條件的數(shù)據(jù)中的第一個(gè)

需求:刪除users集合中name=tony的文檔信息。如果匹配到很多文檔信息翠订,只會(huì)刪除第一個(gè)文檔信息巢音。

37.png

可以根據(jù)條件刪除多個(gè)文檔:

db.集合名.deleteMany( ... ):根據(jù)條件刪除所有符合條件的數(shù)據(jù)

需求: 刪除users集合中,符合name=tony的所有文檔信息尽超。

38.png

查詢操作

基本查詢

查詢所有

    db.集合名.find()
    db.集合名.find().pretty()

需求:查詢所有文檔

db.users.find()

16.png

需求:查詢所有文檔官撼,并且格式化打印

db.users.find().pretty()

17.png

根據(jù)條件查詢

    db.集合名.find(query, projection)

query :可選似谁,使用查詢操作符指定查詢條件

projection :可選傲绣,使用投影操作符指定返回的鍵。查詢時(shí)返回文檔中所有鍵值巩踏, 只需省略該參數(shù)即可(默認(rèn)省略)秃诵。

需求:查詢所有name=tony的文檔信息

db.users.find({name:"tony"})

18.png

排序查詢

    db.集合名.find().sort({字段: 1}) 按照字段升序排列
    db.集合名.find().sort({字段: -1}) 按照字段降序排列

需求:查詢users集合的所有數(shù)據(jù),并按照年齡升序進(jìn)行排序

db.users.find().sort({age: 1})

需求:查詢users集合中的所有數(shù)據(jù)塞琼,先按照年齡升序排序菠净,然后再按照id降序排序

db.users.find().sort({age:1,id:-1})

19.png

分頁(yè)查詢

    sikp(num) 跳過(guò)num個(gè)文檔,相當(dāng)于start
    limit(num) 限制顯示num個(gè)文檔彪杉,相當(dāng)于pageSize

需求:按照年齡降序排列毅往,查詢第2頁(yè),每頁(yè)顯示3個(gè)

db.users.find().sort({age:-1}).skip(3).limit(3)

20.png

高級(jí)查詢

等值查詢

    find({字段: 值}) 查詢集合中符合字段和值都相等的文檔信息

需求:查詢users集合中年齡為29歲的文檔信息

db.users.find({age:29})

21.png

比較查詢

    db.集合名.find({字段:{比較運(yùn)算符:值....}})

(>) 大于 - $gt

需求:查詢users集合中年齡大于29歲的文檔信息

db.users.find({age:{$gt:29}})

22.png
(<) 小于 - $lt

需求:查詢users集合中年齡大于26歲派近,小于29歲的文檔信息

db.users.find({age:{gt:26,lt:29}})

(>=) 大于等于 - $gte

需求:查詢users集合中年齡大于等于26歲的文檔信息

db.users.find({age:{$gte:26}})

(<= ) 小于等于 - $lte

需求:查詢users集合中年齡大于等于26歲攀唯,并且小于等于29歲的文檔信息。

db.users.find({age:{lte:29,gte:26}})

23.png
(!=) 不等 - $ne

需求:查詢users集合中name不是tony的文檔信息

db.users.find({name:{$ne:"tony"}})

24.png
集合運(yùn)算 - $in 如:{name: {$in: ["xiaoyao"渴丸,"bunny"]}}

需求:查詢users集合中id為 3,4,6的文檔信息

db.users.find({id:{$in:[3,4,6]}})

25.png
判斷存在 - $exists 如:{name: {$exists:true}}

需求:返回users集合中符合name字段存不存在的數(shù)據(jù)文檔信息

db.users.find({name:{$exists:true}})

如果設(shè)置成true, 返回含有name字段的文檔信息

db.users.find({name:{$exists:false}})

如果設(shè)置成false,返回不含有name字段的文檔信息

26.png

邏輯查詢

    find({邏輯操作符: [條件1侯嘀, 條件2战坤, ...]})

    (&&) 與 - $and

需求:獲取users集合中name為tony且age大于等于20歲的文檔信息


db.users.find({
$and:[
    {name:"tony"},
    {age:{$gte:20}}
        ]
})

27.png
(||) 或 - $or

需求:獲取users集合中name為tony或者age大于等于29歲的文檔信息

db.users.find({
    $or:[
          {name:"tony"},
           {age:{$gte:29}}
        ]
})

28.png
(!) 非 - $not

需求:獲取users集合中age小于等于20,或者age字段不存在的文檔信息

db.users.find({age:{not:{gt:20}}})

29.png

模糊查詢

    {name: {$regex: /^.*keyword.*$/}} keyword作為關(guān)鍵字,進(jìn)行模糊匹配

MongoDB的模糊查詢使用的是正則表達(dá)式的語(yǔ)法 如:{name: {regex: /^.*keyword.*/}}
實(shí)際上MongoDB也是不擅長(zhǎng)執(zhí)行模糊查詢的残拐,在實(shí)際開(kāi)發(fā)中也是不使用的,該功能了解即可

需求:獲取users集合中,name字段中包含tony的文檔信息

db.users.find({name:{regex:/^.*tony.*/}})

30.png

設(shè)置MongoDB的用戶和密碼

以下操作必須在cmd命令行中操作碟嘴,執(zhí)行以下命令

//1.選中admin數(shù)據(jù)庫(kù)

use admin

//2.往里面添加一個(gè)超級(jí)管理員賬號(hào)

db.createUser({user:"root", pwd: "admin", roles:["root"]})

//user:賬號(hào) pwd:密碼 roles:角色->root超級(jí)管理員

修改MongoDB的配置文件:安裝目錄/Server/bin/mongod.cfg

約在29行位置溪食,配置開(kāi)啟權(quán)限認(rèn)證

security:

authorization: enabled

完成上面配置后重啟服務(wù)器

設(shè)置MongoDB密碼.png

SpringBoot整合MongoDB

數(shù)據(jù):

db.users.insert({"id":NumberLong(1),"name":"tony","age":NumberInt(18)})

db.users.insert({"id":NumberLong(2),"name":"tony","age":NumberInt(20)})

db.users.insert({"id":NumberLong(3),"name":"zhang quan dan","age":NumberInt(33)})

db.users.insert({"id":NumberLong(4),"name":"zhang kun","age":NumberInt(26)})

db.users.insert({"id":NumberLong(6),"name":"cai xv kun","age":NumberInt(29)})

db.users.insert({"id":NumberLong(7),"name":"jia nai liang","age":NumberInt(25)})

db.users.insert({"id":NumberLong(8),"name":"fu rong wang","age":NumberInt(28)})

db.users.insert({"id":NumberLong(9),"name":"wang da","age":NumberInt(31)})

db.users.insert({"id":NumberLong(10),"name":"wang tony","age":NumberInt(32)})

db.users.insert({"id":NumberLong(11),"name":"tony","age":NumberInt(26)})

pom.xml:

<dependencies>

<dependency>

<groupId>org.springframework.boot</groupId>

<artifactId>spring-boot-starter</artifactId>

</dependency>

<dependency>

<groupId>org.springframework.boot</groupId>

<artifactId>spring-boot-starter-test</artifactId>

<scope>test</scope>

</dependency>

<dependency>

<groupId>org.projectlombok</groupId>

<artifactId>lombok</artifactId>

</dependency>

<!--spring boot data mongodb-->

<dependency>

<groupId>org.springframework.boot</groupId>

<artifactId>spring-boot-starter-data-mongodb</artifactId>

</dependency>

</dependencies>

User:

@AllArgsConstructor
@NoArgsConstructor
@Setter
@Getter
@ToString
@Document("users")//設(shè)置文檔所在的集合
public class User {
    @Id
    private ObjectId _id; //文檔的id使用ObjectId類型來(lái)封裝,并且貼上@Id注解

    private Long id;
    private String name;
    private Integer age;

}

UserMongoRepository:


/**
 * 自定義一個(gè)接口繼承MongoRepository娜扇,
 * 泛型1:domain類型
 * 泛型2:主鍵類型
 * 貼上@Repository注解错沃,底層會(huì)創(chuàng)建出動(dòng)態(tài)代理對(duì)象,交給Spring管理
 */

@Repository
public interface UserMongoRepository extends MongoRepository<User, ObjectId> {

}

使用已經(jīng)提供的API方法雀瓢,進(jìn)行DML操作:

@RunWith(SpringRunner.class)
@SpringBootTest(classes = App.class)
public class MongoDBTest {

    @Autowired
    private UserMongoRepository userMongoRepository;

    //保存單個(gè)對(duì)象
    @Test
    public void testSave() throws Exception {
        User user = new User();
        user.setAge(184);
        user.setName("ruhuaQ");
        userMongoRepository.save(user);
    }

    //保存多個(gè)對(duì)象
    @Test
    public void testSaveMore() throws Exception {
        Iterable<User> iterable = new ArrayList<>();
        User user = new User();
        user.setAge(18);
        user.setName("heihei");

        User user1 = new User();
        user1.setAge(19);
        user1.setName("haha");

        ((ArrayList<User>) iterable).add(user);
        ((ArrayList<User>) iterable).add(user1);

        userMongoRepository.saveAll(iterable);
    }

    // 修改
    @Test
    public void testUpdate() throws Exception {
        User user = new User();
        user.setId(14L);
        user.setName("haha");
        user.setAge(4);
        user.set_id(new ObjectId("5d614d91783671106f16d9f7"));
        userMongoRepository.save(user);
    }

    // 刪除
    // 根據(jù)對(duì)象刪除  必須要設(shè)置 _id
    @Test
    public void testDeleteByObject() throws Exception {
        User user = new User();
        user.setAge(184);
        user.setName("ruhuaQ");
        user.set_id(new ObjectId("5d614cc978367110673a5b3c"));
        userMongoRepository.delete(user);
    }

    // 根據(jù)id刪除
    @Test
    public void testDeleteById() throws Exception {
        userMongoRepository.deleteById(new ObjectId("5d6145bb783671100737b424"));
    }
}

使用已經(jīng)提供的API方法枢析,進(jìn)行DQL操作:


    //查詢所有數(shù)據(jù)
    @Test
    public void testFindAll() throws Exception {
        List<User> userList = userMongoRepository.findAll();
        userList.forEach(System.out::println);
    }

    // 查詢所有數(shù)據(jù)并按照age降序排序
    @Test
    public void testFindAllAndSortDesc() throws Exception {
//      List<User> users = userMongoRepository.findAll(Sort.by(Sort.Order.desc("age")));//方式一
        List<User> users = userMongoRepository.findAll(Sort.by(Sort.Direction.DESC, "age"));//方式二
        users.forEach(System.out::println);
    }

    // 查詢所有數(shù)據(jù)并按照age升序排序
    @Test
    public void testFindAllSortAsc() throws Exception {
//      List<User> usersAsc = userMongoRepository.findAll(Sort.by("age")); // 方式一
//      List<User> usersAsc = userMongoRepository.findAll(Sort.by(Sort.Order.asc("age")));//方式二
        List<User> usersAsc = userMongoRepository.findAll(Sort.by(Sort.Direction.ASC, "age"));//方式三
        usersAsc.forEach(System.out::println);
    }

    // 根據(jù)ObjectId 查詢對(duì)應(yīng)的user信息
    @Test
    public void testFindById() throws Exception {
        Optional<User> userOptional = userMongoRepository.findById(new ObjectId("5d614d91783671106f16d9f7"));
        System.out.println(userOptional);
    }

    // 根據(jù)多個(gè)ObjectId 查詢對(duì)應(yīng)的user信息
    @Test
    public void testByIds() throws Exception {
        Iterable<ObjectId> objectIds = new ArrayList<>();
        ((ArrayList<ObjectId>) objectIds).add(new ObjectId("5d614d91783671106f16d9f7"));
        ((ArrayList<ObjectId>) objectIds).add(new ObjectId("5d610458ab75afa90a18e82b"));
        ((ArrayList<ObjectId>) objectIds).add(new ObjectId("5d610458ab75afa90a18e82d"));

        Iterable<User> usersByIds = userMongoRepository.findAllById(objectIds);
        usersByIds.forEach(System.out::println);
    }

    // 根據(jù)自定義條件查詢所有符合條件的user的信息
    @Test
    public void testFindAllByCondition() throws Exception {
        User user = new User();
        user.setAge(26);
        List<User> list = userMongoRepository.findAll(Example.of(user));
        list.forEach(System.out::println);
    }

    // 根據(jù)自定義的條件查詢符合條件的user的信息但是只獲取第一個(gè)作為結(jié)果
    @Test
    public void testFindOne() throws Exception {
        User user = new User();
        user.setAge(26);
        user.setName("zhang kun");
        Optional<User> user1 = userMongoRepository.findOne(Example.of(user));
        System.out.println("user1 = " + user1);
    }

    // 獲取第一頁(yè)的數(shù)據(jù),每頁(yè)顯示3條
    @Test
    public void testFindPage() throws Exception {
        // 第一個(gè)參數(shù)表示獲取第幾頁(yè)刃麸,頁(yè)碼是從0開(kāi)始的
        // 第二個(gè)參數(shù)表示一頁(yè)顯示多少條數(shù)據(jù)醒叁。
        Page<User> users = userMongoRepository.findAll(PageRequest.of(0, 3));
        users.forEach(System.out::println);
    }

    // 先排序,然后再獲取第一頁(yè)的數(shù)據(jù)泊业,每頁(yè)顯示3條
    @Test
    public void testFindPageAndSort() throws Exception {
        // 第一個(gè)參數(shù)表示獲取第幾頁(yè)把沼,頁(yè)碼是從0開(kāi)始的
        // 第二個(gè)參數(shù)表示一頁(yè)顯示多少條數(shù)據(jù)。
        // 第三個(gè)參數(shù)表示排序
        Page<User> users = userMongoRepository.findAll(PageRequest.of(0, 3, Sort.by(Sort.Order.desc("age"))));
        users.forEach(System.out::println);
    }

自定義查詢方法:

/**
 * 自定義一個(gè)接口繼承MongoRepository吁伺,
 * 泛型1:domain類型
 * 泛型2:主鍵類型
 * 貼上@Repository注解饮睬,底層會(huì)創(chuàng)建出動(dòng)態(tài)代理對(duì)象,交給Spring管理
 */

@Repository
public interface UserMongoRepository extends MongoRepository<User, ObjectId> {

    // 根據(jù)name 和 age 進(jìn)行查找 SQL:where name=? and age=?
    User findByNameAndAge(String name, Integer age);


    // 根據(jù)name 或者 age 進(jìn)行匹配 SQL:where name=? or age=?
    List<User> findByNameOrAge(String name, Integer age);


    // 根據(jù)name進(jìn)行查找 SQL:where name = ?
    List<User> findByName(String name);


    // 根據(jù)name進(jìn)行查找 SQL:where name = ? (忽略大小寫(xiě))
    List<User> findByNameIgnoreCase(String name);


    // 根據(jù)age的范圍進(jìn)行查找 SQL:where age between ? and ?
    List<User> findByAgeBetween(Integer min, Integer max);


    // 根據(jù)age小于指定值的數(shù)據(jù) SQL:where age < ?
    List<User> findByAgeLessThan(Integer age);

    List<User> findByAgeBefore(Integer age);


    // 根據(jù)age小于等于指定值的數(shù)據(jù) SQL:where age <= ?
    List<User> findByAgeLessThanEqual(Integer age);


    // 根據(jù)age大于指定值的數(shù)據(jù) SQL:where age > ?
    List<User> findByAgeGreaterThan(Integer age);

    List<User> findByAgeAfter(Integer age);


    // 根據(jù)age大于等于指定值的數(shù)據(jù) SQL:where age >= ?
    List<User> findByAgeGreaterThanEqual(Integer age);


    // 查找name為null的數(shù)據(jù) SQL:where name is null
    List<User> findByNameIsNull();


    // 查找name不為null的數(shù)據(jù) SQL:where name is not null
    List<User> findByNameIsNotNull();

    // 根據(jù)name字段進(jìn)行模糊查詢 SQL:where name like ?
    List<User> findByNameLike(String name);


    //根據(jù)name字段進(jìn)行模糊查詢(取反) SQL:where name not like ?
    List<User> findByNameNotLike(String name);


    // 查詢name中以指定條件開(kāi)頭的數(shù)據(jù)  SQL:where name like '?%'
    List<User> findByNameStartingWith(String name);


    // 查詢name中以指定條件結(jié)尾的數(shù)據(jù) SQL:where name like '%?'
    List<User> findByNameEndingWith(String name);


    // 查詢name中包含了指定條件的數(shù)據(jù) SQL:where name like '%?%'
    List<User> findByNameContaining(String name);


    // 查詢符合指定年齡的數(shù)據(jù)篮奄,并按照id的值升序排序 SQL:where id = ? order by Id
    List<User> findByAgeOrderById(Integer age);

    // 查詢符合指定年齡的數(shù)據(jù)捆愁,并按照id的值降序排序 SQL:where id = ? order by Id [desc]
    List<User> findByAgeOrderByIdDesc(Integer age);


    // 查詢name不等于指定條件的數(shù)據(jù) SQL:where name != ?
    List<User> findByNameNot(String name);


    // 查詢指定id的數(shù)據(jù) SQL:where id in ( ... )
    List<User> findByIdIn(List<Long> ids);


    // 查詢指定id的數(shù)據(jù)(取反) SQL:where id not in ( ... )
    List<User> findByIdNotIn(List<Long> ids);


    // 查詢指定條件為true的數(shù)據(jù) SQL:where Xx = true
    //List<User> findByXxTrue();


    // 查詢指定條件為false的數(shù)據(jù) SQL:where Xx = false
   // List<User> findByXxFalse();

}

測(cè)試自定義查詢的方法:


    // 查找name=tony,age=18的user信息
    @Test
    public void test1() throws Exception {
        User user = userMongoRepository.findByNameAndAge("tony", 18);
        System.out.println("user = " + user);
    }

    // 查詢name=tony 或者 age=33的user信息
    @Test
    public void test2() throws Exception {
        List<User> list = userMongoRepository.findByNameOrAge("tony", 33);
        list.forEach(System.out::println);
    }

    // 查詢name=tony的user信息
    @Test
    public void test3() throws Exception {
        List<User> list = userMongoRepository.findByName("tony");
        list.forEach(System.out::println);
    }

    // 查詢name=tony的user信息(tony忽略大小寫(xiě))
    @Test
    public void test4() throws Exception {
        List<User> list = userMongoRepository.findByNameIgnoreCase("tony");
        list.forEach(System.out::println);
    }

    // 查詢age 在28 到 33 的user信息(注意不包括28和33)
    @Test
    public void test5() throws Exception {
        List<User> list = userMongoRepository.findByAgeBetween(28, 33);
        list.forEach(System.out::println);
    }

    // 查詢 age 小于 28 的user信息
    @Test
    public void test6() throws Exception {
        List<User> list = userMongoRepository.findByAgeLessThan(28);
        list.forEach(System.out::println);
    }

    // 查詢 age 小于 28 的user的信息
    @Test
    public void test7() throws Exception {
        List<User> list = userMongoRepository.findByAgeBefore(28);
        list.forEach(System.out::println);
    }

    // 查詢age 小于等于 26 的user信息
    @Test
    public void test8() throws Exception {
        List<User> list = userMongoRepository.findByAgeLessThanEqual(26);
        list.forEach(System.out::println);
    }

    // 查詢age 大于 26的user信息
    @Test
    public void test9() throws Exception {
        List<User> list = userMongoRepository.findByAgeGreaterThan(26);
        list.forEach(System.out::println);
    }

    // 查詢 age 大于 26的user信息
    @Test
    public void test10() throws Exception {
        List<User> list = userMongoRepository.findByAgeAfter(26);
        list.forEach(System.out::println);
    }

    // 查詢age 大于等于26的user信息
    @Test
    public void test11() throws Exception {
        List<User> list = userMongoRepository.findByAgeGreaterThanEqual(26);
        list.forEach(System.out::println);
    }

    // 查詢name=null的user信息
    @Test
    public void test12() throws Exception {
        List<User> list = userMongoRepository.findByNameIsNull();
        list.forEach(System.out::println);
    }

    // 查詢name!=null的user信息
    @Test
    public void test13() throws Exception {
        List<User> list = userMongoRepository.findByNameIsNotNull();
        list.forEach(System.out::println);
    }

    // 查詢 name 中包含tony的user信息
    @Test
    public void test14() throws Exception {
        List<User> list = userMongoRepository.findByNameLike("tony");
        list.forEach(System.out::println);
    }

    // 查詢name中沒(méi)有包含tony的user信息
    @Test
    public void test15() throws Exception {
        List<User> list = userMongoRepository.findByNameNotLike("tony");
        list.forEach(System.out::println);
    }

    //查詢name以to字母開(kāi)頭的user信息
    @Test
    public void test16() throws Exception {
        List<User> list = userMongoRepository.findByNameStartingWith("to");
        list.forEach(System.out::println);
    }

    // 查詢name以n字母結(jié)尾的user信息
    @Test
    public void test17() throws Exception {
        List<User> list = userMongoRepository.findByNameEndingWith("n");
        list.forEach(System.out::println);
    }
    // 查詢name中包含tony的user信息
    @Test
    public void test18() throws Exception {
        List<User> list = userMongoRepository.findByNameContaining("tony");
        list.forEach(System.out::println);
    }

    // 查詢年齡為26的user信息并以id的值升序排序
    @Test
    public void test19() throws Exception {
//        List<User> list = userMongoRepository.findByAgeOrderById(26);
        List<User> list = userMongoRepository.findByAgeOrderByIdDesc(26);
        list.forEach(System.out::println);
    }

    // 查詢name 不為tony的user 信息
    @Test
    public void test20() throws Exception {
        List<User> list = userMongoRepository.findByNameNot("tony");
        list.forEach(System.out::println);
    }
    // 查詢id為1窟却,2昼丑,3,4的user信息
    @Test
    public void test21() throws Exception {
        List<User> list = userMongoRepository.findByIdIn(Arrays.asList(1L, 2L, 3L, 4L));
        list.forEach(System.out::println);
    }

    // 查詢id不為 2夸赫,3矾克,4,5的user信息
    @Test
    public void test22() throws Exception {
        List<User> list = userMongoRepository.findByIdNotIn(Arrays.asList(2L, 3L, 4L, 5L));
        list.forEach(System.out::println);
    }


使用MongoTemplate靈活的操作MongoDB

該對(duì)象有SpringBoot完成了自動(dòng)配置憔足,存入Spring容器中胁附,我們直接注入就可以使用了,依靠該對(duì)象能完成任何的
MongoDB操作滓彰,一般和MongoRepository分工合作控妻,多數(shù)用于復(fù)雜的高級(jí)查詢以及底層操作

Query對(duì)象用于封裝查詢條件,配合Criteria一起使用揭绑,來(lái)完成各種條件的描述

使用MongoTemplate完成DML操作弓候。

@RunWith(SpringRunner.class)
@SpringBootTest(classes = App.class)
public class MongoDBTest {

    @Autowired
    private MongoTemplate mongoTemplate;
    
     // 保存操作
    @Test
    public void testTemplate_1() throws Exception {
        User user = new User();
        user.setId(15L);
        user.setName("tmplate");
        user.setAge(12);
        // 保存數(shù)據(jù)到當(dāng)前集合中
        mongoTemplate.save(user);
        // 保存數(shù)據(jù)到指定的temp集合中
        mongoTemplate.save(user, "temp");

        User user1 = new User();
        user1.setId(17L);
        user1.setName("tmplateBatch2");
        user1.setAge(100);
        List<User> list = new ArrayList<>();
        User user2 = new User();
        user2.setId(16L);
        user2.setName("tmplateBatch1");
        user2.setAge(120);
        list.add(user1);
        list.add(user2);
        // 批量保存數(shù)據(jù)到當(dāng)前集合
        mongoTemplate.insertAll(list);
        // 批量保存數(shù)據(jù)到指定集合
        mongoTemplate.insert(list, "users");
    }

    // 刪除操作
    @Test
    public void testTemplate_2() throws Exception {
        User user = new User();
        user.setName("tonny");
        user.setAge(66);
        user.set_id(new ObjectId("5d610458ab75afa90a18e82b"));
        // 刪除指定對(duì)象郎哭,必須要有ObjectId這個(gè)條件
        mongoTemplate.remove(user);
        Query query = new Query();
        query.addCriteria(Criteria.where("_id").in(Arrays.asList("5d610458ab75afa90a18e82c", "5d610458ab75afa90a18e82d")));
        // 根據(jù)條件刪除
        mongoTemplate.remove(query);
        // 根據(jù)條件刪除指定集合中的數(shù)據(jù)
        mongoTemplate.remove(query, "users");
        // 刪除指定名稱(temp)的集合
        mongoTemplate.dropCollection("temp");

    }

    // 修改操作
    @Test
    public void testTemplate_3() throws Exception {
        Query query = new Query();
        //query.addCriteria(Criteria.where("_id").is("5d610458ab75afa90a18e82b"));
        query.addCriteria(Criteria.where("name").is("tonny"));
        Update update = Update.update("name", "tony").set("age", 46);
        // 更新單個(gè)文檔
        // 查找name=tony的user信息,把查找的結(jié)果中第一個(gè)結(jié)果進(jìn)行修改菇存,把name改為tonny夸研,age 改為6
        mongoTemplate.updateFirst(query, update, "users");

        // 更新多個(gè)文檔
        Query query1 = new Query();
        query1.addCriteria(Criteria.where("name").is("tony"));
        Update update1 = Update.update("age","11");
        mongoTemplate.updateMulti(query1,update1,"users");

    }
}

使用MongoTemplate完成DQL操作。


    // 根據(jù) Object ID 查詢user 信息
    @Test
    public void testTemplate_4() throws Exception {
        // 根據(jù)條件依鸥,從當(dāng)前集合中獲取
        User user1 = mongoTemplate.findById("5d64b2c0c892a90c08f4f848", User.class);
        // 根據(jù)條件亥至,從指定集合中獲取
        User user2 = mongoTemplate.findById("5d64b2c0c892a90c08f4f848", User.class, "users");
        System.out.println("user1 = " + user1);
        System.out.println("user2 = " + user2);
    }

    // 查詢所有user信息
    @Test
    public void testTemplate_5() throws Exception {

        // 獲取當(dāng)前集合中所有數(shù)據(jù)
        List<User> list1 = mongoTemplate.findAll(User.class);
        // 獲取指定集合中的所有數(shù)據(jù)
        List<User> list2 = mongoTemplate.findAll(User.class, "users");
        list1.forEach(System.out::println);
        list2.forEach(System.out::println);
    }

    // 分頁(yè)查詢文檔,顯示第2頁(yè)贱迟,每頁(yè)顯示3個(gè)姐扮,按照id升序排列
    @Test
    public void testTemplate_6() throws Exception {
        // 方式一
        Query query = new Query();
        query.with(PageRequest.of(1, 3, Sort.by("id")));
        List<User> userList = mongoTemplate.find(query, User.class);
        userList.forEach(System.out::println);
        // 方式二
        Query query1 = new Query();
        query1.limit(3).skip(3).with(Sort.by("id"));
        List<User> userList1 = mongoTemplate.find(query1, User.class);
        userList1.forEach(System.out::println);
    }

    //查詢所有name為tony或者age<30的文檔
    @Test
    public void testTemplate_7() throws Exception {
        Query query = new Query();
        Criteria criteria = new Criteria();
        criteria.orOperator(Criteria.where("name").is("tony"),
                Criteria.where("age").lt(30));
        query.addCriteria(criteria);
        List<User> list = mongoTemplate.find(query, User.class);
        list.forEach(System.out::println);
    }

    // 查詢所有name含有wang并且30<=age<=32的文檔
    @Test
    public void testTemplate_8() throws Exception {

        Criteria criteria = new Criteria();
        criteria.andOperator(
                Criteria.where("name").regex("wang"),
                Criteria.where("age").lte(32).gte(30)
        );
        Query query = new Query();
        query.addCriteria(criteria);
        List<User> list = mongoTemplate.find(query, User.class);
        list.forEach(System.out::println);
    }

    //需求:查詢所有name=tony的文檔信息
    @Test
    public void testTemplate_9() throws Exception {
        Query query = new Query();
        query.addCriteria(Criteria.where("name").is("tony"));
        List<User> list = mongoTemplate.find(query, User.class);
        list.forEach(System.out::println);
    }

    //需求:查詢users集合中的所有數(shù)據(jù),先按照年齡升序排序衣吠,然后再按照id降序排序
    @Test
    public void testTemplate_10() throws Exception {
        Query query = new Query();
        // 方式一
        //query.with(Sort.by(Sort.Order.asc("age"), Sort.Order.desc("id")));
        // 方式二
        query.with(Sort.by("age")).with(Sort.by(Sort.Order.desc("id")));
        List<User> userList = mongoTemplate.find(query, User.class);
        userList.forEach(System.out::println);
    }

    // 需求:查詢users集合中年齡大于26歲茶敏,小于29歲的文檔信息
    @Test
    public void testTemplate_11() throws Exception {
        Query query = new Query();
        query.addCriteria(Criteria.where("age").gt(26).lt(29));
        List<User> list = mongoTemplate.find(query, User.class);
        list.forEach(System.out::println);
    }

    //需求:查詢users集合中name不是tony的文檔信息
    @Test
    public void testTemplate_12() throws Exception {
       Query query = new Query();
       query.addCriteria(Criteria.where("name").ne("tony"));
       List<User> list = mongoTemplate.find(query,User.class);
       list.forEach(System.out::println);
    }

    // 需求:查詢users集合中id為 3,4,6的文檔信息
    @Test
    public void testTemplate_13() throws Exception {
       Query query = new Query();
       query.addCriteria(Criteria.where("id").in(3,4,6));
       List<User> list = mongoTemplate.find(query,User.class);
       list.forEach(System.out::println);
    }

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市缚俏,隨后出現(xiàn)的幾起案子惊搏,更是在濱河造成了極大的恐慌,老刑警劉巖忧换,帶你破解...
    沈念sama閱讀 218,546評(píng)論 6 507
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件胀屿,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡包雀,警方通過(guò)查閱死者的電腦和手機(jī)宿崭,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,224評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門(mén),熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)才写,“玉大人葡兑,你說(shuō)我怎么就攤上這事≡薏荩” “怎么了讹堤?”我有些...
    開(kāi)封第一講書(shū)人閱讀 164,911評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)厨疙。 經(jīng)常有香客問(wèn)我洲守,道長(zhǎng),這世上最難降的妖魔是什么沾凄? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,737評(píng)論 1 294
  • 正文 為了忘掉前任梗醇,我火速辦了婚禮,結(jié)果婚禮上撒蟀,老公的妹妹穿的比我還像新娘叙谨。我一直安慰自己,他們只是感情好保屯,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,753評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布手负。 她就那樣靜靜地躺著涤垫,像睡著了一般。 火紅的嫁衣襯著肌膚如雪竟终。 梳的紋絲不亂的頭發(fā)上蝠猬,一...
    開(kāi)封第一講書(shū)人閱讀 51,598評(píng)論 1 305
  • 那天,我揣著相機(jī)與錄音统捶,去河邊找鬼榆芦。 笑死,一個(gè)胖子當(dāng)著我的面吹牛瘾境,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播镰惦,決...
    沈念sama閱讀 40,338評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼迷守,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了旺入?” 一聲冷哼從身側(cè)響起兑凿,我...
    開(kāi)封第一講書(shū)人閱讀 39,249評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎茵瘾,沒(méi)想到半個(gè)月后礼华,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,696評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡拗秘,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,888評(píng)論 3 336
  • 正文 我和宋清朗相戀三年圣絮,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片雕旨。...
    茶點(diǎn)故事閱讀 40,013評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡扮匠,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出凡涩,到底是詐尸還是另有隱情棒搜,我是刑警寧澤,帶...
    沈念sama閱讀 35,731評(píng)論 5 346
  • 正文 年R本政府宣布活箕,位于F島的核電站力麸,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏育韩。R本人自食惡果不足惜克蚂,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,348評(píng)論 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望筋讨。 院中可真熱鬧陨舱,春花似錦、人聲如沸版仔。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,929評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至益缎,卻和暖如春谜慌,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背莺奔。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,048評(píng)論 1 270
  • 我被黑心中介騙來(lái)泰國(guó)打工欣范, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人令哟。 一個(gè)月前我還...
    沈念sama閱讀 48,203評(píng)論 3 370
  • 正文 我出身青樓恼琼,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親屏富。 傳聞我的和親對(duì)象是個(gè)殘疾皇子晴竞,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,960評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容