vite+ts-5-Sequelize框架优化

news2024/12/24 11:29:35

random recording 随心记录
What seems to us as bitter trials are often blessings in disguise.
看起来对我们痛苦的试炼,常常是伪装起来的好运。

此系列是一个前后端整合项目,跟往期关联,链接传送到达:
1.vite+ts-1-前期准备(尽量详细)
2.vite+ts-2-通过图片名动态加载图片路径
3.vite+ts-3-ts+koa+mysql后端(慢慢更新)
4.vite+ts-4-ORM框架sequelize搭建后端

Sequelize框架优化改进

目录变化

新建src/modules目录

封装模块,合并define和装饰器模型,提高可扩展性和维护性

目录结构如下
在这里插入图片描述
Userinfo.ts

import { Column,Model,Table } from "sequelize-typescript";
import { DataTypes } from "sequelize";
// 装饰器
@Table({
    tableName:'userinfo'
})
export default class UserinfoModel extends Model<UserinfoModel>{
    @Column({
        type:DataTypes.INTEGER,
        primaryKey:true,
        autoIncrement:true
    })
    userid!:number
    @Column({
        type:DataTypes.STRING(30),
        field:'username',
        allowNull:false
    })
    public username!:string
    @Column({
        type:DataTypes.STRING(30),
        field:'psw',
        allowNull:false
    })
    psw!:string
    @Column({
        type:DataTypes.STRING(50),
        field:'address'
    })
    public address!:string
    @Column({
        type:DataTypes.TINYINT,
        field:'valid',
    })
    valid!:number
    @Column({
        type:DataTypes.DATE,
        field:'birth'
    })
    @Column({
        type:DataTypes.TINYINT,
        field:'age'
    })
    age!:number
}

UserDao.ts

import { Op, Sequelize } from 'sequelize'
import { model } from '../defmodel/index'
// import model from '../../decormodel/Userinfo'
class UserDao {
    static userDao = new UserDao()
    // 添加用户
    addUser(userinfo: UserInfo) {
        return model.create(userinfo)
    }
    // 查询所有用户
    findAllUser() {
        return model.findAll({
            raw: true // 屏蔽其他属性,只要记录
        })
    }
    // 投影查询
    findByProps() {
        return model.findAll({ 
            raw: true,
            attributes:['username','psw'] // 想要查询的字段
        })
    }
    // or and 查询
    findByUserAndPassword(username:string,psw:string){
        return model.findOne({
            raw:true,
            // where 条件
            where:{
                // Op是一种条件类型 or and in like
                [Op.or]:[
                    {username},
                    {psw}
                ]
            }
        })
    }
    // 模糊查询
    findByLike(key:string){
        const matchKey = `%${key}%`
        return model.findAll({
            raw:true,
            where:{
                username:{
                    [Op.like]:matchKey // % _
                }
            }
        })
    }
    // and查询
    findByUserAndAddr(){
        return model.findAll({
            raw:true,
            where:{
                [Op.and]:[
                    {
                        username:{
                            [Op.like]:'%s%'
                        }
                    },
                    {address:'cq'}
                ]
            }
        })
    }
    // 聚合查询 sql:select address,count(valid) from userinfo where valid=1 group by address;
    countUserinfo(){
        return model.findAll({
            raw:true,
            group:'address',
            attributes:['address',[Sequelize.fn('count',Sequelize.col('valid')),'totalcount']],
            where:{
                valid:1
            }
        })
    }
    // 分页查询 sql:select * from userinfo limit offset,pageSize
    findUserWithPager(offset:number,pageSize:number){
        return model.findAll({
            raw:true,
            limit:pageSize,
            offset
        })
    }
}

export type UserInfo = {
    userid: string,
    username: string,
    psw: string,
    address: string,
    valid: number,
    age: number
}
// export const { addUser, findAllUser,findByProps,findByUserAndPassword,findByLike,findByUserAndAddr } = UserDaoDefine
export default UserDao.userDao

definemodel/index.ts

