PageRenderTime 27ms CodeModel.GetById 20ms RepoModel.GetById 0ms app.codeStats 1ms

/cms/setup/index.php

https://github.com/iconifyit/SkyBlue-1.1
PHP | 657 lines | 538 code | 105 blank | 14 comment | 73 complexity | 09fb6f109fa73610a6603d0023184cd4 MD5 | raw file
  1. <?php
  2. /**
  3. * @version 1.1 RC1 2008-11-20 21:18:00 $
  4. * @package SkyBlueCanvas
  5. * @copyright Copyright (C) 2005 - 2008 Scott Edwin Lewis. All rights reserved.
  6. * @license GNU/GPL, see COPYING.txt
  7. * SkyBlueCanvas is free software. This version may have been modified pursuant
  8. * to the GNU General Public License, and as distributed it includes or
  9. * is derivative of works licensed under the GNU General Public License or
  10. * other free or open source software licenses.
  11. * See COPYING.txt for copyright notices and details.
  12. */
  13. ini_set('error_reporting', E_ALL);
  14. ini_set('display_errors', 'On');
  15. define('SKYBLUE', 1);
  16. define('BASE_PAGE', 'index.php');
  17. define('SETUP_PATH_TO_ROOT', '../');
  18. define('SETUP_USERNAME_LENGTH', 4);
  19. define('SETUP_PASSWORD_LENGTH', 4);
  20. define('SETUP_PASSWORD_NOT_SAVED',
  21. 'You username and password could not be saved.');
  22. define('SETUP_USERNAME_NULL',
  23. 'You did not provide a username.');
  24. define('SETUP_USERNAME_TOO_SHORT',
  25. 'Your username must be at least ' . SETUP_USERNAME_LENGTH . ' characters long.');
  26. define('SETUP_PASSWORD_NULL',
  27. 'You did not provide a password.');
  28. define('SETUP_PASSWORD_TOO_SHORT',
  29. 'Your password must be at least ' . SETUP_PASSWORD_LENGTH . ' characters long.');
  30. define('SETUP_PASSWORD_MISMATCH',
  31. 'Your password confirmation did not match the password you entered.');
  32. define('SETUP_URL_LOGIN', '../admin.php');
  33. define('SETUP_HTML_SKIN', '../ui/admin/html/skin.index.html');
  34. define('SETUP_HTML_NO_INSTALL', "html/no.install.html");
  35. define('SETUP_HTML_CONFIG_TABLE', "html/config.table.html");
  36. define('SETUP_HTML_URL', 'html/address.html');
  37. define('SETUP_HTML_PASSWORD', 'html/password.html');
  38. define('SETUP_HTML_FINISH', 'html/finish.html');
  39. define('SETUP_TOKEN_ERROR', '{error}');
  40. define('SETUP_KEY_USERNAME', 'username');
  41. define('SETUP_KEY_PASSWORD', 'password');
  42. define('SETUP_KEY_SAVEPASS', 'savepassword');
  43. define('SETUP_KEY_SAVEURL', 'saveurl');
  44. define('SETUP_KEY_SHOWURL', 'urlpage');
  45. define('SETUP_KEY_FINISH', 'finish');
  46. define('SETUP_KEY_ERROR', 'error');
  47. define('SETUP_KEY_MSG', 'message');
  48. define('SETUP_KEY_EVENT', 'event');
  49. define('SETUP_KEY_START', 'start');
  50. define('SETUP_STR_LOGIN', 'login');
  51. define('SETUP_TYPE_PASSWORD', 'login');
  52. define('SETUP_KEY_CONFIRM_PASSWORD', 'confirmpassword');
  53. define('SETUP_URL_START',
  54. BASE_PAGE
  55. );
  56. define('SETUP_URL_PASSWORD',
  57. BASE_PAGE . '?' . SETUP_KEY_EVENT . '=' . SETUP_KEY_PASSWORD
  58. );
  59. define('SETUP_URL_FINISH',
  60. BASE_PAGE . '?' . SETUP_KEY_EVENT . '=' . SETUP_KEY_FINISH
  61. );
  62. define('SETUP_URL_URL',
  63. BASE_PAGE . '?' . SETUP_KEY_EVENT . '=' . SETUP_KEY_SHOWURL
  64. );
  65. require_once(SETUP_PATH_TO_ROOT . 'includes/object.class.php');
  66. require_once(SETUP_PATH_TO_ROOT . 'includes/observer.class.php');
  67. require_once(SETUP_PATH_TO_ROOT . 'includes/error.class.php');
  68. require_once(SETUP_PATH_TO_ROOT . 'includes/conf.functions.php');
  69. require_once(SETUP_PATH_TO_ROOT . 'includes/filter.php');
  70. require_once(SETUP_PATH_TO_ROOT . 'includes/filesystem.php');
  71. require_once(SETUP_PATH_TO_ROOT . 'includes/core.php');
  72. require_once(SETUP_PATH_TO_ROOT . 'includes/skin.class.php');
  73. require_once(SETUP_PATH_TO_ROOT . 'includes/factory.bundle.php');
  74. require_once(SETUP_PATH_TO_ROOT.'includes/request.php');
  75. $Core = new Core(array('path'=>SETUP_PATH_TO_ROOT));
  76. $config = $Core->LoadConfig();
  77. new SetupWizard();
  78. class SetupWizard {
  79. var $event;
  80. var $html;
  81. var $error;
  82. var $config;
  83. var $IsError;
  84. var $configTable;
  85. var $safeMode;
  86. var $hasPosix;
  87. function __construct() {
  88. global $Core;
  89. $this->hasPosix = $this->hasPosixEnabled();
  90. $this->event = $Core->GetVar($_REQUEST, SETUP_KEY_EVENT, null);
  91. if ($this->event !== SETUP_KEY_FINISH && $this->CheckExistingInstall()) {
  92. $this->ShowNoInstall();
  93. exit(0);
  94. }
  95. $this->GetLastError();
  96. switch ($this->event) {
  97. case SETUP_KEY_SAVEPASS:
  98. $this->SavePassword();
  99. break;
  100. case SETUP_KEY_FINISH:
  101. $this->Finish();
  102. break;
  103. case SETUP_KEY_SAVEURL:
  104. $this->SaveUrl();
  105. break;
  106. case SETUP_KEY_SHOWURL:
  107. if (!$this->DoConfigCheck()) {
  108. $Core->SBRedirect(SETUP_URL_START);
  109. }
  110. $this->UrlPage();
  111. $this->ShowPage();
  112. break;
  113. case SETUP_KEY_PASSWORD:
  114. case SETUP_KEY_START:
  115. if (!$this->DoConfigCheck()) {
  116. $Core->SBRedirect(SETUP_URL_START);
  117. }
  118. $this->StartPage();
  119. $this->ShowPage();
  120. break;
  121. case 'login':
  122. $Core->SBRedirect(SETUP_URL_LOGIN);
  123. break;
  124. default:
  125. $this->ShowConfigTable();
  126. break;
  127. }
  128. }
  129. function SetupWizard() {
  130. $this->__construct();
  131. }
  132. function hasPosixEnabled() {
  133. return (function_exists('posix_geteuid') && is_callable('posix_geteuid'));
  134. }
  135. function makeRequiredDirs() {
  136. $required = array(
  137. SETUP_PATH_TO_ROOT . 'data/ads',
  138. SETUP_PATH_TO_ROOT . 'data/gadgets',
  139. SETUP_PATH_TO_ROOT . 'cache'
  140. );
  141. for ($i=0; $i<count($required); $i++) {
  142. if (!is_dir($required[$i])) {
  143. FileSystem::make_dir($required[$i]);
  144. }
  145. }
  146. }
  147. function DoConfigCheck() {
  148. global $Core;
  149. $this->makeRequiredDirs();
  150. $file_flag = 1;
  151. $dir_flag = 1;
  152. $safemode = ini_get('safe_mode');
  153. $this->safeMode = $safemode;
  154. $files = $Core->ListFiles(SETUP_PATH_TO_ROOT . 'data/xml/', array());
  155. $dirs = array(
  156. SETUP_PATH_TO_ROOT . 'data/',
  157. SETUP_PATH_TO_ROOT . 'data/ads/',
  158. SETUP_PATH_TO_ROOT . 'data/gadgets/',
  159. SETUP_PATH_TO_ROOT . 'data/media/',
  160. SETUP_PATH_TO_ROOT . 'data/plugins/',
  161. SETUP_PATH_TO_ROOT . 'data/skins/',
  162. SETUP_PATH_TO_ROOT . 'data/xml/'
  163. );
  164. $dir_list = array();
  165. for ($i=0; $i<count($dirs); $i++) {
  166. $writable = FileSystem::writable($dirs[$i]);
  167. if ($writable) {
  168. $dir_flag = 0;
  169. }
  170. array_push($dir_list, array($dirs[$i], $writable));
  171. }
  172. $file_list = array();
  173. for ($i=0; $i<count($files); $i++) {
  174. $writable = FileSystem::writable($files[$i]);
  175. if ($writable) {
  176. $file_flag = 0;
  177. }
  178. array_push($file_list, array($files[$i], $writable));
  179. }
  180. $this->configTable = array(
  181. 'safe_mode' => $safemode,
  182. 'dir_list' => $dir_list,
  183. 'file_list' => $file_list
  184. );
  185. if ($dir_flag == 1 || $file_flag == 1) {
  186. return false;
  187. }
  188. return true;
  189. }
  190. function getExpectedPerms($file) {
  191. if (!$this->hasPosix) {
  192. return "775";
  193. }
  194. $pgid = FileSystem::process_gid();
  195. $puid = FileSystem::process_uid();
  196. $sgid = FileSystem::file_group($file);
  197. $suid = FileSystem::file_uid($file);
  198. $snam = FileSystem::file_owner($file);
  199. $pmem = FileSystem::process_members();
  200. if ($puid == $suid) {
  201. return "644";
  202. }
  203. else if ($pgid == $sgid) {
  204. return "775";
  205. }
  206. else if (in_array($suid, $pmem) || in_array($snam, $pmem)) {
  207. return "775";
  208. }
  209. return "777";
  210. }
  211. function ShowConfigTable() {
  212. $flag = $this->DoConfigCheck() == 0;
  213. $safemode = $this->configTable['safe_mode'];
  214. $dir_list = $this->configTable['dir_list'];
  215. $file_list = $this->configTable['file_list'];
  216. $caution_flag = 0;
  217. global $Core;
  218. $this->html = str_replace(
  219. '{page:content}',
  220. FileSystem::read_file(SETUP_HTML_CONFIG_TABLE),
  221. FileSystem::read_file(SETUP_HTML_SKIN)
  222. );
  223. $this->html = str_replace('"ui/', '"../ui/', $this->html);
  224. $dontShow = array(
  225. '{page:dashboard}',
  226. '{analytics}',
  227. '{inc:wysiwygeditor}',
  228. '{inc:scripts}'
  229. );
  230. $class = 'pass';
  231. $value = 'Off';
  232. if ($safemode == 1) {
  233. $class = 'fail';
  234. $value = 'On';
  235. }
  236. $server_settings =
  237. "<tr><td class=\"$class\">Safe Mode</td>"
  238. . "<td class=\"$class\" align=\"center\">{$value}</td>"
  239. . "<td class=\"expected\" align=\"center\">Off</td></tr>";
  240. $class = 'pass';
  241. if (!$this->hasPosix) {
  242. $class = 'fail';
  243. }
  244. $posix = "Enabled";
  245. if (!$this->hasPosix) {
  246. $posix = "Disabled";
  247. }
  248. $server_settings .=
  249. "<tr><td class=\"$class\">Posix Library</td>"
  250. . "<td class=\"$class\" align=\"center\">{$posix}</td>"
  251. . "<td class=\"expected\" align=\"center\">Enabled</td></tr>";
  252. $this->html = str_replace(
  253. '{config_test:settings}',
  254. $server_settings,
  255. $this->html
  256. );
  257. $class = '';
  258. $value = '';
  259. $rows = null;
  260. for ($i=0; $i<count($dir_list); $i++) {
  261. $dirname = str_replace('../', '', $dir_list[$i][0]);
  262. $perms = @substr(decoct(fileperms($dir_list[$i][0])), -3);
  263. $expected = $this->getExpectedPerms($dir_list[$i][0]);
  264. if ($expected == "777") {
  265. $caution_flag = 1;
  266. }
  267. $class = 'pass';
  268. if (!$this->perm_compare($expected, $perms)) {
  269. $flag = 1;
  270. $class = "fail";
  271. }
  272. $rows .= "<tr><td class=\"$class\">{$dirname}</td>"
  273. . "<td align=\"center\" class=\"$class\">{$perms}</td>"
  274. . "<td class=\"expected\" align=\"center\">$expected</td></tr>\n";
  275. }
  276. $this->html = str_replace(
  277. '{config_test:dirs}',
  278. $rows,
  279. $this->html
  280. );
  281. $rows = null;
  282. for ($i=0; $i<count($file_list); $i++) {
  283. $filename = str_replace('../', '', $file_list[$i][0]);
  284. $perms = @substr(decoct(fileperms($file_list[$i][0])), -3);
  285. $expected = $this->getExpectedPerms($file_list[$i][0]);
  286. if ($expected == "777") {
  287. $caution_flag = 1;
  288. }
  289. $class = "pass";
  290. if (!$this->perm_compare($expected, $perms)) {
  291. $flag = 1;
  292. $class = "fail";
  293. }
  294. $rows .= "<tr><td class=\"$class\">{$filename}</td>"
  295. . "<td align=\"center\" class=\"$class\">{$perms}</td>"
  296. . "<td class=\"expected\" align=\"center\">$expected</td></tr>\n";
  297. }
  298. $this->html = str_replace(
  299. '{config_test:files}',
  300. $rows,
  301. $this->html
  302. );
  303. $configStyle = "div#no-posix, #config-pass, #config-warn {display:none;}";
  304. if (!$flag && $caution_flag) {
  305. $configStyle = "div#no-posix, #config-pass, #config-fail {display:none;}";
  306. }
  307. else if (!$flag) {
  308. $configStyle = "div#no-posix, #config-fail, #config-warn {display:none;}";
  309. }
  310. if (!$this->hasPosix) {
  311. $configStyle = "#config-pass, #config-warn, #config-fail {display:none;}";
  312. }
  313. $this->html = str_replace('/*config-style*/', $configStyle, $this->html);
  314. $this->html = str_replace($dontShow, null, $this->html);
  315. $this->html = str_replace('{skyblue:name}', SB_PROD_NAME, $this->html);
  316. $this->html = str_replace('{skyblue:version}', SB_VERSION, $this->html);
  317. $this->html = str_replace('{page:title}', 'Configuration Details', $this->html);
  318. echo $this->html;
  319. }
  320. function perm_compare($perm1, $perm2) {
  321. if (strlen($perm1) != 3) return false;
  322. if (strlen($perm2) != 3) return false;
  323. if (intval($perm1{0}) > intval($perm2{0})) {
  324. return false;
  325. }
  326. if (intval($perm1{1}) > intval($perm2{1})) {
  327. return false;
  328. }
  329. if (intval($perm1{2}) > intval($perm2{2})) {
  330. return false;
  331. }
  332. return true;
  333. }
  334. function CheckExistingInstall() {
  335. global $Core;
  336. if (file_exists(SB_LOGIN_FILE) &&
  337. file_exists(SB_CONFIG_XML_FILE) &&
  338. file_exists(SB_PAGE_FILE) &&
  339. file_exists(SB_MENU_GRP_FILE))
  340. {
  341. return 1;
  342. }
  343. return 0;
  344. }
  345. function ShowNoInstall() {
  346. global $Core;
  347. $this->html = str_replace(
  348. '{page:content}',
  349. FileSystem::read_file(SETUP_HTML_NO_INSTALL),
  350. FileSystem::read_file(SETUP_HTML_SKIN)
  351. );
  352. $this->html = str_replace('"ui/', '"../ui/', $this->html);
  353. $dontShow = array(
  354. '{page:dashboard}',
  355. '{analytics}',
  356. '{inc:wysiwygeditor}',
  357. '{inc:scripts}'
  358. );
  359. $this->html = str_replace($dontShow, null, $this->html);
  360. $this->html = str_replace('{skyblue:name}', SB_PROD_NAME, $this->html);
  361. $this->html = str_replace('{skyblue:version}', SB_VERSION, $this->html);
  362. $this->html = str_replace('{page:title}', 'Create Your Password', $this->html);
  363. echo $this->html;
  364. }
  365. function Finish() {
  366. global $Core;
  367. $this->html = str_replace(
  368. '{page:content}',
  369. FileSystem::read_file(SETUP_HTML_FINISH),
  370. FileSystem::read_file(SETUP_HTML_SKIN)
  371. );
  372. $this->html = str_replace('"ui/', '"' . SETUP_PATH_TO_ROOT . 'ui/', $this->html);
  373. $dontShow = array(
  374. '{page:dashboard}',
  375. '{analytics}',
  376. '{inc:wysiwygeditor}',
  377. '{inc:scripts}'
  378. );
  379. $this->html = str_replace($dontShow, null, $this->html);
  380. $this->html = str_replace('{skyblue:name}', SB_PROD_NAME, $this->html);
  381. $this->html = str_replace('{skyblue:version}', SB_VERSION, $this->html);
  382. $this->html = str_replace('{page:title}', 'Congratulations!', $this->html);
  383. echo $this->html;
  384. }
  385. function GetLastError() {
  386. if (isset($_SESSION[SETUP_KEY_ERROR]) &&
  387. !empty($_SESSION[SETUP_KEY_ERROR]))
  388. {
  389. $error = $_SESSION[SETUP_KEY_ERROR];
  390. unset($_SESSION[SETUP_KEY_ERROR]);
  391. $this->error =
  392. "<div class=\"msg-error\">\n" .
  393. "<h2>Error</h2>\n" .
  394. "<p>" . $error[SETUP_KEY_MSG] . "</p>\n" .
  395. "</div>\n";
  396. }
  397. }
  398. function InitLoginFile() {
  399. global $Core;
  400. if (file_exists(SB_LOGIN_FILE)) {
  401. $this->CheckExistingInstall();
  402. }
  403. $xml = $Core->xmlHandler->ObjsToXML(array(), SETUP_TYPE_PASSWORD);
  404. $Core->WriteFile(SB_LOGIN_FILE, $xml);
  405. }
  406. function SetError($message) {
  407. $_SESSION[SETUP_KEY_ERROR] = array(
  408. SETUP_KEY_MSG => $message
  409. );
  410. }
  411. function ConfirmAuthInfo($username, $password, $confirm) {
  412. if (empty($username)) {
  413. $this->IsError = 1;
  414. $this->SetError(SETUP_USERNAME_NULL);
  415. return;
  416. }
  417. else if (strlen($username) < SETUP_USERNAME_LENGTH) {
  418. $this->IsError = 1;
  419. $this->SetError(SETUP_USERNAME_TOO_SHORT);
  420. return;
  421. }
  422. else if (empty($password)) {
  423. $this->IsError = 1;
  424. $this->SetError(SETUP_PASSWORD_NULL);
  425. return;
  426. }
  427. else if (strlen($password) < SETUP_PASSWORD_LENGTH) {
  428. $this->IsError = 1;
  429. $this->SetError(SETUP_PASSWORD_TOO_SHORT);
  430. return;
  431. }
  432. else if ($password !== $confirm) {
  433. $this->IsError = 1;
  434. $this->SetError(SETUP_PASSWORD_MISMATCH);
  435. return;
  436. }
  437. }
  438. function SavePassword() {
  439. global $Core;
  440. global $config;
  441. $username = $Core->GetVar($_POST, SETUP_KEY_USERNAME, null);
  442. $password = $Core->GetVar($_POST, SETUP_KEY_PASSWORD, null);
  443. $confirm = $Core->GetVar($_POST, SETUP_KEY_CONFIRM_PASSWORD, null);
  444. $this->ConfirmAuthInfo($username, $password, $confirm);
  445. if ($this->IsError) {
  446. $Core->SBRedirect(SETUP_URL_PASSWORD);
  447. exit(0);
  448. }
  449. $_SESSION[SETUP_KEY_ERROR] = null;
  450. $this->InitLoginFile();
  451. $login = new stdClass;
  452. $login->id = 1;
  453. $login->username = md5(
  454. SB_PASS_SALT.$Core->GetVar($_POST, SETUP_KEY_USERNAME, null)
  455. );
  456. $login->password = md5(
  457. SB_PASS_SALT.$Core->GetVar($_POST, SETUP_KEY_PASSWORD, null)
  458. );
  459. $xml = $Core->xmlHandler->ObjsToXML(array($login), SETUP_STR_LOGIN);
  460. if (!$Core->WriteFile(SB_LOGIN_FILE, $xml, 1)) {
  461. $this->IsError = 1;
  462. $this->SetError(SETUP_PASSWORD_NOT_SAVED);
  463. $Core->SBRedirect(SETUP_URL_PASSWORD);
  464. }
  465. $Core->SBRedirect(SETUP_URL_FINISH);
  466. }
  467. function SaveUrl() {
  468. global $Core;
  469. global $config;
  470. $url = $Core->GetVar($_POST, 'url', null);
  471. $arr = $this->sbc_parse_url($url);
  472. if (! isset($arr['host']) || empty($arr['host'])) {
  473. $this->IsError = 1;
  474. $this->SetError(
  475. "You must specify a fully-qualified domain.<br />"
  476. . "Example: http://www.mydomain.com"
  477. );
  478. $Core->SBRedirect(SETUP_URL_URL);
  479. exit(0);
  480. }
  481. $_SESSION[SETUP_KEY_ERROR] = null;
  482. $config = $Core->xmlHandler->ParserMain(SB_CONFIG_XML_FILE);
  483. $config = $config[0];
  484. /**
  485. * Add trailing slash
  486. */
  487. if ($url{strlen($url-1)} != "/") $url .= "/";
  488. $config->site_url = $url;
  489. $xml = $Core->xmlHandler->ObjsToXML(array($config), "configuration");
  490. if (!$Core->WriteFile(SB_CONFIG_XML_FILE, $xml, 1)) {
  491. $this->IsError = 1;
  492. $this->SetError("Your web site address could not be saved");
  493. $Core->SBRedirect(SETUP_URL_URL);
  494. }
  495. $Core->SBRedirect(SETUP_URL_PASSWORD);
  496. }
  497. function sbc_parse_url($url) {
  498. if (empty($url)) return array();
  499. return @parse_url($url);
  500. }
  501. function ShowPage() {
  502. echo str_replace(SETUP_TOKEN_ERROR, $this->error, $this->html);
  503. }
  504. function UrlPage() {
  505. global $Core;
  506. $this->html = str_replace(
  507. '{page:content}',
  508. FileSystem::read_file(SETUP_HTML_URL),
  509. FileSystem::read_file(SETUP_HTML_SKIN)
  510. );
  511. $this->html = str_replace('"ui/', '"' . SETUP_PATH_TO_ROOT . 'ui/', $this->html);
  512. $dontShow = array(
  513. '{page:dashboard}',
  514. '{analytics}',
  515. '{inc:wysiwygeditor}',
  516. '{inc:scripts}'
  517. );
  518. $this->html = str_replace($dontShow, null, $this->html);
  519. $this->html = str_replace('{skyblue:name}', SB_PROD_NAME, $this->html);
  520. $this->html = str_replace('{skyblue:version}', SB_VERSION, $this->html);
  521. $this->html = str_replace('{page:title}', 'Enter Your Site URL', $this->html);
  522. }
  523. function StartPage() {
  524. global $Core;
  525. $this->html = str_replace(
  526. '{page:content}',
  527. FileSystem::read_file(SETUP_HTML_PASSWORD),
  528. FileSystem::read_file(SETUP_HTML_SKIN)
  529. );
  530. $this->html = str_replace('"ui/', '"' . SETUP_PATH_TO_ROOT . 'ui/', $this->html);
  531. if ($this->safeMode == 1) {
  532. $this->html = str_replace(
  533. '<!--#safemode_flag-->',
  534. '<div class="msg-warning"><h2>Warning</h2>' .
  535. '<p>Safe Mode is enabled on your server. You can continue with the installation ' .
  536. 'but this may cause SkyBlueCanvas to malfunction.</p></div>',
  537. $this->html
  538. );
  539. }
  540. $dontShow = array(
  541. '{page:dashboard}',
  542. '{analytics}',
  543. '{inc:wysiwygeditor}',
  544. '{inc:scripts}'
  545. );
  546. $this->html = str_replace($dontShow, null, $this->html);
  547. $this->html = str_replace('{skyblue:name}', SB_PROD_NAME, $this->html);
  548. $this->html = str_replace('{skyblue:version}', SB_VERSION, $this->html);
  549. $this->html = str_replace('{page:title}', 'Create Your Password', $this->html);
  550. }
  551. }
  552. ?>