数据库课程设计之采购与库存管理系统

1 系统需求分析

1.1 系统具体需求

1.2 系统业务流程分析

1.3.1 采购任务分配

1.3.2 采购询价

1.3 系统数据流图

1.3.1 顶层数据流图

1.3.2 零层数据流图

2 数据库设计

2.1 概念结构设计(ER图)

2.2 逻辑结构设计

2.2.1 表清单

2.2.2 表设计

3 数据库应用系统开发

3.1 表创建(表关系图)

3.2 索引创建(可以截图)

3.3 视图创建

3.4 触发器创建

4 功能模块设计

5 功能模块实现

5.1 采购任务分配

5.1.1 下达任务

5.1.2 撤销任务

5.2 采购询价

5.3采购合同编制

5.4 入库申请

5.5 库存汇总查询

5.6 领料申请

5.7 库存预警查询

5.8 python调用

    1. 系统具体需求

1)采购计划管理:由物料部门接受物料清单,结合库存和提前期的MRP计算,形成物料需求计划,然后对采购计划进行调整,审核后下发

  1. 采购管理:采购管理是采购任务分配,询价审价,采购合同签订和接受采购发票等采购活动的全过程
  2. 入库管理:由采购员填写入库申请,保管员对物资名称,规格,数量,质量等验收之后办理实收入库手续
  3. 出库管理:保管员根据各个部门提出的领料申请单,完成物资的实发工作

1.3 系统数据流图

1.3.1 顶层数据流图

1.3.2 零层数据流图

采购计划管理0层

库存管理0层图

2 数据库设计

2.1 概念结构设计ER图

在上述图中,部分对应关系解释如下:

  1. 员工与部门是一对多的关系,一个员工只能来自一个部门,但是一个部门可以拥有多名员工
  2. 合同与员工,任务单物资和供应商,合同被员工编写,由部门领导审核,合同涉及供应商编号,物资编号
  3. 入库,出库中,是由员工或者领料部门发起,和仓库之间对应

2.3 逻辑结构设计

2.3.1 表清单

实体名称

中文注释

Employee

员工信息表

Department(实体领料部门用的也是这个表)

部门信息表

Material

物资信息表

Warehouse

仓库信息表

Supply

供应商信息表

contract

合同信息表

Task

任务单

Enquiry

询价单

rk

入库单

ck

出库单

2.3.2 表设计

(1)Employee表

字段名

数据类型

长度

允许空

主键

说明

eID

int

10

no

yes

员工号

eName

varchar

50

no

no

员工姓名

dNo

varchar

30

no

no

部门编号

(2)Department表

字段名

数据类型

长度

允许空

主键

说明

dNo

int

10

no

yes

部门编号

dName

varchar

50

no

no

部门名称

(3)Material表

字段名

数据类型

长度

允许空

主键

说明

mID

int

10

no

yes

物资编号

mName

varchar

50

no

no

物资名称

mGg

varchar

30

no

no

物资规格

mXh

varchar

50

no

no

物资型号

jldw

varchar

50

no

no

计量单位

  1. Warehouse表
  2. Supply表

字段名

数据类型

长度

允许空

主键

说明

wID

int

10

no

yes

仓库编号

wName

varchar

50

no

no

仓库名称

字段名

数据类型

长度

允许空

主键

说明

sID

int

10

no

yes

供应商编号

sName

varchar

50

no

no

供应商名称

(6)Task表

字段名

数据类型

长度

允许空

主键

说明

Tasknumber

int

10

no

yes

任务单号

mID

int

     10

no

no

物资编号

Requiredquantity

Int

10

no

no

需求数量

Requiredtime

date

20

no

no

需求时间

Procurementtime

date

20

no

no

采购时间

Quantitypurchased

Int

10

no

no

采购数量

eID

int

10

no

no

采购员编号

(7)enquiry表

字段名

数据类型

长度

允许空

主键

说明

enquirynumber

int

10

no

yes

询价单号

mID

int

     10

no

no

物资编号

sID

int

10

no

no

供应商编号

Equantity

Int

10

no

no

购买数量

[unit price]

