1<?php 2 3namespace dokuwiki\Remote; 4 5use dokuwiki\MailUtils; 6use dokuwiki\Utf8\PhpString; 7use IXR\DataType\Base64; 8use IXR\DataType\Date; 9 10/** 11 * Provides wrappers for the API calls as they existed in API Version 11 12 * 13 * No guarantees are made about the exact compatibility of the return values. 14 * 15 * @deprecated 16 */ 17class LegacyApiCore extends ApiCore 18{ 19 /** @inheritdoc */ 20 public function getMethods() 21 { 22 $methods = parent::getMethods(); 23 24 return array_merge( 25 $methods, 26 [ 27 'dokuwiki.getVersion' => new ApiCall($this->legacyGetVersion(...), 'legacy'), 28 'dokuwiki.login' => (new ApiCall($this->legacyLogin(...), 'legacy'))->setPublic(), 29 'dokuwiki.logoff' => new ApiCall($this->legacyLogoff(...), 'legacy'), 30 'dokuwiki.getPagelist' => new ApiCall($this->legacyGetPagelist(...), 'legacy'), 31 'dokuwiki.search' => new ApiCall($this->legacySearch(...), 'legacy'), 32 'dokuwiki.getTime' => new ApiCall($this->legacyGetTime(...), 'legacy'), 33 'dokuwiki.setLocks' => new ApiCall($this->legacySetLocks(...), 'legacy'), 34 'dokuwiki.getTitle' => (new ApiCall($this->legacyGetTitle(...), 'legacy'))->setPublic(), 35 'dokuwiki.appendPage' => new ApiCall($this->legacyAppendPage(...), 'legacy'), 36 'dokuwiki.createUser' => new ApiCall($this->legacyCreateUser(...), 'legacy'), 37 'dokuwiki.deleteUsers' => new ApiCall($this->legacyDeleteUsers(...), 'legacy'), 38 'wiki.getPage' => new ApiCall($this->legacyGetPage(...), 'legacy'), 39 'wiki.getPageVersion' => new ApiCall($this->legacyGetPageVersion(...), 'legacy'), 40 'wiki.getPageHTML' => new ApiCall($this->legacyGetPageHTML(...), 'legacy'), 41 'wiki.getPageHTMLVersion' => new ApiCall($this->legacyGetPageHTMLVersion(...), 'legacy'), 42 'wiki.getAllPages' => new ApiCall($this->legacyGetAllPages(...), 'legacy'), 43 'wiki.getAttachments' => new ApiCall($this->legacyGetAttachments(...), 'legacy'), 44 'wiki.getBackLinks' => new ApiCall($this->legacyGetBackLinks(...), 'legacy'), 45 'wiki.getPageInfo' => new ApiCall($this->legacyGetPageInfo(...), 'legacy'), 46 'wiki.getPageInfoVersion' => new ApiCall($this->legacyGetPageInfoVersion(...), 'legacy'), 47 'wiki.getPageVersions' => new ApiCall($this->legacyGetPageVersions(...), 'legacy'), 48 'wiki.putPage' => new ApiCall($this->legacyPutPage(...), 'legacy'), 49 'wiki.listLinks' => new ApiCall($this->legacyListLinks(...), 'legacy'), 50 'wiki.getRecentChanges' => new ApiCall($this->legacyGetRecentChanges(...), 'legacy'), 51 'wiki.getRecentMediaChanges' => new ApiCall($this->legacyGetRecentMediaChanges(...), 'legacy'), 52 'wiki.aclCheck' => new ApiCall($this->legacyAclCheck(...), 'legacy'), 53 'wiki.putAttachment' => new ApiCall($this->legacyPutAttachment(...), 'legacy'), 54 'wiki.deleteAttachment' => new ApiCall($this->legacyDeleteAttachment(...), 'legacy'), 55 'wiki.getAttachment' => new ApiCall($this->legacyGetAttachment(...), 'legacy'), 56 'wiki.getAttachmentInfo' => new ApiCall($this->legacyGetAttachmentInfo(...), 'legacy'), 57 'dokuwiki.getXMLRPCAPIVersion' => (new ApiCall($this->legacyGetXMLRPCAPIVersion(...), 'legacy')) 58 ->setPublic(), 59 'wiki.getRPCVersionSupported' => (new ApiCall($this->legacyGetRPCVersionSupported(...), 'legacy')) 60 ->setPublic(), 61 ] 62 ); 63 } 64 65 /** 66 * This returns a XMLRPC object that will not work for the new JSONRPC API 67 * 68 * @param int $ts 69 * @return Date 70 */ 71 protected function toDate($ts) 72 { 73 return new Date($ts); 74 } 75 76 77 /** 78 * @deprecated use core.getWikiVersion instead 79 */ 80 public function legacyGetVersion() 81 { 82 return getVersion(); 83 } 84 85 /** 86 * @deprecated use core.getWikiTime instead 87 */ 88 public function legacyGetTime() 89 { 90 return $this->getWikiTime(); 91 } 92 93 94 /** 95 * @deprecated use core.getPage instead 96 */ 97 public function legacyGetPage($id) 98 { 99 try { 100 return $this->getPage($id); 101 } catch (RemoteException $e) { 102 if ($e->getCode() === 121) { 103 return ''; 104 } 105 throw $e; 106 } 107 } 108 109 /** 110 * @deprecated use core.getPage instead 111 */ 112 public function legacyGetPageVersion($id, $rev = '') 113 { 114 try { 115 return $this->getPage($id, $rev); 116 } catch (RemoteException $e) { 117 if ($e->getCode() === 121) { 118 return ''; 119 } 120 throw $e; 121 } 122 } 123 124 /** 125 * @deprecated use core.getMedia instead 126 */ 127 public function legacyGetAttachment($id) 128 { 129 return new Base64(base64_decode($this->getMedia($id))); 130 } 131 132 /** 133 * @deprecated use core.getMediaInfo instead 134 */ 135 public function legacygetAttachmentInfo($id) 136 { 137 $info = $this->getMediaInfo($id); 138 return [ 139 'lastModified' => $this->toDate($info->revision), 140 'size' => $info->size, 141 ]; 142 } 143 144 /** 145 * @deprecated use core.getPageHTML instead 146 */ 147 public function legacyGetPageHTML($id) 148 { 149 try { 150 return $this->getPageHTML($id); 151 } catch (RemoteException $e) { 152 if ($e->getCode() === 121) { 153 return ''; 154 } 155 throw $e; 156 } 157 } 158 159 /** 160 * @deprecated use core.getPageHTML instead 161 */ 162 public function legacyGetPageHTMLVersion($id, $rev = '') 163 { 164 try { 165 return $this->getPageHTML($id, (int)$rev); 166 } catch (RemoteException $e) { 167 if ($e->getCode() === 121) { 168 return ''; 169 } 170 throw $e; 171 } 172 } 173 174 /** 175 * @deprecated use core.listPages instead 176 */ 177 public function legacyGetAllPages() 178 { 179 $pages = $this->listPages('', 0); 180 181 $result = []; 182 foreach ($pages as $page) { 183 $result[] = [ 184 'id' => $page->id, 185 'perms' => $page->permission, 186 'size' => $page->size, 187 'lastModified' => $this->toDate($page->revision), 188 ]; 189 } 190 return $result; 191 } 192 193 /** 194 * @deprecated use core.listPages instead 195 */ 196 public function legacyGetPagelist($ns, $opts = []) 197 { 198 $data = $this->listPages($ns, $opts['depth'] ?? 0, $opts['hash'] ?? false); 199 $result = []; 200 201 foreach ($data as $page) { 202 $result[] = [ 203 'id' => $page->id, 204 'perms' => $page->permission, 205 'size' => $page->size, 206 'rev' => $page->revision, 207 'mtime' => $page->revision, 208 'hash' => $page->hash, 209 210 ]; 211 } 212 213 return $result; 214 } 215 216 /** 217 * @deprecated use core.searchPages instead 218 */ 219 public function legacySearch($query) 220 { 221 $this->searchPages($query); 222 $pages = []; 223 224 foreach ($this->searchPages($query) as $page) { 225 $pages[] = [ 226 'id' => $page->id, 227 'score' => $page->score, 228 'rev' => $page->revision, 229 'lastModified' => $this->toDate($page->revision), 230 'size' => $page->size, 231 'snippet' => $page->snippet, 232 'title' => $page->title 233 ]; 234 } 235 236 return $pages; 237 } 238 239 /** 240 * @deprecated use core.getWikiTitle instead 241 */ 242 public function legacyGetTitle() 243 { 244 return $this->getWikiTitle(); 245 } 246 247 /** 248 * @deprecated use core.listMedia instead 249 */ 250 public function legacyGetAttachments($ns, $options = []) 251 { 252 $files = $this->listMedia($ns, $options['pattern'] ?? '', $options['depth'] ?? 0, $options['hash'] ?? false); 253 $result = []; 254 foreach ($files as $file) { 255 $result[] = [ 256 'id' => $file->id, 257 'perms' => $file->permission, 258 'size' => $file->size, 259 'rev' => $file->revision, 260 'lastModified' => $this->toDate($file->revision), 261 'mtime' => $this->toDate($file->revision), 262 'hash' => $file->hash, 263 'file' => PhpString::basename(mediaFN($file->id)), 264 'writable' => is_writable(mediaFN($file->id)), 265 'isimg' => $file->isimage, 266 267 ]; 268 } 269 return $result; 270 } 271 272 /** 273 * @deprecated use core.getPageBackLinks instead 274 */ 275 public function legacyGetBackLinks($id) 276 { 277 return $this->getPageBackLinks($id); 278 } 279 280 /** 281 * @deprecated use core.getPageInfo instead 282 */ 283 public function legacyGetPageInfo($id) 284 { 285 $info = $this->getPageInfo($id, 0); 286 return [ 287 'name' => $info->id, 288 'lastModified' => $this->toDate($info->revision), 289 'author' => $info->author, 290 'version' => $info->revision, 291 ]; 292 } 293 294 /** 295 * @deprecated use core.getPageInfo instead 296 */ 297 public function legacyGetPageInfoVersion($id, $rev = '') 298 { 299 $info = $this->getPageInfo($id, $rev); 300 return [ 301 'name' => $info->id, 302 'lastModified' => $this->toDate($info->revision), 303 'author' => $info->author, 304 'version' => $info->revision, 305 ]; 306 } 307 308 /** 309 * @deprecated use core.savePage instead 310 */ 311 public function legacyPutPage($id, $text, $params = []) 312 { 313 return $this->savePage($id, $text, $params['sum'] ?? '', $params['minor'] ?? false); 314 } 315 316 /** 317 * @deprecated use core.appendPage instead 318 */ 319 public function legacyAppendPage($id, $text, $params = []) 320 { 321 $ok = $this->appendPage($id, $text, $params['sum'] ?? '', $params['minor'] ?? false); 322 if ($ok === true) { 323 return cleanID($id); 324 } else { 325 return $ok; 326 } 327 } 328 329 /** 330 * @deprecated use plugin.usermanager.createUser instead 331 */ 332 public function legacyCreateUser($userStruct) 333 { 334 if (!auth_isadmin()) { 335 throw new AccessDeniedException('Only admins are allowed to create users', 114); 336 } 337 338 /** @var AuthPlugin $auth */ 339 global $auth; 340 341 if (!$auth->canDo('addUser')) { 342 throw new AccessDeniedException( 343 sprintf('Authentication backend %s can\'t do addUser', $auth->getPluginName()), 344 114 345 ); 346 } 347 348 $user = trim($auth->cleanUser($userStruct['user'] ?? '')); 349 $password = $userStruct['password'] ?? ''; 350 $name = trim(preg_replace('/[\x00-\x1f:<>&%,;]+/', '', $userStruct['name'] ?? '')); 351 $mail = trim(preg_replace('/[\x00-\x1f:<>&%,;]+/', '', $userStruct['mail'] ?? '')); 352 $groups = $userStruct['groups'] ?? []; 353 354 $notify = (bool)$userStruct['notify'] ?? false; 355 356 if ($user === '') throw new RemoteException('empty or invalid user', 401); 357 if ($name === '') throw new RemoteException('empty or invalid user name', 402); 358 if (!MailUtils::isValid($mail)) throw new RemoteException('empty or invalid mail address', 403); 359 360 if ((string)$password === '') { 361 $password = auth_pwgen($user); 362 } 363 364 if (!is_array($groups) || $groups === []) { 365 $groups = null; 366 } 367 368 $ok = $auth->triggerUserMod('create', [$user, $password, $name, $mail, $groups]); 369 370 if ($ok !== false && $ok !== null) { 371 $ok = true; 372 } 373 374 if ($ok) { 375 if ($notify) { 376 auth_sendPassword($user, $password); 377 } 378 } 379 380 return $ok; 381 } 382 383 384 /** 385 * @deprecated use plugin.usermanager.deleteUser instead 386 */ 387 public function legacyDeleteUsers($usernames) 388 { 389 if (!auth_isadmin()) { 390 throw new AccessDeniedException('Only admins are allowed to delete users', 114); 391 } 392 /** @var AuthPlugin $auth */ 393 global $auth; 394 return (bool)$auth->triggerUserMod('delete', [$usernames]); 395 } 396 397 /** 398 * @deprecated use core.saveMedia instead 399 */ 400 public function legacyPutAttachment($id, $file, $params = []) 401 { 402 $ok = $this->saveMedia($id, base64_encode($file), $params['ow'] ?? false); 403 if ($ok === true) { 404 return cleanID($id); 405 } else { 406 return $ok; 407 } 408 } 409 410 /** 411 * @deprecated use core.deleteMedia instead 412 */ 413 public function legacyDeleteAttachment($id) 414 { 415 $ok = $this->deleteMedia($id); 416 if ($ok === true) { 417 return 0; 418 } else { 419 return $ok; 420 } 421 } 422 423 /** 424 * @deprecated use core.aclCheck instead 425 */ 426 public function legacyAclCheck($id, $user = null, $groups = null) 427 { 428 return $this->aclCheck($id, (string)$user, (string)$groups); 429 } 430 431 /** 432 * @deprecated use core.listLinks instead 433 */ 434 public function legacyListLinks($id) 435 { 436 $links = $this->getPageLinks($id); 437 $result = []; 438 foreach ($links as $link) { 439 $result[] = [ 440 'type' => $link['type'], 441 'page' => $link['page'], 442 'href' => $link['href'], 443 ]; 444 } 445 return $result; 446 } 447 448 /** 449 * @deprecated use core.getRecentChanges instead 450 */ 451 public function legacyGetRecentChanges($timestamp) 452 { 453 $recents = $this->getRecentPageChanges($timestamp); 454 $result = []; 455 foreach ($recents as $recent) { 456 $result[] = [ 457 'name' => $recent->id, 458 'lastModified' => $this->toDate($recent->revision), 459 'author' => $recent->author, 460 'version' => $recent->revision, 461 'perms' => auth_quickaclcheck($recent->id), 462 'size' => @filesize(wikiFN($recent->id)), 463 ]; 464 } 465 return $result; 466 } 467 468 /** 469 * @deprecated use core.getRecentMediaChanges instead 470 */ 471 public function legacyGetRecentMediaChanges($timestamp) 472 { 473 $recents = $this->getRecentMediaChanges($timestamp); 474 $result = []; 475 foreach ($recents as $recent) { 476 $result[] = [ 477 'name' => $recent->id, 478 'lastModified' => $this->toDate($recent->revision), 479 'author' => $recent->author, 480 'version' => $recent->revision, 481 'perms' => auth_quickaclcheck($recent->id), 482 'size' => @filesize(mediaFN($recent->id)), 483 ]; 484 } 485 return $result; 486 } 487 488 /** 489 * @deprecated use core.getPageHistory instead 490 */ 491 public function legacyGetPageVersions($id, $first = 0) 492 { 493 $revisions = $this->getPageHistory($id, $first); 494 $result = []; 495 496 foreach ($revisions as $revision) { 497 $result[] = [ 498 'user' => $revision->author, 499 'ip' => $revision->ip, 500 'type' => $revision->type, 501 'sum' => $revision->summary, 502 'modified' => $this->toDate($revision->revision), 503 'version' => $revision->revision, 504 ]; 505 } 506 return $result; 507 } 508 509 /** 510 * @deprecated Wiki RPC spec is no longer supported 511 */ 512 public function legacyGetRPCVersionSupported() 513 { 514 return 2; 515 } 516 517 /** 518 * @deprecated use core.lockPages and core.unlockPages instead 519 */ 520 public function legacySetLocks($set) 521 { 522 $locked = $this->lockPages($set['lock']); 523 $lockfail = array_diff($set['lock'], $locked); 524 525 $unlocked = $this->unlockPages($set['unlock']); 526 $unlockfail = array_diff($set['unlock'], $unlocked); 527 528 return [ 529 'locked' => $locked, 530 'lockfail' => $lockfail, 531 'unlocked' => $unlocked, 532 'unlockfail' => $unlockfail 533 ]; 534 } 535 536 /** 537 * @deprecated use core.getAPIVersion instead 538 */ 539 public function legacyGetXMLRPCAPIVersion() 540 { 541 return $this->getAPIVersion(); 542 } 543 544 /** 545 * @deprecated use core.login instead 546 */ 547 public function legacyLogin($user, $pass) 548 { 549 return parent::login($user, $pass); 550 } 551 552 /** 553 * @deprecated use core.logoff instead 554 */ 555 public function legacyLogoff() 556 { 557 return parent::logoff(); 558 } 559} 560