import { DataTypes } from "sequelize";
import { sequelize } from "../../BaseDao";
class UserInfo{
    static createMode(){         //表名
        const model =  sequelize.define('userinfo',{
            // 属性
            userid:{
                type:DataTypes.INTEGER, // 必须属性,类型
                field:'userid',
                primaryKey:true,
                autoIncrement:true
            },
            username:{
                type:DataTypes.STRING(30),
                field:'username',
                allowNull:false
            },
            psw:{
                type:DataTypes.STRING(30),
                field:'psw',
                allowNull:false
            },
            address:{
                type:DataTypes.STRING(50),
                field:'address'
            },
            valid:{
                type:DataTypes.TINYINT,
                field:'valid',
            },
            birth:{
                type:DataTypes.DATE,
                field:'birth'
            },
            age:{
                type:DataTypes.TINYINT,
                field:'age'
            }
        },
        // 可选参数
        {
            freezeTableName:true, // true表示使用给定表名,false表示模型名后加s作为表名
            timestamps:false // true表示给模型加时间戳(createAt,updateAt),false不加
        }
        )
        model.sync({force:false}) // 同步数据库,true,表存在先删除后创建,false不存在才创建
        return model
    }
}
export const model = UserInfo.createMode()

BaseDao.ts

import dbConfig from "../conf/DbConfig";
import { Dialect } from "sequelize";
import { Sequelize } from "sequelize-typescript";
import path from 'path'
class BaseDao{
    static baseDao:BaseDao = new BaseDao()
    sequelize!:Sequelize
    constructor(){
        this.initSeqConf('mysql')
    }
    initSeqConf(dialect:Dialect){
        let {host,user,password,port,database} = dbConfig.getConf()
        this.sequelize = new Sequelize(database,user,password,{
            host,
            port,
            dialect,
            define:{timestamps:false,freezeTableName:false}
        })
        // this.addModels()
    }
    addModels(){
        const modelPath = path.join(process.cwd(),'/src/modules/decormodel')
        this.sequelize.addModels([modelPath])
    }
}
// 合并第一和第三种模型
const baseDao = BaseDao.baseDao
baseDao.addModels()
export const {sequelize} = baseDao

修改router/user.ts

import userDao,{ UserInfo } from "../modules/userinfo/dao/UserDao"; // define模型
// import userDao from "../modules/userinfo/dao/UserDao"; // 装饰器模型
// 使用 define模型
// post请求 http://localhost:6789/book/usermodule/addUser
router.post('/addUser',async (ctx)=>{
    const user:UserInfo = ctx.request.body
    ctx.body = `你好,${user.username}`
    const userinfo:UserInfo = ctx.request.body
    const dbUserinfo = await userDao.addUser(userinfo)
    ctx.body = success(dbUserinfo)
})
// 查询所有用户 http://localhost:6789/book/usermodule/findAllUser
router.get('/findAllUser',async (ctx:Context)=>{
    const dbUser = await userDao.findAllUser()
    console.log(dbUser)
    ctx.body = success(dbUser)
})

Koa高性能访问数据库 || sequelize数据库连接池

连接池

数据库连接池是负责创建,分配,释放数据库连接对象,在项目启动时会创建一定数量数据库连接放入连接池对象,并允许应用重复使用现有数据库连接,而不是重新创建新的连接。
Sequelize底层,连接池是由ConnectionManager类管理的pool对象,通过pool类对象来管理和共享多个连接对象。

工作原理

连接池技术的核心思想是连接复用,通过建立一个数据库连接池以及一套连接使用、分配和管理策略,使得该连接池中的连接可以得到高效、安全的复用,避免了数据库连接频繁建立、关闭的开销。

连接池配置

new Sequelize(database,user,password,{
            host,
            port,
            dialect,
            define:{timestamps:false,freezeTableName:false},
            pool:{
                // 数据库连接池
                max:500, // 最大连接池对象个数
                min:50, // 最小连接数
                idle:10000, // 空闲连接最长等待时间 毫秒ms
                acquire:10000 // 一条sql语句查询在获取链接资源之前最长等待时间 ms
            }
        })

service层

service层应用场景

  • 当一个业务功能需要执行一个dao类中的多个方法才能完成时
  • 当一个业务功能需要执行多个dao中方法才能完成时
  • 当一个业务功能需要对dao类取出来的数据进行处理时

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/55950.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