decimal(4, 1)

20

no

no

商品单价

Eexpense

decimal(5, 1)

10

no

no

总计花费

(8)store表

字段名

数据类型

长度

允许空

主键

说明

sID

int

10

no

yes

库存单号

mID

int

     10

no

no

物资编号

mName

Varchar(20)

20

no

no

物资名称

mDate

Date

10

no

no

库存所属月份

mQuantity

Int

20

no

no

库存数量

wID

int

10

no

no

仓库编号

(9)rk表

字段名

数据类型

长度

允许空

主键

说明

rID

int

10

no

yes

入库单号

mID

int

     10

no

no

物资编号

rApplyQuantity

Int

20

no

no

申请入库数量

rDate

Date

10

no

no

入库时间

rQuantity

Int

20

no

no

实际入库数量

sID

int

10

no

no

供应商编号

eIDBg

Int

10

No

No

保管员编号

eIDSq

Int

10

No

No

申请员编号

contractnumber

Int

10

No

No

合同单号

wID

int

10

no

no

仓库编号

(9)ck表

字段名

数据类型

长度

允许空

主键

说明

cID

int

10

no

yes

出库单号

mID

int

     10

no

no

物资编号

cApplyQuantity

Int

20

no

no

申请领料数量

cDate

Date

10

no

no

领料时间

cQuantity

Int

20

no

no

实际领料数量

Department

int

10

no

no

领料部门编号

eIDBg

Int

10

No

No

保管员编号

eIDSq

Int

10

No

No

申请员编号

contractnumber

Int

10

No

No

合同单号

wID

int

10

no

no

仓库编号

3 数据库应用系统开发

3.1 表创建(表关系图)

3.2 索引创建(可以截图)

索引名

代码

未使用索引

3.3 视图创建

视图名(作用)MaterialDemandList (创建物料需求清单视图)

CREATE VIEW MaterialDemandList AS
SELECT m.mID, m.mName, m.mGg, m.mXh, m.jldw,t.Requiredquantity, t.Requiredtime
FROM Meterial m
JOIN Task t ON m.mID = t.mID;

3.4 触发器创建

触发器名(作用)

tri__update3

入库单表中更新实收数量,对应更新库存表中该物资的库存

数量

create  trigger tri__update3
on rk
after update
as
begin
	if (update(rQuantity)) 
	begin
	    update store
		set mQuantity=(select sum(rQuantity) from rk r
		 WHERE r.mID = store.mID and
	     (substring(convert(varchar,rDate,112),1,6)=substring(convert(varchar,mDate,112),1,6)))
	 WHERE store.mID IN (SELECT DISTINCT mID FROM inserted);
	end
end

tri__updateck出库单中更新实发数量,更新对应物资的库存

create  trigger tri__updateck
on ck
after update
as
begin
	if (update(cQuantity)) 
	begin
	    update store
		SET mQuantity = mQuantity - (SELECT cQuantity FROM inserted) from
		ck c
		WHERE c.mID = store.mID and
	  substring(convert(varchar,cDate,112),1,6)=substring(convert(varchar,mDate,112),1,6)
	    and store.mID IN (SELECT DISTINCT mID FROM inserted)
	end
end

4 功能模块设计与实现

功能名称

模块名称

说明

采购计划管理

物料需求清单接收

通过调用存储过程,实现查询具体的物料需求

MRP量计算

通过调用存储过程,输入需求时间,从而得出具体的采购时间

MRP期计算

通过调用存储过程,输入需求数量,从而得出具体的采购数量

采购任务分配

采购任务下达

通过调用存储过程,实现将任务分配给员工

采购任务撤销

通过调用存储过程,实现将已经分配任务取消

采购询价

采购订单询价

对多家供应商的的商品在质量无差异的前提下,选择价格最低的一家

采购合同

采购合同编制

通过调用存储过程,将输入的合同内容录入合同中

入库申请

合同入库申请单编制

合同入库申请,物资信息储存在合同中,无需填写物资编号

零星入库申请单编制

零星入库申请,物资信息储存在物资单中,无需填写合同编号

