欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Node.js數(shù)據(jù)庫鉤子的使用

 更新時間:2023年05月26日 15:54:40   作者:Brett Hoyer  
本文主要介紹了Node.js數(shù)據(jù)庫鉤子的使用,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

在本文中,我將解釋如何在您的Node.js應(yīng)用程序中使用數(shù)據(jù)庫鉤子來解決在開發(fā)過程中可能出現(xiàn)的特定問題。

許多應(yīng)用程序只需要在服務(wù)器、數(shù)據(jù)庫之間建立連接池并執(zhí)行查詢。然而,根據(jù)您的應(yīng)用程序和數(shù)據(jù)庫部署情況,可能需要進(jìn)行其他配置。

例如,多區(qū)域分布式SQL數(shù)據(jù)庫可以根據(jù)應(yīng)用程序用例的不同拓?fù)溥M(jìn)行部署。某些拓?fù)湫枰诿總€會話中在數(shù)據(jù)庫上設(shè)置屬性。

讓我們探索一下Node.js生態(tài)系統(tǒng)中一些最受歡迎的數(shù)據(jù)庫客戶端和ORM提供的一些鉤子。

基礎(chǔ)

在使用最流行的關(guān)系數(shù)據(jù)庫時,Node.js社區(qū)有許多可供選擇的驅(qū)動程序。在這里,我將重點關(guān)注與兼容PostgreSQL的數(shù)據(jù)庫客戶端,它們可以用于連接到Y(jié)ugabyteDB或其他PostgreSQL數(shù)據(jù)庫。
Sequelize、Prisma、Knex和node-postgres是一些功能各異的受歡迎的客戶端,具體取決于您的需求。我鼓勵您閱讀它們的文檔,以確定哪個最適合您的需求。
這些客戶端提供了不同用例的鉤子。例如:

  • 連接鉤子: 在連接和斷開與數(shù)據(jù)庫的連接之前或之后立即執(zhí)行函數(shù)。 
  • 日志鉤子: 在不同的日志級別下將消息記錄到stdout。 
  • 生命周期鉤子: 在對數(shù)據(jù)庫進(jìn)行調(diào)用之前或之后立即執(zhí)行函數(shù)。 

在本文中,我將介紹這些客戶端提供的一些鉤子,并說明您如何在分布式SQL應(yīng)用程序中使用它們的好處。

我還將演示如何在創(chuàng)建用戶之前使用鉤子對用戶的密碼進(jìn)行散列,并在連接到具有讀副本的多區(qū)域數(shù)據(jù)庫后如何設(shè)置運(yùn)行時配置參數(shù)。

Sequelize

Sequelize ORM提供了許多鉤子來管理數(shù)據(jù)庫事務(wù)的整個生命周期。

beforeCreate生命周期鉤子可用于在創(chuàng)建新用戶之前對密碼進(jìn)行散列處理:

User.beforeCreate(async (user, options) => {
 const hashedPassword = await hashPassword(user.password);
 user.password = hashedPassword;
});

接下來,我使用afterConnect連接鉤子來設(shè)置會話參數(shù)。

通過這個YugabyteDB部署,您可以從跟隨者執(zhí)行讀取操作以減少延遲,并且無需從主集群節(jié)點讀取:

const config = {
? host: process.env.DB_HOST,
? port: 5433,
? dialect: "postgres",
? dialectOptions: {
? ? ssl: {
? ? ? require: true,
? ? ? rejectUnauthorized: true,
? ? ? ca: [CERTIFICATE],
? ? },
? },
? pool: {
? ? max: 5,
? ? min: 1,
? ? acquire: 30000,
? ? idle: 10000,
? },
? hooks: {
? ? ?async afterConnect(connection) {
? ? ? ?if (process.env.DB_DEPLOYMENT_TYPE === "multi_region_with_read_replicas") {
? ? ? ? ?await connection.query("set yb_read_from_followers = true; set session characteristics as transaction read only;");
? ? ? ?}
? ? ?},
? ?},
};
const connection = new Sequelize(
? ?process.env.DATABASE_NAME,
? ?process.env.DATABASE_USER,
? ?process.env.DATABASE_PASSWORD,
? ?config
);

通過使用這個鉤子,在連接池中的每個數(shù)據(jù)庫會話在建立新連接時都會設(shè)置這些參數(shù):

  • set yb_read_from_followers = true;:此參數(shù)控制是否啟用從跟隨者讀取。
  • set session characteristics as transaction read only;:此參數(shù)將只讀設(shè)置應(yīng)用于后續(xù)的所有語句和事務(wù)塊。 

