Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/58.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Mysql 构建管理审批系统的最佳实践_Mysql_Database Design_Admin_Change Management - Fatal编程技术网

Mysql 构建管理审批系统的最佳实践

Mysql 构建管理审批系统的最佳实践,mysql,database-design,admin,change-management,Mysql,Database Design,Admin,Change Management,应该有一个管理面板的子系统,不同的用户可以管理他们的产品,但是每次更改都应该在影响主产品表之前得到管理员的批准。 有三个主表: 产品:存储最终批准并在整个系统中使用的产品 Changes_versions:一个与产品表有一对多关系的表,表示每个更改版本由谁提交、何时提交、是否被管理员批准/拒绝或仍处于挂起状态。表结构如下: CREATE TABLE `changes_versions` ( `xid` int(11) unsigned NOT NULL AUTO_INCREMENT, `

应该有一个管理面板的子系统,不同的用户可以管理他们的产品,但是每次更改都应该在影响主产品表之前得到管理员的批准。 有三个主表:

  • 产品:存储最终批准并在整个系统中使用的产品
  • Changes_versions:一个与产品表有一对多关系的表,表示每个更改版本由谁提交、何时提交、是否被管理员批准/拒绝或仍处于挂起状态。表结构如下:

    CREATE TABLE `changes_versions` (
      `xid` int(11) unsigned NOT NULL AUTO_INCREMENT,
      `xcreated_date` datetime DEFAULT NULL,
      `xupdated_date` timestamp NULL DEFAULT NULL,
      `xversion` int(11) DEFAULT NULL,
      `xobject_id` int(11) DEFAULT NULL,
      `xobject_type` varchar(255) DEFAULT NULL,
      `xstate` enum('PENDING','ACCEPTED','REJECTED') DEFAULT 'PENDING',
      PRIMARY KEY (`xid`)
    ) ENGINE=InnoDB AUTO_INCREMENT=165 DEFAULT CHARSET=utf8
    
    CREATE TABLE `changes` (
      `xid` int(11) unsigned NOT NULL AUTO_INCREMENT,
      `xcreated_date` datetime DEFAULT NULL,
      `xcreated_by` varchar(255) DEFAULT NULL,
      `xupdated_date` timestamp NULL DEFAULT NULL,
      `xupdated_by` varchar(255) DEFAULT NULL,
      `xversion_id` int(11) DEFAULT NULL,
      `xcolumn_name` varchar(255) DEFAULT NULL,
      `xcolumn_value` varchar(255) DEFAULT NULL,
      `xstate` enum('PENDING','ACCEPTED','REJECTED') DEFAULT 'PENDING',
      `xadmin_review` text,
      PRIMARY KEY (`xid`)
    ) ENGINE=InnoDB AUTO_INCREMENT=764 DEFAULT CHARSET=utf8
    
  • 变更:一个与变更有一对多关系的表,该表保留主表(这里我指的是产品表)的每一列变更记录,通过管理员批准变更版本记录,其相关变更记录将放置在主表列中。表结构如下:

    CREATE TABLE `changes_versions` (
      `xid` int(11) unsigned NOT NULL AUTO_INCREMENT,
      `xcreated_date` datetime DEFAULT NULL,
      `xupdated_date` timestamp NULL DEFAULT NULL,
      `xversion` int(11) DEFAULT NULL,
      `xobject_id` int(11) DEFAULT NULL,
      `xobject_type` varchar(255) DEFAULT NULL,
      `xstate` enum('PENDING','ACCEPTED','REJECTED') DEFAULT 'PENDING',
      PRIMARY KEY (`xid`)
    ) ENGINE=InnoDB AUTO_INCREMENT=165 DEFAULT CHARSET=utf8
    
    CREATE TABLE `changes` (
      `xid` int(11) unsigned NOT NULL AUTO_INCREMENT,
      `xcreated_date` datetime DEFAULT NULL,
      `xcreated_by` varchar(255) DEFAULT NULL,
      `xupdated_date` timestamp NULL DEFAULT NULL,
      `xupdated_by` varchar(255) DEFAULT NULL,
      `xversion_id` int(11) DEFAULT NULL,
      `xcolumn_name` varchar(255) DEFAULT NULL,
      `xcolumn_value` varchar(255) DEFAULT NULL,
      `xstate` enum('PENDING','ACCEPTED','REJECTED') DEFAULT 'PENDING',
      `xadmin_review` text,
      PRIMARY KEY (`xid`)
    ) ENGINE=InnoDB AUTO_INCREMENT=764 DEFAULT CHARSET=utf8
    
  • 使用我处理的这个系统和表模式来处理记录更改、用户获取记录列表,如果用户有任何挂起的状态更改版本,系统将提取其相关的更改记录,并将它们放置在获取的产品行的右列中(临时仅用于显示),所以,即使用户有任何挂起的状态更改,他/她也可以在其面板(不是主系统,只有其面板)中看到其更改

    问题是插入新记录时,我可以创建更改版本记录并将所有用户数据保存到指向新更改版本记录的更改表中,但更改版本记录未连接到任何产品记录,因为没有记录

    注意,基于系统的复杂性和当前的稳定性,我不想在product表中添加任何列来表示这是一个临时记录

    因此,我需要一种策略来处理这样的问题:当我在用户面板中对产品进行分页并用最后一次挂起的更改填充它们时,插入的记录中没有产品记录可以用更改填充,因此用户无法看到他/她以前插入的产品



    我还应该注意到,对于这个问题,这个表结构的某些内容可能看起来很复杂。这个结构很复杂,因为更改和更改表保存并显示了许多具有不同结构的表的历史和管理审批流程。

    我认为SQL View在这里很方便,更改表名并添加一个标记字段,该字段标记临时行,然后创建一个名为Product的视图,并在视图中排除该字段和该字段标记的行,这样您的原始表(现在已转换为视图)将保持不变(如果我错了,请纠正我)

    系统中有不同的项目(如产品),每个项目类型有一个(InnoDB)表。 每个项目表都有一个自动增量列(如
    id
    )。 您有一个项目版本表(
    changes\u versions
    )来存储特定项目的不同版本。 该项由列标识

    • 引用表的类型(如“产品”)
    • xobject\u id
      这是一个引用上表主键的“多态外键”
    问题是:当用户创建新项时,不应将其插入到items表中, 但是您需要一个引用来存储在
    xobject\u id
    列中

    一种可能的解决方案是:通过在事务中插入和删除一行来“保留”ID

    例如:

    start transaction;
    insert into products(column_1, column_2) values ('value_1', 'value_2');
    delete from products where id = last_insert_id();
    select last_insert_id();
    commit;
    
    您将得到:

    • 插入的行对于其他用户将永远不可见,因为它在同一事务中被删除
    • last\u insert\u id()
      仍将从删除的行返回自动生成的id
    • 该ID将被“烧掉”,因此引擎将不再生成该ID
    • 当管理员接受该项目时,您仍然可以手动插入该ID
    • 不需要更改数据库模式

    演示:

    解决方案是按说明创建所有表,当用户将产品创建到
    changes\u version
    表中时,应该有一个mysql事件,定期检查
    product
    表中的每个记录,并将其与
    changes\u version
    表匹配。如果在其中发现任何更改或新插入
    已更改\u版本
    表,应相应插入/更新
    产品

    修订后的解决方案:

    您可以在用户登录时将用户记录从
    changes\u version
    插入产品表,并在注销时将其删除。这适用于尚未移动到
    product
    表中的产品,您可以通过查询进行检查


    如果您有前端源代码,那么您可以仅向用户显示
    更改\u version
    记录,并在其获得批准时通过触发器将其移动到
    产品
    表中。

    如果版本表中包含来自产品的所有列以及授权列,是否会更简单更改是通过将主字段从版本表复制到产品来完成的。对于新记录,Version.productID将为空,但可以在创建产品记录后填写。@NigelRen我也应该解释一下,版本控制系统的用法不仅仅适用于产品表。它还适用于具有不同t结构和列,因此您的方式不适用于我的情况。是否可以更改一个新项目(产品),该项目(产品)不在原始表(
    products
    )中,因为它从未被接受过?@PaulSpiegel我不完全理解您的问题。在我的系统中,我希望该用户创建一行(假设管理员尚未批准)可以编辑该行too@ArefAnafgeh我的问题回答得很好。我问了它,因为如果不是这样的话,您可以将
    NULL
    写入
    xobject\u id
    并在