mysql between 2 dates does not working with 2 different months - mysql

Hello i need expert advice for my mysql query
I'm trying to filter values between 2 months
If start day lower then end day of different months all working well
But if i try higher day value on start return none
this is working code
SELECT id, teslim_tarihi AS tarih, toplam, marka, model, malzeme
FROM ariza
WHERE durum = '7' AND (teslim_tarihi BETWEEN '01-02-2018 00:00' AND '01-03-2018 23:59')
ORDER BY tarih DESC
Not working at all
SELECT id,teslim_tarihi as tarih ,toplam,marka,model,malzeme
FROM ariza
WHERE durum = '7' AND (teslim_tarihi BETWEEN '14-02-2018 00:00' AND '01-03-2018 23:59')
ORDER BY tarih DESC
date format dd-mm-yyyy H:i

As has been suggested by #stackFan, it really does make considerable sense to stick with mysql's default date and time formats. However, for whatever reason, you seem to be stuck with a different format so I'll attempt to work with that.
Your current query isn't working in your second example because mysql doesn't recognise these as dates and a strings starting '14-02-2018' is greater than another string starting '01-03-2018'. e.g.
SELECT '14-02-2018' > '01-03-2018';
+-----------------------------+
| '14-02-2018' > '01-03-2018' |
+-----------------------------+
| 1 |
+-----------------------------+
The values when using BETWEEN ... AND have to have the min value first and the max value Documentation, so in your second example the comparison is the wrong way round because '14-02-2018' is greater than '01-03-2018', hence no rows returned.
You didn't answer the query about the data type of your column teslim_tarihi which would have made answering your query simpler. I'll assume it is a DATETIME or TIMESTAMP. Your comparison should be made against something that mysql knows to be a date or recognises as a date and that means getting the dates into YYYY-MM-DD or YY-MM-DD format. Mysql will helpfully cast values to the appropriate type if the format is one it recognises. e.g.
SELECT DATE '2018-02-14' < '2018-03-01';
+-----------------------------------+
| DATE '2018-02-14' < '2018-03-01' |
+-----------------------------------+
| 1 |
+-----------------------------------+
You should be able to get the query working by turning your strings into dates in the following manner.
SELECT DATE '2018-03-01'
BETWEEN STR_TO_DATE('14-02-2018 00:00', '%d-%m-%Y %H:%i')
AND STR_TO_DATE('01-04-2018 23:59','%d-%m-%Y %H:%i') 'between dates';
+---------------+
| between dates |
+---------------+
| 1 |
+---------------+
If your column teslim_tarihi is a VARCHAR, then convert that in the same manner to get the query to work.

As per the documentation the default format of date in MySQL is YYYY-MM-DD. Can you try using this query instead?
SELECT id,teslim_tarihi as tarih ,toplam,marka,model,malzeme
FROM ariza
WHERE durum = '7' AND (teslim_tarihi BETWEEN '2018-02-14 00:00:00' AND '2018-03-01 23:59:59')
ORDER BY tarih DESC

Related

Possibly Mysql 5.6.20 bug. Date - now()?

