diff options
| -rw-r--r-- | inc/config.php | 9 | ||||
| -rw-r--r-- | inc/mod.php | 130 | ||||
| -rw-r--r-- | inc/user.php | 87 | ||||
| -rw-r--r-- | mod.php | 73 |
4 files changed, 201 insertions, 98 deletions
diff --git a/inc/config.php b/inc/config.php index 164c1f1a..3bb24b85 100644 --- a/inc/config.php +++ b/inc/config.php @@ -67,6 +67,9 @@ define('ERROR_INVALID', 'Invalid username and/or password.', true); define('ERROR_INVALIDAFTER', 'Invalid username and/or password. Your user may have been deleted or changed.'); define('ERROR_MALFORMED','Invalid/malformed cookies.', true); + define('ERROR_MISSEDAFIELD', 'Your browser didn\'t submit an input when it should have.', true); + define('ERROR_REQUIRED', 'The %s field is required.', true); + define('ERROR_INVALIDFIELD', 'The %s field was invalid.', true); // For resizing, max values define('THUMB_WIDTH', 200, true); @@ -132,6 +135,10 @@ // The page that is first shown when a moderator logs in. Defaults to the dashboard. define('MOD_DEFAULT', '/', true); + define('MOD_JANITOR', 0, true); + define('MOD_MOD', 1, true); + define('MOD_ADMIN', 2, true); + // A small file in the main directory indicating that the script has been ran and the board(s) have been generated. // This keeps the script from querying the database and causing strain when not needed. define('HAS_INSTALLED', '.installed', true); @@ -139,7 +146,7 @@ // Name of the boards. Typically '/%s/' (/b/, /mu/, etc) // BOARD_ABBREVIATION - BOARD_TITLE define('BOARD_ABBREVIATION', '/%s/', true); - + // Automatically convert things like "..." to Unicode characters ("…") define('AUTO_UNICODE', true, true); // Use some Wiki-like syntax (''em'', '''strong''', ==Heading==, etc) diff --git a/inc/mod.php b/inc/mod.php index 00f94544..83e4cfdf 100644 --- a/inc/mod.php +++ b/inc/mod.php @@ -1,8 +1,96 @@ -<?php - +<?php + // 'false' means that the user is not logged in as a moderator + $mod = false; + + // Creates a small random string for validating moderators' cookies + function mkhash($length=12) { + // The method here isn't really important, + // but I think this generates a relatively + // unique string that looks cool. + // If you choose to change this, make sure it cannot include a ':' character. + return substr(base64_encode(sha1(rand() . time(), true)), 0, $length); + } + + function login($username, $password, $makehash=true) { + global $sql, $mod; + + // SHA1 password + if($makehash) { + $password = sha1($password); + } + + $res = mysql_query(sprintf( + "SELECT `id`,`type` FROM `mods` WHERE `username` = '%s' AND `password` = '%s' LIMIT 1", + mysql_real_escape_string($username), + $password + ), $sql) or error(mysql_error($sql)); + + if($user = mysql_fetch_array($res)) { + return $mod = Array( + 'id' => $user['id'], + 'type' => $user['type'], + 'username' => $username, + 'password' => $password, + 'hash' => isset($_SESSION['mod']['hash']) ? $_SESSION['mod']['hash'] : mkhash() + ); + } else return false; + } + + function setCookies() { + global $mod; + if(!$mod) error('setCookies() was called for a non-moderator!'); + + // MOD_COOKIE contains username:hash + setcookie(MOD_COOKIE, $mod['username'] . ':' . $mod['hash'], time()+COOKIE_EXPIRE, JAIL_COOKIES?ROOT:'/', null, false, true); + + // Put $mod in the session + $_SESSION['mod'] = $mod; + + // Lock sessions to IP addresses + if(MOD_LOCK_IP) + $_SESSION['mod']['ip'] = $_SERVER['REMOTE_ADDR']; + } + + function destroyCookies() { + // Delete the cookies + setcookie(MOD_COOKIE, 'deleted', time()-COOKIE_EXPIRE, JAIL_COOKIES?ROOT:'/', null, false, true); + + // Unset the session + unset($_SESSION['mod']); + } + + if(isset($_COOKIE['mod']) && isset($_SESSION['mod']) && is_array($_SESSION['mod'])) { + // Should be username:session hash + $cookie = explode(':', $_COOKIE['mod']); + if(count($cookie) != 2) { + destroyCookies(); + error(ERROR_MALFORMED); + } + + // Validate session + if( $cookie[0] != $_SESSION['mod']['username'] || + $cookie[1] != $_SESSION['mod']['hash']) { + // Malformed cookies + destroyCookies(); + error(ERROR_MALFORMED); + } + + // Open connection + sql_open(); + + // Check username/password + if(!login($_SESSION['mod']['username'], $_SESSION['mod']['password'], false)) { + destroyCookies(); + error(ERROR_INVALIDAFTER); + } + + } + // Generates a <ul> element with a list of linked // boards and their subtitles. function ulBoards() { + global $mod; + $body = '<ul>'; // List of boards @@ -14,12 +102,44 @@ sprintf(BOARD_PATH, $b['uri']) . FILE_INDEX . '">' . sprintf(BOARD_ABBREVIATION, $b['uri']) . - '</a>' . - (isset($b['subtitle']) ? ' - ' . $b['subtitle'] : '') . + '</a> - ' . + $b['title'] . + (isset($b['subtitle']) ? '<span class="unimportant"> — ' . $b['subtitle'] . '</span>' : '') . '</li>'; } + if($mod['type'] == MOD_ADMIN) { + $body .= '<li style="margin-top:15px;"><a href="?/new"><strong>Create new board</strong></a></li>'; + } return $body . '</ul>'; } - + + function form_newBoard() { + return '<fieldset><legend>New board</legend>' . + '<form action="?/new" method="post">' . + '<table>' . + '<tr>' . + '<th><label for="board">URI:</label></th>' . + '<td><input type="text" name="uri" id="board" size="3" maxlength="8" />' . + ' <span class="unimportant">(eg. "b"; "mu")</span>' . + '</tr>' . + '<tr>' . + '<th><label for="title">Title:</label></th>' . + '<td><input type="text" name="title" id="title" size="15" maxlength="20" />' . + ' <span class="unimportant">(eg. "Random")</span>' . + '</tr>' . + '<tr>' . + '<th><label for="subtitle">Subtitle:</label></th>' . + '<td><input type="text" name="subtitle" id="subtitle" size="20" maxlength="40" />' . + ' <span class="unimportant">(optional)</span>' . + '</tr>' . + '<tr>' . + '<td></td>' . + '<td><input name="new_board" type="submit" value="New Board" /></td>' . + '</tr>' . + '</table>' . + '</form>' . + '</fieldset>'; + } + ?>
\ No newline at end of file diff --git a/inc/user.php b/inc/user.php index 05deb0e3..126777bd 100644 --- a/inc/user.php +++ b/inc/user.php @@ -21,91 +21,4 @@ $user = Array('valid' => true, 'appeared' => $_COOKIE[TIME_COOKIE]); } - // 'false' means that the user is not logged in as a moderator - $mod = false; - - // Creates a small random string for validating moderators' cookies - function mkhash($length=12) { - // The method here isn't really important, - // but I think this generates a relatively - // unique string that looks cool. - // If you choose to change this, make sure it cannot include a ':' character. - return substr(base64_encode(sha1(rand() . time(), true)), 0, $length); - } - - function login($username, $password, $makehash=true) { - global $sql, $mod; - - // SHA1 password - if($makehash) { - $password = sha1($password); - } - - $res = mysql_query(sprintf( - "SELECT `id`,`type` FROM `mods` WHERE `username` = '%s' AND `password` = '%s' LIMIT 1", - mysql_real_escape_string($username), - $password - ), $sql) or error(mysql_error($sql)); - - if($user = mysql_fetch_array($res)) { - return $mod = Array( - 'id' => $user['id'], - 'type' => $user['type'], - 'username' => $username, - 'password' => $password, - 'hash' => mkhash() - ); - } else return false; - } - - function setCookies() { - global $mod; - if(!$mod) error('setCookies() was called for a non-moderator!'); - - // MOD_COOKIE contains username:hash - setcookie(MOD_COOKIE, $mod['username'] . ':' . $mod['hash'], time()+COOKIE_EXPIRE, JAIL_COOKIES?ROOT:'/', null, false, true); - - // Put $mod in the session - $_SESSION['mod'] = $mod; - - // Lock sessions to IP addresses - if(MOD_LOCK_IP) - $_SESSION['mod']['ip'] = $_SERVER['REMOTE_ADDR']; - } - - function destroyCookies() { - // Delete the cookies - setcookie(MOD_COOKIE, 'deleted', time()-COOKIE_EXPIRE, JAIL_COOKIES?ROOT:'/', null, false, true); - - // Unset the session - unset($_SESSION['mod']); - } - - if(isset($_COOKIE['mod']) && isset($_SESSION['mod']) && is_array($_SESSION['mod'])) { - // Should be username:session hash - $cookie = explode(':', $_COOKIE['mod']); - if(count($cookie) != 2) { - destroyCookies(); - error(ERROR_MALFORMED); - } - - // Validate session - if( $cookie[0] != $_SESSION['mod']['username'] || - $cookie[1] != $_SESSION['mod']['hash']) { - // Malformed cookies - destroyCookies(); - error(ERROR_MALFORMED); - } - - // Open connection - sql_open(); - - // Check username/password - if(!login($_SESSION['mod']['username'], $_SESSION['mod']['password'], false)) { - destroyCookies(); - error(ERROR_INVALIDAFTER); - } - - $mod = $_SESSION['mod']; - } ?>
\ No newline at end of file @@ -38,27 +38,90 @@ loginForm(); } } else { - $query = $_SERVER['QUERY_STRING']; + $query = isset($_SERVER['QUERY_STRING']) ? $_SERVER['QUERY_STRING'] : ''; $regex = Array( 'board' => str_replace('%s', '(\w{1,8})', preg_quote(BOARD_PATH, '/')) ); if(preg_match('/^\/?$/', $query)) { // Dashboard - - // Body $body = ''; $body .= '<fieldset><legend>Boards</legend>' . ulBoards() . '</fieldset>'; - die(Element('page.html', Array( + // TODO: Statistics, etc, in the dashboard. + + echo Element('page.html', Array( 'index'=>ROOT, 'title'=>'Dashboard', 'body'=>$body ) - )); + ); + } elseif(preg_match('/^\/new$/', $query)) { + // New board + $body = ''; + + if(isset($_POST['new_board'])) { + // Create new board + if( !isset($_POST['uri']) || + !isset($_POST['title']) || + !isset($_POST['subtitle']) + ) error(ERROR_MISSEDAFIELD); + + $b = Array( + 'uri' => $_POST['uri'], + 'title' => $_POST['title'], + 'subtitle' => $_POST['subtitle'] + ); + + // Check required fields + if(empty($b['uri'])) + error(sprintf(ERROR_REQUIRED, 'URI')); + if(empty($b['title'])) + error(sprintf(ERROR_REQUIRED, 'title')); + + // Check string lengths + if(strlen($b['uri']) > 8) + error(sprintf(ERROR_TOOLONG, 'URI')); + if(strlen($b['title']) > 20) + error(sprintf(ERROR_TOOLONG, 'title')); + if(strlen($b['subtitle']) > 40) + error(sprintf(ERROR_TOOLONG, 'subtitle')); + + if(!preg_match('/^\w+$/', $b['uri'])) + error(sprintf(ERROR_INVALIDFIELD, 'URI')); + + mysql_query(sprintf( + "INSERT INTO `boards` VALUES (NULL, '%s', '%s', " . + (empty($b['subtitle']) ? 'NULL' : "'%s'" ) . + ")", + mysql_real_escape_string($b['uri']), + mysql_real_escape_string($b['title']), + mysql_real_escape_string($b['subtitle']) + ), $sql) or error(mysql_error($sql)); + + // Open the board + openBoard($b['uri']) or error("Couldn't open board after creation."); + + // Create the posts table + mysql_query(Element('posts.sql', Array('board' => $board['uri'])), $sql) or error(mysql_error($sql)); + + // Build the board + buildIndex(); + } + + $body .= form_newBoard(); + + // TODO: Statistics, etc, in the dashboard. + + echo Element('page.html', Array( + 'index'=>ROOT, + 'title'=>'New board', + 'body'=>$body + ) + ); } elseif(preg_match('/^\/' . $regex['board'] . '(' . preg_quote(FILE_INDEX, '/') . ')?$/', $query, $matches)) { // Board index |