Prisma

盡管在Node.js社區(qū)中,Prisma是許多人首選的ORM,但在撰寫本文時,Prisma并不包含Sequelize中的許多內(nèi)置鉤子。目前,該庫包含用于處理查詢生命周期、日志記錄和斷開連接的鉤子,但在建立連接之前或之后提供的幫助很少。

以下是如何使用Prisma的生命周期中間件在創(chuàng)建用戶之前對密碼進(jìn)行哈希處理的方法:

prisma.$use(async (params, next) => {
?if (params.model == 'User' && params.action == 'create') {
? ?params.args.data.password = await hashPassword(params.args.data.password);
?}
?return next(params)
})
const create = await prisma.user.create({
?data: {
? ?username: 'bhoyer',
? ?password: 'abc123'
?},
})

要設(shè)置會話參數(shù)以利用我們的讀取副本,我們需要在查詢數(shù)據(jù)庫之前執(zhí)行一條語句:

await prisma.$executeRaw(`set yb_read_from_followers = true; set session characteristics as transaction read only;`);
const users = await prisma.user.findMany();

如果您需要立即在連接池中建立連接以設(shè)置參數(shù),您可以使用Prisma顯式地進(jìn)行連接,而不使用連接池的延遲連接。

Prisma具有查詢(query)、錯誤(error)、信息(info)和警告(warn)等日志級別??梢允褂没谑录娜罩居涗泚硖幚聿樵兪录?/p>

const prisma = new PrismaClient({
?log: [
? ?{
? ? ?emit: 'event',
? ? ?level: 'query',
? ?},
? ?{
? ? ?emit: 'stdout',
? ? ?level: 'error',
? ?},
? ?{
? ? ?emit: 'stdout',
? ? ?level: 'info',
? ?},
? ?{
? ? ?emit: 'stdout',
? ? ?level: 'warn',
? ?},
?],
});

prisma.$on('query', (e) => {
?console.log('Query: ' + e.query);
?console.log('Params: ' + e.params);
?console.log('Duration: ' + e.duration + 'ms');
});

這在開發(fā)過程中對于在分布式系統(tǒng)中進(jìn)行查詢調(diào)優(yōu)非常有幫助。
下面是如何在退出之前使用beforeExit鉤子來訪問數(shù)據(jù)庫的示例:???????

const prisma = new PrismaClient();
prisma.$on('beforeExit', async () => {
?// PrismaClient still available
?await prisma.issue.create({
? ?data: {
? ? ?message: 'Connection exiting.'?
? ?},
?})
});

Knex是一個輕量級的查詢構(gòu)建器,但它沒有更全功能的ORM中的查詢中間件。
要對密碼進(jìn)行哈希處理,可以使用自定義函數(shù)來手動處理:

async function handlePassword(password) {
  const hashedPassword = await hashPassword(password);
  return hashedPassword;
}
const password = await handlePassword(params.password);
knex('users').insert({...params, password});

在Knex.js查詢構(gòu)建器中實現(xiàn)連接鉤子所需的語法與Sequelize類似。以下是如何設(shè)置會話參數(shù)以從YugabyteDB的副本節(jié)點讀取的示例代碼:

const knex = require('knex')({
  client: 'pg',
  connection: {/*...*/},
  pool: {
    afterCreate: function (connection, done) {
      connection.query('set yb_read_from_followers = true; set session characteristics as transaction read only;', function (err) {
        if (err) {
          //Query failed
          done(err, conn);
        } else {
          console.log("Reading from replicas.");
       done();
        }
      });
    }
  }
});

node-postgres庫是所有討論過的庫中最低級的庫。在底層,使用Node.js的EventEmitter來觸發(fā)連接事件。

當(dāng)在連接池中建立新連接時,會觸發(fā)connect事件。我們可以使用它來設(shè)置我們的會話參數(shù)。我還添加了一個錯誤鉤子來捕獲和記錄所有錯誤消息的示例代碼:???????

const config = {
? user: process.env.DB_USER,
? host: process.env.DB_HOST,
? password: process.env.DB_PASSWORD,
? port: 5433,
? database: process.env.DB_NAME,
? min: 1,
? max: 10,
? idleTimeoutMillis: 5000,
? connectionTimeoutMillis: 5000,
? ssl: {
? ? rejectUnauthorized: true,
? ? ca: [CERTIFICATE],
? ? servername: process.env.DB_HOST,
? }
};
const pool = new Pool(config);
pool.on("connect", (c) => {
? c.query("set yb_read_from_followers = true; set session characteristics as transaction read only;");
});
pool.on("error", (e) => {
? console.log("Connection error: ", e);
});

