mirror of
https://github.com/vichan-devel/vichan.git
synced 2024-11-25 07:50:23 +01:00
commit
5816b75bd7
@ -873,9 +873,10 @@
|
||||
// Custom stylesheets available for the user to choose. See the "stylesheets/" folder for a list of
|
||||
// available stylesheets (or create your own).
|
||||
$config['stylesheets']['Yotsuba B'] = ''; // Default; there is no additional/custom stylesheet for this.
|
||||
$config['stylesheets']['Yotsuba'] = 'yotsuba.css';
|
||||
// $config['stylesheets']['Futaba'] = 'futaba.css';
|
||||
// $config['stylesheets']['Dark'] = 'dark.css';
|
||||
$config['stylesheets']['Yotsuba'] = 'yotsuba.css';
|
||||
// $config['stylesheets']['Futaba'] = 'futaba.css';
|
||||
// $config['stylesheets']['Dark'] = 'dark.css';
|
||||
$config['stylesheets']['Tomorrow'] = 'tomorrow.css';
|
||||
|
||||
// The prefix for each stylesheet URI. Defaults to $config['root']/stylesheets/
|
||||
// $config['uri_stylesheets'] = 'http://static.example.org/stylesheets/';
|
||||
@ -1222,21 +1223,21 @@
|
||||
$config['capcode'] = ' <span class="capcode">## %s</span>';
|
||||
|
||||
// "## Custom" becomes lightgreen, italic and bold:
|
||||
//$config['custom_capcode']['Custom'] ='<span class="capcode" style="color:lightgreen;font-style:italic;font-weight:bold"> ## %s</span>';
|
||||
$config['custom_capcode']['Custom'] ='<span class="capcode" style="color:lightgreen;font-style:italic;font-weight:bold"> ## %s</span>';
|
||||
|
||||
// "## Mod" makes everything purple, including the name and tripcode:
|
||||
//$config['custom_capcode']['Mod'] = array(
|
||||
// '<span class="capcode" style="color:purple"> ## %s</span>',
|
||||
// 'color:purple', // Change name style; optional
|
||||
// 'color:purple' // Change tripcode style; optional
|
||||
//);
|
||||
$config['custom_capcode']['Mod'] = array(
|
||||
'<span class="capcode" style="color:purple"> ## %s</span>',
|
||||
'color:purple', // Change name style; optional
|
||||
'color:purple' // Change tripcode style; optional
|
||||
);
|
||||
|
||||
// "## Admin" makes everything red and bold, including the name and tripcode:
|
||||
//$config['custom_capcode']['Admin'] = array(
|
||||
// '<span class="capcode" style="color:red;font-weight:bold"> ## %s</span>',
|
||||
// 'color:red;font-weight:bold', // Change name style; optional
|
||||
// 'color:red;font-weight:bold' // Change tripcode style; optional
|
||||
//);
|
||||
$config['custom_capcode']['Admin'] = array(
|
||||
'<span class="capcode" style="color:red;font-weight:bold"> ## %s</span>',
|
||||
'color:red;font-weight:bold', // Change name style; optional
|
||||
'color:red;font-weight:bold' // Change tripcode style; optional
|
||||
);
|
||||
|
||||
// Enable the moving of single replies
|
||||
$config['move_replies'] = false;
|
||||
@ -1381,14 +1382,30 @@
|
||||
$config['mod']['flood'] = &$config['mod']['bypass_filters'];
|
||||
// Raw HTML posting
|
||||
$config['mod']['rawhtml'] = ADMIN;
|
||||
|
||||
|
||||
// Clean System
|
||||
// Post edits remove local clean?
|
||||
$config['clean']['edits_remove_local'] = true;
|
||||
// Post edits remove global clean?
|
||||
$config['clean']['edits_remove_global'] = true;
|
||||
// Mark post clean for board rule
|
||||
$config['mod']['clean'] = JANITOR;
|
||||
// Mark post clean for global rule
|
||||
$config['mod']['clean_global'] = MOD;
|
||||
|
||||
/* Administration */
|
||||
// View the report queue
|
||||
$config['mod']['reports'] = JANITOR;
|
||||
// Dismiss an abuse report
|
||||
$config['mod']['report_dismiss'] = JANITOR;
|
||||
// Remove global status from a report
|
||||
$config['mod']['report_demote'] = JANITOR;
|
||||
// Elevate a global report to a local report.
|
||||
$config['mod']['report_promote'] = JANITOR;
|
||||
// Dismiss all abuse reports by an IP
|
||||
$config['mod']['report_dismiss_ip'] = JANITOR;
|
||||
// Dismiss all abuse reports on an individual post or thread
|
||||
$config['mod']['report_dismiss_content'] = JANITOR;
|
||||
// View list of bans
|
||||
$config['mod']['view_banlist'] = MOD;
|
||||
// View the username of the mod who made a ban
|
||||
|
@ -343,6 +343,7 @@ function embed_html($link) {
|
||||
return 'Embedding error.';
|
||||
}
|
||||
|
||||
|
||||
class Post {
|
||||
public function __construct($post, $root=null, $mod=false) {
|
||||
global $config;
|
||||
@ -389,11 +390,43 @@ class Post {
|
||||
public function build($index=false) {
|
||||
global $board, $config;
|
||||
|
||||
return Element('post_reply.html', array('config' => $config, 'board' => $board, 'post' => &$this, 'index' => $index, 'mod' => $this->mod));
|
||||
return Element('post_reply.html', array(
|
||||
'config' => $config,
|
||||
'board' => $board,
|
||||
'post' => &$this,
|
||||
'index' => $index,
|
||||
'mod' => $this->mod,
|
||||
'clean' => $this->getClean(),
|
||||
));
|
||||
}
|
||||
|
||||
public function getClean( ) {
|
||||
global $board;
|
||||
|
||||
if( !isset( $this->clean ) ) {
|
||||
$query = prepare("SELECT * FROM `post_clean` WHERE `post_id` = :post AND `board_id` = :board");
|
||||
$query->bindValue( ':board', $board['uri'] );
|
||||
$query->bindValue( ':post', $this->id );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
if( !($this->clean = $query->fetch(PDO::FETCH_ASSOC)) ) {
|
||||
$this->clean = array(
|
||||
'post_id' => $this->id,
|
||||
'board_id' => $board['uri'],
|
||||
'clean_local' => "0",
|
||||
'clean_global' => "0",
|
||||
'clean_local_mod_id' => null,
|
||||
'clean_global_mod_id' => null,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
return $this->clean;
|
||||
}
|
||||
};
|
||||
|
||||
class Thread {
|
||||
class Thread extends Post {
|
||||
public function __construct($post, $root = null, $mod = false, $hr = true) {
|
||||
global $config;
|
||||
if (!isset($root))
|
||||
@ -453,7 +486,16 @@ class Thread {
|
||||
|
||||
event('show-thread', $this);
|
||||
|
||||
$built = Element('post_thread.html', array('config' => $config, 'board' => $board, 'post' => &$this, 'index' => $index, 'hasnoko50' => $hasnoko50, 'isnoko50' => $isnoko50, 'mod' => $this->mod));
|
||||
$built = Element('post_thread.html', array(
|
||||
'config' => $config,
|
||||
'board' => $board,
|
||||
'post' => &$this,
|
||||
'index' => $index,
|
||||
'hasnoko50' => $hasnoko50,
|
||||
'isnoko50' => $isnoko50,
|
||||
'mod' => $this->mod,
|
||||
'clean' => $this->getClean(),
|
||||
));
|
||||
|
||||
return $built;
|
||||
}
|
||||
|
@ -311,6 +311,7 @@ function _syslog($priority, $message) {
|
||||
function verbose_error_handler($errno, $errstr, $errfile, $errline) {
|
||||
if (error_reporting() == 0)
|
||||
return false; // Looks like this warning was suppressed by the @ operator.
|
||||
|
||||
error(utf8tohtml($errstr), true, array(
|
||||
'file' => $errfile . ':' . $errline,
|
||||
'errno' => $errno,
|
||||
@ -894,10 +895,14 @@ function insertFloodPost(array $post) {
|
||||
$query->bindValue(':board', $board['uri']);
|
||||
$query->bindValue(':time', time());
|
||||
$query->bindValue(':posthash', make_comment_hex($post['body_nomarkup']));
|
||||
if ($post['has_file'])
|
||||
|
||||
if ($post['has_file']) {
|
||||
$query->bindValue(':filehash', $post['filehash']);
|
||||
else
|
||||
}
|
||||
else {
|
||||
$query->bindValue(':filehash', null, PDO::PARAM_NULL);
|
||||
}
|
||||
|
||||
$query->bindValue(':isreply', !$post['op'], PDO::PARAM_INT);
|
||||
$query->execute() or error(db_error($query));
|
||||
}
|
||||
@ -2318,24 +2323,38 @@ function DNS($host) {
|
||||
|
||||
function shell_exec_error($command, $suppress_stdout = false) {
|
||||
global $config, $debug;
|
||||
|
||||
if ($config['debug'])
|
||||
|
||||
if( $config['debug'] ) {
|
||||
$which = microtime(true);
|
||||
}
|
||||
|
||||
// Determine if $command is a valid command. If we don't, the following is considered valid output.
|
||||
// '$command' is not recognized as an internal or external command, operable program or batch file.
|
||||
if( empty( shell_exec("which $command") ) ) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if( $config['debug'] ) {
|
||||
$start = microtime(true);
|
||||
|
||||
}
|
||||
|
||||
|
||||
$return = trim(shell_exec('PATH="' . escapeshellcmd($config['shell_path']) . ':$PATH";' .
|
||||
$command . ' 2>&1 ' . ($suppress_stdout ? '> /dev/null ' : '') . '&& echo "TB_SUCCESS"'));
|
||||
$return = preg_replace('/TB_SUCCESS$/', '', $return);
|
||||
|
||||
if ($config['debug']) {
|
||||
$time = microtime(true) - $start;
|
||||
|
||||
if( $config['debug'] ) {
|
||||
$time_which = $start - $which;
|
||||
$time = microtime(true) - $start;
|
||||
|
||||
$debug['exec'][] = array(
|
||||
'command' => $command,
|
||||
'time' => '~' . round($time * 1000, 2) . 'ms',
|
||||
'command' => $command,
|
||||
'time' => '~' . round($time * 1000, 2) . 'ms + ~' . round($time_which * 1000, 2) . 'ms',
|
||||
'response' => $return ? $return : null
|
||||
);
|
||||
$debug['time']['exec'] += $time;
|
||||
}
|
||||
|
||||
|
||||
return $return === 'TB_SUCCESS' ? false : $return;
|
||||
}
|
||||
|
||||
|
@ -18,15 +18,15 @@
|
||||
$config['db']['user'] = 'root';
|
||||
$config['db']['password'] = '';
|
||||
$config['timezone'] = 'UTC';
|
||||
$config['cache']['enabled'] = 'apc';
|
||||
|
||||
|
||||
$config['cache']['enabled'] = false;
|
||||
|
||||
|
||||
$config['cookies']['mod'] = 'mod';
|
||||
$config['cookies']['salt'] = '';
|
||||
|
||||
|
||||
$config['spam']['hidden_inputs_max_pass'] = 128;
|
||||
$config['spam']['hidden_inputs_expire'] = 60 * 60 * 4; // three hours
|
||||
|
||||
|
||||
$config['flood_time'] = 5;
|
||||
$config['flood_time_ip'] = 30;
|
||||
$config['flood_time_same'] = 2;
|
||||
@ -46,10 +46,10 @@
|
||||
$config['thread_subject_in_title'] = true;
|
||||
$config['spam']['hidden_inputs_max_pass'] = 128;
|
||||
$config['ayah_enabled'] = true;
|
||||
|
||||
|
||||
// Load database credentials
|
||||
require "secrets.php";
|
||||
|
||||
|
||||
// Image shit
|
||||
$config['thumb_method'] = 'gm+gifsicle';
|
||||
$config['thumb_ext'] = '';
|
||||
|
@ -496,7 +496,7 @@ function mod_new_board() {
|
||||
error(sprintf($config['error']['boardexists'], $board['url']));
|
||||
}
|
||||
|
||||
$query = prepare('INSERT INTO ``boards`` VALUES (:uri, :title, :subtitle)');
|
||||
$query = prepare('INSERT INTO ``boards`` (``uri``, ``title``, ``subtitle``) VALUES (:uri, :title, :subtitle)');
|
||||
$query->bindValue(':uri', $_POST['uri']);
|
||||
$query->bindValue(':title', $_POST['title']);
|
||||
$query->bindValue(':subtitle', $_POST['subtitle']);
|
||||
@ -1606,6 +1606,35 @@ function mod_edit_post($board, $edit_raw_html, $postID) {
|
||||
}
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
if( $config['clean']['edits_remove_local'] || $config['clean']['edits_remove_global'] ) {
|
||||
|
||||
$query_global = "`clean_global` = :clean";
|
||||
$query_global_mod = "`clean_global_mod_id` = :mod";
|
||||
$query_local = "`clean_local` = :clean";
|
||||
$query_local_mod = "`clean_local_mod_id` = :mod";
|
||||
|
||||
if( $config['clean']['edits_remove_local'] && $config['clean']['edits_remove_global'] ) {
|
||||
$query = prepare("UPDATE `post_clean` SET {$query_global}, {$query_global_mod}, {$query_local}, {$query_local_mod} WHERE `board_id` = :board AND `post_id` = :post");
|
||||
}
|
||||
else if( $config['clean']['edits_remove_global'] ) {
|
||||
$query = prepare("UPDATE `post_clean` SET {$query_global}, {$query_global_mod} WHERE `board_id` = :board AND `post_id` = :post");
|
||||
}
|
||||
else {
|
||||
$query = prepare("UPDATE `post_clean` SET {$query_local}, {$query_local_mod} WHERE `board_id` = :board AND `post_id` = :post");
|
||||
}
|
||||
|
||||
$query->bindValue( ':clean', false );
|
||||
$query->bindValue( ':mod', NULL );
|
||||
$query->bindValue( ':board', $board );
|
||||
$query->bindValue( ':post', $postID );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
// Finally, run a query to tidy up our records.
|
||||
$cleanup = prepare("DELETE FROM `post_clean` WHERE `clean_local` = FALSE AND `clean_global` = FALSE");
|
||||
$query->execute() or error(db_error($query));
|
||||
}
|
||||
|
||||
if ($edit_raw_html) {
|
||||
modLog("Edited raw HTML of post #{$postID}");
|
||||
} else {
|
||||
@ -1614,7 +1643,7 @@ function mod_edit_post($board, $edit_raw_html, $postID) {
|
||||
}
|
||||
|
||||
buildIndex();
|
||||
|
||||
|
||||
rebuildThemes('post', $board);
|
||||
|
||||
header('Location: ?/' . sprintf($config['board_path'], $board) . $config['dir']['res'] . sprintf($config['file_page'], $post['thread'] ? $post['thread'] : $postID) . '#' . $postID, true, $config['redirect_http']);
|
||||
@ -2257,133 +2286,516 @@ function mod_rebuild() {
|
||||
));
|
||||
}
|
||||
|
||||
function mod_reports($global = false) {
|
||||
|
||||
function mod_reports() {
|
||||
global $config, $mod;
|
||||
|
||||
if (!hasPermission($config['mod']['reports']))
|
||||
error($config['error']['noaccess']);
|
||||
// Parse arguments.
|
||||
$urlArgs = func_get_args();
|
||||
$global = in_array( "global", $urlArgs );
|
||||
|
||||
if ($mod['type'] == '20' and $global)
|
||||
if( !hasPermission($config['mod']['reports']) ) {
|
||||
error($config['error']['noaccess']);
|
||||
|
||||
$query = prepare("SELECT * FROM ``reports`` " . ($mod["type"] == "20" ? "WHERE board = :board" : "") . " ORDER BY `time` DESC LIMIT :limit");
|
||||
if ($mod['type'] == '20')
|
||||
$query->bindValue(':board', $mod['boards'][0]);
|
||||
|
||||
if ($global) {
|
||||
$query = prepare("SELECT * FROM ``reports`` WHERE global = TRUE ORDER BY `time` DESC LIMIT :limit");
|
||||
}
|
||||
|
||||
$query->bindValue(':limit', $config['mod']['recent_reports'], PDO::PARAM_INT);
|
||||
|
||||
|
||||
if( $mod['type'] == '20' and $global ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
// Limit reports to ONLY those in our scope.
|
||||
$report_scope = $global ? "global" : "local";
|
||||
|
||||
// Get REPORTS.
|
||||
$query = prepare("SELECT * FROM ``reports`` " . ($mod["type"] == "20" ? "WHERE board = :board" : "") . " WHERE ``".($global ? "global" : "local")."`` = TRUE LIMIT :limit");
|
||||
|
||||
// Limit reports by board if the moderator is local.
|
||||
if( $mod['type'] == '20' ) {
|
||||
$query->bindValue(':board', $mod['boards'][0]);
|
||||
}
|
||||
|
||||
// Limit by config ceiling.
|
||||
$query->bindValue( ':limit', $config['mod']['recent_reports'], PDO::PARAM_INT );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
$reports = $query->fetchAll(PDO::FETCH_ASSOC);
|
||||
|
||||
$report_queries = array();
|
||||
foreach ($reports as $report) {
|
||||
if (!isset($report_queries[$report['board']]))
|
||||
$report_queries[$report['board']] = array();
|
||||
$report_queries[$report['board']][] = $report['post'];
|
||||
}
|
||||
|
||||
$report_posts = array();
|
||||
foreach ($report_queries as $board => $posts) {
|
||||
$report_posts[$board] = array();
|
||||
// Cut off here if we don't have any reports.
|
||||
$reportCount = 0;
|
||||
$reportHTML = '';
|
||||
if( count( $reports ) > 0 ) {
|
||||
|
||||
$query = query(sprintf('SELECT * FROM ``posts_%s`` WHERE `id` = ' . implode(' OR `id` = ', $posts), $board)) or error(db_error());
|
||||
while ($post = $query->fetch(PDO::FETCH_ASSOC)) {
|
||||
$report_posts[$board][$post['id']] = $post;
|
||||
// Build queries to fetch content.
|
||||
$report_queries = array();
|
||||
foreach ($reports as $report) {
|
||||
if (!isset($report_queries[$report['board']]))
|
||||
$report_queries[$report['board']] = array();
|
||||
$report_queries[$report['board']][] = $report['post'];
|
||||
}
|
||||
|
||||
// Get reported CONTENT.
|
||||
$report_posts = array();
|
||||
foreach ($report_queries as $board => $posts) {
|
||||
$report_posts[$board] = array();
|
||||
|
||||
$query = query(sprintf('SELECT * FROM ``posts_%s`` WHERE `id` = ' . implode(' OR `id` = ', $posts), $board)) or error(db_error());
|
||||
while ($post = $query->fetch(PDO::FETCH_ASSOC)) {
|
||||
$report_posts[$board][$post['id']] = $post;
|
||||
}
|
||||
}
|
||||
|
||||
// Develop an associative array of posts to reports.
|
||||
$report_index = array();
|
||||
foreach( $reports as &$report ) {
|
||||
|
||||
// Delete reports which are for removed content.
|
||||
if( !isset( $report_posts[ $report['board'] ][ $report['post'] ] ) ) {
|
||||
// Invalid report (post has since been deleted)
|
||||
$query = prepare("DELETE FROM ``reports`` WHERE `post` = :id AND `board` = :board");
|
||||
$query->bindValue(':id', $report['post'], PDO::PARAM_INT);
|
||||
$query->bindValue(':board', $report['board']);
|
||||
$query->execute() or error(db_error($query));
|
||||
continue;
|
||||
}
|
||||
|
||||
// Build a unique ID.
|
||||
$content_key = "{$report['board']}.{$report['post']}";
|
||||
|
||||
// Create a dummy array if it doesn't already exist.
|
||||
if( !isset( $report_index[ $content_key ] ) ) {
|
||||
$report_index[ $content_key ] = array(
|
||||
"board_id" => $report['board'],
|
||||
"post_id" => $report['post'],
|
||||
"content" => $report_posts[ $report['board'] ][ $report['post'] ],
|
||||
"reports" => array(),
|
||||
);
|
||||
}
|
||||
|
||||
// Add the report to the list of reports.
|
||||
$report_index[ $content_key ]['reports'][ $report['id'] ] = $report;
|
||||
|
||||
// Increment the total report count.
|
||||
++$reportCount;
|
||||
}
|
||||
|
||||
// Only continue if we have something to do.
|
||||
// If there are no valid reports left, we're done.
|
||||
if( $reportCount > 0 ) {
|
||||
|
||||
// Sort this report index by number of reports, desc.
|
||||
usort( $report_index, function( $a, $b ) {
|
||||
$ra = count( $a['reports'] );
|
||||
$rb = count( $b['reports'] );
|
||||
|
||||
if( $ra < $rb ) {
|
||||
return 1;
|
||||
}
|
||||
else if( $rb > $ra ) {
|
||||
return -1;
|
||||
}
|
||||
else {
|
||||
return 0;
|
||||
}
|
||||
} );
|
||||
|
||||
// Loop through the custom index.
|
||||
foreach( $report_index as &$report_item ) {
|
||||
$content = $report_item['content'];
|
||||
|
||||
// Load board content.
|
||||
openBoard($report_item['board_id']);
|
||||
|
||||
// Load the reported content.
|
||||
if( !$content['thread'] ) {
|
||||
// Still need to fix this:
|
||||
$po = new Thread($content, '?/', $mod, false);
|
||||
}
|
||||
else {
|
||||
$po = new Post($content, '?/', $mod);
|
||||
}
|
||||
|
||||
// Fetch clean status.
|
||||
$po->getClean();
|
||||
$clean = $po->clean;
|
||||
|
||||
|
||||
// Add each report's template to this container.
|
||||
$report_html = "";
|
||||
$reports_can_demote = false;
|
||||
$reports_can_promote = false;
|
||||
$content_reports = 0;
|
||||
foreach( $report_item['reports'] as $report ) {
|
||||
$uri_report_base = "reports/" . ($global ? "global/" : "" ) . $report['id'];
|
||||
$report_html .= Element('mod/report.html', array(
|
||||
'report' => $report,
|
||||
'config' => $config,
|
||||
'mod' => $mod,
|
||||
'global' => $global,
|
||||
'clean' => $clean,
|
||||
|
||||
'uri_dismiss' => "?/{$uri_report_base}/dismiss",
|
||||
'uri_ip' => "?/{$uri_report_base}/dismissall",
|
||||
'uri_demote' => "?/{$uri_report_base}/demote",
|
||||
'uri_promote' => "?/{$uri_report_base}/promote",
|
||||
'token_dismiss' => make_secure_link_token( $uri_report_base . '/dismiss' ),
|
||||
'token_ip' => make_secure_link_token( $uri_report_base . '/dismissall' ),
|
||||
'token_demote' => make_secure_link_token( $uri_report_base . '/demote' ),
|
||||
'token_promote' => make_secure_link_token( $uri_report_base . '/promote' ),
|
||||
));
|
||||
|
||||
// Determines if we can "Demote All" / "Promote All"
|
||||
// This logic only needs one instance of a demotable or promotable report to work.
|
||||
// DEMOTE can occur when we're global and the report has a 1 for local (meaning locally, it's not dismissed)
|
||||
// PROMOTE can occur when we're local and the report has a 0 for global (meaning it's not global).
|
||||
if( $global && $report['local'] == "1" ) {
|
||||
$reports_can_demote = true;
|
||||
}
|
||||
else if( !$global && $report['global'] != "1" ) {
|
||||
$reports_can_promote = true;
|
||||
}
|
||||
|
||||
++$content_reports;
|
||||
}
|
||||
|
||||
// Build the ">>>/b/ thread reported 3 times" title.
|
||||
$report_title = sprintf(
|
||||
_('<a href="%s" title="View content" target="_new">>>>/%s/</a> %s reported %d time(s).'),
|
||||
"?/{$report_item['board_id']}/res/" . ( $content['thread'] ?: $content['id'] ) . ".html#{$content['thread']}",
|
||||
$report_item['board_id'],
|
||||
_( $content['thread'] ? "reply" : "thread" ),
|
||||
$content_reports
|
||||
);
|
||||
|
||||
|
||||
// Figure out some stuff we need for the page.
|
||||
$reports_can_demote = ( $clean['clean_local'] ? false : $reports_can_demote );
|
||||
$reports_can_promote = ( $clean['clean_global'] ? false : $reports_can_promote );
|
||||
$uri_content_base = "reports/" . ($global ? "global/" : "" ) . "content/";
|
||||
$uri_clean_base = "reports/" . ($global ? "global/" : "" ) . "{$report_item['board_id']}/clean/{$content['id']}";
|
||||
|
||||
// Build the actions page.
|
||||
$content_html = Element('mod/report_content.html', array(
|
||||
'reports_html' => $report_html,
|
||||
'reports_can_demote' => $reports_can_demote,
|
||||
'reports_can_promote' => $reports_can_promote,
|
||||
'report_count' => $content_reports,
|
||||
'report_title' => $report_title,
|
||||
|
||||
'content_html' => $po->build(true),
|
||||
'content_board' => $report_item['board_id'],
|
||||
'content' => (array) $content,
|
||||
|
||||
'clean' => $clean,
|
||||
|
||||
'uri_content_demote' => "?/{$uri_content_base}{$report_item['board_id']}/{$content['id']}/demote",
|
||||
'uri_content_promote' => "?/{$uri_content_base}{$report_item['board_id']}/{$content['id']}/promote",
|
||||
'uri_content_dismiss' => "?/{$uri_content_base}{$report_item['board_id']}/{$content['id']}/dismiss",
|
||||
'token_content_demote' => make_secure_link_token( "{$uri_content_base}{$report_item['board_id']}/{$content['id']}/demote" ),
|
||||
'token_content_promote' => make_secure_link_token( "{$uri_content_base}{$report_item['board_id']}/{$content['id']}/promote" ),
|
||||
'token_content_dismiss' => make_secure_link_token( "{$uri_content_base}{$report_item['board_id']}/{$content['id']}/dismiss" ),
|
||||
|
||||
'uri_clean' => "?/{$uri_clean_base}/local",
|
||||
'uri_clean_global' => "?/{$uri_clean_base}/global",
|
||||
'uri_clean_both' => "?/{$uri_clean_base}/global+local",
|
||||
'token_clean' => make_secure_link_token( $uri_clean_base . '/local' ),
|
||||
'token_clean_global' => make_secure_link_token( $uri_clean_base . '/global' ),
|
||||
'token_clean_both' => make_secure_link_token( $uri_clean_base . '/global+local' ),
|
||||
|
||||
'global' => $global,
|
||||
'config' => $config,
|
||||
'mod' => $mod,
|
||||
));
|
||||
|
||||
$reportHTML .= $content_html;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$count = 0;
|
||||
$body = '';
|
||||
foreach ($reports as $report) {
|
||||
if (!isset($report_posts[$report['board']][$report['post']])) {
|
||||
// // Invalid report (post has since been deleted)
|
||||
$query = prepare("DELETE FROM ``reports`` WHERE `post` = :id AND `board` = :board");
|
||||
$query->bindValue(':id', $report['post'], PDO::PARAM_INT);
|
||||
$query->bindValue(':board', $report['board']);
|
||||
$query->execute() or error(db_error($query));
|
||||
continue;
|
||||
}
|
||||
|
||||
openBoard($report['board']);
|
||||
|
||||
$post = &$report_posts[$report['board']][$report['post']];
|
||||
|
||||
if (!$post['thread']) {
|
||||
// Still need to fix this:
|
||||
$po = new Thread($post, '?/', $mod, false);
|
||||
} else {
|
||||
$po = new Post($post, '?/', $mod);
|
||||
}
|
||||
|
||||
// a little messy and inefficient
|
||||
$append_html = Element('mod/report.html', array(
|
||||
'report' => $report,
|
||||
'config' => $config,
|
||||
'mod' => $mod,
|
||||
'token' => make_secure_link_token('reports/' . $report['id'] . '/dismiss'),
|
||||
'token_all' => make_secure_link_token('reports/' . $report['id'] . '/dismissall')
|
||||
));
|
||||
|
||||
// Bug fix for https://github.com/savetheinternet/Tinyboard/issues/21
|
||||
$po->body = truncate($po->body, $po->link(), $config['body_truncate'] - substr_count($append_html, '<br>'));
|
||||
|
||||
if (mb_strlen($po->body) + mb_strlen($append_html) > $config['body_truncate_char']) {
|
||||
// still too long; temporarily increase limit in the config
|
||||
$__old_body_truncate_char = $config['body_truncate_char'];
|
||||
$config['body_truncate_char'] = mb_strlen($po->body) + mb_strlen($append_html);
|
||||
}
|
||||
|
||||
$po->body .= $append_html;
|
||||
|
||||
$body .= $po->build(true) . '<hr>';
|
||||
|
||||
if (isset($__old_body_truncate_char))
|
||||
$config['body_truncate_char'] = $__old_body_truncate_char;
|
||||
|
||||
$count++;
|
||||
}
|
||||
$pageArgs = array(
|
||||
'count' => $reportCount,
|
||||
'reports' => $reportHTML,
|
||||
'global' => $global,
|
||||
);
|
||||
|
||||
mod_page(sprintf('%s (%d)', _('Report queue'), $count), 'mod/reports.html', array('reports' => $body, 'count' => $count));
|
||||
mod_page( sprintf('%s (%d)', _( ( $global ? 'Global report queue' : 'Report queue' ) ), $reportCount), 'mod/reports.html', $pageArgs );
|
||||
}
|
||||
|
||||
function mod_report_dismiss($id, $all = false) {
|
||||
global $config;
|
||||
function mod_report_dismiss() {
|
||||
global $config, $mod;
|
||||
|
||||
$query = prepare("SELECT `post`, `board`, `ip` FROM ``reports`` WHERE `id` = :id");
|
||||
$query->bindValue(':id', $id);
|
||||
$query->execute() or error(db_error($query));
|
||||
if ($report = $query->fetch(PDO::FETCH_ASSOC)) {
|
||||
$ip = $report['ip'];
|
||||
$board = $report['board'];
|
||||
$post = $report['post'];
|
||||
} else
|
||||
error($config['error']['404']);
|
||||
// Parse arguments.
|
||||
$arguments = func_get_args();
|
||||
$global = in_array( "global", $arguments );
|
||||
$content = in_array( "content", $arguments );
|
||||
|
||||
if (!$all && !hasPermission($config['mod']['report_dismiss'], $board))
|
||||
if( $mod['type'] == '20' and $global ) {
|
||||
error($config['error']['noaccess']);
|
||||
|
||||
if ($all && !hasPermission($config['mod']['report_dismiss_ip'], $board))
|
||||
error($config['error']['noaccess']);
|
||||
|
||||
if ($all) {
|
||||
$query = prepare("DELETE FROM ``reports`` WHERE `ip` = :ip");
|
||||
$query->bindValue(':ip', $ip);
|
||||
} else {
|
||||
$query = prepare("DELETE FROM ``reports`` WHERE `id` = :id");
|
||||
$query->bindValue(':id', $id);
|
||||
}
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
if( $content ) {
|
||||
$board = @$arguments[2];
|
||||
$post = @$arguments[3];
|
||||
|
||||
if( !hasPermission($config['mod']['report_dismiss_content'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
if( $board != "" && $post != "" ) {
|
||||
|
||||
$query = prepare("SELECT `id` FROM `reports` WHERE `board` = :board AND `post` = :post");
|
||||
$query->bindValue(':board', $board);
|
||||
$query->bindValue(':post', $post);
|
||||
$query->execute() or error(db_error($query));
|
||||
if( count( $reports = $query->fetchAll(PDO::FETCH_ASSOC) ) > 0 ) {
|
||||
|
||||
$report_ids = array();
|
||||
foreach( $reports as $report ) {
|
||||
$report_ids[ $report['id'] ] = $report['id'];
|
||||
}
|
||||
|
||||
if( $global ) {
|
||||
$scope = "``global`` = FALSE AND ``local`` = FALSE";
|
||||
}
|
||||
else {
|
||||
$scope = "``local`` = FALSE";
|
||||
}
|
||||
|
||||
$query = prepare("UPDATE ``reports`` SET {$scope} WHERE `id` IN (".implode(',', array_map('intval', $report_ids)).")");
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
modLog("Promoted " . count($report_ids) . " local report(s) for post #{$post}", $board);
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
$report = @$arguments[1];
|
||||
$all = in_array( "all", $arguments );
|
||||
|
||||
if( $report != "" ) {
|
||||
|
||||
$query = prepare("SELECT `post`, `board`, `ip` FROM ``reports`` WHERE `id` = :id");
|
||||
$query->bindValue(':id', $report);
|
||||
$query->execute() or error(db_error($query));
|
||||
if ($reportobj = $query->fetch(PDO::FETCH_ASSOC)) {
|
||||
$ip = $reportobj['ip'];
|
||||
$board = $reportobj['board'];
|
||||
$post = $reportobj['post'];
|
||||
|
||||
if( !$all && !hasPermission($config['mod']['report_dismiss'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
if( $all && !hasPermission($config['mod']['report_dismiss_ip'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
// Determine scope (local and global or just local) based on /global/ being in URI.
|
||||
if( $global ) {
|
||||
$scope = "`global` = FALSE";
|
||||
$boards = "";
|
||||
}
|
||||
else {
|
||||
$scope = "`local` = FALSE";
|
||||
$boards = "AND `board` = '{$board}'";
|
||||
}
|
||||
|
||||
// Prepare query.
|
||||
// We don't delete reports, only modify scope.
|
||||
if( $all ) {
|
||||
$query = prepare("UPDATE ``reports`` SET {$scope} WHERE `ip` = :ip {$boards}");
|
||||
$query->bindValue(':ip', $ip);
|
||||
}
|
||||
else {
|
||||
$query = prepare("UPDATE ``reports`` SET {$scope} WHERE `id` = :id {$boards}");
|
||||
$query->bindValue(':id', $report);
|
||||
}
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
|
||||
// Cleanup - Remove reports that have been completely dismissed.
|
||||
$query = prepare("DELETE FROM `reports` WHERE `local` = FALSE AND `global` = FALSE");
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
|
||||
if( $all ) {
|
||||
modLog("Dismissed all reports by <a href=\"?/IP/{$ip}\">{$ip}</a>");
|
||||
}
|
||||
else {
|
||||
modLog("Dismissed a report for post #{$post}", $board);
|
||||
}
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
|
||||
if ($all)
|
||||
modLog("Dismissed all reports by <a href=\"?/IP/$ip\">$ip</a>");
|
||||
else
|
||||
modLog("Dismissed a report for post #{$id}", $board);
|
||||
if( $global ) {
|
||||
header('Location: ?/reports/global', true, $config['redirect_http']);
|
||||
}
|
||||
else {
|
||||
header('Location: ?/reports', true, $config['redirect_http']);
|
||||
}
|
||||
}
|
||||
|
||||
function mod_report_demote() {
|
||||
global $config, $mod;
|
||||
|
||||
if( $mod['type'] == '20' ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
// Parse arguments.
|
||||
$arguments = func_get_args();
|
||||
$content = in_array( "content", $arguments );
|
||||
|
||||
if( $content ) {
|
||||
$board = @$arguments[2];
|
||||
$post = @$arguments[3];
|
||||
|
||||
if( !hasPermission($config['mod']['report_demote'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
if( $board != "" && $post != "" ) {
|
||||
|
||||
$query = prepare("SELECT `id` FROM `reports` WHERE `global` = TRUE AND `board` = :board AND `post` = :post");
|
||||
$query->bindValue(':board', $board);
|
||||
$query->bindValue(':post', $post);
|
||||
$query->execute() or error(db_error($query));
|
||||
if( count( $reports = $query->fetchAll(PDO::FETCH_ASSOC) ) > 0 ) {
|
||||
|
||||
$report_ids = array();
|
||||
foreach( $reports as $report ) {
|
||||
$report_ids[ $report['id'] ] = $report['id'];
|
||||
}
|
||||
|
||||
$query = prepare("UPDATE ``reports`` SET ``global`` = FALSE WHERE `id` IN (".implode(',', array_map('intval', $report_ids)).")");
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
modLog("Demoted " . count($report_ids) . " global report(s) for post #{$post}", $board);
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
$report = @$arguments[1];
|
||||
|
||||
if( $report != "" ) {
|
||||
|
||||
$query = prepare("SELECT `post`, `board`, `ip` FROM ``reports`` WHERE `id` = :id AND ``global`` = TRUE");
|
||||
$query->bindValue(':id', $report);
|
||||
$query->execute() or error(db_error($query));
|
||||
if( $reportobj = $query->fetch(PDO::FETCH_ASSOC) ) {
|
||||
$ip = $reportobj['ip'];
|
||||
$board = $reportobj['board'];
|
||||
$post = $reportobj['post'];
|
||||
|
||||
if( !hasPermission($config['mod']['report_demote'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
$query = prepare("UPDATE ``reports`` SET ``global`` = FALSE WHERE `id` = :id");
|
||||
$query->bindValue(':id', $report);
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
modLog("Demoted a global report for post #{$report}", $board);
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
|
||||
header('Location: ?/reports/global', true, $config['redirect_http']);
|
||||
}
|
||||
|
||||
function mod_report_promote() {
|
||||
global $config, $mod;
|
||||
|
||||
// Parse arguments.
|
||||
$arguments = func_get_args();
|
||||
$content = in_array( "content", $arguments );
|
||||
|
||||
if( $content ) {
|
||||
$board = @$arguments[2];
|
||||
$post = @$arguments[3];
|
||||
|
||||
if( !hasPermission($config['mod']['report_promote'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
if( $board != "" && $post != "" ) {
|
||||
$query = prepare("SELECT `id` FROM `reports` WHERE `global` = FALSE AND `board` = :board AND `post` = :post");
|
||||
$query->bindValue(':board', $board);
|
||||
$query->bindValue(':post', $post);
|
||||
$query->execute() or error(db_error($query));
|
||||
if( count( $reports = $query->fetchAll(PDO::FETCH_ASSOC) ) > 0 ) {
|
||||
|
||||
$report_ids = array();
|
||||
foreach( $reports as $report ) {
|
||||
$report_ids[ $report['id'] ] = $report['id'];
|
||||
}
|
||||
|
||||
$query = prepare("UPDATE ``reports`` SET ``global`` = TRUE WHERE `id` IN (".implode(',', array_map('intval', $report_ids)).")");
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
modLog("Promoted " . count($report_ids) . " local report(s) for post #{$post}", $board);
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
$report = @$arguments[1];
|
||||
|
||||
if( $report != "" ) {
|
||||
$query = prepare("SELECT `post`, `board`, `ip` FROM ``reports`` WHERE `id` = :id AND ``global`` = FALSE");
|
||||
$query->bindValue(':id', $report);
|
||||
$query->execute() or error(db_error($query));
|
||||
if ($reportobj = $query->fetch(PDO::FETCH_ASSOC)) {
|
||||
$ip = $reportobj['ip'];
|
||||
$board = $reportobj['board'];
|
||||
$post = $reportobj['post'];
|
||||
|
||||
if( !hasPermission($config['mod']['report_promote'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
$query = prepare("UPDATE ``reports`` SET ``global`` = TRUE WHERE `id` = :id");
|
||||
$query->bindValue(':id', $report);
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
modLog("Promoted a local report for post #{$report}", $board);
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
else {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
|
||||
header('Location: ?/reports', true, $config['redirect_http']);
|
||||
}
|
||||
@ -2444,6 +2856,150 @@ function mod_recent_posts($lim) {
|
||||
|
||||
}
|
||||
|
||||
function mod_report_clean( $global_reports, $board, $unclean, $post, $global, $local ) {
|
||||
global $config, $mod;
|
||||
|
||||
if( !openBoard($board) ) {
|
||||
error($config['error']['noboard']);
|
||||
}
|
||||
|
||||
$query_global = "";
|
||||
$query_global_mod = "";
|
||||
if( $global ) {
|
||||
if( !hasPermission($config['mod']['clean_global'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
$query_global = "`clean_global` = :clean";
|
||||
$query_global_mod = "`clean_global_mod_id` = :mod";
|
||||
}
|
||||
|
||||
$query_local = "";
|
||||
$query_local_mod = "";
|
||||
if( $local ) {
|
||||
if( !hasPermission($config['mod']['clean'], $board) ) {
|
||||
error($config['error']['noaccess']);
|
||||
}
|
||||
|
||||
$query_local = "`clean_local` = :clean";
|
||||
$query_local_mod = "`clean_local_mod_id` = :mod";
|
||||
}
|
||||
|
||||
|
||||
// Marking this post as "Clean" (report immune?)
|
||||
if( !$unclean ) {
|
||||
// Attempt to find a `post_clean` row for this content.
|
||||
$query = prepare("SELECT * FROM `post_clean` WHERE `board_id` = :board AND `post_id` = :post");
|
||||
$query->bindValue( ':board', $board );
|
||||
$query->bindValue( ':post', $post );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
// If the $clean object doesn't exist we need to insert a row for this post.
|
||||
if( !($cleanRecord = $query->fetch(PDO::FETCH_ASSOC)) ) {
|
||||
$query = prepare("INSERT INTO `post_clean` (`post_id`, `board_id`) VALUES ( :post, :board )");
|
||||
$query->bindValue( ':board', $board );
|
||||
$query->bindValue( ':post', $post );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
if( $query->rowCount() == 0 ) {
|
||||
error("The database failed to create a record for this content in `post_clean` to record clean status.");
|
||||
}
|
||||
|
||||
$cleanRecord = true;
|
||||
}
|
||||
}
|
||||
// Revoking clean status (open it to reports?)
|
||||
else {
|
||||
// Attempt to find a `post_clean` row for this content.
|
||||
$query = prepare("SELECT * FROM `post_clean` WHERE `board_id` = :board AND `post_id` = :post");
|
||||
$query->bindValue( ':board', $board );
|
||||
$query->bindValue( ':post', $post );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
if( !($cleanRecord = $query->fetch(PDO::FETCH_ASSOC)) ) {
|
||||
error($config['error']['404']);
|
||||
}
|
||||
}
|
||||
|
||||
// Update the `post_clean` row represented by $clean.
|
||||
if( $cleanRecord ) {
|
||||
// Build our query based on the URI arguments.
|
||||
if( $global && $local ) {
|
||||
$query = prepare("UPDATE `post_clean` SET {$query_global}, {$query_global_mod}, {$query_local}, {$query_local_mod} WHERE `board_id` = :board AND `post_id` = :post");
|
||||
}
|
||||
else if( $global ) {
|
||||
$query = prepare("UPDATE `post_clean` SET {$query_global}, {$query_global_mod} WHERE `board_id` = :board AND `post_id` = :post");
|
||||
}
|
||||
else {
|
||||
$query = prepare("UPDATE `post_clean` SET {$query_local}, {$query_local_mod} WHERE `board_id` = :board AND `post_id` = :post");
|
||||
}
|
||||
|
||||
$query->bindValue( ':clean', !$unclean );
|
||||
$query->bindValue( ':mod', $unclean ? NULL : $mod['id'] );
|
||||
$query->bindValue( ':board', $board );
|
||||
$query->bindValue( ':post', $post );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
// Finally, run a query to tidy up our records.
|
||||
if( $unclean ) {
|
||||
// Query is removing clean status from content.
|
||||
// Remove any clean records that are now null.
|
||||
$cleanup = prepare("DELETE FROM `post_clean` WHERE `clean_local` = FALSE AND `clean_global` = FALSE");
|
||||
$query->execute() or error(db_error($query));
|
||||
}
|
||||
else {
|
||||
// Content is clean, auto-handle all reports.
|
||||
|
||||
// If this is a total clean, we don't need to update records first.
|
||||
if( !($global && $local) ) {
|
||||
$query = prepare("UPDATE `reports` SET `" . ($local ? "local" : "global") . "` = FALSE WHERE `board` = :board AND `post` = :post");
|
||||
$query->bindValue( ':board', $board );
|
||||
$query->bindValue( ':post', $post );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
// If we didn't hit anything, this content doesn't have reports, so don't run the delete query.
|
||||
$require_delete = ($query->rowCount() > 0);
|
||||
|
||||
if( $require_delete ) {
|
||||
$query = prepare("DELETE FROM `reports` WHERE `local` = FALSE and `global` = FALSE");
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
}
|
||||
}
|
||||
// This is a total clean, so delete content by ID rather than via cleanup.
|
||||
else {
|
||||
$query = prepare("DELETE FROM `reports` WHERE `board` = :board AND `post` = :post");
|
||||
|
||||
$query->bindValue( ':board', $board );
|
||||
$query->bindValue( ':post', $post );
|
||||
|
||||
$query->execute() or error(db_error($query));
|
||||
}
|
||||
}
|
||||
|
||||
// Log the action.
|
||||
// Having clear wording of ths log is very important because of the nature of clean status.
|
||||
$log_action = ($unclean ? "Closed" : "Re-opened" );
|
||||
$log_scope = ($local && $global ? "local and global" : ($local ? "local" : "global" ) );
|
||||
modLog( "{$log_action} reports for post #{$post} in {$log_scope}.", $board);
|
||||
|
||||
rebuildPost( $post );
|
||||
}
|
||||
|
||||
// Redirect
|
||||
if( $global_reports ) {
|
||||
header('Location: ?/reports/global', true, $config['redirect_http']);
|
||||
}
|
||||
else {
|
||||
header('Location: ?/reports', true, $config['redirect_http']);
|
||||
}
|
||||
}
|
||||
|
||||
function mod_config($board_config = false) {
|
||||
global $config, $mod, $board;
|
||||
|
||||
|
32
install.php
32
install.php
@ -579,7 +579,8 @@ if ($step == 0) {
|
||||
</p>';
|
||||
|
||||
echo Element('page.html', $page);
|
||||
} elseif ($step == 1) {
|
||||
}
|
||||
elseif ($step == 1) {
|
||||
$page['title'] = 'Pre-installation test';
|
||||
|
||||
$can_exec = true;
|
||||
@ -761,7 +762,8 @@ if ($step == 0) {
|
||||
'title' => 'Checking environment',
|
||||
'config' => $config
|
||||
));
|
||||
} elseif ($step == 2) {
|
||||
}
|
||||
elseif ($step == 2) {
|
||||
// Basic config
|
||||
$page['title'] = 'Configuration';
|
||||
|
||||
@ -775,7 +777,8 @@ if ($step == 0) {
|
||||
'title' => 'Configuration',
|
||||
'config' => $config
|
||||
));
|
||||
} elseif ($step == 3) {
|
||||
}
|
||||
elseif ($step == 3) {
|
||||
$instance_config =
|
||||
'<?php
|
||||
|
||||
@ -814,7 +817,8 @@ if ($step == 0) {
|
||||
|
||||
if (@file_put_contents('inc/instance-config.php', $instance_config)) {
|
||||
header('Location: ?step=4', true, $config['redirect_http']);
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
$page['title'] = 'Manual installation required';
|
||||
$page['body'] = '
|
||||
<p>I couldn\'t write to <strong>inc/instance-config.php</strong> with the new configuration, probably due to a permissions error.</p>
|
||||
@ -826,7 +830,8 @@ if ($step == 0) {
|
||||
';
|
||||
echo Element('page.html', $page);
|
||||
}
|
||||
} elseif ($step == 4) {
|
||||
}
|
||||
elseif ($step == 4) {
|
||||
// SQL installation
|
||||
|
||||
buildJavascript();
|
||||
@ -846,11 +851,15 @@ if ($step == 0) {
|
||||
|
||||
$sql_errors = '';
|
||||
foreach ($queries as $query) {
|
||||
if ($mysql_version < 50503)
|
||||
if ($mysql_version < 50503) {
|
||||
$query = preg_replace('/(CHARSET=|CHARACTER SET )utf8mb4/', '$1utf8', $query);
|
||||
}
|
||||
|
||||
$query = preg_replace('/^([\w\s]*)`([0-9a-zA-Z$_\x{0080}-\x{FFFF}]+)`/u', '$1``$2``', $query);
|
||||
if (!query($query))
|
||||
|
||||
if (!query($query)) {
|
||||
$sql_errors .= '<li>' . db_error() . '</li>';
|
||||
}
|
||||
}
|
||||
|
||||
$page['title'] = 'Installation complete';
|
||||
@ -858,7 +867,8 @@ if ($step == 0) {
|
||||
|
||||
if (!empty($sql_errors)) {
|
||||
$page['body'] .= '<div class="ban"><h2>SQL errors</h2><p>SQL errors were encountered when trying to install the database. This may be the result of using a database which is already occupied with a vichan installation; if so, you can probably ignore this.</p><p>The errors encountered were:</p><ul>' . $sql_errors . '</ul><p><a href="?step=5">Ignore errors and complete installation.</a></p></div>';
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
$boards = listBoards();
|
||||
foreach ($boards as &$_board) {
|
||||
setupBoard($_board);
|
||||
@ -866,13 +876,11 @@ if ($step == 0) {
|
||||
}
|
||||
|
||||
file_write($config['has_installed'], VERSION);
|
||||
/*if (!file_unlink(__FILE__)) {
|
||||
$page['body'] .= '<div class="ban"><h2>Delete install.php!</h2><p>I couldn\'t remove <strong>install.php</strong>. You will have to remove it manually.</p></div>';
|
||||
}*/
|
||||
}
|
||||
|
||||
echo Element('page.html', $page);
|
||||
} elseif ($step == 5) {
|
||||
}
|
||||
elseif ($step == 5) {
|
||||
$page['title'] = 'Installation complete';
|
||||
$page['body'] = '<p style="text-align:center">Thank you for using vichan. Please remember to report any bugs you discover.</p>';
|
||||
|
||||
|
46
mod.php
46
mod.php
@ -53,10 +53,23 @@ $pages = array(
|
||||
'/edit/(\%b)' => 'secure_POST edit_board', // edit board details
|
||||
'/new-board' => 'secure_POST new_board', // create a new board
|
||||
|
||||
'/rebuild' => 'secure_POST rebuild', // rebuild static files
|
||||
'/reports' => 'reports', // report queue
|
||||
'/reports/(global)' => 'reports', // global report queue
|
||||
'/reports/(\d+)/dismiss(all)?' => 'secure report_dismiss', // dismiss a report
|
||||
'/rebuild' => 'secure_POST rebuild', // rebuild static files
|
||||
|
||||
// Report management
|
||||
// (global) denotes if the action is being carried out from the global dashboard,
|
||||
// and if the return address should also be the global dashboard.
|
||||
// Important to note that (?:global) will make no argument.
|
||||
// (global)? will make argument 0 either "global" or "".
|
||||
'/reports(?:/)?' => 'reports', // report queue
|
||||
'/reports/(global)?(?:/)?' => 'reports', // global report queue
|
||||
'/reports/(global)?(?:/)?(content)/(\%b)/(\d+)(?:/)?' => 'reports', // specific reported content (also historic)
|
||||
'/reports/(global)?(?:/)?(content)/(\%b)/(\d+)/dismiss(?:/)?' => 'secure report_dismiss', // dismiss all reports on content
|
||||
'/reports/(global)?(?:/)?(content)/(\%b)/(\d+)/demote(?:/)?' => 'secure report_demote', // demote all reports on content
|
||||
'/reports/(global)?(?:/)?(content)/(\%b)/(\d+)/promote(?:/)?' => 'secure report_promote', // demote all reports on content
|
||||
'/reports/(global)?(?:/)?(\d+)/dismiss(all)?(?:/)?' => 'secure report_dismiss', // dismiss a report
|
||||
'/reports/(global)?(?:/)?(\d+)/demote(?:/)?' => 'secure report_demote', // demote a global report to a local report
|
||||
'/reports/(global)?(?:/)?(\d+)/promote(?:/)?' => 'secure report_promote', // promote a local report to a global report
|
||||
'/reports/(global)?(?:/)?(\%b)/(un)?clean/(\d+)/(global)?(?:\+)?(local)?' => 'secure report_clean', // protect/unprotect from reports
|
||||
|
||||
'/IP/([\w.:]+)' => 'secure_POST ip', // view ip address
|
||||
'/IP/([\w.:]+)/remove_note/(\d+)' => 'secure ip_remove_note', // remove note from ip address
|
||||
@ -73,18 +86,19 @@ $pages = array(
|
||||
'/search' => 'search_redirect', // search
|
||||
'/search/(posts|IP_notes|bans|log)/(.+)/(\d+)' => 'search', // search
|
||||
'/search/(posts|IP_notes|bans|log)/(.+)' => 'search', // search
|
||||
|
||||
'/(\%b)/ban(&delete)?/(\d+)' => 'secure_POST ban_post', // ban poster
|
||||
'/(\%b)/move/(\d+)' => 'secure_POST move', // move thread
|
||||
'/(\%b)/move_reply/(\d+)' => 'secure_POST move_reply', // move reply
|
||||
'/(\%b)/edit(_raw)?/(\d+)' => 'secure_POST edit_post', // edit post
|
||||
'/(\%b)/delete/(\d+)' => 'secure delete', // delete post
|
||||
'/(\%b)/deletefile/(\d+)/(\d+)' => 'secure deletefile', // delete file from post
|
||||
'/(\%b+)/spoiler/(\d+)/(\d+)' => 'secure spoiler_image', // spoiler file
|
||||
'/(\%b)/deletebyip/(\d+)(/global)?' => 'secure deletebyip', // delete all posts by IP address
|
||||
'/(\%b)/(un)?lock/(\d+)' => 'secure lock', // lock thread
|
||||
'/(\%b)/(un)?sticky/(\d+)' => 'secure sticky', // sticky thread
|
||||
'/(\%b)/bump(un)?lock/(\d+)' => 'secure bumplock', // "bumplock" thread
|
||||
|
||||
// Content management
|
||||
'/(\%b)/ban(&delete)?/(\d+)' => 'secure_POST ban_post', // ban poster
|
||||
'/(\%b)/move/(\d+)' => 'secure_POST move', // move thread
|
||||
'/(\%b)/move_reply/(\d+)' => 'secure_POST move_reply', // move reply
|
||||
'/(\%b)/edit(_raw)?/(\d+)' => 'secure_POST edit_post', // edit post
|
||||
'/(\%b)/delete/(\d+)' => 'secure delete', // delete post
|
||||
'/(\%b)/deletefile/(\d+)/(\d+)' => 'secure deletefile', // delete file from post
|
||||
'/(\%b+)/spoiler/(\d+)/(\d+)' => 'secure spoiler_image', // spoiler file
|
||||
'/(\%b)/deletebyip/(\d+)(/global)?' => 'secure deletebyip', // delete all posts by IP address
|
||||
'/(\%b)/(un)?lock/(\d+)' => 'secure lock', // lock thread
|
||||
'/(\%b)/(un)?sticky/(\d+)' => 'secure sticky', // sticky thread
|
||||
'/(\%b)/bump(un)?lock/(\d+)' => 'secure bumplock', // "bumplock" thread
|
||||
|
||||
'/themes' => 'themes_list', // manage themes
|
||||
'/themes/(\w+)' => 'secure_POST theme_configure', // configure/reconfigure theme
|
||||
|
83
post.php
83
post.php
@ -2,10 +2,13 @@
|
||||
/*
|
||||
* Copyright (c) 2010-2014 Tinyboard Development Group
|
||||
*/
|
||||
|
||||
require "./inc/functions.php";
|
||||
require "./inc/anti-bot.php";
|
||||
|
||||
require 'inc/functions.php';
|
||||
require 'inc/anti-bot.php';
|
||||
include "inc/dnsbls.php";
|
||||
// The dnsbls is an optional DNS blacklist include.
|
||||
// Squelch warnings if it doesn't exist.
|
||||
@include "./inc/dnsbls.php";
|
||||
|
||||
// Fix for magic quotes
|
||||
if (get_magic_quotes_gpc()) {
|
||||
@ -101,7 +104,8 @@ if (isset($_POST['delete'])) {
|
||||
header('Content-Type: text/json');
|
||||
echo json_encode(array('success' => true));
|
||||
}
|
||||
} elseif (isset($_POST['report'])) {
|
||||
}
|
||||
elseif (isset($_POST['report'])) {
|
||||
if (!isset($_POST['board'], $_POST['reason']))
|
||||
error($config['error']['bot']);
|
||||
|
||||
@ -131,25 +135,45 @@ if (isset($_POST['delete'])) {
|
||||
markup($reason);
|
||||
|
||||
foreach ($report as &$id) {
|
||||
$query = prepare(sprintf("SELECT `thread` FROM ``posts_%s`` WHERE `id` = :id", $board['uri']));
|
||||
$query = prepare(
|
||||
"SELECT
|
||||
`thread`,
|
||||
`post_clean`.`clean_local`,
|
||||
`post_clean`.`clean_global`
|
||||
FROM `posts_{$board['uri']}`
|
||||
LEFT JOIN `post_clean`
|
||||
ON `post_clean`.`board_id` = '{$board['uri']}'
|
||||
AND `post_clean`.`post_id` = :id
|
||||
WHERE `id` = :id"
|
||||
);
|
||||
$query->bindValue(':id', $id, PDO::PARAM_INT);
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
$thread = $query->fetchColumn();
|
||||
|
||||
if ($config['syslog'])
|
||||
_syslog(LOG_INFO, 'Reported post: ' .
|
||||
'/' . $board['dir'] . $config['dir']['res'] . sprintf($config['file_page'], $thread ? $thread : $id) . ($thread ? '#' . $id : '') .
|
||||
' for "' . $reason . '"'
|
||||
);
|
||||
$query = prepare("INSERT INTO ``reports`` VALUES (NULL, :time, :ip, :board, :post, :reason, :global)");
|
||||
$query->bindValue(':time', time(), PDO::PARAM_INT);
|
||||
$query->bindValue(':ip', $_SERVER['REMOTE_ADDR'], PDO::PARAM_STR);
|
||||
$query->bindValue(':board', $board['uri'], PDO::PARAM_INT);
|
||||
$query->bindValue(':post', $id, PDO::PARAM_INT);
|
||||
$query->bindValue(':reason', $reason, PDO::PARAM_STR);
|
||||
$query->bindValue(':global', isset($_POST['global']), PDO::PARAM_BOOL);
|
||||
$query->execute() or error(db_error($query));
|
||||
if( $post = $query->fetch(PDO::FETCH_ASSOC) ) {
|
||||
$report_local = !$post['clean_local'];
|
||||
$report_global = isset($_POST['global']) && !$post['clean_global'];
|
||||
|
||||
if( $report_local || $report_global ) {
|
||||
$thread = $post['thread'];
|
||||
|
||||
if ($config['syslog']) {
|
||||
_syslog(LOG_INFO, 'Reported post: ' .
|
||||
'/' . $board['dir'] . $config['dir']['res'] . sprintf($config['file_page'], $thread ? $thread : $id) . ($thread ? '#' . $id : '') .
|
||||
' for "' . $reason . '"'
|
||||
);
|
||||
}
|
||||
|
||||
$query = prepare("INSERT INTO `reports` (`time`, `ip`, `board`, `post`, `reason`, `local`, `global`) VALUES (:time, :ip, :board, :post, :reason, :local, :global)");
|
||||
$query->bindValue(':time', time(), PDO::PARAM_INT);
|
||||
$query->bindValue(':ip', $_SERVER['REMOTE_ADDR'], PDO::PARAM_STR);
|
||||
$query->bindValue(':board', $board['uri'], PDO::PARAM_INT);
|
||||
$query->bindValue(':post', $id, PDO::PARAM_INT);
|
||||
$query->bindValue(':reason', $reason, PDO::PARAM_STR);
|
||||
$query->bindValue(':local', $report_local, PDO::PARAM_BOOL);
|
||||
$query->bindValue(':global', $report_global, PDO::PARAM_BOOL);
|
||||
$query->execute() or error(db_error($query));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$is_mod = isset($_POST['mod']) && $_POST['mod'];
|
||||
@ -161,7 +185,8 @@ if (isset($_POST['delete'])) {
|
||||
header('Content-Type: text/json');
|
||||
echo json_encode(array('success' => true));
|
||||
}
|
||||
} elseif (isset($_POST['post'])) {
|
||||
}
|
||||
elseif (isset($_POST['post'])) {
|
||||
if (!isset($_POST['body'], $_POST['board']))
|
||||
error($config['error']['bot']);
|
||||
|
||||
@ -573,14 +598,16 @@ if (isset($_POST['delete'])) {
|
||||
}
|
||||
|
||||
$md5cmd = $config['bsd_md5'] ? 'md5 -r' : 'md5sum';
|
||||
|
||||
if ($output = shell_exec_error("cat $filenames | $md5cmd")) {
|
||||
|
||||
if( ($output = shell_exec_error("cat $filenames | $md5cmd")) !== false ) {
|
||||
$explodedvar = explode(' ', $output);
|
||||
$hash = $explodedvar[0];
|
||||
$post['filehash'] = $hash;
|
||||
} elseif ($config['max_images'] === 1) {
|
||||
}
|
||||
elseif ($config['max_images'] === 1) {
|
||||
$post['filehash'] = md5_file($upload);
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
$str_to_hash = '';
|
||||
foreach (explode(' ', $filenames) as $i => $f) {
|
||||
$str_to_hash .= file_get_contents($f);
|
||||
@ -884,7 +911,8 @@ if (isset($_POST['delete'])) {
|
||||
'id' => $id
|
||||
));
|
||||
}
|
||||
} elseif (isset($_POST['appeal'])) {
|
||||
}
|
||||
elseif (isset($_POST['appeal'])) {
|
||||
if (!isset($_POST['ban_id']))
|
||||
error($config['error']['bot']);
|
||||
|
||||
@ -925,7 +953,8 @@ if (isset($_POST['delete'])) {
|
||||
$query->execute() or error(db_error($query));
|
||||
|
||||
displayBan($ban);
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
if (!file_exists($config['has_installed'])) {
|
||||
header('Location: install.php', true, $config['redirect_http']);
|
||||
} else {
|
||||
|
128
stylesheets/mod/mod.css
Normal file
128
stylesheets/mod/mod.css
Normal file
@ -0,0 +1,128 @@
|
||||
.mod-reports {
|
||||
display: block;
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.mod-report {
|
||||
border: none;
|
||||
border-bottom: 1px solid #B7C5D9;
|
||||
clear: left;
|
||||
|
||||
padding: 0.5em;
|
||||
}
|
||||
.mod-report:last-child {
|
||||
border-bottom: none;
|
||||
}
|
||||
|
||||
.report-header {
|
||||
margin: 0 0 0.25em 0;
|
||||
}
|
||||
|
||||
.report-list {
|
||||
display: block;
|
||||
list-style: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.report-item {
|
||||
display: inline-block;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.report-item .report {
|
||||
background: #D6DAF0;
|
||||
margin: 0.2em 4px 0.2em 0;
|
||||
padding: 0.3em 0.3em 0.5em 0.6em;
|
||||
border-width: 1px;
|
||||
border-style: none solid solid none;
|
||||
border-color: #B7C5D9;
|
||||
display: inline-block;
|
||||
max-width: 94% !important;
|
||||
}
|
||||
.report-reason {
|
||||
display: block;
|
||||
font-size: 115%;
|
||||
line-height: 115%;
|
||||
}
|
||||
|
||||
.report-details {
|
||||
display: block;
|
||||
margin: 0.3em 0 0 0;
|
||||
padding: 0.3em 0 0 0;
|
||||
clear: left;
|
||||
list-style: none;
|
||||
}
|
||||
.report-detail {
|
||||
display: block;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
.detail-name {
|
||||
display: inline-block;
|
||||
min-width: 6.25em;
|
||||
}
|
||||
|
||||
.report-actions {
|
||||
display: block;
|
||||
border: none;
|
||||
border-top: 1px solid #B7C5D9;
|
||||
margin: 0.3em 0 0 0;
|
||||
padding: 0.3em 0 0 0;
|
||||
clear: left;
|
||||
list-style: none;
|
||||
}
|
||||
.report-action {
|
||||
display: inline-block;
|
||||
margin: 0 0.5em 0 0;
|
||||
padding: 0;
|
||||
}
|
||||
.report-action::after {
|
||||
display: inline-block;
|
||||
margin: 0 0 0 0.5em;
|
||||
padding: 0;
|
||||
content: ' | ';
|
||||
}
|
||||
.report-action:last-child::after {
|
||||
display: none;
|
||||
content: '';
|
||||
}
|
||||
|
||||
|
||||
.report-content div.post.reply,
|
||||
.report-content div.thread {
|
||||
background: #D6DAF0;
|
||||
margin: 0.2em 4px 0.2em 0;
|
||||
padding: 0.3em 0.3em 0.5em 0.6em;
|
||||
border-width: 1px;
|
||||
border-style: none solid solid none;
|
||||
border-color: #B7C5D9;
|
||||
display: inline-block;
|
||||
max-width: 94% !important;
|
||||
}
|
||||
.mod-report:hover .report-content div.post.reply,
|
||||
.mod-report:hover .report-content div.thread {
|
||||
background: #FFC4C4;
|
||||
border-color: #F88;
|
||||
}
|
||||
.report-content-actions {
|
||||
display: block;
|
||||
padding: 0.3em 0;
|
||||
clear: left;
|
||||
list-style: none;
|
||||
}
|
||||
.report-content-action {
|
||||
display: inline-block;
|
||||
margin: 0 0.5em 0 0;
|
||||
padding: 0;
|
||||
}
|
||||
.report-content-action::after {
|
||||
display: inline-block;
|
||||
margin: 0 0 0 0.5em;
|
||||
padding: 0;
|
||||
content: ' | ';
|
||||
}
|
||||
.report-content-action:last-child::after {
|
||||
display: none;
|
||||
content: '';
|
||||
}
|
@ -288,6 +288,18 @@ div.post.reply {
|
||||
max-width: 94%!important;
|
||||
}
|
||||
|
||||
div.post_modified {
|
||||
min-width: 47.5em;
|
||||
margin-left: 1.8em;
|
||||
padding-top: 0.8em;
|
||||
}
|
||||
|
||||
div.post_modified div.content-status {
|
||||
margin-top: 0.5em;
|
||||
padding-bottom: 0em;
|
||||
font-size: 72%;
|
||||
}
|
||||
|
||||
span.trip {
|
||||
color: #228854;
|
||||
}
|
||||
@ -327,6 +339,7 @@ div#wrap {
|
||||
margin: 0 auto;
|
||||
}
|
||||
|
||||
div.module,
|
||||
div.ban {
|
||||
background: white;
|
||||
border: 1px solid #98E;
|
||||
@ -334,7 +347,8 @@ div.ban {
|
||||
margin: 30px auto;
|
||||
}
|
||||
|
||||
div.ban p,div.ban h2 {
|
||||
div.ban p,
|
||||
div.ban h2 {
|
||||
padding: 3px 7px;
|
||||
}
|
||||
|
||||
@ -658,7 +672,7 @@ pre {
|
||||
margin-left: -20px;
|
||||
}
|
||||
|
||||
div.thread:hover {
|
||||
.theme-catalog div.thread:hover {
|
||||
background: #D6DAF0;
|
||||
border-color: #B7C5D9;
|
||||
}
|
||||
|
152
stylesheets/tomorrow.css
Normal file
152
stylesheets/tomorrow.css
Normal file
@ -0,0 +1,152 @@
|
||||
/** TOMORROW, I'LL ...
|
||||
|
||||
A cool dark skin by 7185.
|
||||
https://github.com/7185/8chan-tomorrow/
|
||||
|
||||
**/
|
||||
body {
|
||||
background:#1d1f21 none;
|
||||
color:#C5C8C6
|
||||
}
|
||||
h1,div.subtitle {
|
||||
color:#C5C8C6!important
|
||||
}
|
||||
a:link,a:visited,p.intro a.email span.name {
|
||||
color:#81a2be
|
||||
}
|
||||
a:link:hover {
|
||||
color:#5F89AC
|
||||
}
|
||||
a.post_no {
|
||||
color:#C5C8C6
|
||||
}
|
||||
a.post_no:hover {
|
||||
color:#5F89AC!important
|
||||
}
|
||||
div.banner {
|
||||
background-color:#1d1f21
|
||||
}
|
||||
div.post.reply {
|
||||
background-color:#282a2e;
|
||||
border:1px solid #282a2e;
|
||||
margin-bottom:2px;
|
||||
margin-left:16px;
|
||||
margin-top:2px
|
||||
}
|
||||
div.post.reply.highlighted {
|
||||
background-color:#1d1d21;
|
||||
border:1px solid #111
|
||||
}
|
||||
div.post.reply div.body a {
|
||||
color:#81a2be
|
||||
}
|
||||
div.post.reply div.body a:hover {
|
||||
color:#5F89AC
|
||||
}
|
||||
div.post-hover {
|
||||
border:1px solid #000!important;
|
||||
box-shadow:none!important
|
||||
}
|
||||
div.thread:hover {
|
||||
background-color:#1d1f21;
|
||||
border-color:#000
|
||||
}
|
||||
p.intro span.subject {
|
||||
color:#b294bb
|
||||
}
|
||||
p.intro span.name {
|
||||
color:#C5C8C6
|
||||
}
|
||||
span.quote {
|
||||
color:#adbd68
|
||||
}
|
||||
span.heading {
|
||||
color:#F20
|
||||
}
|
||||
form table tr th {
|
||||
background:#282a2e;
|
||||
border:1px solid #111;
|
||||
color:#C5C8C6
|
||||
}
|
||||
div.ban h2 {
|
||||
background:#FCA;
|
||||
color:inherit
|
||||
}
|
||||
div.ban {
|
||||
border-color:#800
|
||||
}
|
||||
div.ban p {
|
||||
color:#000
|
||||
}
|
||||
div.pages {
|
||||
background:#1d1f21;
|
||||
border-color:#1d1f21
|
||||
}
|
||||
div.pages a.selected {
|
||||
color:#81a2be;
|
||||
font-weight:700
|
||||
}
|
||||
div.boardlist {
|
||||
background-color:#282a2e!important;
|
||||
color:#C5C8C6
|
||||
}
|
||||
div.boardlist:nth-of-type(1) {
|
||||
border-bottom:1px solid #111!important;
|
||||
box-shadow:0 0 3px 0 #111
|
||||
}
|
||||
div.boardlist a {
|
||||
color:#81a2be
|
||||
}
|
||||
hr {
|
||||
background-color:#282a2e;
|
||||
border:0;
|
||||
height:1px
|
||||
}
|
||||
div#options_div {
|
||||
background-color:#282a2e
|
||||
}
|
||||
div.options_tab_icon {
|
||||
color: #AAA
|
||||
}
|
||||
div.options_tab_icon:hover {
|
||||
background-color: #111
|
||||
}
|
||||
div.options_tab_icon.active {
|
||||
color: #F20
|
||||
}
|
||||
div.blotter {
|
||||
color:#F20
|
||||
}
|
||||
span.omitted {
|
||||
color:#707070
|
||||
}
|
||||
p.intro a, span.omitted a {
|
||||
text-decoration:none
|
||||
}
|
||||
form#quick-reply {
|
||||
padding-right:1px;
|
||||
border: 1px solid #111
|
||||
}
|
||||
span.capcode {
|
||||
background-color: #000;
|
||||
padding:2px 5px;
|
||||
border-radius: 10px
|
||||
}
|
||||
div#watchlist {
|
||||
border:1px solid #111;
|
||||
background-color:#282a2e
|
||||
}
|
||||
div#watchlist a,a.watchThread {
|
||||
color:#81a2be;
|
||||
text-decoration:none
|
||||
}
|
||||
div#watchlist a:hover,a.watchThread:hover {
|
||||
color:#5F89AC
|
||||
}
|
||||
/* Keep small thumbnails */
|
||||
a:not([data-expanded="true"]) .post-image{
|
||||
width:auto!important;
|
||||
height:auto!important;
|
||||
max-height:200px!important;
|
||||
max-width:200px!important
|
||||
}
|
@ -223,8 +223,7 @@
|
||||
</style>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
|
||||
<body class="8chan index">
|
||||
<div id="main">
|
||||
|
||||
<header>
|
||||
|
@ -6,7 +6,7 @@
|
||||
<title>{{ board.url }} - {{ board.name }}</title>
|
||||
{% endblock %}
|
||||
</head>
|
||||
<body>
|
||||
<body class="8chan {% if mod %}is-moderator{% else %}is-not-moderator{% endif %}" data-stylesheet="{% if config.default_stylesheet.1 != '' and not mod %}{{ config.default_stylesheet.1 }}{% else %}default{% endif %}">
|
||||
{{ boardlist.top }}
|
||||
{% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr />{% endif %}
|
||||
{% if config.url_banner %}<img class="banner" src="{{ config.url_banner }}" {% if config.banner_width or config.banner_height %}style="{% if config.banner_width %}width:{{ config.banner_width }}px{% endif %};{% if config.banner_width %}height:{{ config.banner_height }}px{% endif %}" {% endif %}alt="" />{% endif %}
|
||||
|
@ -14,7 +14,7 @@
|
||||
{% include 'header.html' %}
|
||||
<title>{{ board.url }} - {{ board.title|e }}</title>
|
||||
</head>
|
||||
<body>
|
||||
<body class="8chan {% if mod %}is-moderator{% else %}is-not-moderator{% endif %}" data-stylesheet="{% if config.default_stylesheet.1 != '' and not mod %}{{ config.default_stylesheet.1 }}{% else %}default{% endif %}">
|
||||
{{ boardlist.top }}
|
||||
|
||||
{% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr />{% endif %}
|
||||
|
@ -96,11 +96,6 @@ var saved = {};
|
||||
|
||||
|
||||
var selectedstyle = '{% endraw %}{{ config.default_stylesheet.0|addslashes }}{% raw %}';
|
||||
/*var styles = {
|
||||
{% endraw %}
|
||||
{% for stylesheet in stylesheets %}{% raw %}'{% endraw %}{{ stylesheet.name|addslashes }}{% raw %}' : '{% endraw %}{{ stylesheet.uri|addslashes }}{% raw %}',
|
||||
{% endraw %}{% endfor %}{% raw %}
|
||||
};*/
|
||||
var board_name = false;
|
||||
|
||||
function changeStyle(styleName, link) {
|
||||
@ -115,36 +110,78 @@ function changeStyle(styleName, link) {
|
||||
{% endif %}
|
||||
{% raw %}
|
||||
|
||||
if (!document.getElementById('stylesheet')) {
|
||||
var s = document.createElement('link');
|
||||
s.rel = 'stylesheet';
|
||||
s.type = 'text/css';
|
||||
s.id = 'stylesheet';
|
||||
// Find the <dom> for the stylesheet. May be nothing.
|
||||
var domStylesheet = document.getElementById('stylesheet');
|
||||
// Determine if this stylesheet is the default.
|
||||
var setToDefault = ( styles[styleName] == "" || styles[styleName] == "/stylesheets/" );
|
||||
// Turn "Yotsuba B" to "yotsuba_b"
|
||||
var attributeName = styleName.replace(/[^a-z0-9_\-]/gi, '_').toLowerCase();
|
||||
|
||||
if( !domStylesheet && !setToDefault ) {
|
||||
domStylesheet = document.createElement('link');
|
||||
domStylesheet.rel = 'stylesheet';
|
||||
domStylesheet.type = 'text/css';
|
||||
domStylesheet.id = 'stylesheet';
|
||||
|
||||
var x = document.getElementsByTagName('head')[0];
|
||||
x.appendChild(s);
|
||||
x.appendChild(domStylesheet);
|
||||
}
|
||||
|
||||
{% endraw %}
|
||||
var root = "{{ config.root }}";
|
||||
{% raw %}
|
||||
root = root.replace(/\/$/, "");
|
||||
|
||||
document.getElementById('stylesheet').href = root + styles[styleName];
|
||||
selectedstyle = styleName;
|
||||
|
||||
if (document.getElementsByClassName('styles').length != 0) {
|
||||
var styleLinks = document.getElementsByClassName('styles')[0].childNodes;
|
||||
for (var i = 0; i < styleLinks.length; i++) {
|
||||
styleLinks[i].className = '';
|
||||
if( !setToDefault ) {
|
||||
{% endraw %}
|
||||
var root = "{{ config.root }}";
|
||||
{% raw %}
|
||||
root = root.replace(/\/$/, "");
|
||||
|
||||
domStylesheet.href = root + styles[styleName];
|
||||
selectedstyle = styleName;
|
||||
|
||||
if (document.getElementsByClassName('styles').length != 0) {
|
||||
var styleLinks = document.getElementsByClassName('styles')[0].childNodes;
|
||||
for (var i = 0; i < styleLinks.length; i++) {
|
||||
styleLinks[i].className = '';
|
||||
}
|
||||
}
|
||||
|
||||
if (link) {
|
||||
link.className = 'selected';
|
||||
}
|
||||
}
|
||||
|
||||
if (link) {
|
||||
link.className = 'selected';
|
||||
else if( domStylesheet ) {
|
||||
domStylesheet.parentNode.removeChild( domStylesheet );
|
||||
}
|
||||
|
||||
if (typeof $ != 'undefined')
|
||||
// Fix the classes on the body tag.
|
||||
var body = document.getElementsByTagName('body')[0];
|
||||
|
||||
if( body ) {
|
||||
var bodyClasses = document.getElementsByTagName('body')[0].getAttribute('class').split(" ");
|
||||
var bodyClassesNew = [];
|
||||
|
||||
for( i = 0; i < bodyClasses.length; ++i ) {
|
||||
var bodyClass = bodyClasses[ i ];
|
||||
|
||||
// null class from a double-space.
|
||||
if( bodyClass == "" ) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if( bodyClass.indexOf( "stylesheet-" ) == 0 ) {
|
||||
continue;
|
||||
}
|
||||
|
||||
bodyClassesNew.push( bodyClass );
|
||||
}
|
||||
|
||||
// Add stylesheet-yotsuba_b at the end.
|
||||
bodyClassesNew.push( "stylesheet-" + attributeName );
|
||||
body.setAttribute( 'class', bodyClassesNew.join(" ") );
|
||||
body.setAttribute( 'data-stylesheet', attributeName );
|
||||
}
|
||||
|
||||
if (typeof $ != 'undefined') {
|
||||
$(window).trigger('stylesheet', styleName);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -190,7 +227,7 @@ function init_stylechooser() {
|
||||
}
|
||||
}
|
||||
}
|
||||
{% endraw%}
|
||||
{% endraw %}
|
||||
{% else %}
|
||||
{% raw %}
|
||||
if (localStorage.stylesheet) {
|
||||
@ -208,10 +245,13 @@ function init_stylechooser() {
|
||||
|
||||
function get_cookie(cookie_name) {
|
||||
var results = document.cookie.match ( '(^|;) ?' + cookie_name + '=([^;]*)(;|$)');
|
||||
if (results)
|
||||
|
||||
if (results) {
|
||||
return (unescape(results[2]));
|
||||
else
|
||||
}
|
||||
else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
function highlightReply(id) {
|
||||
|
@ -1,40 +1,5 @@
|
||||
<fieldset>
|
||||
<legend>{% trans 'Boards' %}</legend>
|
||||
|
||||
<ul>
|
||||
{% for board in boards %}
|
||||
{% if board.uri in mod.boards or mod.boards[0] == '*' %}
|
||||
<li>
|
||||
<a href="?/{{ config.board_path|sprintf(board.uri) }}{{ config.file_index }}">{{ config.board_abbreviation|sprintf(board.uri) }}</a>
|
||||
-
|
||||
{{ board.title|e }}
|
||||
{% if board.subtitle %}
|
||||
<small>—
|
||||
{% if config.allow_subtitle_html %}
|
||||
{{ board.subtitle }}
|
||||
{% else %}
|
||||
{{ board.subtitle|e }}
|
||||
{% endif %}
|
||||
</small>
|
||||
|
||||
{% endif %}
|
||||
{% if mod.type == "20" %}
|
||||
<a href="?/settings/{{ board.uri }}"><small>[{% trans 'settings' %}]</small></a>
|
||||
{% endif %}
|
||||
{% if mod|hasPermission(config.mod.manageboards) %}
|
||||
<a href="?/edit/{{ board.uri }}"><small>[{% trans 'edit' %}]</small></a>
|
||||
{% endif %}
|
||||
</li>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
|
||||
{% if mod|hasPermission(config.mod.newboard) %}
|
||||
<li style="margin-top:15px"><a href="?/new-board"><strong>{% trans 'Create new board' %}</strong></a></li>
|
||||
{% endif %}
|
||||
</ul>
|
||||
</fieldset>
|
||||
|
||||
<fieldset>
|
||||
<!-- Messages -->
|
||||
<fieldset class="mod-dash mod-dash-set mod-dash-messages">
|
||||
<legend>{% trans 'Messages' %}</legend>
|
||||
<ul>
|
||||
{% if mod|hasPermission(config.mod.noticeboard) %}
|
||||
@ -78,7 +43,8 @@
|
||||
</ul>
|
||||
</fieldset>
|
||||
|
||||
<fieldset>
|
||||
<!-- Administration -->
|
||||
<fieldset class="mod-dash mod-dash-set mod-dash-messages">
|
||||
<legend>{% trans 'Administration' %}</legend>
|
||||
|
||||
<ul>
|
||||
@ -91,7 +57,6 @@
|
||||
{% if mod.type != 20 %}<a href="?/reports/global">Global reports ({{global_reports}})</a>{% endif %}
|
||||
{% if reports > 0 %}</strong>{% endif %}
|
||||
</li>
|
||||
|
||||
{% endif %}
|
||||
{% if mod|hasPermission(config.mod.view_banlist) %}
|
||||
<li><a href="?/bans">{% trans 'Ban list' %}</a></li>
|
||||
@ -123,57 +88,99 @@
|
||||
</ul>
|
||||
</fieldset>
|
||||
|
||||
<!-- Search -->
|
||||
{% if mod|hasPermission(config.mod.search) %}
|
||||
<fieldset>
|
||||
<legend>{% trans 'Search' %}</legend>
|
||||
|
||||
<ul>
|
||||
<li>
|
||||
{% include 'mod/search_form.html' %}
|
||||
</li>
|
||||
</ul>
|
||||
</fieldset>
|
||||
<fieldset class="mod-dash mod-dash-set mod-dash-search">
|
||||
<legend>{% trans 'Search' %}</legend>
|
||||
|
||||
<ul>
|
||||
<li>
|
||||
{% include 'mod/search_form.html' %}
|
||||
</li>
|
||||
</ul>
|
||||
</fieldset>
|
||||
{% endif %}
|
||||
|
||||
{% if config.mod.dashboard_links|count %}
|
||||
<fieldset>
|
||||
<legend>{% trans 'Other' %}</legend>
|
||||
<!-- Boards -->
|
||||
<fieldset class="mod-dash mod-dash-set mod-dash-boards">
|
||||
<legend>{% trans 'Boards' %}</legend>
|
||||
|
||||
<ul>
|
||||
{% for label,link in config.mod.dashboard_links %}
|
||||
<li><a href="{{ link }}">{{ label }}</a></li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</fieldset>
|
||||
{% endif %}
|
||||
|
||||
{% if config.debug %}
|
||||
<fieldset>
|
||||
<legend>{% trans 'Debug' %}</legend>
|
||||
<ul>
|
||||
<li><a href="?/debug/antispam">{% trans 'Anti-spam' %}</a></li>
|
||||
<li><a href="?/debug/recent">{% trans 'Recent posts' %}</a></li>
|
||||
{% if mod|hasPermission(config.mod.debug_sql) %}
|
||||
<li><a href="?/debug/sql">{% trans 'SQL' %}</a></li>
|
||||
{% endif %}
|
||||
</ul>
|
||||
</fieldset>
|
||||
{% endif %}
|
||||
|
||||
{% if newer_release %}
|
||||
<fieldset>
|
||||
<legend>Update</legend>
|
||||
<ul>
|
||||
<ul>
|
||||
{% for board in boards %}
|
||||
{% if board.uri in mod.boards or mod.boards[0] == '*' %}
|
||||
<li>
|
||||
A newer version of Tinyboard
|
||||
(<strong>v{{ newer_release.massive }}.{{ newer_release.major }}.{{ newer_release.minor }}</strong>) is available!
|
||||
See <a href="http://tinyboard.org">http://tinyboard.org/</a> for upgrade instructions.
|
||||
<a href="?/{{ config.board_path|sprintf(board.uri) }}{{ config.file_index }}">{{ config.board_abbreviation|sprintf(board.uri) }}</a>
|
||||
-
|
||||
{{ board.title|e }}
|
||||
{% if board.subtitle %}
|
||||
<small>—
|
||||
{% if config.allow_subtitle_html %}
|
||||
{{ board.subtitle }}
|
||||
{% else %}
|
||||
{{ board.subtitle|e }}
|
||||
{% endif %}
|
||||
</small>
|
||||
|
||||
{% endif %}
|
||||
{% if mod.type == "20" %}
|
||||
<a href="?/settings/{{ board.uri }}"><small>[{% trans 'settings' %}]</small></a>
|
||||
{% endif %}
|
||||
{% if mod|hasPermission(config.mod.manageboards) %}
|
||||
<a href="?/edit/{{ board.uri }}"><small>[{% trans 'edit' %}]</small></a>
|
||||
{% endif %}
|
||||
</li>
|
||||
</ul>
|
||||
</fieldset>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
|
||||
{% if mod|hasPermission(config.mod.newboard) %}
|
||||
<li style="margin-top:15px"><a href="?/new-board"><strong>{% trans 'Create new board' %}</strong></a></li>
|
||||
{% endif %}
|
||||
</ul>
|
||||
</fieldset>
|
||||
|
||||
<!-- Misc -->
|
||||
{% if config.mod.dashboard_links|count %}
|
||||
<fieldset class="mod-dash mod-dash-set mod-dash-misc">
|
||||
<legend>{% trans 'Other' %}</legend>
|
||||
|
||||
<ul>
|
||||
{% for label,link in config.mod.dashboard_links %}
|
||||
<li><a href="{{ link }}">{{ label }}</a></li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</fieldset>
|
||||
{% endif %}
|
||||
|
||||
<fieldset>
|
||||
<!-- Debug Information -->
|
||||
{% if config.debug %}
|
||||
<fieldset class="mod-dash mod-dash-set mod-dash-debug">
|
||||
<legend>{% trans 'Debug' %}</legend>
|
||||
<ul>
|
||||
<li><a href="?/debug/antispam">{% trans 'Anti-spam' %}</a></li>
|
||||
<li><a href="?/debug/recent">{% trans 'Recent posts' %}</a></li>
|
||||
{% if mod|hasPermission(config.mod.debug_sql) %}
|
||||
<li><a href="?/debug/sql">{% trans 'SQL' %}</a></li>
|
||||
{% endif %}
|
||||
</ul>
|
||||
</fieldset>
|
||||
{% endif %}
|
||||
|
||||
<!-- Update -->
|
||||
{% if newer_release %}
|
||||
<fieldset class="mod-dash mod-dash-set mod-dash-update">
|
||||
<legend>Update</legend>
|
||||
<ul>
|
||||
<li>
|
||||
A newer version of Tinyboard
|
||||
(<strong>v{{ newer_release.massive }}.{{ newer_release.major }}.{{ newer_release.minor }}</strong>) is available!
|
||||
See <a href="http://tinyboard.org">http://tinyboard.org/</a> for upgrade instructions.
|
||||
</li>
|
||||
</ul>
|
||||
</fieldset>
|
||||
{% endif %}
|
||||
|
||||
<!-- Account Actions -->
|
||||
<fieldset class="mod-dash mod-dash-set mod-dash-account">
|
||||
<legend>{% trans 'User account' %}</legend>
|
||||
|
||||
<ul>
|
||||
|
1
templates/mod/header.html
Normal file
1
templates/mod/header.html
Normal file
@ -0,0 +1 @@
|
||||
<link rel="stylesheet" media="screen" href="{{ config.uri_stylesheets }}mod/mod.css" />
|
@ -1,26 +1,56 @@
|
||||
<div class="report">
|
||||
<hr>
|
||||
{% trans 'Board' %}: <a href="?/{{ report.board }}/{{ config.file_index }}">{{ config.board_abbreviation|sprintf(report.board) }}</a>
|
||||
<br>
|
||||
{% trans 'Reason' %}: {{ report.reason }}
|
||||
<br>
|
||||
{% trans 'Report date' %}: {{ report.time|date(config.post_date) }}
|
||||
<br>
|
||||
{% if mod|hasPermission(config.mod.show_ip, report.board) %}
|
||||
{% trans 'Reported by' %}: <a href="?/IP/{{ report.ip }}">{{ report.ip }}</a>
|
||||
<br>
|
||||
{% endif %}
|
||||
{% if mod|hasPermission(config.mod.report_dismiss, report.board) or mod|hasPermission(config.mod.report_dismiss_ip, report.board) %}
|
||||
<hr>
|
||||
{% if mod|hasPermission(config.mod.report_dismiss, report.board) %}
|
||||
<a title="{% trans 'Discard abuse report' %}" href="?/reports/{{ report.id }}/dismiss/{{ token }}">Dismiss</a>
|
||||
{% endif %}
|
||||
{% if mod|hasPermission(config.mod.report_dismiss_ip, report.board) %}
|
||||
{% if mod|hasPermission(config.mod.report_dismiss, report.board) %}
|
||||
|
|
||||
<li class="report-item">
|
||||
<div class="report" id="report-{{ report.id }}">
|
||||
<span class="report-reason">{% if report.reason %}{{ report.reason }}{% else %}<em>{% trans 'No reason given.' %}</em>{% endif %}</span>
|
||||
|
||||
<ul class="report-details">
|
||||
<li class="report-detail detail-date">
|
||||
<span class="detail-name">{% trans 'Report date' %}:</span>
|
||||
<span class="detail-value">{{ report.time|date(config.post_date) }}</span>
|
||||
</li>
|
||||
|
||||
{% if mod|hasPermission(config.mod.show_ip, report.board) %}
|
||||
<li class="report-detail detail-date">
|
||||
<span class="detail-name">{% trans 'Reported by' %}:</span>
|
||||
<span class="detail-value"><a href="?/IP/{{ report.ip }}">{{ report.ip }}</a></span>
|
||||
</li>
|
||||
{% endif %}
|
||||
<a title="{% trans 'Discard all abuse reports by this IP address' %}" href="?/reports/{{ report.id }}/dismissall/{{ token_all }}">Dismiss+</a>
|
||||
</ul>
|
||||
|
||||
{% if mod|hasPermission(config.mod.report_dismiss, report.board) or mod|hasPermission(config.mod.report_dismiss_ip, report.board) %}
|
||||
<ul class="report-actions">
|
||||
{% if mod|hasPermission(config.mod.report_dismiss, report.board) %}
|
||||
<li class="report-action">
|
||||
<a class="action-item action-available" title="{% trans 'Discard abuse report' %}" href="{{uri_dismiss}}/{{token_dismiss}}">Dismiss</a>
|
||||
</li>
|
||||
{% endif %}
|
||||
|
||||
{% if mod|hasPermission(config.mod.report_dismiss_ip, report.board) %}
|
||||
<li class="report-action">
|
||||
<a class="action-item action-available" title="{% trans 'Discard all abuse reports by this IP address' %}" href="{{uri_ip}}/{{token_ip}}">Dismiss+</a>
|
||||
</li>
|
||||
{% endif %}
|
||||
|
||||
{% if global and mod|hasPermission(config.mod.report_demote, report.board) %}
|
||||
<li class="report-action">
|
||||
{% if clean.clean_local %}
|
||||
<span class="content-action-item content-action-unavailable" title="{% trans 'Content is permitted by board rules' %}">Demote</span>
|
||||
{% elseif report.local %}
|
||||
<a class="action-item action-available" title="{% trans 'Demote global abuse report to a local report' %}" href="{{uri_demote}}/{{token_demote}}">Demote</a>
|
||||
{% else %}
|
||||
<span class="action-item action-unavailable" title="{% trans 'Report has already been dismissed locally' %}">Demote</span>
|
||||
{% endif %}
|
||||
</li>
|
||||
{% elseif not global and mod|hasPermission(config.mod.report_promote, report.board) %}
|
||||
<li class="report-action">
|
||||
{% if clean.clean_global %}
|
||||
<span class="content-action-item content-action-unavailable" title="{% trans 'Content is permitted by global rules' %}">Promote</span>
|
||||
{% elseif report.global %}
|
||||
<span class="action-item action-unavailable" title="{% trans 'Report is already a global report' %}">Promote</span>
|
||||
{% else %}
|
||||
<a class="action-item action-available" title="{% trans 'Promote local abuse report to a global report' %}" href="{{uri_promote}}/{{token_promote}}">Promote</a>
|
||||
{% endif %}
|
||||
</li>
|
||||
{% endif %}
|
||||
</ul>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
</li>
|
67
templates/mod/report_content.html
Normal file
67
templates/mod/report_content.html
Normal file
@ -0,0 +1,67 @@
|
||||
<li class="mod-report">
|
||||
<h2 class="report-header">{{ report_title }}</h2>
|
||||
|
||||
<div class="report-content">
|
||||
{{ content_html }}
|
||||
|
||||
<!-- Content Sweep Actions -->
|
||||
<ul class="report-content-actions">
|
||||
{% if mod|hasPermission(config.mod.report_dismiss_content, report.board) %}
|
||||
<!-- Dismiss All -->
|
||||
<li class="report-content-action">
|
||||
<a class="content-action-item content-action-available" title="{% trans 'Discard all abuse reports on this content' %}" href="{{uri_content_dismiss}}/{{token_content_dismiss}}">Dismiss All</a>
|
||||
</li>
|
||||
{% endif %}
|
||||
|
||||
{% if global and mod|hasPermission(config.mod.report_demote, report.board) %}
|
||||
<!-- Demote All -->
|
||||
<li class="report-action">
|
||||
{% if reports_can_demote %}
|
||||
<a class="content-action-item content-action-available"title="{% trans 'Demote global abuse reports to local reports' %}" href="{{uri_content_demote}}/{{token_content_demote}}">Demote All</a>
|
||||
{% elseif clean.clean_local %}
|
||||
<span class="content-action-item content-action-unavailable" title="{% trans 'Content is permitted by board rules' %}">Demote All</span>
|
||||
{% else %}
|
||||
<span class="content-action-item content-action-unavailable" title="{% trans 'Reports have all been dismissed locally' %}">Demote All</span>
|
||||
{% endif %}
|
||||
</li>
|
||||
{% elseif not global and mod|hasPermission(config.mod.report_promote, report.board) %}
|
||||
<!-- Promote All -->
|
||||
<li class="report-action">
|
||||
{% if reports_can_promote %}
|
||||
<a class="content-action-item content-action-available"title="{% trans 'Promote all local abuse reports to global reports' %}" href="{{uri_content_promote}}/{{token_content_promote}}">Promote All</a>
|
||||
{% elseif clean.clean_global %}
|
||||
<span class="content-action-item content-action-unavailable" title="{% trans 'Content is permitted by global rules' %}">Promote All</span>
|
||||
{% else %}
|
||||
<span class="content-action-item content-action-unavailable" title="{% trans 'Reports are already global reports' %}">Promote All</span>
|
||||
{% endif %}
|
||||
</li>
|
||||
{% endif %}
|
||||
|
||||
{% if not clean.clean_local or not clean.clean_global %}
|
||||
{% if mod|hasPermission(config.mod.clean, report.board) or mod|hasPermission(config.mod.clean_global, report.board) %}
|
||||
<li class="report-content-action">
|
||||
Clean
|
||||
{% if not clean.clean_local and mod|hasPermission(config.mod.clean, report.board) %}
|
||||
<!-- Clean Local -->
|
||||
<a class="content-action-item content-action-available" title="{% trans 'Ignore and dismiss local abuse reports on this post for this board' %}" href="{{ uri_clean }}/{{ token_clean }}">(/{{ content_board }}/)</a>
|
||||
|
||||
{% endif %}
|
||||
{% if not clean.clean_global and mod|hasPermission(config.mod.clean_global, report.board) %}
|
||||
<!-- Clean Global -->
|
||||
<a class="content-action-item content-action-available" title="{% trans 'Ignore and demote global abuse reports on this post' %}" href="{{ uri_clean_global }}/{{ token_clean_global }}">(Global)</a>
|
||||
{% if not clean.clean_local and mod|hasPermission(config.mod.clean, report.board) %}
|
||||
|
||||
<!-- Clean Local + Global -->
|
||||
<a class="content-action-item content-action-available" title="{% trans 'Ignore and dismiss local AND global abuse reports on this post' %}" href="{{ uri_clean_both }}/{{ token_clean_both }}">(/{{ content_board }}/+Global)</a>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
</li>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<ul class="report-list">
|
||||
{{ reports_html }}
|
||||
</ul>
|
||||
</li>
|
@ -1,6 +1,8 @@
|
||||
{% if reports %}
|
||||
<ul class="mod-reports reports-global">
|
||||
{{ reports }}
|
||||
</ul>
|
||||
{% else %}
|
||||
<p style="text-align:center" class="unimportant">({% trans 'There are no reports.' %})</p>
|
||||
<p style="text-align:center" class="unimportant">({% trans 'There are no reports.' %})</p>
|
||||
{% endif %}
|
||||
|
||||
|
@ -6,9 +6,10 @@
|
||||
active_page = "page";
|
||||
</script>
|
||||
{% include 'header.html' %}
|
||||
{% if mod %}{% include 'mod/header.html' %}{% endif %}
|
||||
<title>{{ title }}</title>
|
||||
</head>
|
||||
<body>
|
||||
<body class="8chan {% if mod %}is-moderator{% else %}is-not-moderator{% endif %} stylesheet-{% if config.default_stylesheet.1 != '' and not mod %}{{ config.default_stylesheet.1 }}{% else %}default{% endif %}">
|
||||
{% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr>{% endif %}
|
||||
<header>
|
||||
<h1>{{ title }}</h1>
|
||||
|
@ -1,4 +1,11 @@
|
||||
{% if post.edited_at %}
|
||||
<br>
|
||||
<span class="unimportant edited">Post last edited at <em class="edited-time">{{ post.edited_at }}</em></span>
|
||||
{% endif %}
|
||||
<div class="post_modified">
|
||||
{% if post.edited_at %}
|
||||
<div class="content-status edited">{% trans 'Post last edited at' %} <em class="edited-time">{{ post.edited_at }}</em></div>
|
||||
{% endif %}
|
||||
{% if clean.clean_local == '1' %}
|
||||
<div class="content-status clean-local">{% trans 'Board rules permit this content' %}</div>
|
||||
{% endif %}
|
||||
{% if clean.clean_global == '1' %}
|
||||
<div class="content-status clean-global">{% trans 'Global rules permit this content' %}</div>
|
||||
{% endif %}
|
||||
</div>
|
@ -22,8 +22,8 @@
|
||||
{% if post.modifiers['ban message'] %}
|
||||
{{ config.mod.ban_message|sprintf(post.modifiers['ban message']) }}
|
||||
{% endif %}
|
||||
{% include 'post/edited_at.html' %}
|
||||
</div>
|
||||
{% include 'post/edited_at.html' %}
|
||||
</div>
|
||||
<br/>
|
||||
{% endfilter %}
|
||||
|
@ -1,7 +1,7 @@
|
||||
{% filter remove_whitespace %}
|
||||
{# tabs and new lines will be ignored #}
|
||||
|
||||
<div id="thread_{{ post.id }}" data-board="{{ board.uri }}">
|
||||
<div class="thread" id="thread_{{ post.id }}" data-board="{{ board.uri }}">
|
||||
{% if not index %}<a id="{{ post.id }}" class="post_anchor"></a>{% endif %}
|
||||
|
||||
{% include 'post/fileinfo.html' %}
|
||||
@ -55,7 +55,6 @@
|
||||
{% if post.modifiers['ban message'] %}
|
||||
{{ config.mod.ban_message|sprintf(post.modifiers['ban message']) }}
|
||||
{% endif %}
|
||||
{% include 'post/edited_at.html' %}
|
||||
</div>
|
||||
{% if post.omitted or post.omitted_images %}
|
||||
<span class="omitted">
|
||||
@ -78,6 +77,7 @@
|
||||
{% endif %} {% trans %}omitted. Click reply to view.{% endtrans %}
|
||||
</span>
|
||||
{% endif %}
|
||||
{% include 'post/edited_at.html' %}
|
||||
{% if not index %}
|
||||
{% endif %}
|
||||
</div>{% endfilter %}
|
||||
|
@ -11,7 +11,7 @@
|
||||
{% if config.default_stylesheet.1 != '' %}<link rel="stylesheet" type="text/css" id="stylesheet" href="{{ config.uri_stylesheets }}{{ config.default_stylesheet.1 }}">{% endif %}
|
||||
{% if config.font_awesome %}<link rel="stylesheet" href="{{ config.root }}{{ config.font_awesome_css }}">{% endif %}
|
||||
</head>
|
||||
<body>
|
||||
<body class="8chan {% if mod %}is-moderator{% else %}is-not-moderator{% endif %}" data-stylesheet="{% if config.default_stylesheet.1 != '' and not mod %}{{ config.default_stylesheet.1 }}{% else %}default{% endif %}">
|
||||
{{ boardlist.top }}
|
||||
<header>
|
||||
<h1>{{ settings.title }}</h1>
|
||||
|
@ -10,7 +10,7 @@
|
||||
{% include 'header.html' %}
|
||||
<title>{{ board.url }} - {% if config.thread_subject_in_title and thread.subject %}{{ thread.subject }}{% else %}{{ board.title|e }}{% endif %}</title>
|
||||
</head>
|
||||
<body>
|
||||
<body class="8chan {% if mod %}is-moderator{% else %}is-not-moderator{% endif %}" data-stylesheet="{% if config.default_stylesheet.1 != '' and not mod %}{{ config.default_stylesheet.1 }}{% else %}default{% endif %}">
|
||||
{{ boardlist.top }}
|
||||
{% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr />{% endif %}
|
||||
{% if config.url_banner %}<img class="board_image" src="{{ config.url_banner }}?board={{ board.uri }}" {% if config.banner_width or config.banner_height %}style="{% if config.banner_width %}width:{{ config.banner_width }}px{% endif %};{% if config.banner_width %}height:{{ config.banner_height }}px{% endif %}" {% endif %}alt="" />{% endif %}
|
||||
|
Loading…
Reference in New Issue
Block a user