获取基于日期范围的工作计划模板

问题描述 投票:0回答:1

我的 MySQL 数据库中有一个表,其中包含我的工作人员的日程模板,然后在日程规划器中使用这些模板。当员工的雇佣合同发生修改时,新的时间表会添加一组新的记录。

到目前为止我有以下疑问:

SELECT
    ehp.id_pers_empleado employee_id,
    ehp.diasem weekday,
    ehp.hora_inicio `from`,
    ehp.hora_fin `to`,
    ehp.validez `starts`,
    TIMESTAMPDIFF( MINUTE, ehp.hora_inicio, ehp.hora_fin ) / 60 worked
FROM
    empleados_horarios_predeterminados ehp 
WHERE
    id_pers_empleado = 476 
ORDER BY
    `starts`,
    weekday 

该查询返回以下字段:

类型 描述
员工_id int 员工ID
工作日 int 1(星期一)至7(星期日)
来自 时间 轮班开始时间
时间 轮班结束时间
开始 日期 该记录生效的日期
小时 漂浮 员工的工作时间(以节省时间)

这样我得到的记录如下:

员工_id 工作日 来自 开始 工作了
00000476 1 09:00:00 14:00:00 2024-04-01 5.0000
00000476 2 09:00:00 14:00:00 2024-04-01 5.0000
00000476 3 09:00:00 14:00:00 2024-04-01 5.0000
00000476 4 09:00:00 14:00:00 2024-04-01 5.0000
00000476 5 09:00:00 14:00:00 2024-04-01 5.0000
00000476 1 07:00:00 15:30:00 2024-05-01 8.5000
00000476 2 07:00:00 15:00:00 2024-05-01 8.0000
00000476 3 07:00:00 15:00:00 2024-05-01 8.0000
00000476 4 07:00:00 15:00:00 2024-05-01 8.0000
00000476 5 07:00:00 15:00:00 2024-05-01 8.0000

我需要知道员工在特定日期范围内的工作安排。

例如,如果我查询从 4/29/2024 到 5/5/2024 的一周,我期望收到:

  • 星期一 04/29 → 于 04/01/2024 开始的时间表的第 1 周
  • 星期二 04/30 → 2024 年 4 月 1 日开始的日程的第 2 周
  • 星期三 05/01 → 2024 年 5 月 1 日开始的日程表的第 3 周
  • 05/02 星期四 → 2024 年 5 月 1 日开始的日程表的第 4 周
  • 星期五 05/03 → 2024 年 5 月 1 日开始的日程表的第 5 日

即以下一组记录:

员工_id 日期 来自 开始 工作了
00000476 2024-04-29 09:00:00 14:00:00 2024-04-01 5.0000
00000476 2024-04-30 09:00:00 14:00:00 2024-04-01 5.0000
00000476 2024-05-01 07:00:00 15:00:00 2024-05-01 8.0000
00000476 2024-05-02 07:00:00 15:00:00 2024-05-01 8.0000
00000476 2024-05-03 07:00:00 15:00:00 2024-05-01 8.0000

通过这些数据,我想知道该员工该周工作了多少小时,或者自动创建未来几周的时间表。

我一整天都在绞尽脑汁试图找到一种方法使其成为可能,但我尝试的一切都没有给出预期的结果。

最后一次尝试是:

SELECT
    * 
FROM (
    SELECT
        ehp.id_pers_empleado AS employee_id,
        ehp.diasem AS weekday,
        ehp.hora_inicio AS `from`,
        ehp.hora_fin AS `to`,
        ehp.validez AS `starts`,
        TIMESTAMPDIFF( MINUTE, ehp.hora_inicio, ehp.hora_fin ) / 60 AS worked,
        DATE_ADD( "2024-04-29", INTERVAL diasem - 1 DAY ) effective_day 
    FROM
        empleados_horarios_predeterminados ehp 
    WHERE
        id_pers_empleado = 476 
    ORDER BY
        STARTS,
        weekday 
) q1 
WHERE
    effective_day >= q1.`starts` 
    AND STARTS <= "2024-05-01" 
GROUP BY
    weekday

这为我一直在谈论的具体案例提供了正确的结果集,但由于其他员工有超过 2 个时间表或在其他日期范围内,因此失败。

sql mysql
1个回答
0
投票

您可以使用递归 CTE 创建日期系列横向派生表以获得正确的时间表:

WITH RECURSIVE date_range (dt) AS (
    SELECT '2024-04-29' -- start date
    UNION ALL
    SELECT dt + INTERVAL 1 DAY FROM date_range WHERE dt < '2024-05-03' -- end date
)
SELECT *
FROM date_range dr
JOIN LATERAL (
    SELECT *, (TIME_TO_SEC(hora_fin) - TIME_TO_SEC(hora_inicio)) / 3600 AS worked
    FROM empleados_horarios_predeterminados
    WHERE id_pers_empleado = 476
    AND validez <= dr.dt
    AND WEEKDAY(dr.dt) + 1 = diasem
    ORDER BY validez DESC
    LIMIT 1
) ehp;

这是一个db<>小提琴

© www.soinside.com 2019 - 2024. All rights reserved.