【问题标题】:how to limit data from dates passed in mysql stored procedure如何限制mysql存储过程中传递的日期数据
【发布时间】:2017-07-14 16:02:47
【问题描述】:

已设置存储过程,因此用户可以使用任何日期调用它。我希望能够将过去的日期限制为两个月。

现在,当用户在未选择任何日期的情况下调用报表时,报表服务器会因为数据过多而崩溃。如果经过的日期超过 2 个月,我希望能够限制行数。

    DELIMITER ;;
    DROP PROCEDURE IF EXISTS rpt_missing_payroll_files_report_test;;
    CREATE PROCEDURE `rpt_missing_payroll_files_report_test`(
      IN BEGIN_DATE VARCHAR(255),
      IN END_DATE VARCHAR(255)
    )
    BEGIN

    SELECT c.id,
           c.name,
           ip.name AS icp_name,
           s.name AS country_name,
           sc.name AS pm_name,
           pc.frequency,
           pc.check_date AS check_date,
           pc.transmit_date,
           IFNULL(ps.updated_at, ph.updated_at) AS submit_date,
           cpp.created_at AS date_received,
           ifnull(cpp.import_filename,'N/A') AS import_filename,
           CASE WHEN cpp.created_at IS NOT NULL THEN 1 END AS date_received_sum,
           CASE WHEN cpp.success = 1 THEN 1 END AS file_successsum,
           DATEDIFF(pc.check_date,cpp.created_at) AS date_diff,
           DATE_FORMAT(BEGIN_DATE,'%m/%d/%Y') AS BeginDate,
           DATE_FORMAT(END_DATE,'%m/%d/%Y') AS EndDate
    FROM co_payroll_calendars pc
    inner join co_infos c on pc.co_info_id = c.id                                                                                                                               
    inner join icp_countries icp on c.icp_country_id = icp.id
    INNER JOIN sys_countries s ON icp.sys_country_id = s.id
    INNER JOIN icp_infos ip ON ip.id = icp.icp_info_id
    LEFT OUTER JOIN co_payroll_entry_setups ps ON pc.id = ps.co_payroll_calendar_id                                                   
    LEFT OUTER JOIN co_payroll_entry_setup_histories ph ON pc.id = ph.co_payroll_calendar_id                                
    LEFT OUTER JOIN co_payroll_processes cpp ON cpp.check_date >= (pc.check_date - INTERVAL 10 DAY ) AND cpp.co_info_id = c.id
    LEFT OUTER JOIN sys_csrs sc ON c.sys_csr_id = sc.id
    -- below is the part i probably need to change
    WHERE  (ifnull(BEGIN_DATE,'') = ''
           OR pc.check_date >= BEGIN_DATE)
      AND (ifnull(END_DATE,'') = ''
           OR pc.check_date <= END_DATE)
    GROUP BY id,
             check_date
    ORDER BY country_name, check_date DESC, c.id;

    END;;
    DELIMITER ;

以下应该是允许的

CALL rpt_missing_payroll_files_report_test('2017-06-01','2017-07-01')

以下内容不应被允许或限制在一定数量的行中

CALL rpt_missing_payroll_files_report_test('2016-01-01','2017-07-01')

【问题讨论】:

  • 注意日期应该是DATE类型,而不是任意的VARCHAR字段。

标签: mysql stored-procedures parameter-passing limit pentaho-report-designer


【解决方案1】:

将参数设置为正确的类型(即,使用 DATE,而不是 VARCHAR)。

你也应该检查一下:

LEFT OUTER JOIN co_payroll_processes cpp 
ON cpp.check_date >= (pc.check_date - INTERVAL 10 DAY ) 
AND cpp.co_info_id = c.id

请注意,不等式将选择所有具有匹配 id 且日期晚于 (pc.check_date - INTERVAL 10 DAY ) 的行。这可能很多,也可能不多,具体取决于您的架构。您应该在没有 GROUP BY 和 ORDER BY 的情况下测试查询,并检查它返回的确切内容。如果您发现很多重复项,那么您可以通过使用更好的 JOIN 条件来加快查询速度。

现在,关于您的主要问题,答案很简单:将其添加到您的过程中

IF END_DATE > (BEGIN_DATE + INTERVAL 2 MONTH) THEN
    raise an error
ELSE
    your huge SELECT
END IF

这很简单。这是在 mysql 存储过程中raise an error 的方法(方法取决于您的版本)。

您也可以简单地执行“SELECT 'your message here'”,消息字符串将返回给客户端(然后可能会崩溃,因为它需要一组特定的列,所以最好引发错误)。

【讨论】:

  • 一个问题。如果我这样做,我无法在 pentaho(报告软件)中调用 proc,这就是我如何调用报告 {call rpt_missing_payroll_files_report(${Begin_Date},${End_Date},${Country},${is_submitted}, ${file_success})} 如果我这样做,唯一显示的字段是错误消息
  • 是的,您必须找到一种方法将错误传达给您的报告软件(我从未使用过这个,所以在这里无法提供帮助)。
  • 有没有办法将所有字段显示为空白和错误?而不是只在 mysql>? 中显示 1 错误字段
猜你喜欢
  • 2014-07-27
  • 2017-04-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-06-23
  • 1970-01-01
  • 2013-02-24
  • 2021-11-15
相关资源
最近更新 更多