FreeRtos于嵌入式环境的应用

FreeRtos操作系统 首先&#xff0c;应该介绍什么是FreeRtos&#xff0c;他于单片机而言就是一个管理器&#xff0c;作为管理者管理嵌入式芯片中的任务&#xff0c;堆栈&#xff0c;中断&#xff0c;队列等等资源&#xff0c;对于操作系统而言&#xff0c;又分为实时操作系统和…

分布式事物-全面详解(学习总结---从入门到深化)

分布式事物处理_认识本地事物 什么是事物 事务就是针对数据库的一组操作&#xff0c;它可以由一条或多条SQL语句组 成&#xff0c;同一个事务的操作具备同步的特点&#xff0c;事务中的语句要么都执 行&#xff0c;要么都不执行。 举个栗子&#xff1a; 你去小卖铺买东西&#…

kafka中partition数量与消费者对应关系以及Java实践(Spring 版本)

文章目录分区理解一、单播模式&#xff0c;只有一个消费者组1. topic只有1个partition2. topic有多个partition,该组内有多个消费者二、广播模式&#xff0c;多个消费者组2.1. 多个消费者组&#xff0c;1个partition2.2. 多个消费者组&#xff0c;多个partition三、Java实践-pr…

谈谈JS二进制:File、Blob、FileReader、ArrayBuffer、Base64

当互联网进入存量时代&#xff0c;增量正在成为行业的稀缺资源。而本地生活服务恰恰是当前互联网行业为数不多的增量。 前瞻产业研究院数据显示&#xff0c;2021年中国互联网本地生活服务行业市场规模达到2.6万亿元&#xff0c;到2025年&#xff0c;其市场规模有望达到4万亿元&…

吉林优美姿文化:抖音店铺怎么优化页面?

要知道&#xff0c;新手开始做直播间影响人气的三大要素就是在线人数&#xff0c;互动量&#xff0c;以及留存率&#xff0c;那么当这些要素都非常高的时候&#xff0c;抖音系统就会自动把你的直播间推荐给更多的观众&#xff0c;获取更多的流量&#xff0c;那么抖音新手怎么开…

简单了解Vue

1、vue概述 Vue是一套前端框架&#xff0c;可以免除原生JavaScript中的DOM操作&#xff0c;简化书写。 基于MVVM&#xff08;Model-View-View Model&#xff09;思想&#xff0c;实现数据的双向绑定&#xff0c;将编程的关注点放在数据上 vue的官网&#xff1a;https://cn.v…

猿如意---Python3.10版本手把手教学安装和下载.

亲自为大家示范如何使用猿如意以及在猿如意当中下载&#xff0c;安装和使用python3.10版本&#xff0c;让大家喜欢上这款好用的app—猿如意。 文章目录前言一、手把手教你猿如意的安装、下载二、手把手教你Python3.10版本的安装、下载1.找到我需要的工具2.我需要的工具的安装、…

Docker容器

1.什么是Docker&#xff1f; 1.为什么会出现docker&#xff1f; 我们写的代码会接触到好几个环境&#xff1a;开发环境、测试环境以及生产环境等等。多种环境去部署同一份代码&#xff0c;由于环境原因往往会出现软件跨环境迁移的问题&#xff08;也就是“水土”不服&#xf…

Android车载应用开发——DLNA开发浅析

DNLA的建立 DLNA 成立于2003 年6 月24 日, 其前身是DHWG &#xff08;Digital Home Working Group 数字家庭工作组&#xff09;&#xff0c;由Sony、Intel、Microsoft等发起成立、旨在解决个人PC &#xff0c;消费电器&#xff0c;移动设备在内的无线网络和有线网络的互联互通…

基于x86架构的CentOS7虚拟机通过qemu安装ARM架构OpenEuler虚拟机

【原文链接】基于x86架构的CentOS7虚拟机通过qemu安装ARM架构OpenEuler虚拟机 &#xff08;1&#xff09;首先需要有一台CentOS虚拟机&#xff0c;如没有可参考 VMWare安装CentOS7操作系统的虚拟机 安装一台CentOS虚拟机 &#xff08;2&#xff09;安装基础命令 yum install…

17:00面试,17:09就出来了 ,问的实在是太...

