mongoose操作mongodb

http://mongoosejs.com/docs/api.html#index-js
mongoose是nodejs環境下操作mongodb的模塊封裝,使用mongoose之后,實際上只需要在mongodb中創建好數據庫與用戶,集合的定義、創建、操作等直接使用mongoose即可。

  • 一、連接
  • 二、重要概念
  • 三、基本操作
    • 1、Schema
    • 2、Model
    • 3、實例化document
    • 4、保存數據
    • 5、文檔查詢
    • 6、文檔更新
    • 7、文檔刪除
    • 8、自定義方法
    • 9、虛擬屬性
    • 10、前置與后置鉤子

一、連接

let mongoose = require('mongoose');//連接mongodb
//非auth模式
//mongoose.connect('mongodb://localhost:27017/mall');
//auth模式
/**
mongodb 為協議
第一個mall: 連接數據庫的用戶名
123456: 用戶的密碼
localhost: mongodb地址
27017: mongodb端口號
第二個mall: 數據庫名字
**/
mongoose.connect('mongodb://mall:123456@localhost:27017/mall');//連接失敗
mongoose.connection.on('connected',() => {console.log('mongodb connected!');
});//連接成功
mongoose.connection.on('error',(err) => {console.log('mongodb connect fail:'+err);
});//連接斷開
mongoose.connection.on('disconnected',() => {console.log('mongodb connect disconnected!');
});// connection的事件列表可查看:http://mongoosejs.com/docs/api.html#connection_Connection
// 或 ./node_modules/mongoose/lib/connection.js#Connection()// 關閉的兩種方式
// mongoose.connection.close(); 等同于 db.close();
// mongoose.disconnect();

二、重要概念

moog
  Mongooose中,有三個比較重要的概念,Schema、Model、Document。Schema生成Model,Model實例化成為Document。

  Schema用于定義數據庫的結構。類似創建表時的數據定義(不僅僅可以定義文檔的結構和屬性,還可以定義文檔的實例方法、靜態模型方法、復合索引等),每個Schema會映射到mongodb中的一個collection,Schema不具備操作數據庫的能力。

  Model是由Schema編譯而成的構造器,具有抽象屬性和行為,可以對數據庫進行增刪查改。Model的每一個實例(instance)就是一個文檔document。

  Document是new Model后創建的實例,它的操作會影響數據庫。

三、基本操作

1、Schema

Schema是對mongodb中某個集合的結構描述,它定義一個集合中應該包含哪些數據項,每個數據項的數據類型與檢查約束。可以想象成一個抽象類,只有定義,沒有實現。就是規定好某個集合的框架應該是怎么樣的。也可以理解是mysql中的表結構。
可以為數據項指定的數據類型有8種:

String      字符串
Number      數字    
Date        日期
Buffer      二進制
Boolean     布爾值
Mixed       混合類型
ObjectId    對象ID    
Array       數組

創建Schema

