Best (and easiest) way to test that a "date string" (mm/dd/yyyy) is valid

P

Petyr David

Just looking for the simplest. right now my perl script returns an
error messge to the user if the date string is invalid. would like to
do this before accessing the server.

TX
 
V

VK

Petyr said:
Just looking for the simplest. right now my perl script returns an
error messge to the user if the date string is invalid. would like to
do this before accessing the server.

How do you get the date string from the user? Does she has to type it
in manually in strict mm/dd/yyyy format in a form's text field?
 
M

Matt Kruse

Petyr said:
Just looking for the simplest. right now my perl script returns an
error messge to the user if the date string is invalid. would like to
do this before accessing the server.

If your date format is not flexible and you don't care to support ancient
browsers, a simple regular expression can quickly test that the input is
well-formed, but can't verify that the values are valid. For that you need
to split the values out and apply some logic.

If you want a solution that does all the work for you and can validate
arbitrary formats, check out my date lib at:
http://www.javascripttoolbox.com/lib/date
 
D

Dr J R Stockton

In comp.lang.javascript message
Sun said:
Just looking for the simplest. right now my perl script returns an
error messge to the user if the date string is invalid. would like to
do this before accessing the server.

Always include the question within the article; the Subject is not
necessarily simultaneously visible.

It's a good idea to read the newsgroup and its FAQ. See below. You
could have discovered how to validate standard numeric date strings by
doing that, and then you should be able to adapt it for FFF strings.


Except that your "Best (and easiest) way" is rather meaningless. All
sensible methods are easy, if you only have to copy them. But does
"Best" refer to code size, code speed, or code comprehensibility, pr
proving code validity?


And you need to define what is valid. For today, 2006-12-3 is
unambiguous, but it is not valid by ISO 8601, which calls for
2006-12-03. You have only indicated that, for you, mm/dd/yyyy can be
good.
 
R

RobG

Petyr said:
Just looking for the simplest. right now my perl script returns an
error messge to the user if the date string is invalid. would like to
do this before accessing the server.

You need to define "valid" and "simplest". The simplest test I can
think of is for 3 numbers separated by "/":

function isValidDate(dateString){
return /^\d{1,2}\/\d{1,2}\/\d{4}$/.test(dateString);
}

But that may not be of much use - the input may not be a valid date,
e.g. 2/29/2006 will return true (as will a very large number of other
"valid" input strings).

If you want to check that the date is valid according to your required
mm/dd/yyyy, the easiest way is to firstly check the format, then that
it will generate a valid date:

function isValidDate(dateString){
if (/^\d{1,2}\/\d{1,2}\/\d{4}$/.test(dateString)){
var testDate = new Date(dateString);
var dateBits = dateString.split('/');
if ( dateBits[1] == testDate.getDate() &&
(dateBits[0]-1) == testDate.getMonth() ){
return true;
}
}
return false;
}

