Несколько запросов MySQL с Express Node - PullRequest
0 голосов
/ 22 ноября 2018

Я использую сервер Express и подключаюсь к базе данных MySQL.У меня есть две таблицы, на которые ссылаются через user_id.Когда пользователь указывает адрес электронной почты, мне нужно запросить users, чтобы найти user_id, а затем выполнить другой запрос, чтобы присоединиться к таблицам tracking.Каков наилучший способ достичь этого?Также приветствуются рекомендации по любой части кода!

Спасибо

MySQL

CREATE TABLE users (
  user_id INT NOT NULL AUTO_INCREMENT UNIQUE,
  first_name VARCHAR(100) NOT NULL,
  last_name VARCHAR(100) DEFAULT NULL,
  email VARCHAR(320) NOT NULL UNIQUE,
  date_created TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
  PRIMARY KEY (user_id)
);

CREATE TABLE tracking (
  tracking_id INT NOT NULL AUTO_INCREMENT,
  user_id INT NOT NULL,
  metric VARCHAR(100) NOT NULL,
  unit VARCHAR(100) NOT NULL,
  amount DOUBLE DEFAULT NULL,
  date_tracked DATE,
  date_created TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
  PRIMARY KEY (tracking_id),
  INDEX user_ind (user_id),
  FOREIGN KEY (user_id)
   REFERENCES users(user_id)
   ON DELETE CASCADE
);

Express (Nodejs)

const express = require("express");
const app = express();
const port = 3000;
var mysql = require("mysql");
var connection = mysql.createConnection({
  host: "",
  user: "",
  password: "",
  database: "tracker"
});

app.get("/data/:email/metric/:metric", (req, res) => {
  console.log(req.params);
  let user_id = "";

  connection.connect();

  connection.query(
    `SELECT user_id FROM users WHERE email = '${req.params.email}';`,
    function(error, results, fields) {
      if (error) throw error;
      user_id = results[0].user_id;
    }
  );

  connection.query(
    `SELECT users.first_name, users.last_name, users.email, tracking.metric, tracking.unit, tracking.amount, tracking.date_tracked FROM users JOIN tracking ON users.user_id = tracking.user_id WHERE users.user_id = '${user_id}' AND metric = '${
      req.params.metric
    }';`,
    function(error, results, fields) {
      if (error) throw error;
      res.send(results);
    }
  );

  connection.end();
});

app.listen(port, () => console.log(`Example app listening on port ${port}!`));

Ответы [ 2 ]

0 голосов
/ 22 ноября 2018

Мне нужно запросить пользователей, чтобы найти user_id, а затем выполнить другой запрос, чтобы присоединиться к таблицам отслеживания.Каков наилучший способ добиться этого?

Вы можете достичь этого только с одним запросом:

    SELECT users.first_name, users.last_name, users.email, 
            tracking.metric, tracking.unit, tracking.amount,
            tracking.date_tracked 
    FROM users 
    JOIN tracking 
    ON users.user_id = tracking.user_id 
    WHERE users.email = '${req.params.email}' AND 
          metric = '${req.params.metric}

Также любые рекомендации передового опыта для любой части кодаприветствуется!

Прежде всего, вы должны подключиться к mySql после запуска сервера.

Подключение и отключение при каждом запросе будут влиять на производительность (Это дорогостоящая задача - открыть сокет и подключитьснаружи)

поэтому попробуйте что-то вроде:

    CONNECTION.connect().then(() => {
        // mysql is ready , let's start express server 
        // accepting connections
        app.listen(port, () => console.log(`ready on ${port}!`));
    }).catch(console.error)

Еще одна полезная практика, которую вы должны знать, - это выполнение запросов параллельно с Promise.all ([]).когда вам нужно выполнить несколько несвязанных запросов, вы можете выполнить их все один за другим, уменьшив время ожидания total для всех результатов.

0 голосов
/ 22 ноября 2018

Вы можете сделать это с помощью одного запроса, просто JOIN таблиц на user_id

SELECT 
  u.first_name, 
  u.last_name, 
  u.email, 
  t.metric, 
  t.unit, 
  t.amount, 
  t.date_tracked 
FROM users u
INNER JOIN tracking AS t ON t.user_id = u.user_id
WHERE u.email = '<email>' AND t.metric = '<metric>'

Также, FWIW, вы должны использовать параметризованные запросы, чтобы защитить себя от SQL-инъекций

const values = [
  req.params.email, 
  req.params.metric
];
connection.query(
  'SELECT ... WHERE u.email = ? AND t.metric = ?', 
  values, 
  (err, results, fields) => {
    if (err) return next(e); // propagate the error to Express, rather than throwing in the callback

    res.send(results);
  }
);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...