从外包出来&#xff0c;没想到算法死在另一家厂子 自从加入这家公司&#xff0c;每天都在加班&#xff0c;钱倒是给的不少&#xff0c;所以也就忍了。没想到8月一纸通知&#xff0c;所有人不许加班&#xff0c;薪资直降30%&#xff0c;顿时有吃不起饭的赶脚。 好在有个兄弟内…

java基于PHP+MySQL教务选课管理系统的设计与实现

基于PHP的教务管理系统主要高校内部提供服务,系统分为管理员,教师用户和学生用户三部分。 在基于PHP的教务管理系统中分为管理员用户,教师用户和学生用户三部分,其中管理员用户主要是用来管理教师信息,学生信息,公告信息,课程信息,专业信息和班级信息等内容,教师用户主要是用来…

Cartesi 2022 年 11 月回顾

查看你不想错过的更新2022年12月1日 &#xff0c;欢迎新的建设者加入Cartesi 生态系统并认识更多的新的开发者社区。 从紧张繁忙的11月到12月&#xff0c;11月 ETH Global 因为在旧金山举办了迄今为止最盛大的黑客马拉松活动而轰动一时。有13位才华横溢的学者加入了我们的 Hack…

原生JS的拖拽属性draggable(详解)

摘要 作为h5新增的属性draggable&#xff0c;它能够给与一切的html元素拖动的效果。而在这个属性之下&#xff0c;也有着关于拖动效果的各个方法。 而这一篇文章&#xff0c;主要就是说一下关于draggable属性的使用以及工作场景。 1.了解draggable属性的使用 对我来讲&#…

【单片机基础】初始51单片机

文章目录学习单片机需要掌握的基础知识1、用一句话说透什么是单片机&#xff1a;2、单片机上集成了什么&#xff1f;3、STC89C51/52单片机过时了吗&#xff1f;4、STC89C51和STC89C52有什么区别&#xff1f;5、单片机时序的概念&#xff08;基础知识很重要&#xff09;6、单片机…

基于功能安全的车载计算平台开发:系统层面

相对于功能安全概念阶段&#xff0c;系统阶段更专注于产品的详细设计&#xff0c;涉及系统工程、安全工程和架构设计等不同技术领域。同时&#xff0c;系统阶段也经常扮演着供应链上、下游功能安全的DIA交互阶段&#xff0c;是功能安全中非常重要且考验技术水平的阶段。 01 应…

微服务框架 SpringCloud微服务架构 8 Gateway 网关 8.6 过滤器链执行顺序

微服务框架 【SpringCloudRabbitMQDockerRedis搜索分布式&#xff0c;系统详解springcloud微服务技术栈课程|黑马程序员Java微服务】 SpringCloud微服务架构 文章目录微服务框架SpringCloud微服务架构8 Gateway 网关8.6 过滤器链执行顺序8.6.1 过滤器执行顺序8.6.2 总结8 Gat…

【毕业设计】大数据房价数据分析可视化 - python

文章目录0 前言1 课题背景2 数据爬取2.1 爬虫简介2.2 房价爬取3 数据可视化分析3.1 ECharts3.2 相关可视化图表4 最后0 前言 &#x1f525; Hi&#xff0c;大家好&#xff0c;这里是丹成学长的毕设系列文章&#xff01; &#x1f525; 对毕设有任何疑问都可以问学长哦! 这两…

深度讲解风险策略的调优|附实操案例

量化风控审核过程中的通过率在贷前策略中是一大重要的内容&#xff0c;另外一个是逾期率。二者之间的因果关系就是通过率高低变化决定了逾期率风险的走势&#xff0c;通过率决定了逾期率的结果&#xff0c;而逾期率又对通过率起到了一个制衡的作用。 我们在本周早前详细谈过这个…

先验 后验 似然估计

一、完备事件组 设E是随机试验&#xff0c;Ω是相应的样本空间&#xff0c;A1&#xff0c;A2&#xff0c;...An为Ω的一个事件组&#xff0c;若 &#xff08;1&#xff09;AiAj&#xff08;ij&#xff09; &#xff08;2&#xff09;A1A2...AnΩ 则称A1A2...An为样本空间的…