在node-postgres中,我們沒有可用的生命周期鉤子,所以像Prisma一樣,我們必須手動進(jìn)行密碼哈希處理:

async function handlePassword(password) {
  const hashedPassword = await hashPassword(password);
  return hashedPassword;
}
const password = await handlePassword(params.password);
const user = await pool.query('INSERT INTO user(username, password) VALUES ($1, $2) RETURNING *', [params.username, password]);

總結(jié)

正如你所看到的,鉤子可以解決之前由復(fù)雜且容易出錯的應(yīng)用程序代碼所引起的許多問題。每個應(yīng)用程序都有不同的要求和面臨新的挑戰(zhàn)。在你的開發(fā)過程中,可能會經(jīng)過很多年才需要使用特定的鉤子,但現(xiàn)在,當(dāng)那一天來臨時,請準(zhǔn)備就緒。

到此這篇關(guān)于Node.js數(shù)據(jù)庫鉤子的使用的文章就介紹到這了,更多相關(guān)Node.js數(shù)據(jù)庫鉤子內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Node.js實現(xiàn)大文件斷點續(xù)傳示例詳解

    Node.js實現(xiàn)大文件斷點續(xù)傳示例詳解

    這篇文章主要為大家介紹了Node.js實現(xiàn)大文件斷點續(xù)傳示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-11-11
  • Node.js中對通用模塊的封裝方法

    Node.js中對通用模塊的封裝方法

    這篇文章主要介紹了Node.js中對通用模塊的封裝方法,封裝方法參考了Underscore.js的實現(xiàn),需要的朋友可以參考下
    2014-06-06
  • npm查看鏡像源與切換鏡像源方法詳解

    npm查看鏡像源與切換鏡像源方法詳解

    這篇文章主要為大家介紹了npm查看鏡像源與切換鏡像源方法詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-06-06
  • 利用nodejs讀取圖片并將二進(jìn)制數(shù)據(jù)轉(zhuǎn)換成base64格式

    利用nodejs讀取圖片并將二進(jìn)制數(shù)據(jù)轉(zhuǎn)換成base64格式

    這篇文章主要介紹了利用nodejs讀取圖片并將二進(jìn)制數(shù)據(jù)轉(zhuǎn)換成base64格式,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-08-08
  • node.js從數(shù)據(jù)庫獲取數(shù)據(jù)

    node.js從數(shù)據(jù)庫獲取數(shù)據(jù)

    這篇文章主要為大家詳細(xì)介紹了node.js從數(shù)據(jù)庫獲取數(shù)據(jù)的具體代碼,nodejs可以獲取具體某張數(shù)據(jù)表信息,感興趣的朋友可以參考一下
    2016-05-05
  • Express.JS使用詳解

    Express.JS使用詳解

    Express 是一個簡潔而靈活的 node.js Web應(yīng)用框架, 提供一系列強(qiáng)大特性幫助你創(chuàng)建各種Web應(yīng)用。下面我們將逐步分析下,各位不要輕易離開
    2014-07-07
  • Windows安裝Node.js報錯:2503、2502的解決方法

    Windows安裝Node.js報錯:2503、2502的解決方法

    這篇文章主要給大家介紹了關(guān)于在Windows系統(tǒng)下安裝Node.js報錯:2503、2502的解決方法,文中將解決的方法一步步介紹的非常詳細(xì),需要的朋友可以參考借鑒,下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧。
    2017-10-10
  • Node.js編程中客戶端Session的使用詳解

    Node.js編程中客戶端Session的使用詳解

    這篇文章主要介紹了Node.js編程中客戶端Session的使用詳解,是Node.js入門學(xué)習(xí)中的基礎(chǔ)知識,需要的朋友可以參考下
    2015-06-06
  • 詳解node.js的http模塊實例演示

    詳解node.js的http模塊實例演示

    這篇文章主要介紹了詳解node.js的http模塊實例演示,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2018-07-07
  • 在Node.js應(yīng)用中使用Redis的方法簡介

    在Node.js應(yīng)用中使用Redis的方法簡介

    這篇文章主要介紹了在Node.js應(yīng)用中使用Redis的方法,最簡單的數(shù)據(jù)讀寫操作相關(guān),需要的朋友可以參考下
    2015-06-06

最新評論