date_newOrd, now(), date_newOrd-now() AS `time`
this is my query. date_newOrd is type date. I try to calculate the time remaining for next arrival of order. I better show you the screenshot:
the result is doesn't make any sense. What am i supposed to do>
You cannot subtract dates like that:
mysql> select '2015-06-01 18:20:03' - now();
+-------------------------------+
| '2015-06-01 18:20:03' - now() |
+-------------------------------+
| -20150602073525 |
+-------------------------------+
While that may look (vaguely) like a date, it's really an integer, and can't be used for further date math without extra processing.
You have to use datediff() or timediff():
mysql> select timediff('2015-06-01 18:20:03', now()) as td, datediff('2015-06-01 18:20:03', now()) as dd;
+-----------+------+
| td | dd |
+-----------+------+
| -13:37:47 | -1 |
+-----------+------+
note that datediff deals only with DATES, and timediff deals with datetime values.
When you do a subtraction, MySQL is going to evaluate NOW() in a numeric context, it returns a numeric value.
SELECT NOW()+0
20150602135210.000000
So, your statement is doing a subtraction of numbers, not doing a DATE calculation.
Some possibilities:
You could convert the datetime values into unix_timestamp values, (UNIX_TIMESTMAP() function) and then do a subtraction of those to get a difference in integer seconds.
The DATEDIFF() function would get you a difference in integer days. (That operates only on the date portion, it ignores the time... so that probably doesn't give you the resolution you are looking for.)
The TIMESTAMPDIFF() and TIMEDIFF() functions are also available. (The TIMEDIFF functions returns a TIME datatype value; the maximum value of that datatype is 838:59:59, so that's limited to just under 35 days elapsed).
For example:
SELECT UNIX_TIMESTAMP('2015-06-03') - UNIX_TIMESTAMP(NOW()) AS secs
secs
-------
35856

DATETIME comparisons?

I'm trying to switch from using UNIX timestamps to DATETIME columns in MySQL and am having a little trouble finding the correct way to make comparisons between dates.
I tried using the + and - operators to compare two DATETIMEs and the results don't make any sense to me.
For example:
1.
SELECT UTC_TIMESTAMP(), UTC_TIMESTAMP() - INTERVAL 1 HOUR
Outputs
2014-07-06 19:19:13 | 2014-07-06 18:19:13
These
SELECT UTC_TIMESTAMP() - DATE_SUB(UTC_TIMESTAMP(), INTERVAL 1 HOUR)
SELECT UTC_TIMESTAMP() - (UTC_TIMESTAMP() - INTERVAL 1 HOUR)
Both output 10000. This number doesn't make sense to me, but then it gets more confusing as this:
SELECT UTC_TIMESTAMP()-DATE_SUB(UTC_TIMESTAMP(), INTERVAL 1 SECOND)
Outputs 1. Why is that? What does that number represent?
2.
The manual page for date and time functions shows DATE_ADD() and DATE_SUB() can be used to add and subtract intervals from dates, but I don't see any functions in the manual that correspond to the great than and less than operators, so how would I check to see if the current date is greater than some other date?
I tried using the < and > operators and they seem to work, but I can't seem to find anything on this in the manual and want to make sure it's OK to use these operators like this:
SELECT UTC_TIMESTAMP() > DATE_SUB(UTC_TIMESTAMP(), INTERVAL 1 HOUR)
Can anyone demystify DATETIME comparisons in MySQL?
To quote the documentation about UTC_TIMESTAMP():
Returns the current UTC date and time as a value in 'YYYY-MM-DD
HH:MM:SS' or YYYYMMDDHHMMSS format, depending on whether the function
is used in a string or numeric context.
Because the value is being used in the context of a number, it is treated as a number, which is the behavior that you see.
I've just found this out myself, but here's a quick example that shows you how it works.
#GordonLinoff's answer is neither here nor there, because your question isn't really about the format returned from utc_timestamp(). What you're really asking is what format does MySQL return when you use numeric operands + and - on timestamps.
I tend to agree with you that the documentation is a bit fuzzy on the topic. But this is what I found. You can build this view yourself to see the example in simpler terms.
create view cbhview as
select utc_timestamp() as nowtime,
utc_timestamp() - interval 1 hour as thentime,
date_sub(utc_timestamp(),INTERVAL 1 HOUR) as thentime2,
date_sub(utc_timestamp(),INTERVAL 1 SECOND) as justthentime;
select nowtime, thentime, thentime2, justthentime,
nowtime-thentime,
nowtime-justthentime,
thentime-thentime2
from cbhview;
+---------------------+---------------------+---------------------+---------------------+------------------+----------------------+--------------------+
| nowtime | thentime | thentime2 | justthentime | nowtime-thentime | nowtime-justthentime | thentime-thentime2 |
+---------------------+---------------------+---------------------+---------------------+------------------+----------------------+--------------------+
| 2014-07-06 20:22:58 | 2014-07-06 19:22:58 | 2014-07-06 19:22:58 | 2014-07-06 20:22:57 | 10000 | 1 | 0 |
+---------------------+---------------------+---------------------+---------------------+------------------+----------------------+--------------------+
1 row in set (0.00 sec)
100000 represents 1h 00min 00second
1 represents 1second
0 represents no difference between the two
In short, unless you know exactly what you're doing and exactly what you're trying to achieve, don't use numeric operands on date and timestamp datatypes. Keep to the functions that have been designed for the purpose date_add() and date_sub().

Mysql DATETIME evaluation: Get all records whose value is before midnight of the current day (basically yesterday and before

This is really simple yet I always struggle with it. I need help getting records before midnight:
AND last_checked < date('2013-06-25 00:00:00'))
This obviously doesn't work, since its string evaluation. I do not want to restrict it to this year and put a between in the code. Any help is extremely appreciated :)
You can also do this in a generic way
AND last_checked < ( DATE(NOW()) + INTERVAL 0 SECOND );
Watch this:
mysql> SELECT DATE(NOW()) + INTERVAL 0 SECOND Midnight;
+---------------------+
| Midnight |
+---------------------+
| 2013-06-25 00:00:00 |
+---------------------+
1 row in set (0.00 sec)
mysql>
You should be able to just do
AND last_checked < '2013-06-25 00:00:00'
Using the date() function just extracts the date part of the argument.
If last_checked is of datetime data type, then your WHERE clause will look like this:
WHERE ...
AND cast (last_checked as date) = '2013-06-25'
CAST (datetime as date) drops time part, so you can easily get all data between 00h:00m:00s and 23h:59m:59s .

How to use a string/column value as a mysql date interval constant (DAY, MONTH...)?

I have three columns: a date column, a integer column, and a varchar column like this:
+------------+------+---------+
| date |value | unit |
+------------+------+---------+
| 2009-01-01 | 2 | DAY |
| 2009-02-01 | 3 | MONTH |
+------------+------+---------+
I want to use the values of the integer and the varchar column in a mysql date_add() function as part of the "INTVERAL" expression, added to the date in the 'date' column.
For example:
date_add(2009-01-01, INTERVAL 2 DAY), so that the '2009-01-01' is from the 'date' column, the '2' is from the "value"/integer column and the "DAY" is from the 'unit'/varchar column.
And the select would look like this:
select date_add(table.date_column, INTERVAL table.integer_column table.varchar_column) from table
Problem is: it doesn't work. The date and the integer column work, so this is ok:
select date_add(table.date_column, INTERVAL table.integer_column DAY) from table
but as soon I try to replace the "DAY" Keyword with a string value from a column I get an error message.
Any Ideas?
I guess more generally the problem is:
How do I use dynamically retrieved values as constants/key expressions? Is there a kind of "eval" function in mysql ?
This problem has been bugging me for a long time now, any help would be really great.
Beat
Unfortunately MySQL expects a keyword after INTERVAL and not any string or numeric value. You can achieve what you want by using a CASE statement and give the different cases with the different keywords.
As an example, let's say you want to add the value with the appropriate unit to the date then the SQL statement would be as follows:
SELECT CASE unit
WHEN "DAY" THEN date_add(date, INTERVAL value DAY)
WHEN "MONTH" THEN date_add(date, INTERVAL value MONTH)
END
AS newDate
FROM table
Also works in the WHERE clause by the way :)
I think you're better off using a CASE statement for each possible value of the unit column, since it is a finite universe. You can choose whether to keep the column as a varchar, or use an integer code instead.
I would discourage use of dynamically executing SQL statements, even when generated from an existing table unless you are 120% careful in restricting the values that get inserted in the table. What would you do if you somehow got the following values in the table? Oops!
+------------+------+------------------------------------+
| date |value | unit |
+------------+------+------------------------------------+
| 2009-01-01 | 2 | DAY |
| 2009-02-01 | 3 | MONTH |
| 2009-03-01 | 4 | DAY) FROM table; DROP TABLE table; |
+------------+------+------------------------------------+
I'm in the middle of reinstalling MySQL on my machine, so I can't test it, but perhaps concatenating them into a valid string might help, if CONCAT() is allowed here:
SELECT
DATE_ADD(
table.date_column,
INTERVAL CONCAT(
table.integer_column,
' ',
table.varchar_column
)
)

