Sql-ORM addition, deletion, modification and query
ORM framework: object-relational mapping, facing object sql
This section uses sequelize as the orm-sql framework, and the database is sqlite
Preparation
Similarly, you need to install the corresponding js version of the database Driver, such as: PostgreSQL -> pg, mysql/mariadb -> mysql, sqlite -> sqlite3…
- Install sqlite3 dependencies
npm install sqlite3
- Install sequelize dependencies
npm install sequelize
- Introduce dependencies
const app = express();
const {
Sequelize } = require('sequelize');
- It is recommended to install a suitable database interface tool, the author uses Beekeeper Studio.
create project
Copy the first section of the HelloWorld project
create sqlite connection
Specify the dialect as sqlite, and the persistence path as data.db in this directory
const sqlite = new Sequelize({
dialect: 'sqlite',
storage: './data.db'
})
define table model
Sequelize focuses on object-oriented SQL, so we need to create a class corresponding to the data table
. Just like the previous section, let's create an identical user table:
- Introducing DataTypes
const { Sequelize,DataTypes } = require('sequelize');
- Define the User object
Model.init(schema,options)
const User = sqlite.define('User', {
id: {
primaryKey: true,
type: DataTypes.INTEGER,
allowNull: false,
autoIncrement: true
},
// 在这里定义模型属性
uname: {
type: DataTypes.STRING,
allowNull: true
},
passwd: {
type: DataTypes.STRING
// allowNull 默认为 true
}
}, {
// 直接指定表名,不指定的话sequelize将默认以模型的复数形式作为表名
tableName: 'user'
});
There is another method, the effect is the same, depending on personal preference:
- Additional introduction of Model
const {
Sequelize,DataTypes,Model } = require('sequelize');
- Initialize the User class
Model.init(schema,options)
User继承Model类
class User extends Model {
};
User.init(
{
id: {
primaryKey: true,
type: DataTypes.INTEGER,
allowNull: false,
autoIncrement: true
},
// 在这里定义模型属性
uname: {
type: DataTypes.STRING,
allowNull: true,
},
passwd: {
type: DataTypes.STRING,
defaultValue: '123456', //默认值
//allowNull 默认为 true
}
},
{
// 这是其他模型参数
sqlite, // 我们需要传递连接实例
modelName: 'User1', // 我们需要选择模型名称,
// 直接指定表名
tableName: 'user',
}
);
Model Synchronization
Model.sync
: The underlying execution is create table if not exist
- If the corresponding table does not exist in the database, the table will be created directly according to the model; if it exists, no operation
Model.sync({force: true})
: the bottom layer is first drop if and then create - If the table already exists, it will be dropped and then created from the model
Model.sync({alter: true})
: - If the table already exists, the table structure will be modified to match the model
The bells and whistles, in short, ensure that there is a table corresponding to the model in the database
Create user table
We use to User.sync()
create a user table
app.put('/db/user', async function (req, res) {
let what = await User.sync();
res.json(what);
});
Use the api debugging tool PUT 127.0.0.1:8080/db/user, you will get 1, note that as long as it can be successfully mapped to the data table, it will be 1
Use Beekeeper to view our user table, and you will find that it is a little different from the model we defined: there are two more fields - createdAt and updatedAt, that is, creation time and modification time. Sequelize will automatically manage these two fields. Note that when you
use If other sql tools are used to modify the table, these two fields will not be updated automatically
If you don't want these two values, or want to change the name, you can add these settings to options when defining the model:
// 禁止createdAt和updatedAt
timestamps: false,
// 只禁止createdAt
createdAt: false,
// 给updatedAt换个名字
updatedAt: 'updateTime'
delete user table
The drop() method, the bottom layer is drop if, which can act on both the model and the database:
sqlite.drop(); //这将删除当前data.db下所有的表
We use User.drop()
to delete the user table
app.delete('/db/user', async function (req, res) {
let what = await User.drop();
res.json(what);
});
Use the api debugging tool PUT 127.0.0.1:8080/db/user, you will get 1, note that even if the table is gone, it is still 1
data table crud
increase
Before operating table records, we first Model.build
create an instance through the model ( ), and then call save()
to insert this instance into the table.
Of course, if the data you get from the front end can be used without processing and conversion, you can also directly Model.create
insert record with
app.use(express.json({
type: 'application/json'}));
app.put('/db/user/record', async function (req, res) {
/**前端请求体
{
"uname": "evanp",
"passwd": "iloveu"
}
*/
try {
let user = User.build(req.body);
let what = await user.save();
// let what = await User.create(req.body);
res.json(what);
}catch(e){
res.json(e);
}
});
Use the api debugging tool PUT 127.0.0.1:8080/db/user/record with the corresponding request body, you will get:
{
"id": 1,
"uname": "evanp",
"passwd": "iloveu",
"updatedAt": "2023-03-19T08:03:37.964Z",
"createdAt": "2023-03-19T08:03:37.964Z"
}
Yes, after the record is successfully added, it will check out the entire record as the return result
Ok, so now there is a record with id=1 in the user table, let's try to create a record with the same id... the
server hangs directly, we don't want this, it means there is any wrong sql It may cause the server to crash, so what should I do?
Some friends may remember that in the previous section, try-catch syntax sugar was used to wrap SQL operations, which is a good method
check
The sequelize model has built-in methods that allow us to query directly based on the model
- findAll finds all, the bottom layer is
select * from ...
- findOne finds one, the bottom layer is
select * from ... LIMIT 1
- findByPk Find by primary key
- findAndCountAll Find and return the total number of matching items, often used for pagination
- findOrCreate create if not found
These methods can add options parameters to set WHERE, LIMIT and other restrictions.
We use findOne to query a record on evanp with correct username and password:
//我为了方便直接url传参了,实际上为了隐私,至少应该放在请求体内
app.get('/db/user/record', async function (req, res) {
let evanp = await User.findOne({
where: req.query});
res.json(evanp);
});
If you only need to query some of the fields, set attributes in options:
User.findAll({
attributes: ['id','uname']
});
If you want to alias the field, for example, name the id uid like this:
User.findAll({
attributes: [['id','uid'],'uname']
});
change
Model.update(修改项,限制)
app.post('/db/user/record', async function (req, res) {
/*请求体
{
"set":{
"passwd": "123456"
},
"where": {
"uname": "evanp",
"passwd": "iloveu"
}
}
*/
let what = await User.update(req.body.set,{
where: req.body.where})
res.json(what);
});
Use the api tool for debugging. If the modification is successful, it will return 1, and if the modification fails, it will return 0 (cannot be found/cannot be changed)
delete
Model.destroy(限制)
app.delete('/db/user/record', async function (req, res) {
/*请求体
{
"uname": "evanp",
"passwd": "123456"
}
*/
let what = await User.destroy({
where: req.body})
res.json(what);
});
Use the api tool to debug, if the deletion is successful, it will return 1, and if the deletion fails, it will return 0 (cannot find/delete)
Native SQL
Of course, if you need to use sql statement directly, it is also possible. 连接实例.query(sqlStr)
Usually
, the returned result contains 2 values, one is the result array, and the other is related information
app.post('/db/user/record/freely', async function (req, res) {
/*json请求体
{
"sql": "xxx"
}
*/
let what = null;
try {
what = await sqlite.query(req.body.sql);
} catch (e) {
what = e;
}
res.json(what);
});
Be careful before executing insert. If this table is synchronized by sequelize, there may be those two time fields. Don’t forget
The examples in this section are just to demonstrate how to use sequelize to operate the database in express.js. For more extended and advanced usage methods of sequelize, please go to the official sequelize document https://www.sequelize.cn/