Revert r83993
authorSam Reed <reedy@users.mediawiki.org>
Wed, 16 Mar 2011 00:13:10 +0000 (00:13 +0000)
committerSam Reed <reedy@users.mediawiki.org>
Wed, 16 Mar 2011 00:13:10 +0000 (00:13 +0000)
includes/api/ApiQueryCategoryMembers.php
includes/installer/MysqlUpdater.php
maintenance/archives/patch-cl_type.sql [new file with mode: 0644]
maintenance/tables.sql

index 7ca0322..e2d0149 100644 (file)
@@ -122,39 +122,27 @@ class ApiQueryCategoryMembers extends ApiQueryGeneratorBase {
                        $this->addOption( 'USE INDEX', 'cl_timestamp' );
                } else {
                        if ( $params['continue'] ) {
-                               // from|sortkey
-                               $cont = explode( '|', $params['continue'], 2 );
-                               if ( count( $cont ) != 2 ) {
+                               // type|from|sortkey
+                               $cont = explode( '|', $params['continue'], 3 );
+                               if ( count( $cont ) != 3 ) {
                                        $this->dieUsage( 'Invalid continue param. You should pass the original value returned '.
                                                'by the previous query', '_badcontinue'
                                        );
                                }
-                               list ( $from, $contsortkey )  = $cont;
-                               if ( intval( $from ) == 0 ) {
-                                       $this->dieUsage( 'Invalid continue param. You should pass the original value returned '.
-                                               'by the previous query', '_badcontinue'
-                                       );
-                               }
-                               $where_outer = array();
-                               $where_inner = array();
-                               $db = $this->getDB();
-                               $op = ( $dir === 'newer' ? '>' : '<' );
-                               $sortdir = ( $dir === 'newer' ? 'asc' : 'desc' );
-                               $where_outer[] = 'cl_sortkey ' . $op . ' ' .
-                                       $db->addQuotes( $contsortkey );
-                               // OR
-                                       $where_inner[] = 'cl_sortkey = ' .
-                                               $db->addQuotes( $contsortkey );
-                                       // AND
-                                       $where_inner[] = 'cl_from ' . $op . '= '.  $from;
-
-                               $where_outer[] = $db->makeList( $where_inner, LIST_AND );
-                               $this->addWhere( $db->makeList( $where_outer, LIST_OR ) );
-                               $this->addOption( 'ORDER BY', 
-                                       'cl_sortkey ' . $sortdir .', cl_from ' . $sortdir );
+                               $escType = $this->getDB()->addQuotes( $cont[0] );
+                               $from = intval( $cont[1] );
+                               $escSortkey = $this->getDB()->addQuotes( $cont[2] );
+                               $op = $dir == 'newer' ? '>' : '<';
+                               $this->addWhere( "cl_type $op $escType OR " .
+                                       "(cl_type = $escType AND " .
+                                       "(cl_sortkey $op $escSortkey OR " .
+                                       "(cl_sortkey = $escSortkey AND " .
+                                       "cl_from $op= $from)))"
+                               );
                                
                        } else {
-                               // The below produces ORDER BY cl_sortkey, cl_from, possibly with DESC added to each of them
+                               // The below produces ORDER BY cl_type, cl_sortkey, cl_from, possibly with DESC added to each of them
+                               $this->addWhereRange( 'cl_type', $dir, null, null );
                                $this->addWhereRange( 'cl_sortkey',
                                        $dir,
                                        $params['startsortkey'],
@@ -183,7 +171,7 @@ class ApiQueryCategoryMembers extends ApiQueryGeneratorBase {
                                        // because we don't have to worry about pipes in the sortkey that way
                                        // (and type and from can't contain pipes anyway)
                                        $this->setContinueEnumParameter( 'continue',
-                                               "{$row->cl_from}|{$row->cl_sortkey}"
+                                               "{$row->cl_type}|{$row->cl_from}|{$row->cl_sortkey}"
                                        );
                                }
                                break;
@@ -225,7 +213,7 @@ class ApiQueryCategoryMembers extends ApiQueryGeneratorBase {
                                                $this->setContinueEnumParameter( 'start', wfTimestamp( TS_ISO_8601, $row->cl_timestamp ) );
                                        } else {
                                                $this->setContinueEnumParameter( 'continue',
-                                                       "{$row->cl_from}|{$row->cl_sortkey}"
+                                                       "{$row->cl_type}|{$row->cl_from}|{$row->cl_sortkey}"
                                                );
                                        }
                                        break;
index c3186f2..db9f9c5 100644 (file)
@@ -175,6 +175,7 @@ class MysqlUpdater extends DatabaseUpdater {
                        array( 'dropIndex', 'archive', 'ar_page_revid',         'patch-archive_kill_ar_page_revid.sql' ),
                        array( 'addIndex', 'archive', 'ar_revid',               'patch-archive_ar_revid.sql' ),
                        array( 'doLangLinksLengthUpdate' ),
+                       array( 'doClTypeVarcharUpdate' ),
                );
        }
 
@@ -828,4 +829,18 @@ class MysqlUpdater extends DatabaseUpdater {
                        $this->output( "...ll_lang is up-to-date.\n" );
                }
        }
+       
+       protected function doClTypeVarcharUpdate() {
+               $categorylinks = $this->db->tableName( 'categorylinks' );
+               $res = $this->db->query( "SHOW COLUMNS FROM $categorylinks LIKE 'cl_type'" );
+               $row = $this->db->fetchObject( $res );
+               
+               if ( $row && substr( $row->Type, 0, 4 ) == 'enum' ) {
+                       $this->output( 'Changing cl_type from enum to varchar...' );
+                       $this->applyPatch( 'patch-cl_type.sql' );
+                       $this->output( "done.\n" );
+               } else {
+                       $this->output( "...cl_type is up-to-date.\n" );
+               }
+       }
 }
diff --git a/maintenance/archives/patch-cl_type.sql b/maintenance/archives/patch-cl_type.sql
new file mode 100644 (file)
index 0000000..cf7b9c3
--- /dev/null
@@ -0,0 +1,6 @@
+--
+-- Change cl_type to a varchar from an enum because of the weird semantics of
+-- the < and > operators when working with enums
+--
+
+ALTER TABLE /*_*/categorylinks MODIFY cl_type varchar(6) NOT NULL default 'page';
index 11392f1..99b70e4 100644 (file)
@@ -521,7 +521,9 @@ CREATE TABLE /*_*/categorylinks (
   -- paginate the three categories separately.  This never has to be updated
   -- after the page is created, since none of these page types can be moved to
   -- any other.
-  cl_type ENUM('page', 'subcat', 'file') NOT NULL default 'page'
+  -- This used to be ENUM('page', 'subcat', 'file') but was changed to a
+  -- varchar because of the weird semantics of < and > when used on enums
+  cl_type varchar(6) NOT NULL default 'page'
 ) /*$wgDBTableOptions*/;
 
 CREATE UNIQUE INDEX /*i*/cl_from ON /*_*/categorylinks (cl_from,cl_to);