2016-07-22 5 views
2

일부 작업을 수행하기 위해 날짜 프로토 타입의 일부 확장 기능을 사용했습니다. (조언 : 그렇게하지 마십시오. 현재 프로젝트에서 나에게 너무 늦었습니다.) 평소보다 더 많은 이슈. 자바 스크립트가 제대로 파싱되지 않습니다.

는 H에서 문자열을 구문 분석하려면, n 형식, 나는 사용자 정의 함수를 만들어이 같은 날짜 프로토 타입에 할당 :

Date.__parse = Date.parse; 

Date.parse = function(string){ 
    var pattern = /^\d{1,2}:\d{1,2}/ig; 

    var today = new Date(); 

    if (pattern.exec(string)){ 
     var year = today.getFullYear(); 
     var month = today.getMonth()+1; 
     var day = today.getDate(); 

     var t = year+"-"+month+"-"+day+" "+string; 
     var timestamp = Date.__parse(t); 

     return new Date(timestamp); 
    } 
    else{ 
     return new Date(Date.__parse(string)); 
    } 
} 

미운 최근까지 날짜 개체 만 작업을 로그온 할 때.

한동안 Date.parse는 "d-m-Y"형식의 날짜로 작동하지만 최근에는 "invalid date"를 반환합니다.

주요 브라우저가 날짜를 구문 분석하거나 사양을 변경하는 방식이 변경되었거나 이전에 오류가 있었던 것으로 가정해야만하고 행운 이었기 때문에 "잘못된 날짜"가 표시되지 않았습니까? (주로 입력 필드의 유효성을 검사하는 함수를 사용하므로 주목받지 못합니다.)

내 자신의 날짜 스크립트를 작성해야하고 js Date 객체를 완전히 잊어 버릴 것 같아요. 정말 끔찍한데 (moment.js를 사용하려고했지만, 사용하는 구성 요소의 성능이 매우 좋지 않았습니다. 왜 사용자 정의 함수를 만들어야하는지).

더 나은 이해를 위해 편집

; 내가 일을하고 있었는지

이 작동 듯 : 나는 유효성 검사 오류를 추적 한 후 무엇을 발견

Date.parse("23-7-2016") // Never got an error, expected 23 Jul 2016 

:

var startDate = Date.parse("23-7-2016"); 
console.log(startDate.toISOString()); //Got Invalid Date 

무슨 일이 있었했다고 생각 무엇

var startDate = Date.parse("12-7-2016"); 
// expected 12 Jul 2016, got 7 Dec 2016, silently fails, everyone is happy 

왜 나는 이전 생각합니다. 대소 문자가 혼동되지 않는 경우 : 대화식 스케줄러를 사용하고 수천 개의 테스트를 수행했지만 거의 이러한 오류가 눈에 띄지 않게되었습니다.

최악의 시나리오 : 크롬이 날짜를 구문 분석하는 방식을 업데이트하고 변경했습니다.

확실하지 않습니다 ... 누군가 나를 계몽 할 수 있기를 바랍니다.

+0

당신이이 기능을 제공 값에 대한 몇 가지 입력 예제를 줄 수 있습니까? 또한 일반적인 질문 - 왜 날짜를 문자열로 바꾸고 그 반대도 마찬가지입니까? 일부 외부 소스에서 날짜를 문자열로 얻거나 클라이언트 - 서버 통신을 위해 날짜를 입력했기 때문입니까? –

+0

나는 pattern.exec 대신 예제를 기반으로 pattern.test를 사용해야한다고 생각한다. –

+0

미안하지만 예제가 너무 광범위 할 것이다. 내가 주로하는 일은 월 달력, 주 일정 또는 일일 일정으로 볼 수있는 이벤트 스케줄러입니다. 예를 들어 주간보기에서는 weekDays 이상 반복 한 다음 몇 시간에 걸쳐 이벤트를 후크하고 나중에 그려야합니다. 이 기능의 일부는 이벤트를 추가하는 것이므로 날짜를 반복 할 때 읽을 수있는 현지화 된 문자열로 변환해야합니다 (텍스트 파서를 전체적으로 게시하지 않음). 그리고 viceversa. 하루를 클릭하면 날짜 값을 저장해야합니다 ... 등등. – sergio0983

답변

1

나는 당신의 방법이 유효한 입력을 위해 작동해야한다고 판단했습니다. 문제는 정규식이 23 시간 이상 59 분 이상 유효하다는 것입니다.

유효한 모든 입력을 나열하는 내 jsfiddle을 참조하십시오. https://jsfiddle.net/kLngLL72/4/

필자는 함수의 무한 중첩을 방지하기 위해 예제에서 Date.parse 함수를 덮어 쓰지 않았습니다.

Date.__parse = Date.parse; 

var dparse = function(string){ 
    var pattern = /^\d{1,2}:\d{1,2}/ig; 

    var today = new Date(); 

    if (pattern.exec(string)){ 
     var year = today.getFullYear(); 
     var month = today.getMonth()+1; 
     var day = today.getDate(); 

     var t = year+"-"+month+"-"+day+" "+string; 
     var timestamp = Date.__parse(t); 

     return new Date(timestamp); 
    } 
    else{ 
     return new Date(Date.__parse(string)); 
    } 
} 

$("#data").append("<tr><td>" + dparse("01-01-2016 1:31") + "</td></tr>"); 
$("#data").append("<tr><td>" + dparse("1-1-2016 0:0") + "</td></tr>"); 
$("#data").append("<tr><td>" + dparse("1-1-2016 12:59") + "</td></tr>"); 
$("#data").append("<tr><td>" + dparse("1-1-2016 23:59") + "</td></tr>"); 
$("#data").append("<tr><td>" + dparse("12-31-2016 1:1") + "</td></tr>"); 
$("#data").append("<tr><td>" + dparse("12-31-2016") + "</td></tr>"); 
$("#data").append("<tr><td>" + dparse("12-31-2016 24:0") + "</td></tr>"); 
$("#data").append("<tr><td>" + dparse("12-31-2016 99:99") + "</td></tr>"); 

