简体   繁体   中英

How to fix two Knex MySQL queries dependent on each other in a router.get

I am attempting to display data from two database tables on a route using Node, Express and JavaScript. I have connected my Express app to the database using knex, and am attempting to use MySQL SELECT queries to elicit data from the two tables to display on the server.

The data in the 'column' attribute/column in the 'offence_columns' table appears as a column in the 'offences' table, hence why I have two promises, one in which takes the data from the 'column' attribute in the 'offence_columns' table, and the other in which selects the 'area' attribute in the 'offences' table and another attribute/column that is what was selected from the 'columns' attribute.

Since 'column' is a reserved word in MySQL, I have had some issues in selecting it. Using single quote marks like in the code provided provides me with a code in the terminal:

Unhandled rejection Error: ER_PARSE_ERROR: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'as 0 from offences ' at line 1.

I get the same error if I substitute the single quotes for back ticks ( column ), but if I try using both (' column ') I get a different error:

Error: ER_BAD_FIELD_ERROR: Unknown column ' column ' in 'field list'.

I tried using aliases but it didn't seem to help.

router.get('/api/search/:offence', function(req, res, next) {
  req.db.from('offence_columns').select('column').where('pretty',"=",req.params.offence)
    .then((rows) => {
      req.db.from('offences').select('area', rows)
        .then((rows2) => {
          res.json({"Error" : false, "Message" : "Success", "City" : rows2})
        })
    })
    .catch((err) => {
      console.log(err);
      res.json({"Error" : true, "Message" : "Error in MySQL query"})
    })
});

First of all, consider adjusting your schema. column is a really terrible name for a database column... it'll cause all sorts of confusion, as you have already discovered!

However, Knex normally surrounds names with backticks in its output which should avoid the reserved word issue. This is not actually your problem. What you're seeing is the result of trying to issue a query with an array in it:

req.db.from('offences').select('area', rows)

Here, rows is an array, which may or may not be empty. It's the result of the previous query.

I suspect what you're looking for is something more along these lines (guesswork, because I don't know what your schema is):

db.from("offence_columns")
  .select("column")
  .where("pretty", "=", req.params.offence)
  .then(rows => {
    if (rows.length === 0) {
      res.json({ error: false, message: "No cities matched." });
    }

    req.db
      .from("offences")
      // This assumes that `offence_columns` has an `area` column
      .where("area", "=", rows[0].area)
      .then(areas => {
        res.json({ Error: false, Message: "Success", city: areas[0] });
      });
  });

There are still a number of problems here. For one thing, what if either query can return more than one result? Furthermore, you're probably better off with a join in the first place:

db
  .select('city')
  .from('offence_columns')
  .join('offences', 'offence_columns.area', '=', 'offences.area')
  .where('pretty', '=', req.params.offence)

However, it's all guesswork without knowing what your schema looks like.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM