Update the FSF's address in all these GPL stub headers
[lhc/web/wiklou.git] / maintenance / namespaceDupes.php
1 <?php
2 # Copyright (C) 2005 Brion Vibber <brion@pobox.com>
3 # http://www.mediawiki.org/
4 #
5 # This program is free software; you can redistribute it and/or modify
6 # it under the terms of the GNU General Public License as published by
7 # the Free Software Foundation; either version 2 of the License, or
8 # (at your option) any later version.
9 #
10 # This program is distributed in the hope that it will be useful,
11 # but WITHOUT ANY WARRANTY; without even the implied warranty of
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 # GNU General Public License for more details.
14 #
15 # You should have received a copy of the GNU General Public License along
16 # with this program; if not, write to the Free Software Foundation, Inc.,
17 # 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18 # http://www.gnu.org/copyleft/gpl.html
19
20 $options = array( 'fix', 'suffix', 'help' );
21
22 /** */
23 require_once( 'commandLine.inc' );
24 #require_once( 'maintenance/userDupes.inc' );
25
26 if(isset( $options['help'] ) ) {
27 print <<<END
28 usage: namespaceDupes.php [--fix] [--suffix=<text>] [--help]
29 --help : this help message
30 --fix : attempt to automatically fix errors
31 --suffix=<text> : dupes will be renamed with correct namespace with <text>
32 appended after the article name.
33
34 END;
35 die;
36 }
37
38 class NamespaceConflictChecker {
39 function NamespaceConflictChecker( &$db ) {
40 $this->db =& $db;
41 }
42
43 function checkAll( $fix, $suffix = '' ) {
44 global $wgContLang;
45 $spaces = $wgContLang->getNamespaces();
46 $ok = true;
47 foreach( $spaces as $ns => $name ) {
48 $ok = $this->checkNamespace( $ns, $name, $fix, $suffix ) && $ok;
49 }
50 return $ok;
51 }
52
53 function checkNamespace( $ns, $name, $fix, $suffix = '' ) {
54 echo "Checking namespace $ns: \"$name\"\n";
55 if( $name == '' ) {
56 echo "... skipping article namespace\n";
57 return true;
58 }
59
60 $conflicts = $this->getConflicts( $ns, $name );
61 $count = count( $conflicts );
62 if( $count == 0 ) {
63 echo "... no conflicts detected!\n";
64 return true;
65 }
66
67 echo "... $count conflicts detected:\n";
68 $ok = true;
69 foreach( $conflicts as $row ) {
70 $resolvable = $this->reportConflict( $row, $suffix );
71 $ok = $ok && $resolvable;
72 if( $fix && ( $resolvable || $suffix != '' ) ) {
73 $ok = $this->resolveConflict( $row, $resolvable, $suffix ) && $ok;
74 }
75 }
76 return $ok;
77 }
78
79 function getConflicts( $ns, $name ) {
80 $page = $this->newSchema() ? 'page' : 'cur';
81 $table = $this->db->tableName( $page );
82
83 $prefix = $this->db->strencode( $name );
84 $likeprefix = str_replace( '_', '\\_', $prefix);
85
86 $sql = "SELECT {$page}_id AS id,
87 {$page}_title AS oldtitle,
88 $ns AS namespace,
89 TRIM(LEADING '$prefix:' FROM {$page}_title) AS title
90 FROM {$table}
91 WHERE {$page}_namespace=0
92 AND {$page}_title LIKE '$likeprefix:%'";
93
94 $result = $this->db->query( $sql, 'NamespaceConflictChecker::getConflicts' );
95
96 $set = array();
97 while( $row = $this->db->fetchObject( $result ) ) {
98 $set[] = $row;
99 }
100 $this->db->freeResult( $result );
101
102 return $set;
103 }
104
105 function reportConflict( $row, $suffix ) {
106 $newTitle = Title::makeTitle( $row->namespace, $row->title );
107 printf( "... %d (0,\"%s\") -> (%d,\"%s\") [[%s]]\n",
108 $row->id,
109 $row->oldtitle,
110 $row->namespace,
111 $row->title,
112 $newTitle->getPrefixedText() );
113
114 $id = $newTitle->getArticleId();
115 if( $id ) {
116 echo "... *** cannot resolve automatically; page exists with ID $id ***\n";
117 return false;
118 } else {
119 return true;
120 }
121 }
122
123 function resolveConflict( $row, $resolvable, $suffix ) {
124 if( !$resolvable ) {
125 $row->title .= $suffix;
126 $title = Title::makeTitle( $row->namespace, $row->title );
127 echo "... *** using suffixed form [[" . $title->getPrefixedText() . "]] ***\n";
128 }
129 $tables = $this->newSchema()
130 ? array( 'page' )
131 : array( 'cur', 'old' );
132 foreach( $tables as $table ) {
133 $this->resolveConflictOn( $row, $table );
134 }
135 return true;
136 }
137
138 function resolveConflictOn( $row, $table ) {
139 $fname = 'NamespaceConflictChecker::resolveConflictOn';
140 echo "... resolving on $table... ";
141 $this->db->update( $table,
142 array(
143 "{$table}_namespace" => $row->namespace,
144 "{$table}_title" => $row->title,
145 ),
146 array(
147 "{$table}_namespace" => 0,
148 "{$table}_title" => $row->oldtitle,
149 ),
150 $fname );
151 echo "ok.\n";
152 return true;
153 }
154
155 function newSchema() {
156 return class_exists( 'Revision' );
157 }
158 }
159
160
161
162
163 $wgTitle = Title::newFromText( 'Namespace title conflict cleanup script' );
164
165 $fix = isset( $options['fix'] );
166 $suffix = isset( $options['suffix'] ) ? $options['suffix'] : '';
167 $dbw =& wfGetDB( DB_MASTER );
168 $duper = new NamespaceConflictChecker( $dbw );
169 $retval = $duper->checkAll( $fix, $suffix );
170
171 if( $retval ) {
172 echo "\nLooks good!\n";
173 exit( 0 );
174 } else {
175 echo "\nOh noeees\n";
176 exit( -1 );
177 }
178
179 ?>