Need to get records from MySQL database by date only from a datetime field

This seems rather simple but it has been giving me a headache. I have a column in my events table that is called 'date_time' and it's type is datetime.
I need to write a query that will get events by day.
Example of table
============================
| id | date_time |
============================
| 5 | 2009-03-27 14:16:00 |
============================
Now I need to get the event with the Id = 5, except I only have a date (unix timestamp) to work with. I have tried many things such as converting to mysql format and selecting between 2009-03-27 00:00:00 and 2009-03-28 00:00:00 but I couldn't get it to work.
What is the best way to do this?
Thanks muchly.
SELECT * FROM table
WHERE date_time BETWEEN '2009-03-27 00:00:00' AND '2009-03-27 23:59:59'
Should do it.
Alternatively, try this:
SELECT * FROM table WHERE DATE(date_time) = '2009-03-27'
The DATE() function extracts the date part of the datetime column.
select * from table WHERE date(date_time) = '2009-03-27' works for me
if you have an unix timestamp you could also do
select * from table WHERE UNIX_TIMESTAMP(date_time) = your_timestamp
BETWEEN isn't safe if timestamps include fractional seconds. This is always safe:
SELECT *
FROM table
WHERE date_time >= '2009-03-26 00:00:00' AND date_time < '2009-03-27 00:00:00'