Check bad dates and redirect, instead of 404ing, as necessary and appropriate.

Adds query, conditional, and canonical Unit Tests.

Props kovshenin, SergeyBiryukov, DrewAPicture.
Fixes #10935.



git-svn-id: https://develop.svn.wordpress.org/trunk@25280 602fd350-edb4-49c9-b593-d223f7449a82
This commit is contained in:
Scott Taylor 2013-09-06 16:35:22 +00:00
parent 69a949d160
commit 09b9c44de9
5 changed files with 85 additions and 4 deletions

View File

@ -101,6 +101,20 @@ function redirect_canonical( $requested_url = null, $do_redirect = true ) {
}
}
if ( get_query_var( 'day' ) && get_query_var( 'monthnum' ) && get_query_var( 'year' ) ) {
$year = get_query_var( 'year' );
$month = get_query_var( 'monthnum' );
$day = get_query_var( 'day' );
$date = sprintf( '%04d-%02d-%02d', $year, $month, $day );
if ( ! wp_checkdate( $month, $day, $year, $date ) ) {
$redirect_url = get_month_link( $year, $month );
$redirect['query'] = _remove_qs_args_if_not_in_url( $redirect['query'], array( 'year', 'monthnum', 'day' ), $redirect_url );
}
} elseif ( get_query_var( 'monthnum' ) && get_query_var( 'year' ) && 12 < get_query_var( 'monthnum' ) ) {
$redirect_url = get_year_link( get_query_var( 'year' ) );
$redirect['query'] = _remove_qs_args_if_not_in_url( $redirect['query'], array( 'year', 'monthnum' ), $redirect_url );
}
if ( ! $redirect_url ) {
if ( $redirect_url = redirect_guess_404_permalink() ) {
$redirect['query'] = _remove_qs_args_if_not_in_url( $redirect['query'], array( 'page', 'feed', 'p', 'page_id', 'attachment_id', 'pagename', 'name', 'post_type' ), $redirect_url );

View File

@ -1513,15 +1513,24 @@ class WP_Query {
if ( $qv['day'] ) {
if ( ! $this->is_date ) {
$this->is_day = true;
$this->is_date = true;
$date = sprintf( '%04d-%02d-%02d', $qv['year'], $qv['monthnum'], $qv['day'] );
if ( $qv['monthnum'] && $qv['year'] && ! wp_checkdate( $qv['monthnum'], $qv['day'], $qv['year'], $date ) ) {
$qv['error'] = '404';
} else {
$this->is_day = true;
$this->is_date = true;
}
}
}
if ( $qv['monthnum'] ) {
if ( ! $this->is_date ) {
$this->is_month = true;
$this->is_date = true;
if ( 12 < $qv['monthnum'] ) {
$qv['error'] = '404';
} else {
$this->is_month = true;
$this->is_date = true;
}
}
}

View File

@ -239,6 +239,9 @@ class Tests_Canonical extends WP_UnitTestCase {
array( '/?year=2008', '/2008/'),
array( '/2012/13/', '/2012/'),
array( '/2012/11/51/', '/2012/11/'),
// Authors
array( '/?author=%d', '/author/canonical-author/' ),
// array( '/?author=%d&year=2008', '/2008/?author=3'),

View File

@ -629,4 +629,12 @@ class Tests_Query_Conditionals extends WP_UnitTestCase {
// '[0-9]{4}/[0-9]{1,2}/[0-9]{1,2}/[^/]+/attachment/([^/]+)/trackback/?$' => 'index.php?attachment=$matches[1]&tb=1',
// '[0-9]{4}/[0-9]{1,2}/[0-9]{1,2}/[^/]+/attachment/([^/]+)/feed/(feed|rdf|rss|rss2|atom)/?$' => 'index.php?attachment=$matches[1]&feed=$matches[2]',
// '[0-9]{4}/[0-9]{1,2}/[0-9]{1,2}/[^/]+/attachment/([^/]+)/(feed|rdf|rss|rss2|atom)/?$' => 'index.php?attachment=$matches[1]&feed=$matches[2]',
function test_bad_dates() {
$this->go_to( '/2013/13/13/' );
$this->assertQueryTrue( 'is_404' );
$this->go_to( '/2013/11/41/' );
$this->assertQueryTrue( 'is_404' );
}
}

View File

@ -486,4 +486,51 @@ class Tests_Query_Results extends WP_UnitTestCase {
$author_ids = array_unique( wp_list_pluck( $posts, 'post_author' ) );
$this->assertEqualSets( array( $author_1 ), $author_ids );
}
/**
* @ticket 10935
*/
function test_query_is_date() {
$this->q->query( array(
'year' => '2007',
'monthnum' => '01',
'day' => '01',
) );
$this->assertTrue( $this->q->is_date );
$this->assertTrue( $this->q->is_day );
$this->assertFalse( $this->q->is_month );
$this->assertFalse( $this->q->is_year );
$this->q->query( array(
'year' => '2007',
'monthnum' => '01',
) );
$this->assertTrue( $this->q->is_date );
$this->assertFalse( $this->q->is_day );
$this->assertTrue( $this->q->is_month );
$this->assertFalse( $this->q->is_year );
$this->q->query( array(
'year' => '2007',
) );
$this->assertTrue( $this->q->is_date );
$this->assertFalse( $this->q->is_day );
$this->assertFalse( $this->q->is_month );
$this->assertTrue( $this->q->is_year );
$this->q->query( array(
'year' => '2007',
'monthnum' => '01',
'day' => '50',
) );
$this->assertTrue( $this->q->is_404 );
$this->assertFalse( $this->q->is_date );
$this->assertFalse( $this->q->is_day );
$this->assertFalse( $this->q->is_month );
$this->assertFalse( $this->q->is_year );
}
}