库存汇总查询

仓库汇总查询

按照仓库,查询某一时间段内某物资的储存量

领料申请

限额领料申请单编制

限额领料申请,生产部门通过之前提交的物料需求单进行限额领料,采购部门将其所需要的物资按合同购置,物资的具体信息储存在合同单里

零星领料单申请单编制

零星领料申请,物资信息储存在物资单中,无需填写合同单号

库存预警

库存预警查询

通过存储过程,查询仓库中的物资数量是否在安全库存内,如果低于安全库存,则发出提醒

Python调用

Python调用存储过程

通过调用python实现功能的具体使用

4.1.1 物料需求接受

语句

CREATE PROCEDURE GetAllMaterialDemandList

AS

BEGIN

    SELECT *

    FROM MaterialDemandList;

END;

EXEC GetAllMaterialDemandList

执行结果

4.1.2MRP计算

语句

alter procedure MRP_caculating

@MID int,

@Requiredquantity int, --需求数量

@Requiredtime date --需求时间

as

declare @Safetystock int;--安全库存

declare @currentstock int;--目前可用库存

declare @purchaseday int;--采购提前期

declare @Quantitypurchased int ;--采购数量

declare @Procurementtime date;--采购时间

select @Safetystock=Safetystock ,@currentstock=mQuantity ,@purchaseday=purchaseday

from Meterial m  ,store s

where m.mID=s.mID and m.mID=@MID

--set @Quantitypurchased=@Requiredquantity-@currentstock+@Safetystock --采购数量MRP计算公式

--set @Procurementtime=@Requiredtime-@purchaseday--采购时间MRP计算公式

if (@Quantitypurchased<=0)--表示当前库存可用数量大于需求数量,无需采购,

 set @Quantitypurchased=0

else 

set @Quantitypurchased=@Requiredquantity-@currentstock+@Safetystock

set @Procurementtime=dateadd(day,-@purchaseday,@Requiredtime)

select @Requiredquantity as 需求数量 ,@Safetystock as 安全库存,

@currentstock as 目前可用库存,@Quantitypurchased as 采购数量,@Procurementtime as 采购日期

insert into Task (mID,Requiredquantity,Requiredtime,Procurementtime,Quantitypurchased )

values(@MID,@Requiredquantity,@Requiredtime,@Procurementtime,@Quantitypurchased)

执行结

4.2 采购任务分配

4.2.1 下达任务

语句

CREATE PROCEDURE up_PushTask

@streID int,

@strTaskID int

AS

UPDATE TASK

SET eID=@streID

WHERE Tasknumber=@strTaskID

--exec up_PushTask 826530,100003

执行结果

4.2.2 撤销任务

语句

alter PROCEDURE up_UndoTask  

@streID int,  

@strTaskID int  

AS   

    -- 判断任务是否已分配给员工  

    IF EXISTS (SELECT 1 FROM TASK WHERE Tasknumber = @strTaskID AND eID = @streID)   

        -- 撤销任务: 将eID设置为NULL,表示任务未分配  

        UPDATE Task  

        SET eID = NULL  

        WHERE Tasknumber = @strTaskID

exec up_UndoTask  826530 ,100003

执行结果

4.3 采购询价

4.3.1

语句

alter procedure up_enquiry

as

select 

top 1

enquirynumber,mID,e.sID,sName,min(Eexpense)from enquiry e,Suppy s

where e.sID=s.sID

group by enquirynumber,mID,e.sID,sName

order by min(Eexpense) asc

exec up_enquiry 

执行结果

4.4采购合同

4.4.1 采购合同编制

语句

alter procedure up_contract

@Cnumber int,

@Cdate date,

@eid int,

@sid int ,

@Tasknumber int

as

update contract

set signingdate=@Cdate,eID=@eid,sID=@sid,Tasknumber=@Tasknumber

where contractnumber=@Cnumber

select contractnumber 合同单号,signingdate 签订日期,eID 采购员编号,sID 供应商编号,Tasknumber 任务单号

from contract

exec up_contract  300001,'2023-11-16',816530,22224180,100002

执行结果

4.5入库申请

