当没有记录进入oracle时显示特定的消息

时间:2015-04-14 08:15:09

标签: sql oracle

这是我的Oracle查询,它根据日期差异应为一个月的日期获取记录:

  select *
   from pbxhbl.HBL_TRANSACTIONS  
  where dat_creation between '10-apr-2013' and '10-jun-2013' 
    and MONTHS_BETWEEN('10-jun-2013','10-apr-2013') = 1

我的问题是,当差异超过一个时,我想要显示一条消息:

  

'日期持续时间应为一个月

2 个答案:

答案 0 :(得分:0)

  

MONTHS_BETWEEN(' 10君-2013',' 10-APR-2013&#39)

首先,'10-jun-2013'不是 DATE ,而是 STRING 。 Oracle将进行隐式数据类型转换。请避免这种情况,并始终使用 TO_DATE 将字符串显式转换为日期。

其次,您发布的两个日期之间的月份永远不会为1 将始终为2

SQL> SELECT MONTHS_BETWEEN(to_date('10-jun-2013','dd-mon-yyyy'),to_date('10-apr-2013','dd-mon-yyyy')) dt
  2  FROM dual;

        DT
----------
         2

SQL>

因此,理想情况下,您的查询将始终不返回任何行

SQL> SELECT *
  2  FROM dual
  3  WHERE MONTHS_BETWEEN(to_date('10-jun-2013','dd-mon-yyyy'),to_date('10-apr-2013','dd-mon-yyyy')) =1;

no rows selected

SQL>

回到你的问题,

您可以使用 CASE 表达式。

但是,如果您要过滤掉行,那么您将无法显示任何内容。因此,请删除过滤器,以便每当MONTHS_BETWEEN的值大于1时,您都可以返回该消息。

例如,

SQL> WITH DATA AS(
  2  SELECT to_date('01-03-2015','DD-MM-YYYY') dt1, to_date('01-04-2015','DD-MM-YYYY') dt2 FROM dual UNION ALL
  3  SELECT to_date('01-03-2015','DD-MM-YYYY') dt1, to_date('10-04-2015','DD-MM-YYYY') dt2 FROM dual UNION ALL
  4  SELECT to_date('01-03-2015','DD-MM-YYYY') dt1, to_date('01-05-2015','DD-MM-YYYY') dt2 FROM dual
  5  )
  6  SELECT DT1,
  7    DT2,
  8    CASE
  9      WHEN months_between(dt2, dt1) >1
 10      THEN 'date duration should be one month'
 11      ELSE 'OK'
 12    END MESSAGE
 13  FROM DATA;

DT1       DT2       MESSAGE
--------- --------- ---------------------------------
01-MAR-15 01-APR-15 OK
01-MAR-15 10-APR-15 date duration should be one month
01-MAR-15 01-MAY-15 date duration should be one month

SQL>

答案 1 :(得分:0)

您需要在功能内完成所需。

创建一个函数,它将两个参数作为输入(date, date),并作为输出返回表类型的记录。

在函数内部,在将查询传递给输出之前,插入一个条件控制结构,如CASEIF,以检查给定日期是否符合您的条件。如果是,只需将查询传递给结果,如果没有(假设您希望有人在应用程序中看到它),则返回一个查询,该查询与您通常返回的记录一样,并将消息包含在列中的一列中。休息应该保持NULL

对于上述情况,我认为提出错误不是你真正需要的。

伪代码:

CREATE FUNCTION check_dates_for_hbl_transactions(date, date)
RETURNS record
AS $function$
BEGIN
IF ( MONTHS_BETWEEN( $1 - $2 ) > 1 )
THEN RETURN QUERY SELECT 'Date duration should be one month at max'::text, NULL::bigint, ...
ELSE
RETURN QUERY SELECT * FROM HBL_TRANSACTIONS WHERE dat_creation BETWEEN $1 AND $2
END IF;
END
$function$

重要提示:我写'message'::text, NULL::bigint, ...的原因是为了表明您的select语句必须与返回的集匹配(在这种情况下,表{{1}中的所有列及其类型})。

另外,请考虑为日期$ 2添加额外支票,使其大于日期$ 1参数。

旁注:考虑返回rowtype以使其更容易。我不喜欢这种方法,因为在行类型被更改的情况下它容易出错。我宁愿让失败的功能和手动检查原因,而不是像往常一样正常通过错误的值。