code

후속작:여러 데이터베이스 사용

starcafe 2023. 10. 5. 23:24
반응형

후속작:여러 데이터베이스 사용

두 개의 데이터베이스를 사용하려면 Sequelize 인스턴스를 여러 개 만들어야 합니까?즉, 두 개의 데이터베이스가 같은 컴퓨터에 있는 것입니다.

만약 그렇지 않다면, 이것을 하는 적절한 방법은 무엇이 적절한 방법입니까?두 개의 데이터베이스를 사용하기 위해 두 번 연결해야 하는 것은 과한 일로 보입니다.

예를 들어, 저는 다른 기능에 대해 서로 다른 데이터베이스를 가지고 있습니다. 예를 들어, 한 데이터베이스에 고객 데이터가 있고 다른 데이터베이스에 통계 데이터가 있다고 가정해 보겠습니다.

MySQL에서:

MySQL [customers]> show databases;
+--------------------+
| Database           |
+--------------------+
| customers          |
| stats              |
+--------------------+

그리고 나는 이것을 속편과 연결할 것이 있습니다.

// Create a connection....
var Sequelize = require('sequelize');
var sequelize = new Sequelize('customers', 'my_user', 'some_password', {
    host: 'localhost',
    dialect: 'mysql',

    pool: {
        max: 5,
        min: 0,
        idle: 10000
    },
    logging: function(output) {
        if (opts.log_queries) {
            log.it("sequelize_log",{log: output});
        }
    }

});

// Authenticate it.
sequelize.authenticate().nodeify(function(err) {

    // Do stuff....

});

점 표기법을 사용하여 모델의 정의에 따라 "꼼수"를 부려 보았습니다.

var InterestingStatistics = sequelize.define('stats.interesting_statistics', { /* ... */ });

하지만 그것이 테이블을 만들어 냅니다.customers.stats.interesting_statistics. 통계 데이터베이스의 기존 테이블을 사용해야 합니다.

이를 달성하기 위한 적절한 방법은 무엇입니까?감사해요.

생성할 DB 연결마다 다른 sequelize 인스턴스를 생성해야 합니다.

const { Sequelize } = require('sequelize');
const userDb = new Sequelize(/* ... */);
const contentDb = new Sequelize(/* ... */);

sequelize에서 생성된 각 인스턴스에는 고유한 DB 정보(db host, url, user, pass 등)가 있으며, 이러한 값은 변경할 수 없으므로 sequelize의 하나의 인스턴스와 여러 연결을 만드는 "올바른" 방법은 없습니다.

문서에서:

위의 예에서 Sequelize는 라이브러리 자체를 참조하는 반면 Sequelize는 하나의 데이터베이스에 대한 연결을 나타내는 Sequelize의 인스턴스를 참조합니다.이 규칙은 권장되는 규칙이며 설명서 전체에 걸쳐 수행됩니다.

이를 위한 "일반적인" 접근 방식은 데이터베이스를 A/S에 저장하는 것입니다.config.json파일을 저장하고 루프를 통해 동적으로 연결을 생성합니다. 다음과 같은 것이 있습니다.

config.json

{
    /*...*/
    databases: {
        user: {
            path: 'xxxxxxxx'
        },
        content: {
            path: 'xxxxxxxx'
        }
    }
}

당신의

const Sequelize = require('sequelize');
const config = require('./config.json');

// Loop through
const db = {};
const databases = Object.keys(config.databases);
for(let i = 0; i < databases.length; ++i) {
    let database = databases[i];
    let dbPath = config.databases[database];
    db[database] = new Sequelize( dbPath );
}

// Sequelize instances:
// db.user
// db.content

코딩을 조금 더 해야 작동이 되지만 일반적인 생각입니다.

여러 데이터베이스에 걸쳐 동일한 RDS의 개체를 연결하려는 경우schema.

http://docs.sequelizejs.com/class/lib/model.js ~Model.html#static-method-schema

이렇게 하면 db 이름이 테이블 이름 앞에 붙어서 쿼리가 다음과 같이 나올 수 있습니다.SELECT A.ColA, B.ColB FROM SchemaA.ATable A INNER JOIN SchemaB.BTable B ON B.BId = A.BId

원시 쿼리를 사용하는 게 어때요?이를 통해 하나의 데이터베이스에 연결하고 다른 데이터베이스를 쿼리할 수 있습니다.아래 샘플 코드 참조.

const sequelize = require('db_config');
function test(req, res){
  const qry = `SELECT * FROM db1.affiliates_order co
LEFT JOIN db2.affiliates m ON m.id = co.campaign_id`;
  sequelize.query(qry, null, {  raw: true}).then(result=>{
    console.log(result);
  })
}

여러 데이터베이스에서 마이그레이션을 실행할 수 있기를 원했기 때문에 선택한 답변을 추가하는 것입니다. 이렇게 하면 설정하기가 다소 번거롭기는 하지만, 설정이 완료되면 마이그레이션을 쉽게 추가할 수 있는 보다 간단한 방법이 있을 수 있습니다.