4.5.1 入库申请单编制

语句

alter  PROCEDURE up_rkapply  

    @type   VARCHAR(10),  

@rid    int,

    @mid   INT = NULL,  

    @rdate  DATE,  

    @eidsq  INT,  

    @eidbg   INT,  

    @wid     INT,  

    @Cnumber INT = NULL  

AS   

    IF @type = '合同入库'  --通过条件判断是合同入库还是零星入库

UPDATE rk

        SET rDate = @rdate, eIDSq = @eidsq, eIDBg = @eidbg, wID = @wid, contractnumber = @Cnumber

   where rID=@rid --合同入库则更新合同单号而不更新物资编号

    ELSE    

UPDATE rk

        SET rDate = @rdate, mID = @mid, eIDSq = @eidsq, eIDBg = @eidbg, wID = @wid

where rID=@rid  --零星入库则更新物资编号而不更新合同单号

SELECT @mid 物资编号, @rdate 入库日期, @eidsq 申请员编号, @eidbg 保管员编号, @wid 仓库编号, @Cnumber 合同单号  

 exec up_rkapply @type=合同入库,@rid=202319 ,@rdate='2023-01-11', 

 @eidsq  =826530,@eidbg=826531, @wid =4,@Cnumber=300001

执行结果

4.6库存汇总查询

4.6.1仓库汇总查询

语句

alter PROCEDURE GetWarehouseStorageSummary  

    @WarehouseID INT, -- 仓库ID  

    @StartDate DATE,  -- 开始日期  

    @EndDate DATE      -- 结束日期  

AS  

BEGIN  

    SELECT   

        w.wID,  

        s.mID ,

SUM(mQuantity)

        --(SELECT SUM(mQuantity) FROM store WHERE mDate BETWEEN @StartDate AND @EndDate) AS MaterialCount  

    FROM   

        Warehouse w  

        JOIN store s ON w.wID = s.wID

    WHERE   

        w.wID = @WarehouseID AND s.mDate BETWEEN @StartDate AND @EndDate  

    GROUP BY   

         w.wID, s.wID,s.mID  

END;

 exec GetWarehouseStorageSummary  4,'2023-01-01','2023-02-01' 

执行结果

4.7领料申请

4.7.1限额领料单和零星领料单的编制

语句

create  PROCEDURE up_ckapply  

    @type   VARCHAR(10),  

@cid    int,

    @mid    INT = NULL,  

    @cdate  DATE,  

    @eidsq  INT,  

    @eidbg   INT,  

    @wid     INT,  

@department varchar(10),

    @Cnumber INT = NULL  

AS   

    IF @type = '限额领料'  --通过条件判断是生产领料还是零星领料

UPDATE ck              --生产领料也等于限额领料,生产部门通过之前提交的物料需求单进行限额领料

        SET cDate = @cdate, eIDSq = @eidsq, eIDBg = @eidbg, wID = @wid, department =@department,contractnumber = @Cnumber

   where cID=@cid --生产领料则更新合同单号而不更新物资编号

    ELSE    

UPDATE ck

        SET cDate = @cdate, mID = @mid, eIDSq = @eidsq, eIDBg = @eidbg, wID = @wid ,department =@department

where cID=@cid  --零星领料则更新物资编号而不更新合同单号

SELECT @mid 物资编号, @cdate 出库日期, @eidsq 申请员编号, @eidbg 保管员编号, @wid 仓库编号,@department 部门编号, @Cnumber 合同单号  

 exec up_ckapply @type=限额领料,@cid=20230013 ,@cdate='2023-01-11', 

 @eidsq  =826530,@eidbg=826531, @wid =4,@department=3, @Cnumber=300001

执行结果

4.8库存预警

4.8.1库存预警查询

语句

alter procedure warehouse_warning7

@ProductName VARCHAR(50)

@Warehousename varchar(50)

 @Warningnumber  int = 50

as

 declare @StockQuantity int;  

SELECT

top 1

w.wName=@Warehousename, m.mName=@ProductName, @StockQuantity=s.mQuantity

FROM Warehouse w

