I have HTML form which I don't want users to be able to use more then once per day.
So far iv'e figured out what I should do but I'm not really sure how.
When a user submits the form I store their "IP" (column ip) aswell as the current time (column submitTime) and the current time + 23 hours (column releaseTime):
$submitDate = date("Y-m-d H:i:s");
$currentTime = time();
$releaseTime = date("Y-m-d H:i:s", strtotime('+23 hour', $currentTime));
But what I dont know is how can I proceed? I feel like I'm stuck.
I know I should compare $currentTime with the releaseTime I get from MySQL, but how?
So far I got this code (see the comment lines):
$ip = $_SERVER['REMOTE_ADDR'];
$stmt1 = $conn->prepare('SELECT * FROM IPlock WHERE ip=?') or die('Couldn\'t check the IP');
$stmt1->bind_param("s", $ip);
$stmt1->execute();
$stmt1->store_result();
$countRows = $stmt1->num_rows;
$stmt1->close();
if ($countRows > 0) {
/*
Code to check for how long the IP has existed in MySQL
If it has existed for more then 23 hours, remove it and proceed.
else abort (since its blacklisted for another x hours)
*/
}
I know I should not use the IP to identify an user since some users share their IP, but in this case I really have to.
You can use this to check if one has submitted the form in the last 24 hours.
SELECT * FROM IPlock WHERE `ip`=? AND `submitTime` > NOW() - INTERVAL 24 HOUR;
If IP has not submitted in the past 24 hours, no rows will be returned.
EDIT:
In addition to that, there's no need to use PHP date() function, you can do your insert like
INSERT INTO IPlock (`ip`, `submitTime`) VALUES ('127.0.0.1', NOW());
Note that CURRENT_TIMESTAMP will work just as well.
In fact, your problem is different from what you asked.
To compare a datetime value of mysql format you just have to compare it - not a big deal.
The real question is how to get the value for comparison (with your current code you can't) and what to do if you found that the record is outdated.
So, first you need to fetch the datetime value:
$stmt1 = $conn->prepare('SELECT releaseTime FROM IPlock WHERE ip=?');//never use die()
$stmt1->bind_param("s", $_SERVER['REMOTE_ADDR']);
$stmt1->execute();
$stmt1->store_result();
$stmt1->bind_result($releaseTime);
$stmt1->fetch();
and now you can start checking the date. Note that you don't need the num rows here.
if ($releaseTime > date("Y-m-d H:i:s")) {
/*
Code to check for how long the IP has existed in MySQL
If it has existed for more then 23 hours, remove it and proceed.
else abort (since its blacklisted for another x hours)
*/
}
Related
I am creating a new website and so far everything is working perfect but I have one small issue and i am wondering if anyone knows a way to sort it out.
Users come to my site to generate pin codes for my applications now this works perfect the pins are saved to a db with a created_at time and then an expires_at time with is creation time + 3 hours.
It works perfect most of the day but I run into issues when it gets to about 9:30 pm every day.
When you create a pin around 9:30 the creation time will be:
9:23:43
Now then expiration time will be
00:23:43
and this is where the issue is when they add the pin to my applications. It checks them from the database by comparing the current time by creation time using the code below:
<?php
include 'inc.db.php';
include 'inc.clear.php';
date_default_timezone_set('Europe/London');
function Check($key, $pin){
global $mysqli;
$time = date("H:i:s");
$stmt = $mysqli->prepare("SELECT expired FROM tbl_pins WHERE key=? AND pin=?");
$stmt->bind_param('ss', $key, $pin);
$stmt->execute();
$stmt->bind_result($expired);
while($stmt->fetch()) {
if($time >= $expired){
$result = 'Pin Expired';
Clear($pin);
}else{
$result = 'Pin Verified';
}
}
$stmt->close();
return $result;
}
?>
but as it checks the pin, the current time will be
22:10:30 and it checks to see if this is above the expiration time but that's 00:24:22 so because it's after 12am, it's always a lower number.
Does anyone know a way around this?
Use Unix Epoc time
time()
Expiration will be Three hours from now:
time() + (3 * 60 * 60)
Expired true if
time() > Expiration
Use date as well in both created_at and expired_at. If one creates at 1AM and expires at 4AM, do you think 2AM tomorrow (or next year) is still valid? Without date, time is not enough for token expirations for sure.
I have the following at the top of every page so when the website is loaded by anyone PHP deletes any record in a specific database table that is older than 3 days.
$conn = getConnected("oversizeBoard");
mysqli_query($conn, "DELETE FROM postedLoads WHERE date < DATE_SUB(DATE('m-d-Y'), INTERVAL 3 DAY");
The problem is nothing is being deleted.
The data type for my date column is varchar(20) and when I insert a date into MySQL it is entered using date("m-d-Y"). The name of my date field is date. So it appears that the above query would be correct, but I have done something wrong, and I am not certain as to what since every example I've looked at has basically looked the same except they used now() instead of date() but I use a specific date format so I can't use now() in my query.
What have I done wrong?
I even tried putting it into a function:
function deleteOversizeRows() {
$conn = getConnected("oversizeBoard");
mysqli_query($conn, "DELETE FROM postedLoads WHERE date < DATE_SUB(DATE('m-d-Y'), INTERVAL 3 DAY");
}
deleteOversizeRows();
Try to provide date by calculating first and then use it in query like below
$date = date("m-d-Y", strtotime('-3 day'));
$conn = getConnected("oversizeBoard");
mysqli_query($conn, "DELETE FROM postedLoads WHERE date < '".$date."');
It might help you. If need any other solution or help, do ask here.
Use MySQL function TIMESTAMPDIFF(unit,datetime_expr1,datetime_expr2);
Function calculates difference between two dates and returns output based on the unit parameter passed .
Try this:
DELETE FROM postedLoads WHERE TIMESTAMPDIFF('DAY',date,now())<3;
For detailed info of function:http://www.w3resource.com/mysql/date-and-time-functions/mysql-timestampdiff-function.php
MySQL table "flightSched" is connected to time, similar to the one below:
flightNo |day |time |arrivalTimeSec
=============================================
WERE112 |Tuesday | 1:00 |1381186800
FGHG234 |Tuesday |23:00 |1381266000
CGHF345 |Tuesday |00:00 |1381183200
I have a mysql query that select all data between two times. This is the query:
$CurrentTimeMinus30min = date('H:i', strtotime('-30 minutes')); //Current Time minus 30minutes
$CurrentTimeMinus30min = strtotime($CurrentTimeMinus30min);
$CurrentTimePlus4Hours = date('H:i', strtotime('+240 minutes')); //Current Time plus 4 hours
$CurrentTimePlus4Hours = strtotime($CurrentTimePlus4Hours);
$query = $mysqli->query("
SELECT * FROM flightSched
WHERE day = '$currentDay'
AND arrivalTimeSec
BETWEEN '$CurrentTimeMinus30min'
AND '$CurrentTimePlus4Hours'
");
I was advised to used strtotime() function on the time values to be able to use them in a BETWEEN MySQL query. This doesn't seem to be working at all.
Where am I going wrong with this query? Any help will be appreciated.
today I found the same problem with yours (mine about coordinates).
and I found out that in some case, a BETWEEN operator can only be used like this
..... WHERE columname BETWEEN smallervalue AND biggervalue
previously I've tried with the biggervalue at front since I dealt with negative numbers, and it fails.
you might found the same problem with your timestamp.
strtotime returns a timestamp so passing that into the MySQL query, like above, won't work. Try using FROM_UNIXTIME instead.
$query = $mysqli->query("SELECT * FROM flightSched
WHERE day = '$currentDay'
AND FROM_UNIXTIME(arrivalTimeSec) BETWEEN FROM_UNIXTIME($CurrentTimeMinus30min) AND FROM_UNIXTIME($CurrentTimePlus4Hours) " );
EDIT - I hadn't noticed that arrivalTimeSec was also a timestamp. The above mightn't be a workable answer for you, but try it. If it doesn't work, as others say, define what you mean by
This doesn't seem to be working at all.
Is it not returning any rows? Is it returning an error? Can you print out $CurrentTimeMinus30min and $CurrentTimePlus4Hours? Narrow down the potential areas for problems.
Have you tried to encapsulate the between? This could potentially solve your problem:
SELECT * FROM flightSched
WHERE day = '$currentDay'
AND (arrivalTimeSec BETWEEN '$CurrentTimeMinus30min' AND '$CurrentTimePlus4Hours')
Also why not just do:
$CurrentTimeMinus30min = strtotime('-30 minutes');
Or
$CurrentTimeMinus30min = strtotime(date('Y-m-d H:i:00', strtotime('-30 minutes')));
Please send us some examples of what your variables are generating.
Your time calculation with date("H:i",...) and strtotime(..) seems to actually produce the correct results, although there is a much easier way to add/substract n minutes from the current time:
$now = time();
$currentTimeMinus30min = $now - 30*60; // 30 minutes * 60 seconds
$currentTimePlus4Hours = $now + 4*60*60; // 4 hours * 60 minutes * 60 seconds
(I assume your time entries in your database are unix timestamps.)
Your query looks fine, too, but there are a few things to keep in mind:
You have redundant fields in your database (day and time can be calculated from the timestamp)
Working with time variables can easily lead to confusion, as the time passes on and if you have no entries in your database that match the specified time range (-30m to +240m) the result set is empty. So to test the query update the database with current time stamps.
I would suggest the following:
Drop the redundant columns day and time and just use the timestamp as base for your calculations, because the day and time is already included in the timestamp. So just use a simple query like
select * from flightShed
where arrivalTime between $begin and $end
This is what i am trying to do.
id ip timestamp userid
9 127.0.0.1 2013-06-27 16:52:49 35
I would like to first query table to see if ip for the user is persisted. If so, he/she voted 2) Check timestamp of vote against current timestamp, if his voting time is way after 24 hours, then allow him to vote again. Ensure he can only vote once in 24 hours.
This is my current zend_db_select statement. Has some problems coming out with the logic
function checkIfCanLikeH($hlid,$ip){
$canlike = false;
$currenttime = time();
$checkquery = $this->dbo->select()
->from("hl", array("num"=>"COUNT(*)"))
->where("hlid = ?", $hlid)
->where("ip = ?", $ip)
->where("timestamp < ".new Zend_Db_Expr('NOW()'));
$this->dbo->setFetchMode(Zend_Db::FETCH_ASSOC);
$checkrequest = $this->dbo->fetchRow($checkquery);
if($checkrequest['num']!=0){
$ip = true;
}
return $ip;
}
I am stucked at how do i compare the timestamp. I need retrieve the timestamp from table and check if the current time is smaller than value in table (added 24 hours).
Advice appreciated.
->where("timestamp < DATE_SUB(NOW(), INTERVAL 1 DAY)");
This is the advantage of using MySQL's timestamp/datetime/date column types - you can use its inbuilt date and time functions. And I'm pretty sure you don't need Zend_Db_Expr here.
Edit: I'm not completely clear what you're asking, but I think the WHERE clause above does what you want, just the other way around. You could do this instead:
->where("DATE_ADD(timestamp, INTERVAL 1 DAY) < NOW()");
which is the same thing but written a different way. This means "where timestamp + 1 day is less than the current time".
If it helps, try running this query on your database:
SELECT DATE_ADD(timestamp, INTERVAL 1 DAY), NOW() FROM hl
so you can see how the DATE_ADD() function in MySQL works.
Hey guys so, im doing this form with a input that will contain the time and i want to make it so that when users choose the time (for example 8:30 AM), it will be stored in mysql, and will be output by php with the exact time (8:30 AM).
Here is the form. A simple select button with increments of 30 on the time.
http://jsfiddle.net/jXVPS/
The main problem is i dont know how mysql will recognize if it is AM/PM?
What values i should put for the select fields, how i would insert it into the mysql database, and have mysql or php recognize wheather it is 1:00 AM or 1:00 PM. Is there some sort of 24 hour clock in mysql that makes it recognize wheather or not it is AM/PM?
Use TIME column type:
TIME
A time. The range is '-838:59:59' to '838:59:59'. MySQL displays TIME values in 'HH:MM:SS' format, but allows you to assign values to TIME columns using either strings or numbers.
It will parse the values in your select options nicely.
Edit: Example of use:
// saving in the db
$sql = "
INSERT INTO table_name SET
# ...
name_of_the_time_column = '" . mysql_real_escape_string($_POST['start_time']) . "'";
// retrieving from the db
$sql = "
SELECT id, ..., TIME_FORMAT(name_of_the_time_column, '%h:%i:%s %p') AS formatted_time
FROM table_name
# ...
";
Here's MySQL's time/date stuff. I think the TIME type would be best for you since you don't need a date, and the format you've got for your values should fit well. I think you can just put them as strings exactly like that.
http://dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html
http://dev.mysql.com/doc/refman/5.5/en/date-and-time-types.html
After you submit thru form submission or ajax and your responding PHP page takes over, perform a query with the following string in the PHP:
"INSERT INTO table (userId, time, ...) VALUES (..., '$inTime', ...)"
And then echo it out since you want the next page to repeat it.
Response to comment
I figure you mean that wou want 13:00:00 to be 1:00 PM when you echo it out later right?
Theres probably something you can do with time functions for either PHP or MySQL (PHP below, MySQL above), but I don't know from memory and this is simple enough you can just do it on your own.
http://www.php.net/manual/en/ref.datetime.php
$time = //get time field from MySQL
list($h, $m, $s) = explode($time, ':');
if ($h > 12) {$h -= 12; $amOrPm = 'PM'}; else {$amOrPm = 'AM';}
if ($h == 0) {$h = 12;}
echo "$h:$m $amOrPm";
PS - 13:00:00 is 1pm, not am.
Not tested :
INSERT INTO myTable
SET time = TIME(STR_TO_DATE('8:30:00 AM','%h:%m:%s %p'))