feat(medications): 新增完整的药物管理和服药提醒功能
实现了包含药物信息管理、服药记录追踪、统计分析、自动状态更新和推送提醒的完整药物管理系统。 核心功能: - 药物 CRUD 操作,支持多种剂型和自定义服药时间 - 惰性生成服药记录策略,查询时才生成当天记录 - 定时任务自动更新过期记录状态(每30分钟) - 服药前15分钟自动推送提醒(每5分钟检查) - 每日/范围/总体统计分析功能 - 完整的 API 文档和数据库建表脚本 技术实现: - 使用 Sequelize ORM 管理 MySQL 数据表 - 集成 @nestjs/schedule 实现定时任务 - 复用现有推送通知系统发送提醒 - 采用软删除和权限验证保障数据安全
This commit is contained in:
140
src/medications/models/medication.model.ts
Normal file
140
src/medications/models/medication.model.ts
Normal file
@@ -0,0 +1,140 @@
|
||||
import { Column, Model, Table, DataType, HasMany } from 'sequelize-typescript';
|
||||
import { MedicationFormEnum } from '../enums/medication-form.enum';
|
||||
import { RepeatPatternEnum } from '../enums/repeat-pattern.enum';
|
||||
import { MedicationRecord } from './medication-record.model';
|
||||
|
||||
/**
|
||||
* 药物信息模型
|
||||
*/
|
||||
@Table({
|
||||
tableName: 't_medications',
|
||||
underscored: true,
|
||||
paranoid: false, // 使用软删除字段 deleted 而不是 deletedAt
|
||||
})
|
||||
export class Medication extends Model {
|
||||
@Column({
|
||||
type: DataType.STRING(50),
|
||||
primaryKey: true,
|
||||
comment: '药物唯一标识',
|
||||
})
|
||||
declare id: string;
|
||||
|
||||
@Column({
|
||||
type: DataType.STRING(50),
|
||||
allowNull: false,
|
||||
comment: '用户ID',
|
||||
})
|
||||
declare userId: string;
|
||||
|
||||
@Column({
|
||||
type: DataType.STRING(100),
|
||||
allowNull: false,
|
||||
comment: '药物名称',
|
||||
})
|
||||
declare name: string;
|
||||
|
||||
@Column({
|
||||
type: DataType.STRING(255),
|
||||
allowNull: true,
|
||||
comment: '药物照片URL',
|
||||
})
|
||||
declare photoUrl: string;
|
||||
|
||||
@Column({
|
||||
type: DataType.STRING(20),
|
||||
allowNull: false,
|
||||
comment: '药物剂型',
|
||||
})
|
||||
declare form: MedicationFormEnum;
|
||||
|
||||
@Column({
|
||||
type: DataType.DECIMAL(10, 2),
|
||||
allowNull: false,
|
||||
comment: '剂量数值',
|
||||
})
|
||||
declare dosageValue: number;
|
||||
|
||||
@Column({
|
||||
type: DataType.STRING(20),
|
||||
allowNull: false,
|
||||
comment: '剂量单位',
|
||||
})
|
||||
declare dosageUnit: string;
|
||||
|
||||
@Column({
|
||||
type: DataType.INTEGER,
|
||||
allowNull: false,
|
||||
comment: '每日服用次数',
|
||||
})
|
||||
declare timesPerDay: number;
|
||||
|
||||
@Column({
|
||||
type: DataType.JSON,
|
||||
allowNull: false,
|
||||
comment: '服药时间列表,格式:["08:00", "20:00"]',
|
||||
})
|
||||
declare medicationTimes: string[];
|
||||
|
||||
@Column({
|
||||
type: DataType.STRING(20),
|
||||
allowNull: false,
|
||||
defaultValue: RepeatPatternEnum.DAILY,
|
||||
comment: '重复模式',
|
||||
})
|
||||
declare repeatPattern: RepeatPatternEnum;
|
||||
|
||||
@Column({
|
||||
type: DataType.DATE,
|
||||
allowNull: false,
|
||||
comment: '开始日期(UTC时间)',
|
||||
})
|
||||
declare startDate: Date;
|
||||
|
||||
@Column({
|
||||
type: DataType.DATE,
|
||||
allowNull: true,
|
||||
comment: '结束日期(UTC时间)',
|
||||
})
|
||||
declare endDate: Date;
|
||||
|
||||
@Column({
|
||||
type: DataType.TEXT,
|
||||
allowNull: true,
|
||||
comment: '备注信息',
|
||||
})
|
||||
declare note: string;
|
||||
|
||||
@Column({
|
||||
type: DataType.BOOLEAN,
|
||||
allowNull: false,
|
||||
defaultValue: true,
|
||||
comment: '是否激活',
|
||||
})
|
||||
declare isActive: boolean;
|
||||
|
||||
@Column({
|
||||
type: DataType.DATE,
|
||||
defaultValue: DataType.NOW,
|
||||
comment: '创建时间',
|
||||
})
|
||||
declare createdAt: Date;
|
||||
|
||||
@Column({
|
||||
type: DataType.DATE,
|
||||
defaultValue: DataType.NOW,
|
||||
comment: '更新时间',
|
||||
})
|
||||
declare updatedAt: Date;
|
||||
|
||||
@Column({
|
||||
type: DataType.BOOLEAN,
|
||||
allowNull: false,
|
||||
defaultValue: false,
|
||||
comment: '软删除标记',
|
||||
})
|
||||
declare deleted: boolean;
|
||||
|
||||
// 关联关系
|
||||
@HasMany(() => MedicationRecord, 'medicationId')
|
||||
declare records: MedicationRecord[];
|
||||
}
|
||||
Reference in New Issue
Block a user