for (var i = 0; i < 24; i++) 
{ 
    for (var j = 0; j < 60; j++) 
    { 
    $("#data").append("<tr><td>" + dparse("12-31-2016 " + i + ":" + j) + "</td></tr>"); 
    } 
} 

는 업데이트] - NEW JS 뿐인 https://jsfiddle.net/mfe55xun/2/ 이 새로운 예는 단지 시간의 분 문자열을 전달합니다.

Date.__parse = Date.parse; 

var dparse = function(string){ 
    var pattern = /^\d{1,2}:\d{1,2}/ig; 

    var today = new Date(); 

    if (pattern.exec(string)){ 
     var year = today.getFullYear(); 
     var month = today.getMonth()+1; 
     var day = today.getDate(); 

     var t = year+"-"+month+"-"+day+" "+string; 
     var timestamp = Date.__parse(t); 

     return new Date(timestamp); 
    } 
    else{ 
     return new Date(Date.__parse(string)); 
    } 
} 

$("#data").append("<tr><td>" + dparse("99:99") + "</td></tr>"); 

for (var i = 0; i < 24; i++) 
{ 
    for (var j = 0; j < 60; j++) 
    { 
    $("#data").append("<tr><td>" + dparse(i + ":" + j) + "</td></tr>"); 
    } 
} 

UPDATE

당신의 입력 문자열은 날짜를 포함하는 경우, 정규 다음 Date.parse이 당신의 H와 문자열 작업 것을 주목해야한다

: m 형식 :

Date.parse("1/2/2016 4:3") 

"4 : 3"을 현재 날짜 문자열에 추가하기 만하면됩니다. 그러면 사용자 정의 Date.parse 함수를 제거 할 수 있습니다.

업데이트 된 질문

에 대한 또 다른 업데이트 나는 형식 이제까지 당신을 위해 제대로 일을 생각하지 않습니다. 그것은 작동 할 수있는 경우가 있지만 항상 "23rd"일을 한 달로 해석하고 잘못된 날짜를 알려줍니다. 그 형식으로 생각할 수있는 모든 날짜를 반복하는 또 다른 jsfiddle 예제입니다. 1-12 일만 걸립니다. 결과 루프에서 https://jsfiddle.net/mfe55xun/6/

Date.__parse = Date.parse; 

var dparse = function(string){ 
    var pattern = /^\d{1,2}:\d{1,2}/ig; 

    var today = new Date(); 

    if (pattern.exec(string)){ 
     var year = today.getFullYear(); 
     var month = today.getMonth()+1; 
     var day = today.getDate(); 

     var t = year+"-"+month+"-"+day+" "+string; 
     var timestamp = Date.__parse(t); 

     return new Date(timestamp); 
    } 
    else{ 
     return new Date(Date.__parse(string)); 
    } 
} 

for (var i = 0; i <= 31; i++) 
{ 
    for (var j = 0; j <= 12; j++) 
    { 
    $("#data").append("<tr><td>" + i + "-" + j + "-2016 = " + dparse(i + "-" + j + "-2016") + "</td></tr>"); 
    } 
} 

봐 :

test results 

0-0-2016 = Invalid Date 
0-1-2016 = Invalid Date 
0-2-2016 = Invalid Date 
0-3-2016 = Invalid Date 
0-4-2016 = Invalid Date 
0-5-2016 = Invalid Date 
0-6-2016 = Invalid Date 
0-7-2016 = Invalid Date 
0-8-2016 = Invalid Date 
0-9-2016 = Invalid Date 
0-10-2016 = Invalid Date 
0-11-2016 = Invalid Date 
0-12-2016 = Invalid Date 
1-0-2016 = Invalid Date 
1-1-2016 = Fri Jan 01 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-2-2016 = Sat Jan 02 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-3-2016 = Sun Jan 03 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-4-2016 = Mon Jan 04 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-5-2016 = Tue Jan 05 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-6-2016 = Wed Jan 06 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-7-2016 = Thu Jan 07 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-8-2016 = Fri Jan 08 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-9-2016 = Sat Jan 09 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-10-2016 = Sun Jan 10 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-11-2016 = Mon Jan 11 2016 00:00:00 GMT-0500 (Eastern Standard Time) 
1-12-2016 = Tue Jan 12 2016 00:00:00 GMT-0500 (Eastern Standard Time) 

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/parse

The Date.parse() method parses a string representation of a date, and returns the number of milliseconds since January 1, 1970, 00:00:00 UTC or NaN if the string is unrecognised or, in some cases, contains illegal date values (e.g. 2015-02-31).

It is not recommended to use Date.parse as until ES5, parsing of strings was entirely implementation dependent. There are still many differences in how different hosts parse date strings, therefore date strings should be manually parsed (a library can help if many different formats are to be accommodated).

+0

좋은 예이지만 시간/분이 문제를 일으키지 않는다고 확신합니다. 입력 값은 드롭 다운에서 가져오고 잘못된 값을 보낼 수 없으며 표시된 값은 작성한 값과 같은 반복기에서 가져옵니다. 어쨌든 당신이 제안한대로 날짜 분석 파 일을 모두 변경하려고 계획 했으므로 Date 객체를 변경하는 것은 정말 나쁜 생각입니다. – sergio0983

관련 문제