const mongoose = require('mongoose')
//獲取Schema
const Schema = mongoose.Schema;//聲明一個Schema實例,實際就是創建一個集合的結構框架
let animalSchema = new Schema({title: String, //類型可以是首字母大寫age: 'number', //類型也可以寫成字符串全小寫food: [{ //數組name: String}]
});//如果需要為animalSchema增加屬性,可以使用add
animalSchema.add({sex: {type: String,enum: ['male', 'female'] //規定,字段值為枚舉約束,只能填male/female}
});

創建Schema時可以有一系列的約束條件,類似mysql中字段的非空、唯一等約束。
基本語法是:

{name: {type:String, validator:value}}

常用的約束有:

required: 數據必須填寫
default: 默認值
min: 最小值(只適用于數字)
max: 最大值(只適用于數字)
match: 正則匹配(只適用于字符串)
enum:  枚舉匹配(只適用于字符串)
validate: 自定義匹配

其中validate是自定義約束
例如要自定義檢查長度

// 自定義長度檢查
let lengthValidate = (param) => {return param.length <= 10
};//如果需要為animalSchema增加屬性,可以使用add
animalSchema.add({sex: {type: String,enum: ['male', 'female'], //規定,字段值為枚舉約束,只能填male/femalevalidate: lengthValidate}
});

2、Model

model是根據Schema定義的結構框架生成一個映射mongodb的數據模型,可以把它理解是一個類,是根據Schema創建的一個類,他的數據結構是依據Schema生成的,這個類用來生成document實例。

//通過schema構建model,第一個參數是給model起個名字,第二個參數是構造這個model所依據的schema
let animalModel = mongoose.model('animalModel', animalSchema);

3、實例化document

document是相當于是mongodb中的每一條數據了,它是通過new一個model得到的。

  // 通過實例化model得到document,document的數據項需根據schema定義的結構來寫// 通過實例化model得到document,document的數據項需根據schema定義的結構來寫let cat = new animalModel({title: '貓咪',food: [{name: '魚'},{name: '火腿'}],sex: 'male'});

到這一步,mongodb中還沒有animalMode集合以及數據。
這里寫圖片描述

4、保存數據

  • 1、save()
    在mongoose中保存數據,實際就是保存某個document,document通過model實例化來創建。document的save()方法可以將document映射保存到mongodb中,save()方法中可以傳遞一個回調函數作為參數。因為是在document上調用,自然一次只保存一條文檔。
    方法原型:
save(function (err, document) {}) //回調函數中第二個參數是使用保存的數據形成的對象

保存cat:

//保存document,映射成為一條記錄
cat.save((err, catObj) => {if (err) {console.log('保存失敗');console.info(err);}  else {console.info(catObj);}
});

保存后打印:

{ title: '貓咪',food: [ { name: '魚', _id: 5a96555e95f678530054f918 },{ name: '火腿', _id: 5a96555e95f678530054f917 } ],sex: 'male',_id: 5a96555e95f678530054f919,__v: 0 }

保存后這個回調中的第二個參數就被填充好值,其中的主鍵_id也在其中,__v是mongoose用來管理數據版本號的標識,自己不用動。
這時看mongodb中已有集合,集合中已經有一條數據(文檔)了。
這里寫圖片描述
注意:
1、從上圖可以看出來,集合的名字是根據mongoose.model('animalModel', animalSchema)中第一個參數來的,變成小寫且復數形式,如果結尾是數字則不變。比如這個地方如果第一個參數給的是’animal’,則生成的集合名稱就應該是’animals’。
2、在mongoose中操作mongodb,因為有了schema、model、ducument的概念,就不是像mysql一樣,事先創建好表結構,而是根據數據結構設計,在代碼中聲明好schema,再生成model、創建document,進行數據操作。

  • 2、create()
    和save()不一樣的是,create()不是在document上調用的,而是在model上調用的,并且可以一次保存多條文檔。
    接著用上面的animalModel,這次不去new它了,也就是不去操作document了,直接用mongoose.model出來的model。同時保存兩條狗。
    let dog1 = {title: '1號狗狗',food: [{name: '骨頭'},{name: '肉肉'},],sex: 'male'};let dog2 = {title: '2號狗狗',food: [{name: '骨頭'},{name: '肉肉'},],sex: 'male'};animalModel.create(dog1, dog2, (err, rsObj1, rsObj2) => {if (err) {console.log('保存失敗');console.info(err);} else {console.log('保存成功');console.info(rsObj1);console.info(rsObj2);}});

打印的結果:

保存成功
{ title: '1號狗狗',food: [ { name: '骨頭', _id: 5a96607b5ce650532494f010 },{ name: '肉肉', _id: 5a96607b5ce650532494f00f } ],sex: 'male',_id: 5a96607b5ce650532494f011,__v: 0 }
{ title: '2號狗狗',food: [ { name: '骨頭', _id: 5a96607b5ce650532494f013 },{ name: '肉肉', _id: 5a96607b5ce650532494f012 } ],sex: 'male',_id: 5a96607b5ce650532494f014,__v: 0 }

再看看mongodb中:
這里寫圖片描述
注意:這里也驗證了一個問題,就是如果model對應的集合已經存在于mongodb中了,則會直接往這個集合中添加文檔,如果還沒有,則會創建集合。所以在上面保存貓咪的時候,同時創建了集合與添加貓咪文檔,而這里的狗狗,直接添加文檔。

  • 3、insertMany()
    insertMany()也是model的方法,一次插入多條數據,注意回調中的返回值是所有結果對象的數組。
    let monkey1 = {title: '1號猴猴',food: [{name: '香蕉'},{name: '桃'},],sex: 'male'};let monkey2 = {title: '2號猴猴',food: [{name: '香蕉'},{name: '桃'},],sex: 'male'};animalModel.insertMany([monkey1, monkey2], (err, rsArr) => {if (err) {console.log('保存失敗');console.info(err);} else {console.log('保存成功');console.info(rsArr);}});

打印結果:

保存成功
[ { title: '1號猴猴',food: [ [Object], [Object] ],sex: 'male',_id: 5a967c3f44d6d753b6cd6354,__v: 0 },{ title: '2號猴猴',food: [ [Object], [Object] ],sex: 'male',_id: 5a967c3f44d6d753b6cd6357,__v: 0 } ]

5、文檔查詢

mongodb中的數據查詢就是查文檔。

  • 1、find()
    find()是用在model上的,這一點很容易理解,既然是查詢數據,那么當前肯定是不明確要得到的文檔結果是怎樣的,方法也就不會在document上。
    find()方法在官方文檔中的描述是:
Model.find()Parameters [callback] ?Function?
Returns:?Query?Finds documents
The conditions are cast to their respective SchemaTypes before the command is sent.Example:
// named john and at least 18
MyModel.find({ name: 'john', age: { $gte: 18 }});// executes immediately, passing results to callback
MyModel.find({ name: 'john', age: { $gte: 18 }}, function (err, docs) {});// name LIKE john and only selecting the "name" and "friends" fields, executing immediately
MyModel.find({ name: /john/i }, 'name friends', function (err, docs) { })// passing options
MyModel.find({ name: /john/i }, null, { skip: 10 })// passing options and executing immediately
MyModel.find({ name: /john/i }, null, { skip: 10 }, function (err, docs) {});// executing a query explicitly
var query = MyModel.find({ name: /john/i }, null, { skip: 10 })
query.exec(function (err, docs) {});// using the promise returned from executing a query
var query = MyModel.find({ name: /john/i }, null, { skip: 10 });
var promise = query.exec();
promise.addBack(function (err, docs) {});

官方示例find的用法非常清晰了,find方法最簡的參數是只給一個回調函數,表示查詢所有結果,相當于是sql中的select * from 表名。
find()方法返回值是query對象,query對象有exec和一系列方法,exec()可以執行準備好的find()查詢,回調得到結果。

回到animal示例中:
查詢animalmodels集合中所有的文檔:

//方式一:
animalModel.find((err, rs) => {if (err) {console.log('查詢失敗');console.info(err);} else {console.log('查詢成功');console.info(rs);}});//方式二:let animalQuery = animalModel.find();animalQuery.exec((err, rs) => {if (err) {console.log('查詢失敗');console.info(err);} else {console.log('查詢成功');console.info(rs);}});//兩種方式的結果是一樣的,返回的rs是一個包含集合中所有文檔的數組

find()的完整參數列表是:
Model.find([查詢條件], [返回字段列表], [設置選項], [回調函數]);
對于第一個參數,比如age: { $gte: 18 },表示要查詢年齡大于等于18的文檔。常用的條件操作符有:

$lt$lte$gt$gte$in$nin$eq$ne$or(model.find({$or:[{ color: 'red' }, { status: 'emergency' }]}))、$and$not$nor$exits(值是否存在,model.find({name:{$exits:true}}))、$all(通常用來匹配數組里面的鍵值,匹配多個值(同時具有) $all:[“apple”,“banana”,“peach”]})、$size(用來查詢數組的長度值 model.find({name:{$size:3}}); 匹配name的數組長度為3

有一個特殊的操作符$where,可以靈活的設置查詢條件,$where后可以直接寫任何的js作為查詢條件,但實際上完全可以使用model.where()方法來代替,where()會更加方便。

{$where:"this.x == this.y"}
{$where:function(){return obj.x !== obj.y;
}}

這些操作符在find的第一個參數中使用,query中也有一一對一個的方法。

對于第二個參數,可以設置要返回的字段列表,{name:1,_id:0}表示返回name字段,不返回_id字段。

對于第三個參數,官方示例中用到了一個skip,還有limit、sort。

除了find()外,還有findById()、findOne(),與find的用法都是一樣的。只不過findById的第一個參數是準確的id值。這兩個方法都只返回一條文檔。

  • 2、where()
    官網上這么介紹的
Model.where()
Parameters [val] ?Object? optional valueReturns:?Query? 
Creates a Query, applies the passed conditions, and returns the Query.

官方示例:

User.find({age: {$gte: 21, $lte: 65}}, callback);
等同于
User.where('age').gte(21).lte(65).exec(callback);

因為where返回的是query對象,所以可以鏈式調用:

User
.where('age').gte(21).lte(65)
.where('name', /^b/i)
... etc

所以在實際的使用過程中,用query對象來進行查詢是比較方便的,用find()的返回值query鏈式調用其他方法,或者用where()的返回值query鏈式調用其他方法,最后用exec(callback)得到結果,這樣比較清晰。query有一系列的方法,異步官方文檔。

  • 3、query常用方法
sort     排序
skip     跳過
limit    限制
select   顯示字段
exect    執行
count    計數
distinct 去重

關于分頁與排序,query的三個方法:
query.limit(20); //只返回前20個內容
query.skip(2); //跳過多少條,實際就是開始的索引
query.sort({name:1,age:-1}); //1升序,2降序

6、文檔更新

  • 1、update()
    Model.update(conditions, doc, [options], [callback])
    第一個參數conditions為查詢條件,第二個參數doc為需要修改的數據,第三個參數options為控制選項,第四個參數是回調函數。
    options有以下選項:
    safe (boolean): 默認為true。安全模式。upsert (boolean): 默認為false。如果不存在則創建新記錄。multi (boolean): 默認為false。是否更新多個查詢記錄。runValidators: 如果值為true,執行Validation驗證。setDefaultsOnInsert: 如果upsert選項為true,在新建時插入文檔定義的默認值。strict (boolean): 以strict模式進行更新。overwrite (boolean): 默認為false。禁用update-only模式,允許覆蓋記錄。

把名字叫貓咪的文檔的名字更新成貓貓:

    animalModel.update({title :{$eq: '貓咪'}}, {title: '貓貓'}, (err, rs) => {if (err) {console.log('更新失敗');console.info(err);} else {console.log('更新成功');console.info(rs);}});

如果不設置multi的話,即使有多條符合條件的文檔,也只更新一條。
如果設置options里的upsert參數為true,若沒有符合查詢條件的文檔,mongo將會綜合第一第二個參數向集合插入一個新的文檔。

  • 2、updateMany()
    updateMany()與update()的區別是更新多個文檔,即使設置{multi:false}也更新多個。

  • 3、updateOne()
    updateOne()只更新找到的第一條數據,即使設置{multi:true}只更新一個。

  • 4、數組更新
    update第二個參數,實際可以寫成{$set: {title: '貓貓'}}$set操作符表示設值,如果要更新的是數組,可以有以下操作符:

$addToSet  // 當且僅當待添加到數組的元素是當前數組所沒有時,才會去添加
$pop       // 當指定數組的修飾符值為-1時,刪除該數組的第1個元素;當值為1時,刪除最后一個元素
$pull      // 刪除指定查詢條件下的數組元素
$pullAll   // 刪除數組中符合給定的集合的值的所有元素,與$pull的區別于目標刪除元素是被逐一列舉出來的
$push      // 將元素添加到指定的數組中

給貓添加一個食物:

    animalModel.update({title :{$eq: '喵星人'}},{$addToSet:{food: {name: '蛋黃派'}}},(err,rs) =>{if (err) {console.info("保存失敗");console.info(err);} else {console.info("保存成功");console.info(rs);}});

結果:

保存成功
{ n: 1, nModified: 1, ok: 1 }
  • 5、其他
    關于其他更新方法還有findOneAndUpdate()、findByIdAndUpdate()。
    通過查詢+保存操作也可以實現更新,查詢的結果實際是一個document對象,調用save方法,猜想是通過_id與_v來進行的比對,將直接更新本條記錄。
animalModel.where('title').eq('貓貓').exec((err, rs) => {if (err) {console.info(err);} else {console.info(rs);rs.forEach(function(item,index,array){item.title = "喵星人";item.save((err,rs) =>{if (err) {console.info("保存失敗");console.info(err);} else {console.info("保存成功");console.info(rs);}});});}});

7、文檔刪除

  • 1、remove()
    remove方法存在兩個位置,一個是model上,一個是ducument上,model上就是根據條件去刪除集合內某些文檔,文檔上就是刪除自己。
model.remove(conditions, [callback])
document.remove([callback])

示例:

 //model刪除animalModel.remove({title :{$eq: '喵星人'}},(err,rs) =>{if (err) {console.info("刪除失敗");console.info(err);} else {console.info("刪除成功");console.info(rs);}});//document刪除animalModel.where('title').eq('2號猴猴').exec((err, rs) => {if (err) {console.info(err);} else {console.info(rs);rs.forEach(function(item,index,array){item.remove((err,rs) =>{if (err) {console.info("刪除失敗");console.info(err);} else {console.info("刪除成功");console.info(rs);}});});}});
  • 2、findOneAndRemove()
    model的remove()會刪除符合條件的所有數據,如果只刪除符合條件的第一條數據,可以使用model的findOneAndRemove()方法
Model.findOneAndRemove(conditions, [options], [callback])
  • 3、findByIdAndRemove()
    通過id刪除文檔
Model.findByIdAndRemove(id, [options], [callback])
  • 4、其他
    所有刪除方法的回調函數都不能省略,否則不成功。要么寫在方法的回調函數參數中,如果不寫回調函數參數,則可以在最后調用.exec()。

8、自定義方法

mongoose中可以利用已有的api,自定義自己的方法來處理特定的業務需要。

  • 1、實例方法
    通過new model得到的document實例有很多增刪改查的方法,如上面的save()方法用來保存文檔,我們可以給實例增加自定義方法來實現特定的業務邏輯,增加之后就可以像調用save一樣來調用自己的方法,給document增加自定義方法是通過擴展Schema的methods屬性來完成的。

為animalSchema擴展document實例方法:

//為document實例添加eat方法,返回所有喜歡吃的食物
animalSchema.methods.eat = function () {let foodList = this.food;let foodStr = '';foodList.forEach(function (item, index, arr) {if (index == 0) {foodStr += item.name;} else {foodStr += ","+item.name;}});return foodStr;
};

document實例調用:

    animalModel.findById('5a96607b5ce650532494f011').exec((err, rs) => {if (err) {console.info("查詢失敗");console.info(err);} else {console.info("查詢成功");console.info(rs);let eatStr =  rs.eat();console.info(eatStr); //骨頭,肉肉}});
  • 2、靜態方法
    靜態方法,是不需要實例化得到document,而是直接在model上調用的方法。
    所以,實例方法,是操作文檔(mongodb中的某一條記錄)數據用的,靜態方法是操作集合用的。

為animalSchema添加靜態方法:

//為model添加findDogs方法
animalSchema.statics.findDogs = function (backfun){this.find({title: /狗/}).exec(backfun);
};

model調用:

    animalModel.findDogs((err, rs) => {if (err) {console.info("查詢失敗");console.info(err);} else {console.info("查詢成功");console.info(rs); //打印出兩條狗的document}});

-3、查詢方法
擴展schema對象的query屬性,給model添加查詢方法,主要為了擴展query的個性化方法需要。

//為query添加findMonkey方法
animalSchema.query.findMonkey = function (backfun){this.find({title: /猴/}).exec(backfun);
};

query調用:

    let rsQuery = animalModel.find();rsQuery.findMonkey((err, rs) => {if (err) {console.info("查詢失敗");console.info(err);} else {console.info("查詢成功");console.info(rs); //打印出一只猴子的document}});

9、虛擬屬性

schema上除了可以設置方法以外,還可以設置虛擬屬性,就像vue的getter一樣,實際數據庫中沒有這個屬性,但可以通過虛擬屬性機制自定義一個經過處理的值,雖然用方法同樣能實現,但虛擬屬性效率更高。

//添加虛擬屬性nameAndSex
animalSchema.virtual('info').get(function () {return this.title + "," +this.sex;
});

調用:

    animalModel.find({title: /狗/}).exec((err, rs) => {if (err) {console.info("查詢失敗");console.info(err);} else {console.info("查詢成功");rs.forEach( function (item, index, arr) {console.info(item.info);});}});

打印結果:

1號狗狗,male
2號狗狗,male

10、前置與后置鉤子

通過schema可以為指定的某些方法添加前置鉤子函數與后置鉤子函數。前置鉤子函數在指定方法開始前調用,后置鉤子函數不是在指定方法結束后操作,二是在指定方法開始前的最后一步操作。
前置鉤子是pre()
后置鉤子是post()

//為find方法指定前置操作1
animalSchema.pre('find', function (next) {console.info('前置操作1');next();
});//為find方法指定前置操作2
animalSchema.pre('find', function (next) {console.info('前置操作2');next();
});//為find方法指定后置操作1
animalSchema.post('find', function () {console.info('后置操作1');
});//為find方法指定后置操作2
animalSchema.post('find', function () {console.info('后置操作2');
});

調用find()方法

    animalModel.find({title: /狗/}).exec((err, rs) => {if (err) {console.info("查詢失敗");console.info(err);} else {console.info("查詢成功");console.info(rs);}});

得到打印結果:

前置操作1
前置操作2
后置操作1
后置操作2
查詢成功
[ { food: [ [Object], [Object] ],_id: 5a96607b5ce650532494f011,title: '1號狗狗',sex: 'male',__v: 0 },{ food: [ [Object], [Object] ],_id: 5a96607b5ce650532494f014,title: '2號狗狗',sex: 'male',__v: 0 } ]

注意,前置鉤子中有一個next函數,如果方法內不調用next(),被設置前置鉤子的方法(比如find())執行到鉤子時不會繼續向下執行。

可以添加前后鉤子的方法有:

init
validate
save
remove
count
find
findOne
findOneAndRemove
findOneAndUpdate
insertMany
update

以上是mongoose的常用基本操作,還有索引、聚合等等操作需要積累補充。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/247594.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/247594.shtml
英文地址,請注明出處:http://en.pswp.cn/news/247594.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

虛擬機上使用ghost xp

虛擬機ghost 1 先用啟動項里的pq對虛擬機的硬盤格式化&#xff0c;然后最重要的一點就是 --右擊--進階-設定為作用然后執行2 重啟一鍵安裝到C盤就行了轉載于:https://www.cnblogs.com/master-zhu/archive/2009/09/15/1567081.html

iOS11新增版本判斷API

iOS11新增版本判斷API iOS11版本現在有了簡單的API&#xff0c;OC也開始支持swfit的available語法&#xff0c;不用再手寫iOS版本判斷了。 if (available(iOS 11.0, *)) {// 版本適配 } // 或者 #ifdef __IPHONE_11_0 #endif 目前沒發現有iPhoneX的機型判斷API&#xff0…

調試asp

response.Write(sqltext) response.End() response.Write(sqltext) response.End()轉載于:https://www.cnblogs.com/master-zhu/archive/2009/09/21/1570816.html

vue滾動加載插件vue-infinite-scroll

vue-infinite-scroll插件可以無限滾動實現加載更多&#xff0c;其作用是是當滾動條滾動到距離底部的指定高度時觸發某個方法。 https://github.com/ElemeFE/vue-infinite-scroll/ https://www.npmjs.com/package/vue-infinite-scroll 安裝 cnpm i vue-infinite-scroll -S v…

實例適配ios11

不多bb&#xff0c;上碼 #import "ViewController.h" #import "PersonViewModel.h" #import "Person.h" #import "ShowTableViewCell.h" #import <Masonry/Masonry.h> #import <MJRefresh/MJRefresh.h>interface ViewCon…

mac下iterm配色、半透明與樣式設置

主要為了實現命令行顏色高亮與整個命令窗口半透明效果。 1、配色主題包下載 1、http://iterm2colorschemes.com/ 下載后解壓&#xff0c;到iterm2中&#xff0c;左上角iTerm2->preferences->Profiles&#xff0c;右側面板找到Colors選項&#xff0c;右下角展開Color Pr…

一個 Dubbo 服務啟動要兩個小時

前幾天在測試環境碰到一個非常奇怪的與 dubbo 相關的問題&#xff0c;事后我在網上搜索了一圈并沒有發現類似的帖子或文章&#xff0c;于是便有了這篇。 希望對還未碰到或正在碰到的朋友有所幫助。 現象 現象是這樣的&#xff0c;有一天測試在測試環境重新部署一個 dubbo 應用的…

表單提交enctype參數詳解之:application/x-www-form-urlencode和multipart/form-data

application/x-www-form-urlencode 我們在提交表單的時候&#xff0c;form表單參數中會有一個enctype的參數。enctype指定了HTTP請求的Content-Type。 默認情況下&#xff0c;HTML的form表單的enctypeapplication/x-www-form-urlencoded。 application/x-www-form-urlencoded是…

內網端口映射工具

由于開發微信需要一個公網域名&#xff0c;需要將本地端口映射到外網域名&#xff0c;最熱的工具是ngrok&#xff0c;但被微信屏蔽了&#xff0c;這里使用的是natapp&#xff0c;環境是mac&#xff0c;windows下可使用nat123、花生殼等工具實現同樣功能。 簡單記錄一下過程。 …

iOS----------iPhone導出手機所有短信

第一步&#xff1a;手機連接到itunes 選擇本電腦備份 備份的時候不要加密 然后立即備份 第二步&#xff1a;前往文件夾&#xff0c;找到itunes的備份路徑~/Library/Application Support/MobileSync/Backup 在這目錄下搜索 3d0d開頭的文件&#xff0c;這就是 iPhone 短信的…

跨站點腳本(XSS)

1. 簡介 跨站點腳本(XSS)是當前web應用中最危險和最普遍的漏洞之一。安全研究人員在大部分最受歡迎的網站,包括Google, Facebook, Amazon, PayPal等網站都發現這個漏洞。如果你密切關注bug賞金計劃,會發現報道最多的問題屬于XSS。為了避免跨站腳本,瀏覽器也有自己的過濾器,但安…

spring webscoket服務端使用記錄

記錄spring4中websocket的使用方式 pom jar包配置 <dependency> <groupId>org.springframework</groupId> <artifactId>spring-websocket</artifactId> <version>${spring.version}</version> </dependency> <depen…

MVC是什么?(轉載)

MVC (Modal View Controler)本來是存在于Desktop程序中的&#xff0c;M是指數據模型&#xff0c;V是指用戶界面&#xff0c;C則是控制器。使用MVC的目的是將M和V的實現代碼分離&#xff0c;從而使同一個程序可以使用不同的表現形式。比如一批統計數據你可以分別用柱狀圖、餅圖來…

CSRF攻擊原理及防御

CSRF攻擊原理及防御 一、CSRF攻擊原理 CSRF是什么呢&#xff1f;CSRF全名是Cross-site request forgery&#xff0c;是一種對網站的惡意利用&#xff0c;CSRF比XSS更具危險性。想要深入理解CSRF的攻擊特性我們有必要了解一下網站session的工作原理。   session我想大家都不…

H3C FTP配置示例

轉載于:https://www.cnblogs.com/fanweisheng/p/11156596.html

用dotnet自帶的mail類發郵件出現的問題

在使用dotnet自帶的mail類發送郵件的時候&#xff0c;因為默認的smtp端口是25&#xff0c;如果更改了smtp的端口號&#xff0c;則需加上MailMessage msg &#xff1d; new MailMessage();msg.Fields.Add("http://schemas.microsoft.com/cdo/configuration/smtpserverport&…

Angular CLI ng 指令指南

Angular CLI 使用教程指南參考 Angular CLI 現在雖然可以正常使用但仍然處于測試階段. Angular CLI 依賴 Node 4 和 NPM 3 或更高版本. 安裝

spring源碼閱讀(1/4) - Bean生成

上午去繳了上次沒帶駕駛證的扣分罰款&#xff0c;最近在圖書館沒事就看曾國藩家書&#xff0c;曾國藩說人要明強。光強沒有用&#xff0c;你要明強。也就是說要強的有道理。曾國藩又說&#xff0c;做學問不能做死學問&#xff0c;做學問其實很重要的事就是能懂得孝悌&#xff0…

NodeJS解決跨域問題:Access-Control-Allow-Origin

今天在玩vue-resource時&#xff0c;后臺使用nodejs來提供數據&#xff0c;由于需要跨域&#xff0c;在網上也找到了解決方法。 vue-resource代碼(其實就是ajax技術)&#xff1a; this.$http.get({url:"http://localhost:3000/getdata"}) .then(function (data) {co…

windows10系統下MongoDB的安裝及環境配置

windows10系統下MongoDB的安裝及環境配置&#xff1a; MongoDB的安裝 下載地址&#xff1a; https://www.mongodb.com/download-center (這是windows10環境下的教程&#xff01;請注意&#xff01;) 下載后&#xff0c;我們點擊mongodb-win32-x86_64-2008plus-ssl-3.4.3-signed…