Resolve Sequelize 'String based operators are deprecated' warning

When you’re using Sequelize, you might see a warning message in the console saying that String based operators are deprecated.

The warning may look as follows:

$ node index

(node:60610) [SEQUELIZE0003] 
DeprecationWarning: String based operators are deprecated.
Please use Symbol based operators for better security,
read more at https://sequelize.org/master/manual/querying.html#operators

Unfortunately, when you click on the link to read more, you’ll find the page has been moved to several different sections of the documentation.

Let me help you resolve the warning message in this tutorial.

The deprecation warning happens when you add the operatorAliases option in the Sequelize constructor:

const sequelize = new Sequelize("DB", "USERNAME", "PASSWORD", {
  host: "localhost",
  dialect: "mysql",
  operatorsAliases: {
    $gt: Op.gt,
  },
});

To remove the warning message, you need to remove the operatorsAliases option from your Sequelize constructor.

You can then use the properties of the Op object directly in your query methods.

The following example demonstrates how you can use the greater than operator [Op.gt] in your where option:

const cities = await City.findAll({
  where: {
    population: { [Op.gt]: 1000 },
  },
});

But why are string based operators deprecated?

In Sequelize version 4 or below, the string based operator can still be used without any aliases:

const cities = await City.findAll({
  where: {
    population: { $gt: 1000 },
  },
});

But since the operator $gt is based on a string, a malicious hacker could perform SQL injection through user input.

Consider the following code:

const cities = await City.findAll({
  where: {
    population: req.query.population,
  },
});

Through the req object, a bad user can pass population='{"$gt": 200}' to manipulate your Sequelize query.

This is why in version 5 and above, Sequelize introduces the Op object that you can import and use in your code:

const { Sequelize, Op } = require("sequelize");

// ...

const cities = await City.findAll({
  where: {
    population: { [Op.gt]: 1000 },
  },
});

But of course, you may have a big JavaScript project that already uses $ operators in your query methods.

In that case, Sequelize allows you to create operator aliases through the operatorsAliases option that you can add to the constructor.

You can add as many or as few operators as you need:

const sequelize = new Sequelize("DB", "USERNAME", "PASSWORD", {
  host: "localhost",
  dialect: "mysql",
  operatorsAliases: {
    $gt: Op.gt,
    $and: Op.and,
    $or: Op.or,
    $eq: Op.eq,
  },
});

When you omit the option, then using string based operators will cause Sequelize to generate [object Object] in your SQL statement.

The following code:

const { Sequelize, Op } = require("sequelize");

const sequelize = new Sequelize("DB", "USERNAME", "PASSWORD", {
  host: "localhost",
  dialect: "mysql",
});

// ...

const cities = await City.findAll({
  where: {
    population: { $gt: 1000 },
  },
});

Will cause Sequelize to generate and run the following SQL statement:

SELECT `id`, `cityName`, `population`
  FROM `Cities` AS `City`
  WHERE `City`.`population` = '[object Object]';

Now you’ve learned the cause behind String based operators are deprecated warning message and how to resolve it.

For more information, you can find the Sequelize operators documentation here.

I hope this tutorial has been useful for you 🙏

Take your skills to the next level ⚡️

I'm sending out an occasional email with the latest tutorials on programming, web development, and statistics. Drop your email in the box below and I'll send new stuff straight into your inbox!

No spam. Unsubscribe anytime.