join (select  r.mID ,r.wID from rk r) R

on R.wID=w.wID

join store s on s.mid= R.mID

join Meterial m on m.mID=s.mID

--group by w.wID, w.wName, m.mName

order by s.mQuantity

--select @Warehousename, @ProductName,@StockQuantity

IF @StockQuantity < @Warningnumber

    BEGIN

        PRINT '该仓库:'+@Warehousename+ '安全库存不足,物资:' +

@ProductName + ',库存数量:' +

CONVERT(VARCHAR(50), @StockQuantity ) + ',请尽快补货。'; 

    END

exec  warehouse_warning7 50

执行结果

4.9python调用

语句

import pyodbc

# 连接数据库

count_employy = pyodbc.connect('Driver={SQL Server};Server=杨树杰;Database=wzxt;UID=sa;PWD=123123')

if count_employy:

    print("连接成功")

while True:

    x = input("请选择要进行的操作:")

    cursor = count_employy.cursor()  # 创建游标

    if x == '采购计划管理':

        print("先进行物料需求接收后进行MRP计算")

        strsql = 'GetAllMaterialDemandList'  # 物料需求接受对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

        strsql = 'MRP_caculating'  # MRP计算对应的存储名称  

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    elif x == '采购任务下达':

        strsql = 'up_PushTask'  # 采购任务下达对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    elif x == '采购任务撤销':

        strsql = 'up_UndoTask'  # 采购任务撤销对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    elif x == '采购询价':

        strsql = 'up_enquiry'  # 采购询价对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    elif x == '采购合同编制':

        strsql = 'up_contract'  # 采购合同编制对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    elif x == '入库申请':

        strsql = 'up_rkapply'  # 入库申请对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    elif x == '库存汇总查询':

        strsql = 'GetWarehouseStorageSummary'  # 库存汇总查询对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    elif x == '领料申请':

        strsql = 'up_ckapply'  # 领料申请对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    elif x == '库存预警':

        strsql = 'warehouse_warning7'  # 库存预警对应的存储名称

        cursor.execute(strsql)

        row = cursor.fetchone()

        # 返回结果

        while row:

            print(row)

            row = cursor.fetchone()

    else:

        print("不存在对应操作请重新输入")

        break

    cursor.close()  # 关闭游标

执行结果

  1. 结论与体会

在做课设的过程中我们的主要亮点是添加了MRP计算和库存预警,MRP计算可以通过输入需求数量和需求时间结合安全库存和采购提前期计算出实际的采购数量与采购时间,然后添加到任务单里进行分配,另外一个功能库存预警,编写了两个触发器,在出库表和入库表里更新实发数量和实收数量时更新库存表,如果库存表中的数量小于安全库存,则发出警告,具体的体会如下:这次设计让我深刻理解了数据库的实质和重要性。在日常生活和工作中,数据无处不在,而数据库则是对这些数据进行有效管理和利用的重要工具。通过这次设计,我学会了如何从零开始构建一个完整的数据库系统,包括表结构定义、数据插入、查询、更新以及删除等操作。我明白了每一项操作背后的逻辑和原理,也感受到了数据规范化和优化的重要性。在实践过程中,我遇到了很多挑战。例如,在设计复杂的查询语句时,我曾一度感到困惑。但通过反复思考和实践,我逐渐掌握了如何运用SQL语言来高效地检索数据。此外,在处理大量数据时,我意识到了性能优化和安全性的重要性。这让我对数据库的性能调优和安全防护有了更深入的了解。与此同时,我也体会到了团队协作的力量。在课程设计中,我和我的团队成员共同探讨、解决问题,互相学习、共同进步。我们分享彼此的经验和想法,相互支持和鼓励。这种团队氛围让我倍感温暖,也让我明白了沟通与合作在项目中的关键作用。回顾整个过程,我深知自己在数据库领域还有很多需要学习和提高的地方。但这次课程设计为我提供了一个宝贵的实践机会,让我对数据库有了更深入的认识和理解。我相信,这次经历将对我未来的学习和职业生涯产生积极的影响。

  • 28
    点赞
  • 29
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值