sequelize-cli npm i sequelize-cli

  1. 각 db에 대해 이름이 지정된 하위 디렉토리를 사용하여 마이그레이션 디렉토리를 작성합니다(예:/server/migrations/accounting,/server/migrations/users)

  2. 만들기.sequelize-mydb각: db일각예:.sequelize-accounting .sequelize-users 및 각 및 등) DB합니다를및합니다.

    const path = require("path");
    
    module.exports = {
       config: path.resolve("config", "config.json"),
       "models-path": path.resolve("models"),
       "migrations-path": path.resolve("migrations", "accounting"),
    };
    
  3. sequelize config.json 안에서 각 db config의 복사본을 최상위 수준 섹션에 추가합니다.개발/생산 부문을 벗어남(예:

       {
         "development": {
             "baseUrl": "https://example.com/api/v2/",
             "databases": {
             "accounting": {
                 "username": "root",
                 "password": "",
                 "database": "accounting_development",
                 "host": "localhost",
                 "dialect": "mysql",
                 "dialectOptions": {
                 "decimalNumbers": true
                 },
             "users": {} etc
             }
         },
    
         // Copy the above config for each db to the top level ---->>
    
         "accounting": {
             "username": "root",
             "password": "",
             "database": "accounting_development",
             "host": "localhost",
             "dialect": "mysql",
             "dialectOptions": {
             "decimalNumbers": true
             }
         },
         "users": {}
     }
    
  4. 합니다에 을 만들거나 합니다.package.json:

     "scripts": {
       "sequelize:accounting:migrate": "sequelize --options-path ./.sequelize-accounting --env accounting db:migrate",
       "sequelize:users:migrate": "sequelize --options-path ./.sequelize-users --env users db:migrate",
     }
    
  5. 이제 마이그레이션을 생성할 때마다 위에 작성된 상대 마이그레이션 디렉토리에 자동 생성된 마이그레이션 파일을 복사합니다. 예를 들어, 계정 DB에 테이블에 대한 마이그레이션을 생성한 다음 해당 파일을 마이그레이션/계정 디렉토리에 복사합니다.

  6. 마이그레이션을 실행하는 마지막 방법:

     npm run sequelize:accounting:migrate
     npm run sequelize:users:migrate
    

가장 까다로운 부분은 상대 경로를 올바르게 설정하는 것입니다. (특히 Docker용으로 빌드하는 경우) 일단 위치를 지정하면 새 마이그레이션을 생성할 때마다 해당 파일을 해당 디렉토리에 복사해야 하는 추가 작업만 수행할 수 있습니다.

이름이 붙은 테이블에서 데이터를 복사해야 했습니다.solar일순간에mysql데이터베이스를 A에 저장합니다.postgres데이터베이스.

는인 것 요.nodejs할 수 는 javascript code데를 합니다. config 파일에서 database config parameter를 추출하면 database connection을 객체로 추상화하기 때문에 읽기가 더 어렵다고 생각합니다.

이 코드는 대상 db에서 가장 최근 값을 조회한 다음 소스 db에서 새로운 레코드를 조회합니다.그런 다음 100개의 레코드를 쿼리하여 대상에 복사합니다.

// save in file named index.js
// you can then execute the code from your console using `node index.js`
const { Sequelize, Op, DataTypes } = require("sequelize");
const fieldNames = [// These fields will be different for your database
  `battSoc`,
  `panelV`,
  `panelI`,
  `loadV`,
  `loadI`,
  `battV`,
  `battI`,
  `battTemp`,
  `panelW`,
  `loadW`,
  `tempEquip`,
  `ambientTemp`,
];

const SolarFields = {
  id: {
    type: DataTypes.INTEGER,
    autoIncrement: true,
    primaryKey: true,
  },
};

SolarFieldNames.map((fieldName) => {
  SolarFields[fieldName] = { type: DataTypes.FLOAT };
});

async function copyDataMariaToPostgres() {
  const postgres = new Sequelize("postgressdbname", "username", "password", {
    host: "localhost",
    dialect: "postgres",
  });

  const mariaDb = new Sequelize("mariadbname", "username", "password", {
    host: "192.168.1.110",
    dialect: "mariadb",
  });
  let solarSource;
  let solarDest;
  postgres
    .authenticate()
    .then(function (result) {
      return mariaDb.authenticate();
    })
    .then(async function (result) {
      solarSource = mariaDb.define("solar", SolarFields, {
        tableName: "solar",
        timestamps: false,
      });
      solarDest = postgres.define("solar", SolarFields, {
        tableName: "solar",
        timestamps: false,
      });

      await solarSource.sync({ logging: false });
      await solarDest.sync({ logging: false });
      // get last row in dest:
      let lastRow = await solarDest.findOne({ order: [["id", "desc"]] });
      let rows;
      do {
        findAllParams = { logging: false, limit: 100, order: [["id", "asc"]] };
        // lastRow is null if the destination is empty
        if (lastRow) findAllParams.where = { id: { [Op.gt]: lastRow.id } };
        const promises = [];
        rows = await solarSource.findAll(findAllParams);
        rows.forEach(async function (row, i) {
          promises.push(solarDest.create(row.dataValues, { logging: false }));
        });
        const newRows = await Promise.all(promises);
        newRows.forEach((row, i) => {
          console.log(`#${i} ${row.dataValues.id}`);
          lastRow = row;
        });
      } while (rows.length > 0);
    })
    .catch((e) => {
      console.error(e);
    });
}
copyDataMariaToPostgres();

언급URL : https://stackoverflow.com/questions/37078970/sequelize-using-multiple-databases

반응형