Bug #33832 | NOW()/SYSDATE(): Not as documented within stored routines | ||
---|---|---|---|
Submitted: | 12 Jan 2008 15:14 | Modified: | 5 Jun 2009 18:06 |
Reporter: | Paul DuBois | Email Updates: | |
Status: | Closed | Impact on me: | |
Category: | MySQL Server: Stored Routines | Severity: | S3 (Non-critical) |
Version: | 5.0 and up | OS: | Any |
Assigned to: | Paul DuBois | CPU Architecture: | Any |
[12 Jan 2008 15:14]
Paul DuBois
[12 Jan 2008 15:42]
MySQL Verification Team
Thank you for the bug report.
[12 Feb 2008 0:18]
Omer Barnir
Workaround: Set a local variable to the value of now() as the first line in the SP and use it throughout the SP to emulate the intended behavior of now().
[4 Jun 2009 8:08]
Jon Olav Hauglid
More research into the current behavior of NOW() and SYSDATE(): NOW() returns the time when the current statement started executing. SYSDATE() returns the time when it executes. SLEEP() inside statements affects the result from SYSTIME(), but not NOW(). SLEEP() between statements affects both. This is true for regular statements, statements inside a stored procedure, statements inside events and statements inside nested procedures. Example: DELIMITER $$; CREATE PROCEDURE p4(IN p_sys DATETIME, IN p_now DATETIME) BEGIN DO SLEEP(1); SELECT SYSDATE() - p_sys AS sys_psys, NOW() - p_now AS now_pnow, SLEEP(1) AS w1, SYSDATE() - p_sys AS sys_psys1, NOW() - p_now AS now_pnow1; END$$ CALL p4(SYSDATE(), NOW())$$ Result: sys_psys now_pnow w1 sys_psys1 now_pnow1 1.000000 1.000000 0 2.000000 1.000000 However, inside functions, NOW() returns the same time as in the statement from which the function was called. Example: CREATE FUNCTION f5_sys() RETURNS DATETIME BEGIN DO SLEEP(1); RETURN SYSDATE(); END$$ CREATE FUNCTION f6_now() RETURNS DATETIME BEGIN DO SLEEP(1); RETURN NOW(); END$$ SELECT SYSDATE() - f5_sys() AS sys_fsys, SLEEP(1) AS w1, SYSDATE() - f5_sys() AS sys_fsys1$$ SELECT NOW() - f6_now() AS now_fnow, SLEEP(1) AS w1, NOW() - f6_now() AS now_fnow1$$ Result: sys_fsys w1 sys_fsys1 -1.000000 0 -1.000000 now_fnow w1 now_fnow1 0.000000 0 0.000000
[4 Jun 2009 10:38]
Dmitry Lenev
Hello! Just to clarify. In stored functions and triggers (and also in stored procedures which are called from stored functions and triggers) NOW() returns time then execution of the top-level statement which invokes function or trigger was started. Such behaviour is required to be able safely replicate such statements in SBR mode. Stored procedures which are not called from triggers/stored functions are replicated in statement-by-statement fashion. So they don't need NOW() to be constant for the whole duration of routine. Therefore in such procedures NOW() returns time when particular statement in routine has started.
[4 Jun 2009 10:45]
Jon Olav Hauglid
From kostja: This works as intended. So update documentation to match current behavior.
[5 Jun 2009 18:06]
Paul DuBois
The documentation is incorrect. The difference between SYSDATE() and NOW() is not for stored routines and triggers, it is for stored *functions* and triggers. That means there is no effect for stored *procedures*. See also Bug#44996.
[2 Jun 2011 5:08]
Girish Padia
I guess this has been rectified in the newest release. The following query works perfect SELECT SYSDATE(),NOW(), SLEEP(10), NOW(),SYSDATE(); The result is sysdate() NOW() SLEEP(10) NOW() sysdate() ------------------- ------------------- --------- ------------------- ------------------- 2011-06-02 10:35:12 2011-06-02 10:35:12 0 2011-06-02 10:35:12 2011-06-02 10:35:22