There are other methods that don't use a date object and may be
considered 'simpler' by some. Expecting mm/dd/yyyy to correctly
generate a date object when used with new Date() may be overly
dependent on browser implementations (the ECMAScript Language
specification doesn't say that it must, but browsers seem to).

Your required format is native to a small percentage of internet users.
You may wish to consider an international format (i.e. one that is not
peculiar to a small number of countries) such as the ISO format:
yyyy/mm/dd.

However, if your criteria for "simple" include implementation, you
might like to use a library such as that suggested by Matt K.

There is a lot of information on dates here:

<URL: http://www.merlyn.demon.co.uk/js-dates.htm >

You might also wish to search the archives, this question is asked
frequently.

<FAQENTRY>
Should there be an FAQ on date validation? It seems to be asked about
very frequently, a search on "validate date" returns 413 records.

There is a suggestion here from JRS that seems a reasonable start:

<URL:
http://groups.google.com.au/group/c...alidate+date+FAQENTRY&rnum=6#80bd380cdf3407f9
 
D

Dr J R Stockton

Sun said:
If your date format is not flexible and you don't care to support ancient
browsers, a simple regular expression can quickly test that the input is
well-formed, but can't verify that the values are valid. For that you need
to split the values out and apply some logic.

An mm/dd/yyyy string will be read correctly by new Date(S), at least in
WinXP sp2 IE6 (showing that MS's idea of localisation is inadequate).

IF future standards were to implement a reverse method DObj.toNumStr
giving a format correspondingly localised, WHICH CERTAINLY THEY SHOULD,
ISTM that your statement would no longer be true.

OK = new Date(S).toNumStr() == S // untested, obviously.

It would be interesting to code .toNumStr() to make it give whichever of
mm/dd/yyyy and dd/mm/yyyy the current new Date(S) would use (as well as
..toNumStr(0) and .toNumStr(8601) giving yyyy-mm-dd and other arguments
giving other formats). Perhaps your library already does that; but I
don't yet see how it can be possible to do it without splitting the
values out.

function toNumStr(D) { var S
S =
LZ(D.getDate()) +'/'+ LZ(D.getMonth()+1) +'/'+ LZ(D.getFullYear())
return (+new Date(S) == +D) ? S :
S.replace(/(.{3})(.{3})/, "$2$1") }
 
P

Petyr David

User types it in form's text field. This doesn't have to be anything
fancy. The people using this application are computer scientists and
researchers and should be able to follow directions. i simply want to
save then the time it would take for their query to run and return them
bogus results.

TX
 
R

Randy Webb

Dr J R Stockton said the following on 12/4/2006 8:25 AM:
An mm/dd/yyyy string will be read correctly by new Date(S), at least in
WinXP sp2 IE6 (showing that MS's idea of localisation is inadequate).

IF future standards were to implement a reverse method DObj.toNumStr
giving a format correspondingly localised, WHICH CERTAINLY THEY SHOULD,
ISTM that your statement would no longer be true.

And IF a frog had wings it wouldn't bump it's butt when it lands.
 
B

Bart Lateur

Petyr said:
Just looking for the simplest. right now my perl script returns an
error messge to the user if the date string is invalid. would like to
do this before accessing the server.


I'm not sure about the best...

You can use a regexp to extract the digit parts of a date. With those,
you can construct a new Date object. (Note that months start at index 0
for January.)

I found out that with the browsers I tested, this always succeeds, but
it is "corrected" to the proper calendar date, for example April 31 will
be turned into May 1.

So I could test if year, month, day are the same... but I'm guessing
that just testing the month is enough.

So here's a simple function:

function isValidDate(s) {
var m = s.match(/^(\d{1,2})\/(\d{1,2})\/(\d{4})$/);
if(!m) return false;
var d = new Date(m[3], m[1]-1, m[2]);
return m[1] == d.getMonth()+1;
}

HTH,
Bart.
 
D

Dr J R Stockton

In comp.lang.javascript message
Sun said:
You need to define "valid" and "simplest". The simplest test I can
think of is for 3 numbers separated by "/":

function isValidDate(dateString){
return /^\d{1,2}\/\d{1,2}\/\d{4}$/.test(dateString);
}

Suggest isValidDatePattern or isValidDateFFFormat.
But that may not be of much use - the input may not be a valid date,
e.g. 2/29/2006 will return true (as will a very large number of other
"valid" input strings).

If you want to check that the date is valid according to your required
mm/dd/yyyy, the easiest way is to firstly check the format, then that
it will generate a valid date:

function isValidDate(dateString){
if (/^\d{1,2}\/\d{1,2}\/\d{4}$/.test(dateString)){

For the OP, ISTM d{2} not d{1,2}
var testDate = new Date(dateString);

After reading the next comment, = new Date(part1, part2-1, part3)
var dateBits = dateString.split('/');

If the RegExp is used with the match method, and parentheses are
inserted, the splitting will already have been done.
if ( dateBits[1] == testDate.getDate() &&
(dateBits[0]-1) == testDate.getMonth() ){

Given that the RegExp establishes that MM & DD are each in 00..99, ISTM
certain that one need only test the Month. If MM is impossible,
getMonth()+1 cannot give it; if DD is out of range, the apparent Month
will be changed by -1 or +1 / +2 / +3.
There are other methods that don't use a date object and may be
considered 'simpler' by some. Expecting mm/dd/yyyy to correctly
generate a date object when used with new Date() may be overly
dependent on browser implementations (the ECMAScript Language
specification doesn't say that it must, but browsers seem to).

The optimistic will allow for the possibility that future browsers will
recognise MM/DD/YYYY or DD/MM/YYYY according to locale; and even for the
chance that, eventually, only the format chosen for the OS (mine is
YYYY-MM-DD) will be accepted. I cannot recall, and cannot now test,
whether IE4, which takes 01/02/03 as Jan 2, would take 21/02/03 as 21
Feb.

<FAQENTRY>
Should there be an FAQ on date validation?

FAQ Section 3.2 refers. If it contained a Numbered List, I could cite
the number; but a search of the FAQ for any of the words date time
dates times lastModified will find it; the entry was some while ago
altered specifically to include the singular and plural forms, to aid
searching.

My Javascript Date and Time 4 : Validation is not a FAQ, since it puts
unasked questions on the same footing as asked ones.
 
R

RobG

Dr said:
In comp.lang.javascript message
<[email protected]>, Sun, 3 Dec 2006
if ( dateBits[1] == testDate.getDate() &&
(dateBits[0]-1) == testDate.getMonth() ){

Given that the RegExp establishes that MM & DD are each in 00..99, ISTM
certain that one need only test the Month. If MM is impossible,
getMonth()+1 cannot give it; if DD is out of range, the apparent Month
will be changed by -1 or +1 / +2 / +3.

Ah yes, I didn't account for date being limited to two digits.

The optimistic will allow for the possibility that future browsers will
recognise MM/DD/YYYY or DD/MM/YYYY according to locale; and even for the
chance that, eventually, only the format chosen for the OS (mine is
YYYY-MM-DD) will be accepted. I cannot recall, and cannot now test,
whether IE4, which takes 01/02/03 as Jan 2, would take 21/02/03 as 21
Feb.

Optimistic? More like Machiavellian!! ;-)

I think that would greatly complicate matters. I always insist on
on-screen help where a particular format is required; making the input
date format locale dependent would mean that the on-screen help also
needs to be localised. It also infers that either the server is
advised of the format being used by the client system, or the client
system will standardise the format before sending the date to the
server. I wouldn't expect that to be reliable.
FAQ Section 3.2 refers.

I don't think it does - certainly there are links that cover the topic,
but nothing in the FAQ explicitly cites how to validate a date. Simply
responding with "read the FAQ" will almost certainly result in a "can't
find it" response. The number of times code is posted here in response
shows that even regulars don't know of a good FAQ link to suggest.
If it contained a Numbered List,

Got that Randy? ;-)

My suggested new layout was to put these in a UL, but an OL would be a
trivial change for version 10. The CSS should attempt to make the
numbering appear independent of the section numbering.
I could cite
the number; but a search of the FAQ for any of the words date time
dates times lastModified will find it; the entry was some while ago
altered specifically to include the singular and plural forms, to aid
searching.

But not to include the word "validate", which I think is an equally
important keyword for this. There should be an entry that offers an
all digit version with the match() method, along with tips on how to
deal with different formats (dd/mm/yyyy, mm/dd/yyyy, yyyy/mm/dd and
yyyymmdd are probably sufficient). There should also be a version
covering the typical database format dd-mmm-yyyy.

I think you've already expressed a wish to review such an entry rather
than write it, I'll post a first cut later if you don't beat me to it.
 
D

Dr J R Stockton

In comp.lang.javascript message
function isValidDate(s) {
var m = s.match(/^(\d{1,2})\/(\d{1,2})\/(\d{4})$/);
if(!m) return false;
var d = new Date(m[3], m[1]-1, m[2]);
return m[1] == d.getMonth()+1;
}

That can be made slightly shorter :-

function isValidDate(s) {
var m = s.match(/^(\d{1,2})\/(\d{1,2})\/(\d{4})$/);
if(!m) return false;
var d = new Date(m[3], --m[1], m[2]);
return m[1] == d.getMonth();
}

While those answer the current question, ISTM more generally useful to
return either a Date Object or a failure indication such as NaN or new
Date(NaN) - with care in some cases if the input may be 01/01/1970 and
the user may be believed by the system to be using GMT on that date.
Maybe (untested; failure returns undefined)

function isValidFFFDate(s) { var m
if (m = s.match(/^(\d\d)\/(\d\d)\/(\d{4})$/)) {
var d = new Date(m[3], --m[1], m[2]);
if (d.getMonth() == m[1]) return d }
}
 
D

Dr J R Stockton

In comp.lang.javascript message
Mon said:
Dr J R Stockton wrote:
I think that would greatly complicate matters. I always insist on
on-screen help where a particular format is required; making the input
date format locale dependent would mean that the on-screen help also
needs to be localised. It also infers that either the server is
advised of the format being used by the client system, or the client
system will standardise the format before sending the date to the
server. I wouldn't expect that to be reliable.

If the input format matches an output format, then for most countries it
is only necessary to use a new Date("2006/12/25") output in local
all-numeric as an example.

(But one must distinguish between possessing a language feature and
using it.)

In a sensible world all data processing would follow ISO 8601. But as
(I believe) the rational format is/was commended in a US Federal
Standard (FIPS), the Americans will never be willing to comply.

I have this horrible feeling that, over all but 4 provinces of Iraq, FFF
is presented as the Western norm.


I don't think it does - certainly there are links that cover the topic,
but nothing in the FAQ explicitly cites how to validate a date. Simply
responding with "read the FAQ" will almost certainly result in a "can't
find it" response. The number of times code is posted here in response
shows that even regulars don't know of a good FAQ link to suggest.


Got that Randy? ;-)

My suggested new layout was to put these in a UL, but an OL would be a
trivial change for version 10. The CSS should attempt to make the
numbering appear independent of the section numbering.

CSS is not needed (though may be preferred), since <OL type=i> will do.
Similarly in 2.3. But why not use TYPE=i for any third-level numbering,
such as in 2.4? Since the numbers may be quoted in News, CSS decoration
will not suffice.
But not to include the word "validate", which I think is an equally
important keyword for this.

Well, it seems obvious that the concept "validate" can be expressed in
various ways (test, check spring to mind), and so obvious to repeat the
failed search without it. A search (of 8.1) for "valid" alone proves
that no search including it can succeed. And would the user realise
that validate validation and validating are all possible, and search on
just "valid"?


There should be an entry that offers an
all digit version with the match() method, along with tips on how to
deal with different formats (dd/mm/yyyy, mm/dd/yyyy, yyyy/mm/dd and
yyyymmdd are probably sufficient). There should also be a version
covering the typical database format dd-mmm-yyyy.

I think you've already expressed a wish to review such an entry rather
than write it, I'll post a first cut later if you don't beat me to it.

If you've followed the existing FAQ advice, I should have no improvement
to suggest, unless you've made an improvable improvement. My page 4
contains at #ISO about the shortest possible, and at #Genl about the
longest reasonably necessary - perhaps.
 
R

RobG

Dr said:
In comp.lang.javascript message
Mon said:
Dr J R Stockton wrote:
[...]
If the input format matches an output format, then for most countries it
is only necessary to use a new Date("2006/12/25") output in local
all-numeric as an example.

I was discussing input dates sent to a server, not how to display them
on the client - for that an unambiguous format should be used, such as
using the month name rather than number.

[...]
I have this horrible feeling that, over all but 4 provinces of Iraq, FFF
is presented as the Western norm.

There may be others in which FFF is not the norm. :)
CSS is not needed (though may be preferred), since <OL type=i> will do.

The type attribute is deprecated, though that may not really matter. I
just think they need to be differentiated from the heading numbering
scheme.

[...]
Well, it seems obvious that the concept "validate" can be expressed in
various ways (test, check spring to mind), and so obvious to repeat the
failed search without it. A search (of 8.1) for "valid" alone proves
that no search including it can succeed. And would the user realise
that validate validation and validating are all possible, and search on
just "valid"?

I hope so. The various forms of "validate" are generally used in
connection with validating form input, I think at least one of them
should be in an FAQ heading. One or more of the others could be
included in the text. I'd like to see an explicit example, and then
perhaps a link to your page on the topic. e.g.:

How do I validate a date?

Date validation is usually performed when validating
user input to a form...

...code example...

You can find information on how
to check or test for valid dates here:
...links...

I think it's very important, Googling for "javascript date validation"
returned the following example at the very top of the list:

<URL: http://www.smartwebby.com/DHTML/date_validation.asp >

Beware, the author suggests parsing the date string character by
character to test for integers and remove separators. The date
validation routine is also straight from the "never mind the quality,
feel the length" school of programming.

If you've followed the existing FAQ advice, I should have no improvement
to suggest, unless you've made an improvable improvement. My page 4
contains at #ISO about the shortest possible, and at #Genl about the
longest reasonably necessary - perhaps.

My suggestions can be summarised as:

1. The phrase "validate a date" or similar be included in the page
to make finding the answer easier, preferably in a section
dedicated to validating dates

2. At least one code example appear in the page to make the use
of a reasonable date validation routine more likely

3. Explicit links to pages on date validation be included.

I don't have any improvements to the suggested validation routines
themselves, I think that topic has been done to death - which is a sure
sign that whatever is in the FAQ is not sufficient else we'd see
responses like "read FAQ 4.xxx" rather than posted code.
 
V

VK

Petyr said:
User types it in form's text field. This doesn't have to be anything
fancy. The people using this application are computer scientists and
researchers and should be able to follow directions. i simply want to
save then the time it would take for their query to run and return them
bogus results.

You did not specify if you want to run a simple formatting check or a
formatting check plus fit into some given date range.
Overall on form submit form's onsubmit handler is called first (if
presented). If it returns false, then the form submission being
cancelled. This way:

<html>
<head>
<title>Untitled Document</title>
<meta http-equiv="Content-Type"
content="text/html; charset=iso-8859-1">

<script type="text/javascript">
function validate(oForm) {
var ret = true;

// 'date' respectively the name you used
// for the text field, change accordingly
var userInput = oForm.elements['date'].value;

// test() method returns true or false
// unlike Perl, JavaScript doesn't allow
// regexp delimiters overload, so even don't try :)
// simply escape forward slashes
ret = /\d{2}[\/:\.]\d{2}[\/:\.]\d{4}/.test(userInput);


if (!ret) {
window.alert('Invalid date format');
}

return ret;
}
</script>

</head>

<body>
<form method="POST" action=""
onsubmit="return validate(this)">
<input type="text" name="date">
</form>
</body>
</html>

This script only checks if the date is formatted as dd.dd.dddd (regular
style) or dd/dd/dddd ("Euro-style"). From my observations scientists
who spent some time oversea tend to mix both, so maybe it's
user-friendly to allow either one.

If you need a check against a date range them please specify it.
 
D

Dr J R Stockton

In comp.lang.javascript message
Wed said:
function validate(oForm) {
var ret = true;

Why set it true?
// unlike Perl, JavaScript doesn't allow
// regexp delimiters overload, so even don't try :)

Meaning not manifest.
// simply escape forward slashes
ret = /\d{2}[\/:\.]\d{2}[\/:\.]\d{4}/.test(userInput);

No sensible specification allies the second date field delimiter to
differ from the first one (deeming all \s+ to be equivalent).

ret = /\d{2}([\/:\.])\d{2}\1\d{4}/.test(userInput);
This script only checks if the date is formatted as dd.dd.dddd (regular
style) or dd/dd/dddd ("Euro-style").

Trivial, then; not useful or interesting.

It's a good idea to read the newsgroup and its old FAQ. See below.
 
D

Dr J R Stockton

In comp.lang.javascript message
Tue said:
Dr J R Stockton wrote:

The type attribute is deprecated, though that may not really matter. I
just think they need to be differentiated from the heading numbering
scheme.

Well, CSS1 allows OL { list-style-type: lower-roman } and I suppose
OL OL OL could be defined as that. CSS1 offers five distinct sequences,
of which two are limited to 26 elements.


I think it's very important, Googling for "javascript date validation"
returned the following example at the very top of the list:

<URL: http://www.smartwebby.com/DHTML/date_validation.asp >

Beware, the author suggests parsing the date string character by
character to test for integers and remove separators. The date
validation routine is also straight from the "never mind the quality,
feel the length" school of programming.

It is good to teach incomers the general worthlessness of code found by
simple searches ...
I don't have any improvements to the suggested validation routines
themselves, I think that topic has been done to death - which is a sure
sign that whatever is in the FAQ is not sufficient else we'd see
responses like "read FAQ 4.xxx" rather than posted code.

BTW, I tend to use "Read the FAQ; see below." and those who do the
latter carefully ...
 
P

Petyr David

Petyr said:
Just looking for the simplest. right now my perl script returns an
error messge to the user if the date string is invalid. would like to
do this before accessing the server.

TX

thanks all. I stole some JavaScript code from the web, modified it to
make sure date wasn't greater than today. worked fine. now the 2 main
groups of users simply want to enter a number meaning the number of
days ago to start searching from up to and including "today".

That was easy
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,580
Members
45,055
Latest member
SlimSparkKetoACVReview

Latest Threads

Top