<?
//
// Copyright (c) 2002, Cameron McKay
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above copyright
// notice, this list of conditions and the following disclaimer in the
// documentation and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
// FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
// TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
// OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
// OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
//
//
// Informium -- Advanced News Script
//
// System Class (system-class.php)
//
// Author: Cameron McKay
// Note: This class contains miscellaneous functions used by Informium.
//
class system
{
//
// Function: info()
//
// Purpose: Returns various statistics about the Informium database.
//
// Returns: An associative array with the following keys.
// user_total -> The total number of users.
// post_total -> The total number of posts.
// comment_total -> The total number of comments.
// post_today -> The total number of posts today.
// comment_today -> The total number of comments today.
//
function info()
{
// Load the INF array.
global $CONF, $INF;
// Check to make sure the MYSQL class is loaded.
require_once("$CONF[local_path]/class/mysql-class.php");
// Make a new MYSQL object.
$db = new mysql();
// Connect to the database.
$db->pconnect();
// Get the MYSQL timestamp for right now.
$_query = "SELECT NOW() + 0";
$result = $db->query($_query);
$timestamp = $db->result($result);
// Free the result.
$db->free($result);
// Make the last 6 characters wildcards.
$timestamp[8] = '_';
$timestamp[9] = '_';
$timestamp[10] = '_';
$timestamp[11] = '_';
$timestamp[12] = '_';
$timestamp[13] = '_';
// Prepare queries.
$query[user_total] = "SELECT COUNT(*) FROM user WHERE access > 0";
$query[post_total] = "SELECT COUNT(*) FROM news";
$query[comment_total] = "SELECT COUNT(*) FROM comments";
$query[post_today] = "SELECT COUNT(*) FROM news WHERE create_date LIKE '$timestamp'";
$query[comment_today] = "SELECT COUNT(*) FROM comments WHERE create_date LIKE '$timestamp'";
// Cycle through the queries.
foreach ($query as $name => $value)
{
// Query the database.
$result = $db->query($value);
// Get the result.
$return[$name] = number_format($db->result($result));
// Free the result.
$db->free($result);
}
// Return the associative array of values.
return $return;
}
//
// Function: encrypt ( $value );
//
// Purpose: Extremely weak encryption intended to dissuade any ideas to exploit
// the script.
//
// Arguments:
// $value -> The value to encrypt.
//
// Returns: A weakly encrypted string.
//
function encrypt($value)
{
// Cycle through the value transforming the characters.
for ($i = 0; $i < strlen($value); ++$i)
{
// Some arbitrary transformations.
$return[$i] = ord($value[$i]);
$return[$i] = $return[$i] + strlen($value);
$return[$i] = base_convert($return[$i], 10, 32);
}
// Reverse the array.
array_reverse($return);
// Append the word length to the end.
return strtoupper($hash . join('', $return));
}
//
// Function: decrypt ( $value )
//
// Purpose: Decryption of an extremely weakly encrypted value.
//
// Arguments:
// $value -> An encrypted value.
//
// Returns: The value in decrypted form (before it was encrypted with encrypt()).
//
function decrypt($value)
{
// Cycle through the string decrypting it.
for ($i = 0; $i < strlen($value); $i += 2)
{
// De-transform.
$real = base_convert($value[$i].$value[$i+1], 32, 10);
$real = $real - (strlen($value) / 2);
$return[] = chr($real);
}
// Reverse the array.
array_reverse($return);
// Make it back into a string.
return join('', $return);
}
//
// Function: now ( )
//
// Purpose: A meta-function to the MYSQL function NOW().
//
// Returns: The time right now.
//
function now ()
{
// Load the INF array.
global $CONF, $INF;
// Check to make sure the MYSQL class is loaded.
require_once("$CONF[local_path]/class/mysql-class.php");
// Make a new MYSQL object.
$db = new mysql();
// Connect to the database.
$db->pconnect();
// Prepare to query the database.
$query = "SELECT NOW() + 0";
$result = $db->query($query);
$return = $db->result($result);
// Free the result.
$db->free($result);
return $return;
}
//
// Function: auto_link ( $text )
//
// Purpose: Automatically links hyperlinks within the text provided.
//
// Arguments:
// $text -> The text that needs to be autolinked.
//
// Returns: The autolinked text.
//
function auto_link ($text)
{
// Cycle through the text.
for ($x = 0; $x < strlen($text); ++$x)
{
// Check if it starts with an 'http://' and if that...
if (!strcmp('http://', substr($text, $x, 7)) || !strcmp('www.', substr($text, $x, 4))) {
// Copy start position to a variable.
$start = $x;
// Cycle through each character after that to determine when to stop.
while ($x < strlen($text) && preg_match("/[a-z0-9\.\:\?\/\~\-\_\&\=\%\+]/i", $text[$x]))
++$x;
// Check if it's already linked (GASP!).
if (!strcasecmp('</a>', substr($text, $x, 4)))
continue;
// ... Or already within a link.
else if (!strcasecmp('href=', substr($text, $start - 7, 5)))
continue;
// ... Or in an image source tag.
else if (!strcasecmp('src=', substr($text, $start - 6, 4)))
continue;
// Copy the link name to a variable.
$link_name = substr($text, $start, ($x - $start));
// Check if we need to prepend 'http://' to it.
if (!strcmp('www.', substr($text, $start, 4))) {
$link = 'http://' . $link_name;
// Otherwise we just make it the same as the link name...
} else {
$link = $link_name;
}
// Copy the text to another variable for splicing.
$splice = $text;
// Copy the first portion to the $list.
// Copy the link.
// Copy the end portion to the $list.
$text = substr($splice, 0, $start);
$text .= "<a href='$link'>$link_name</a>";
$text .= substr($splice, $x, strlen($splice));
// Skip the loop past this area.
$x += $link + 15;
} // End if.
} // End for.
// Return the autolinked text.
return $text;
}
//
// Function: auto_newl ( $text )
//
// Purpose: Automatically converts newlines to HTML line breaks.
//
// Arguments:
// $text -> The text to be converted.
//
// Returns: The auto-newlined text.
//
function auto_newl ($text)
{
// Cycle through the text.
for ($x = 0; $x < strlen($text); ++$x)
{
// Check if it's a newline.
if (!strcmp("\n", $text[$x])) {
// Check if it's already been line breaked.
if (!strcasecmp('<br />', substr($text, $x - 7, 6)) || !strcasecmp('<br>', substr($text, $x - 5, 4)))
continue;
// Otherwise, add in the <br />.
else {
// Copy the text to another variable for splicing.
$splice = $text;
// Copy the first portion to the $list.
// Copy the link.
// Copy the end portion to the $list.
$text = substr($splice, 0, $x - 1);
$text .= "<br />";
$text .= substr($splice, $x, strlen($splice));
// Skip the loop past this area.
$x += 6;
} // End if.
} // End if.
} // End for.
// Return the auto-newlined text.
return $text;
}
//
// Function: archive_list ( $type )
//
// Purpose: Retrieves an array of arrays containing the months and years
// of articles in the database.
//
// Arguments:
// $type -> Either 0 (for Week) or 1 (for Month).
//
// Returns: An array containing years which contains an array of months.
// (example) $list["2000"]["01"] = TRUE; (January 2000 exists).
//
function archive_list ( $type )
{
// Import CONF.
global $CONF;
// Check to make sure the MYSQL class is loaded.
require_once("$CONF[local_path]/class/mysql-class.php");
// Make a new MYSQL object.
$db = new mysql();
// Connect to the database.
$db->pconnect();
// Prepare and execute query.
$query = "SELECT DISTINCT YEAR(create_date) AS YYYY FROM news ORDER BY YYYY DESC";
$result = $db->query($query);
// Cycle through article years.
while ($list = $db->fetch_array($result)) {
// Reference year.
$YYYY =& $list[YYYY];
$_query = "SELECT DISTINCT MONTH(create_date) AS MM FROM news WHERE create_date LIKE '{$YYYY}__________' ORDER BY MM DESC";
$_result = $db->query($_query);
// Cycle through that particular year's month.
while ($_list = $db->fetch_array($_result)) {
// Reference month.
$MM = sprintf("%02d", $_list[MM]);
// Add date key.
$return[] = "$YYYY-$MM";
}
// Free the result.
$db->free($_result);
}
// Free the result.
$db->free($result);
// Return the array of date keys.
return $return;
}
//
// Function: date_format ( $id, $type, $table = '' )
//
// Purpose: Retrieves a nicely formatted date for the creation date,
// the modification date, or right now.
//
// Arguments:
// $post_id -> The article's post_id or user's user_id.
// $type -> The date type, either 'create_date', 'modify_date', or 'now'.
// $table -> The table to retrieve the date from (either 'news' or 'comment' or 'user').
//
// Returns: A formatted date.
//
function date_format ($id, $type, $table = '')
{
// Import CONF.
global $CONF;
// If we're getting from the news table, than we're checking against
// the post_id. If we're getting form the user table, we're checking
// against the user_id.
if (!strcmp($table, 'news')) {
$type_id = 'post_id';
$date_format = 'article_date';
} else if (!strcmp($table, 'comments')) {
$type_id = 'comment_id';
$date_format = 'comment_date';
} else if (!strcmp($table, 'sections')) {
$type_id = 'section_id';
$date_format = 'user_date';
} else if (!strcmp($table, 'user')) {
$type_id = 'user_id';
$date_format = 'user_date';
}
// Import MYSQL class, if needed.
require_once("$CONF[local_path]/class/mysql-class.php");
// Create a new MYSQL object.
$db = new mysql();
// Connect to the DB.
$db->pconnect();
// If we need now, than we have to modify the argument
// slightly.
if (!strcmp($type, 'now'))
$query = "SELECT UNIX_TIMESTAMP(NOW())";
// Otherwise we do this.
else
$query = "SELECT UNIX_TIMESTAMP($type) FROM $table WHERE $type_id='$id'";
// Now execute the query.
$result = $db->query($query);
$return = $db->result($result);
// Free the result.
$db->free($result);
// Now format the date using the format specified in the configuration
// file.
return date($CONF[$date_format], $return);
}
//
// Function: do_encrypt ( $text, $cipher )
//
// Purpose: Encrypts the given text with the given cipher.
//
// Arguments:
// $text -> The text to encrypt.
// $cipher -> The cipher to use to encrypt the password.
//
// Returns: The encrypted version of the text, or -1 if the cipher is unknown.
//
function do_encrypt ($text, $cipher)
{
// Import CONF;
global $CONF;
// If the cipher is PTXT, we leave it as it is.
if (!strcmp($cipher, 'PTXT')) {
return $text;
// If the cipher is DES, we use DES.
} else if (!strcmp($cipher, 'DES')) {
return crypt($text, $text[0].$text[1]);
// If the cipher is MD5, we use MD5.
} else if (!strcmp($cipher, 'MD5')) {
return md5($text);
// If the cipher is RT13, we use ROT13.
} else if (!strcmp($cipher, 'RT13')) {
$from = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
$to = 'nopqrstuvwxyzabcdefghijklmNOPQRSTUVWXYZABCDEFGHIJKLM';
return strtr($text, $from, $to);
// If the cipher is NUNE, we use MySQL PASSWORD().
} else if (!strcmp($cipher, 'NUNE')) {
// Check to make sure the MYSQL class is loaded.
require_once("$CONF[local_path]/class/mysql-class.php");
// Make a new MYSQL object.
$db = new mysql();
// Connect to the database.
$db->pconnect();
// Prepare and execute query.
$query = "SELECT PASSWORD('$text')";
$result = $db->query($query);
// Get the encrypted password.
$return = $db->result($result);
// Free the result.
$db->free($result);
// Return the answer.
return $return;
// Otherwise, if we don't know the cipher, return -1 for cipher unknown.
} else {
return -1;
}
}
//
// Function: fs_list ( $target, $type )
//
// Purpose: Reads a list of either files or directories in a given directory.
//
// Arguments:
// $target -> The target directory (no trailing slash, please).
// $type -> 0 for all, 1 for directories, 2 for files.
//
// Returns: An array containing the contents of the directory, or -1 for invalid directory.
//
function fs_list ($target, $type)
{
// Import CONF;
global $CONF;
// Check to make sure the directory exists, if it does make an object.
if (!($dir = dir($target))) {
// Return invalid directory error.
return -1;
}
// Cycle through the directory.
while ($item = $dir->read())
{
// Define shortcut for the path.
$path = $target . '/' . $item;
// If it's . or .. then skip.
if (!strcmp($item, '.') || !strcmp($item, '..')) {
// Skip.
continue;
// If 'type' is 1 then we skip if it's a file.
} else if (($type == 1) && (is_file($path))) {
// Skip.
continue;
// If 'type' is 2 then we skip if it's a directory.
} else if (($type == 2) && (is_dir($path))) {
// Skip.
continue;
// Otherwise we include it in the return array.
} else {
$return[] = $item;
} // End if.
} // End while.
// Close the directory.
$dir->close();
// Return the array.
return $return;
}
}
?>