Скрипт форума на PHP своими руками. Часть 5


Прислал: Евгений Токмаков [ 03.07.2008 @ 12:54 ]
Раздел:: [ Статьи по PHP ]


Так, с пользователями форума вроде как разобрались. Теперь давайте рассмотрим функции для добавления нового сообщения (поста) - getAddPostForm() и addPost().

<?php
// Функция возвращает форму для добавления нового сообщения (поста)
function getAddPostForm()
{
  
// Если не передан ID форума - значит функция была вызвана по ошибке
  
if ( !isset( $_GET['idForum'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
// Если не передан ID темы, куда будет добавлено сообщение - 
  // значит функция была вызвана по ошибке
  
if ( !isset( $_GET['id_theme'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
$id_theme = (int)$_GET['id_theme'];
  if ( 
$id_theme ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
  
// Проверяем, не заблокирована ли тема?
  
$query "SELECT locked FROM ".TABLE_THEMES." WHERE id_theme=".$id_theme;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при формировании формы для добавления нового сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue'action=showForum&idForum='.$_GET['idForum'] );
  }
  if ( 
mysql_num_rows$res ) == ) {
    
header'Location: '.$_SERVER['PHP_SELF'].'?action=showForum&idForum='.$_GET['idForum'] );
    die();
  }
  if ( 
mysql_result$res0) == )
    return 
showInfoMessage'Вы не можете добавить сообщение - тема заблокирована.'
                            
'action=showForum&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );  
  
  
$message '';
  
$html '';
  
  if ( isset( 
$_SESSION['viewMessage'] ) and !empty( $_SESSION['viewMessage'] ) ) {
    
$view file_get_contents'./templates/previewMessage.html' );
    
$view str_replace'{message}'print_page$_SESSION['viewMessage'] ), $view ); 
    
$html $html.$view."\n";
    
$message htmlspecialchars$_SESSION['viewMessage'] );
    unset( 
$_SESSION['viewMessage'] );
  }
  
  
// Если при заполнении формы были допущены ошибки
  
if ( isset( $_SESSION['addPostForm'] ) ) {
    
$info file_get_contents'./templates/infoMessage.html' );
    
$info str_replace'{infoMessage}'$_SESSION['addPostForm']['error'], $info );
    
$html $html.$info."\n";
    
$message htmlspecialchars$_SESSION['addPostForm']['message'] );
    unset( 
$_SESSION['addPostForm'] );
  }
  
  
$tpl file_get_contents'./templates/addPostForm.html' );
  
$action $_SERVER['PHP_SELF'].'?action=addPost&idForum='.$_GET['idForum'].'&id_theme='.$id_theme;
  
$tpl str_replace'{action}'$action$tpl );
  
$tpl str_replace'{message}'$message$tpl );
  
  
$html $html $tpl;
  
  return 
$html."\n";
}
?>

Шаблон addPostForm.html

<script language="JavaScript" type="text/javascript" src="./js/send_message.js"></script>

<form name="sendMessageForm" id="sendMessageForm" action="{action}" method="POST" 
enctype="multipart/form-data" onsubmit="return checkForm(this)">

<table class="showTable">
<tr>
  <th colspan="2">Ответить</th>
</tr>
<tr>
  <td>Сообщение</td>
  <td>
    <table cellspacing="0" cellpadding="5" width="500">
    <tr align="center" valign="middle">
      <td>
      <input type="button" accesskey="b" name="addbbcode0" value=" b " 
      style="font-weight:bold; width:30px" onClick="bbstyle(0)" 
      onMouseOver="helpline('b')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" accesskey="i" name="addbbcode2" value=" i " 
      style="font-style:italic; width:30px" onClick="bbstyle(2)" 
      onMouseOver="helpline('i')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" name="addbbcode4" value=" u " 
      style="text-decoration: underline; width:30px" onClick="bbstyle(4)" 
      onMouseOver="helpline('u')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" name="addbbcode6" value="Quote" 
      style="width:50px" onClick="bbstyle(6)" 
      onMouseOver="helpline('q')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" name="addbbcode8" value="Code" 
      style="width:45px" onClick="bbstyle(8)" 
      onMouseOver="helpline('c')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" name="addbbcode10" value="PHP" 
      style="width:45px" onClick="bbstyle(10)" 
      onMouseOver="helpline('p')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" name="addbbcode12" value="List" 
      style="width:40px" onClick="bbstyle(12)" 
      onMouseOver="helpline('l')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" name="addbbcode14" value="List=" 
      style="width:40px" onClick="bbstyle(14)" 
      onMouseOver="helpline('o')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" name="addbbcode16" value="Img" 
      style="width:40px"  onClick="bbstyle(16)" 
      onMouseOver="helpline('m')" onMouseOut="helpline('h')" />
      </td>
      <td>
      <input type="button" name="addbbcode18" value="URL" 
      style="text-decoration: underline; width:40px" onClick="bbstyle(18)" 
      onMouseOver="helpline('w')" onMouseOut="helpline('h')" />
      </td>
    </tr>
    <tr>
      <td colspan="7">Цвет шрифта:
      <select name="addbbcode20" 
      onChange="bbfontstyle('[color=' + this.form.addbbcode20.options[this.form.addbbcode20.selectedIndex].value +
      ']', '[/color]');this.selectedIndex=0;" onMouseOver="helpline('s')" onMouseOut="helpline('h')">
        <option style="color:#000000;" value="default">По умолчанию</option>
        <option style="color:#FF0000;" value="red" />Красный</option>
        <option style="color:#008000;" value="green" />Зелёный</option>
        <option style="color:#0000FF;" value="blue" />Синий</option>
      </select>
      </td>
      <td colspan="3" align="right">
      <a href="javascript:bbstyle(-1)" onMouseOver="helpline('a')" onMouseOut="helpline('h')">Закрыть все теги</a>
      </td>
    </tr>
    <tr>
      <td colspan="10">
      <input type="text" name="helpbox" style="width:100%; font-size:10px" 
      class="helpline" value="Подсказка: Можно быстро применить стили к выделенному тексту" />
      </td>
    </tr>
    </table>

    <textarea name="message" style="width:500; height: 300" onselect="storeCaret(this);" 
    onclick="storeCaret(this);" onkeyup="storeCaret(this);">{message}</textarea>
    <br/>
    Прикрепить:&nbsp;<input type="file" name="attach" size="40" />
    <br/>
    <input type="submit" name="submitForm" value="Отправить" />&nbsp;
    <input type="submit" name="viewMessage" value="Предварительный просмотр" />
  </td>
</tr>
</table>

</form>

Обработчик формы - функция addPost():

<?php
// Функция добавляет новое сообщение(пост) (новую запись в таблицу БД TABLE_POSTS)
function addPost()
{
  
  
// Если не переданы данные формы - значит функция была вызвана по ошибке
  
if ( !isset( $_GET['idForum'] ) or
       !isset( 
$_GET['id_theme'] ) or
       !isset( 
$_POST['message'] ) or
       !isset( 
$_FILES['attach'] ) 
       )
  {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
  
$id_theme = (int)$_GET['id_theme'];
  if ( 
$id_theme ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
  
// Проверяем, не заблокирована ли тема?
  
$query "SELECT locked FROM ".TABLE_THEMES." WHERE id_theme=".$id_theme;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при формировании формы для добавления нового сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue'action=showForum&idForum='.$_GET['idForum'] );
  }
  if ( 
mysql_num_rows$res ) == ) {
    
header'Location: '.$_SERVER['PHP_SELF'].'?action=showForum&idForum='.$_GET['idForum'] );
    die();
  }
  if ( 
mysql_result$res0) == )
    return 
showInfoMessage'Вы не можете добавить сообщение - тема заблокирована.'
                            
'action=showForum&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );

  
$msgLen strlen$_POST['message'] );
                            
  
// Обрезаем сообщение (пост) до длины MAX_POST_LENGTH
  
$message substr$_POST['message'], 0MAX_POST_LENGTH );
  
// Обрезаем лишние пробелы
  
$message trim$message );

  
// Если пользователь хочет посмотреть на сообщение перед отправкой
  
if ( isset( $_POST['viewMessage'] ) ) 
  {
    
$_SESSION['viewMessage'] = $message;
    
header'Location: '.$_SERVER['PHP_SELF'].'?action=addPostForm&idForum='.
            
$_GET['idForum'].'&id_theme='.$id_theme );
    die();
  }

  
// Проверяем, правильно ли заполнены поля формы
  
$error '';
  if ( empty( 
$message ) ) $error $error.'<li>не заполнено поле "Сообщение"</li>'."\n";
  if ( 
$msgLen MAX_POST_LENGTH 
    
$error $error.'<li>длина сообщения больше '.MAX_POST_LENGTH.' символов</li>'."\n";
  if ( !empty( 
$_FILES['attach']['name'] ) and $_FILES['attach']['size'] > MAX_FILE_SIZE 
    
$error $error.'<li>размер файла вложения больше '.(MAX_FILE_SIZE/1024).' Кб</li>'."\n";
    
  
// Если были допущены ошибки при заполнении формы - 
  // перенаправляем пользователя для исправления ошибок
  
if ( !empty( $error ) )
  {
    
$_SESSION['addPostForm'] = array();
    
$_SESSION['addPostForm']['error'] = '<p class="errorMsg">При заполнениии формы были допущены ошибки:</p>'."\n".
    
'<ul class="errorMsg">'."\n".$error.'</ul>'."\n";
    
$_SESSION['addPostForm']['message'] = $message;
    
header'Location: '.$_SERVER['PHP_SELF'].'?action=addPostForm&idForum='.
            
$_GET['idForum'].'&id_theme='.$id_theme );
    die();
  }
  
$file '';
  if ( !empty( 
$_FILES['attach']['name'] ) ) {
    
// Массив недопустимых расширений файла вложения
    
$extentions = array('.php''.phtml''.php3''.html''.htm''.pl');
    
// Извлекаем из имени файла расширение
    
$ext strrchr$_FILES['attach']['name'], "." ); 
    
// Формируем путь к файлу    
    
if ( in_array$ext$extentions ) )
      
$file $id_theme.'-'.date("YmdHis",time()).'.txt'
    else
      
$file $id_theme.'-'.date("YmdHis",time()).$ext
    
// Перемещаем файл из временной директории сервера в директорию files
      
if ( move_uploaded_file $_FILES['attach']['tmp_name'], './files/'.$file ) )
        
chmod'./files/'.$file0644 );
  }
  
  if ( isset( 
$_SESSION['user'] ) ) {
    
$name $_SESSION['user']['name'];
    
$id_user $_SESSION['user']['id_author'];
  } else {
    
$name NOT_REGISTERED_USER;
    
$id_user 0;
  }

  
// Все поля заполнены правильно - выполняем запрос к БД
  
$query "INSERT INTO ".TABLE_POSTS."
            (
            name,
            putfile,
            author,
            id_author,
            time,
            id_theme
            )
            VALUES
            (
            '"
.mysql_real_escape_string$message )."',
            '"
.$file."',
            '"
.mysql_real_escape_string$name )."',
            "
.$id_user.",
            NOW(),
            "
.$id_theme."
            )"
;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при добавлении нового сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue
                             
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );
  }
  
  
// Обновляем количество сообщений для зарегистрированного пользователя
  
if ( isset( $_SESSION['user'] ) ) {
    
$query "UPDATE ".TABLE_USERS." SET posts=posts+1 WHERE id_author = ".$_SESSION['user']['id_author'];
    
$res mysql_query$query );
    if ( !
$res ) {
      
$msg 'Ошибка при добавлении нового сообщения';
      
$err 'Ошибка при выполнении запроса: <br/>'.
             
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
             
'(Файл '__FILE__ .', строка '__LINE__ .')';
      return 
showErrorMessage$msg$errtrue
                               
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );
    }    
  }

  return 
showInfoMessage'Ваше сообщение успешно добавлено'
                          
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );
}
?>

Функция getQuickReplyForm(), которая возвращает форму для быстрого ответа в тему, фактически полностью повторяет функцию getAddPostForm(). Соответственно, функция quickReply() - аналог функции addPost(). Так что не будем на них задерживаться - я просто приведу их исходные коды.

<?php
// Функция возвращает форму для быстрого ответа в тему
function getQuickReplyForm$id_theme )
{
  
$html file_get_contents'./templates/quickReplyForm.html' );
  
$action $_SERVER['PHP_SELF'].'?action=quickReply&idForum='.$_GET['idForum'].'&id_theme='.$id_theme;
  
$html str_replace'{action}'$action$html );
  return 
$html;
}
?>

Обработчик формы - функция quickReply():

<?php
// Функция добавляет новое сообщение(пост) (новую запись в таблицу БД TABLE_POSTS)
function quickReply()
{
  
// Если не переданы данные формы - значит функция была вызвана по ошибке
  
if ( !isset( $_GET['idForum'] ) or
       !isset( 
$_GET['id_theme'] ) or
       !isset( 
$_POST['message'] )
       )
  {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
$id_theme = (int)$_GET['id_theme'];
  if ( 
$id_theme ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
  
// Проверяем, не заблокирована ли тема?
  
$query "SELECT locked FROM ".TABLE_THEMES." WHERE id_theme=".$id_theme;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при формировании формы для добавления нового сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue'action=showForum&idForum='.$_GET['idForum'] );
  }
  if ( 
mysql_num_rows$res ) == ) {
    
header'Location: '.$_SERVER['PHP_SELF'].'?action=showForum&idForum='.$_GET['idForum'] );
    die();
  }
  if ( 
mysql_result$res0) == )
    return 
showInfoMessage'Вы не можете добавить сообщение - тема заблокирована.'
                            
'action=showForum&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );

  if ( isset( 
$_SESSION['user'] ) ) {
    
$name $_SESSION['user']['name'];
    
$id_user $_SESSION['user']['id_author'];
  } else {
    
$name NOT_REGISTERED_USER;
    
$id_user 0;
  }
  
// Обрезаем сообщение (пост) до длины MAX_POST_LENGTH
  
$message substr$_POST['message'], 0MAX_POST_LENGTH );
  
// Обрезаем лишние пробелы
  
$message trim$message );

  
// Проверяем, правильно ли заполнены поля формы
  
if ( empty( $message ) ) 
      return 
showInfoMessage'Не заполнено поле "Сообщение"'
                              
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );

  
// Все поля заполнены правильно - выполняем запрос к БД
  
$query "INSERT INTO ".TABLE_POSTS."
            (
            name,
            putfile,
            author,
            id_author,
            time,
            id_theme
            )
            VALUES
            (
            '"
.mysql_real_escape_string$message )."',
            '',
            '"
.mysql_real_escape_string$name )."',
            "
.$id_user.",
            NOW(),
            "
.$id_theme."
            )"
;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при добавлении нового сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue
                             
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );
  }
  
  
// Обновляем количество сообщений для зарегистрированного пользователя
  
if ( isset( $_SESSION['user'] ) ) {
    
$query "UPDATE ".TABLE_USERS." SET posts=posts+1 WHERE id_author = ".$_SESSION['user']['id_author'];
    
$res mysql_query$query );
    if ( !
$res ) {
      
$msg 'Ошибка при добавлении нового сообщения';
      
$err 'Ошибка при выполнении запроса: <br/>'.
             
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
             
'(Файл '__FILE__ .', строка '__LINE__ .')';
      return 
showErrorMessage$msg$errtrue
                               
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );
    }    
  }

  return 
showInfoMessage'Ваше сообщение успешно добавлено'
                          
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );
}
?>

Кроме ответа в тему, пользователи должны иметь возможность отредактировать ранее опубликованные сообщения. Эту возможность предоставляют функции getEditPostForm() и updatePost().

<?php
// Функция возвращает форму для редактирования сообщения (поста)
function getEditPostForm()
{
  
// Если не передан ID форума - значит функция была вызвана по ошибке
  
if ( !isset( $_GET['idForum'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
// Если не передан ID темы - значит функция была вызвана по ошибке
  
if ( !isset( $_GET['id_theme'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
$id_theme = (int)$_GET['id_theme'];
  if ( 
$id_theme ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
// Если не передан ID сообщения - значит функция была вызвана по ошибке
  
if ( !isset( $_GET['id_post'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
$id_post = (int)$_GET['id_post'];
  if ( 
$id_post ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }

  
// Если сообщение пытается редактировать не зарегистрированный пользователь
  
if ( !isset( $_SESSION['user'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }

  
// Получаем из БД сообщение
  
$query "SELECT name, putfile, id_author, author, time, id_theme, locked 
            FROM "
.TABLE_POSTS.
            WHERE id_post="
.$id_post;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при формировании формы для редактирования сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue'' );
  }
  
// Если сообщение не найдено - редирект на страницу темы
  
if ( mysql_num_rows$res ) == 
    return 
showInfoMessage'Ошибка при формировании формы для редактирования сообщения'
                            
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme );
    
  
$post mysql_fetch_array$res ); 
  
$id_theme $post['id_theme']; 
  
  
// Проверяем, имеет ли пользователь право редактировать это сообщение (пост)
  
if ( !hasRightEditPost$post ) ) {
    
$msg 'У вас нет прав для редактирования этого сообщения';
    
$queryString 'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme;
    return 
showInfoMessage$msg$queryString );
  }    
  
  
$message htmlspecialchars$post['name'] );
  
$html '';
  
  if ( isset( 
$_SESSION['viewMessage'] ) and !empty( $_SESSION['viewMessage'] ) ) {
    
$view file_get_contents'./templates/previewMessage.html' );
    
$view str_replace'{message}'print_page$_SESSION['viewMessage'] ), $view ); 
    
$html $html.$view."\n";
    
$message htmlspecialchars$_SESSION['viewMessage'] );
    unset( 
$_SESSION['viewMessage'] );
  }
  
  
// Если при заполнении формы были допущены ошибки
  
if ( isset( $_SESSION['editPostForm'] ) ) {
    
$html    $html $_SESSION['editPostForm']['error'];
    
$message htmlspecialchars$_SESSION['editPostForm']['message'] );
    unset( 
$_SESSION['editPostForm'] );
  }
  
  
$tpl file_get_contents'./templates/editPostForm.html' );

  
$action $_SERVER['PHP_SELF'].'?action=updatePost&idForum='.
            
$_GET['idForum'].'&id_theme='.$id_theme.'&id_post='.$id_post;
  
$tpl str_replace'{action}'$action$tpl );
  
$tpl str_replace'{message}'$message$tpl );
  
// Если ранее был загружен файл - надо предоставить возможность удалить его
  
$unlinkfile '';
  if ( !empty( 
$post['putfile'] ) and is_file'./files/'.$post['putfile'] ) ) {
    
$unlinkfile '<input type="checkbox" name="unlink" value="1" />&nbsp;Удалить загруженный ранее файл<br/>'."\n";
  }
  
$tpl str_replace'{unlinkfile}'$unlinkfile$tpl );
  
$html $html $tpl;
  
  return 
$html."\n";
}
?>

Обработчик формы - функция updatePost()

<?php
function updatePost()
{
  
// Если не переданы данные формы - значит функция была вызвана по ошибке
  
if ( !isset( $_GET['idForum'] ) or
       !isset( 
$_GET['id_post'] ) or
       !isset( 
$_POST['message'] ) or
       !isset( 
$_FILES['attach'] ) 
    )
  {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
  
$id_post = (int)$_GET['id_post'];
  if ( 
$id_post ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }

  
// Проверяем, имеет ли пользователь право редактировать это сообщение (пост)
  
$query "SELECT * FROM ".TABLE_POSTS." WHERE id_post=".$id_post;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при обновлении сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue'' );
  }
  if ( 
mysql_num_rows$res ) == ) {
    
$msg 'Ошибка при обновлении сообщения: сообщение не найдено';
    return 
showInfoMessage$msg'' );
  }
  
$post mysql_fetch_array$res );
  
$id_theme $post['id_theme'];
  if ( !
hasRightEditPost$post ) ) {
    
$msg 'У вас нет прав для редактирования этого сообщения';
    
$queryString 'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme;
    return 
showInfoMessage$msg$queryString );
  }

  
// Обрезаем сообщение до длины MAX_POST_LENGTH
  
$message substr$_POST['message'], 0MAX_POST_LENGTH );
  
// Обрезаем лишние пробелы
  
$message trim$message );

  
// Если пользователь хочет посмотреть на сообщение перед отправкой
  
if ( isset( $_POST['viewMessage'] ) ) 
  {
    
$_SESSION['viewMessage'] = $message;
    
header'Location: '.$_SERVER['PHP_SELF'].'?action=editPostForm&idForum='.
            
$_GET['idForum'].'&id_theme='.$id_theme.'&id_post='.$id_post );
    die();
  }
  
  
// Проверяем, правильно ли заполнены поля формы
  
$error '';
  if ( empty( 
$message ) ) $error $error.'<li>не заполнено поле "Сообщение"</li>'."\n";
  if ( !empty( 
$_FILES['attach']['name'] ) and $_FILES['attach']['size'] > MAX_FILE_SIZE 
      
$error $error.'<li>размер файла вложения больше '.(MAX_FILE_SIZE/1024).' Кб</li>'."\n";
    
  
// Если были допущены ошибки при заполнении формы - 
  // перенаправляем посетителя для исправления ошибок
  
if ( !empty( $error ) ) {
    
$_SESSION['editPostForm'] = array();
    
$_SESSION['editPostForm']['error'] = '<p class="errorMsg">При заполнениии формы были допущены ошибки:</p>'."\n".
    
'<ul class="errorMsg">'."\n".$error.'</ul>'."\n";
    
$_SESSION['editPostForm']['message'] = $message;
    
header'Location: '.$_SERVER['PHP_SELF'].'?action=editPostForm&idForum='.
             
$_GET['idForum'].'&id_theme='.$id_theme.'&id_post='.$id_post );
    die();
  }
  
  
$file $post['putfile'];
  
// Такой ситуации быть не должно, но я случайтно удалил файл вложения
  // вручную, и после этого нельзя было правильно загрузить файл
  
if ( !empty( $file ) and !is_file'./files/'.$post['putfile'] ) ) $file '';
  
// Если выставлен флажок "Удалить загруженный ранее файл"
  
if ( isset( $_POST['unlink'] ) and !empty( $file ) and is_file'./files/'.$post['putfile'] ) ) {
    if ( 
unlink'./files/'.$post['putfile'] ) ) $file '';
  }
  if ( !empty( 
$_FILES['attach']['name'] ) ) {
    
// Если пользователь загружает новый файл - мы должны сперва удалить старый
    // (при условии, что он вообще был загружен ранее)
    
if ( !empty( $file ) and is_file'./files/'.$post['putfile'] ) ) {
      if ( 
unlink'./files/'.$post['putfile'] ) ) $file '';      
    }
    
// Загружать новый файл мы будем только при условии, что был успешно
    // удален ранее загруженный (или он не загружался вовсе)
    
if ( empty( $file ) ) {
      
// Массив недопустимых расширений файла вложения
      
$extentions = array('.php''.phtml''.php3''.html''.htm''.pl');
      
// Извлекаем из имени файла расширение
      
$ext strrchr$_FILES['attach']['name'], "." ); 
      
// Формируем путь к файлу    
      
if ( in_array$ext$extentions ) )
        
$new $id_theme.'-'.date("YmdHis",time()).'.txt'
      else
        
$new $id_theme.'-'.date("YmdHis",time()).$ext
      
// Перемещаем файл из временной директории сервера в директорию files
      
if ( move_uploaded_file $_FILES['attach']['tmp_name'], './files/'.$new ) ) {
        
chmod'./files/'.$new0644 );
        
$file $new;
      }
    }
  }
  
  
// Все поля заполнены правильно - выполняем запрос к БД
  
$query "UPDATE ".TABLE_POSTS." SET
            name='"
.mysql_real_escape_string$message )."',
            putfile='"
.$file."',
            id_editor="
.$_SESSION['user']['id_author'].",
            edittime=NOW()
            WHERE id_post="
.$id_post;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при обновлении сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
      
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
      
'(Файл '__FILE__ .', строка '__LINE__ .')';
    
$queryString 'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme;
    return 
showErrorMessage$msg$errtrue$queryString );
  } 
    
  
$msg 'Cообщение успешно исправлено';
  
$queryString 'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$id_theme;
  return 
showInfoMessage$msg$queryString );
  
}
?>

Функция hasRightEditPost() возвращает true или false в зависимости от того, имеет ли право пользователь редактировать сообщение (пост).

<?php
// Функция возвращает true или false в зависимости от того, имеет ли
// право пользователь редактировать сообщение (пост)
function hasRightEditPost$post )
{
  
// Незарегистрированный пользователь не имеет право редактировать сообщения
  
if ( !isset( $_SESSION['user'] ) ) return false;
  
// Если пользователь - администратор или модератор, он имеет право 
  // редактировать любые сообщения (посты)
  
if ( $_SESSION['user']['status'] != 'user' ) return true;
  
// Обычный пользователь не может редактировать чужие сообщения (посты)
  
if ( $_SESSION['user']['id_author'] != $post['id_author'] ) return false;
  
// Пользователь не может редактировать сообщение, если оно заблокировано
  
if ( $post['locked'] == ) return false;
  
// Обычный пользователь может редактировать свое сообщение, 
  // только если на него не было ответов
  
$query "SELECT id_post FROM ".TABLE_POSTS.
            WHERE id_theme="
.$post['id_theme']." AND time>'".$post['time']."'";
  
$res mysql_query$query );
  if ( !
$res ) return false;
  if ( 
mysql_num_rows$res ) == 
    return 
true;
  else
    return 
false;
}
?>

И, наконец, функция deletePost()

<?php
// Функция удаляет сообщение (пост)
function deletePost()
{
  
// Если не передан ID форума - значит функция была вызвана по ошибке
  
if ( !isset( $_GET['idForum'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
// Если не прередан ID темы - значит функция вызвана по ошибке
  
if ( !isset( $_GET['id_theme'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
$id_theme = (int)$_GET['id_theme'];
  if ( 
$id_theme ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
// Если не прередан ID сообщения (поста) - значит функция вызвана по ошибке
  
if ( !isset( $_GET['id_post'] ) ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  }
  
$id_post = (int)$_GET['id_post'];
  if ( 
$id_post ) {
    
header'Location: '.$_SERVER['PHP_SELF'] );
    die();
  } 
  
  
// Получаем из БД информацию об удаляемом сообщении - это нужно,
  // чтобы узнать, имеет ли право пользователь удалить это сообщение
  
$query "SELECT * FROM ".TABLE_POSTS." WHERE id_post=".$id_post;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при удалении сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
      
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
      
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue'action=showForum&idForum='.$_GET['idForum'] );
  }
  if ( 
mysql_num_rows$res ) == ) {
    return 
showInfoMessage'Сообщение успешно удалено''action=showForum&idForum='.$_GET['idForum'] );
  }
  
$post mysql_fetch_array$res );  
  if ( !
hasRightDeletePost$post ) ) {
    return 
showInfoMessage'У вас нет прав, чтобы удалить это сообщение'
                            
'action=showForum&idForum='.$_GET['idForum'] );
  }
  
  
// Выдаем пользователю сообщение с просьбой подтвердить свое
  // желание удалить сообщение (пост)
  
if ( !isset( $_GET['confirm'] ) ) {
    
$html '<div align="center"><p>Вы действительно хотите удалить это сообщение?</p>'."\n";
    
$html $html.'<input type="button" name="yes" value="Да" 
            onClick="document.location.href=\''
.$_SERVER['PHP_SELF'].'?action=deletePost&idForum='.
            
$_GET['idForum'].'&id_theme='.$post['id_theme'].'&id_post='.$id_post.
            
'&confirm=yes\'" />&nbsp;&nbsp;'."\n";
    
$html $html.'<input type="button" name="no" value="Нет" 
            onClick="document.location.href=\''
.$_SERVER['PHP_SELF'].'?action=showTheme&idForum='.
            
$_GET['idForum'].'&id_theme='.$post['id_theme'].'\'" /></div>'."\n";
    
$tpl file_get_contents'./templates/infoMessage.html' );
    
$tpl str_replace'{infoMessage}'$html$tpl );
    return 
$tpl
  }
  
  
// Удаляем файл, если он есть
  
if ( !empty( $post['putfile'] ) and is_file'./files/'.$post['putfile'] ) )
    
unlink'./files/'.$post['putfile'] );
  
$query "DELETE FROM ".TABLE_POSTS." WHERE id_post=".$id_post;
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при удалении сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue
                             
'action=showTheme&idForum='.$_GET['idForum'].'&id_theme='.$post['id_theme'] );
  }
  
// Если это - единственное сообщение темы, то надо удалить и тему
  
$query "SELECT COUNT(*) FROM ".TABLE_POSTS." WHERE id_theme=".$post['id_theme'];
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при удалении сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue
                             
'action=showForum&idForum='.$_GET['idForum'] );
  }
  if ( 
mysql_result$res0) == ) {
    
// Прежде чем удалять тему, надо обновить таблицу TABLE_USERS
    
$query "UPDATE ".TABLE_USERS.
              SET themes=themes-1 
              WHERE id_author=
             (SELECT id_author FROM "
.TABLE_THEMES." WHERE id_theme=".$post['id_theme'].")";
    
$res mysql_query$query );
    if ( !
$res ) {
      
$msg 'Ошибка при удалении сообщения';
      
$err 'Ошибка при выполнении запроса: <br/>'.
             
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
            
'(Файл '__FILE__ .', строка '__LINE__ .')';
      return 
showErrorMessage$msg$errtrue'action=showForum&idForum='.$_GET['idForum'] );
    }
    
$query "DELETE FROM ".TABLE_THEMES." WHERE id_theme=".$post['id_theme'];
    
$res mysql_query$query );
    if ( !
$res ) {
      
$msg 'Ошибка при удалении сообщения';
      
$err 'Ошибка при выполнении запроса: <br/>'.
             
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
            
'(Файл '__FILE__ .', строка '__LINE__ .')';
      return 
showErrorMessage$msg$errtrue'action=showForum&idForum='.$_GET['idForum'] );
    }
    
// Если мы удалили тему, то мы не можем в нее вернуться;
    // поэтому редирект будет на страницу форума, а не страницу темы
    
$deleteTheme true;
  } 
  
  
// Обновляем количество сообщений, оставленных автором сообщения
  
$query "UPDATE ".TABLE_USERS." SET posts=posts-1 WHERE id_author=".$post['id_author'];
  
$res mysql_query$query );
  if ( !
$res ) {
    
$msg 'Ошибка при удалении сообщения';
    
$err 'Ошибка при выполнении запроса: <br/>'.
           
$query.'<br/>'.mysql_errno().':&nbsp;'.mysql_error().'<br/>'.
           
'(Файл '__FILE__ .', строка '__LINE__ .')';
    return 
showErrorMessage$msg$errtrue
                             
'action=showForum&idForum='.$_GET['idForum'] );
  }
    
  if ( isset( 
$deleteTheme ) ) {
    return 
showInfoMessage'Сообщение успешно удалено''action=showForum&idForum='.$_GET['idForum'] );
  } else {
    return 
showInfoMessage'Сообщение успешно удалено''action=showTheme&idForum='.
                            
$_GET['idForum'].'&id_theme='.$post['id_theme'] ); 
  }
}
?>

Функция hasRightDeletePost() возвращает true или false в зависимости от того, имеет ли право пользователь удалить это сообщение (пост).

<?php
// Функция возвращает true или false в зависимости от того, имеет ли
// право пользователь удалить это сообщение (пост)
function hasRightDeletePost$post )
{
  
// Незарегистрированный пользователь не имеет право удалять сообщения
  
if ( !isset( $_SESSION['user'] ) ) return false;
  
// Если пользователь - администратор или модератор, он имеет право 
  // удалять любые сообщения (посты)
  
if ( $_SESSION['user']['status'] != 'user' ) return true;
  
// Обычный пользователь не может удалять чужие сообщения (посты)
  
if ( $_SESSION['user']['id_author'] != $post['id_author'] ) return false;
  
// Пользователь не может удалять сообщение, если оно заблокировано
  
if ( $post['locked'] == ) return false
  
// Обычный  пользователь имеет право удалять свои
  // сообщения, если на них еще не было ответа
  
$query "SELECT id_post FROM ".TABLE_POSTS.
            WHERE id_theme="
.$post['id_theme']." AND time>'".$post['time']."'";
  
$res mysql_query$query );
  if ( !
$res ) return false;
  if ( 
mysql_num_rows$res ) == 
    return 
true;
  else
    return 
false;
}
?>

Продолжение следует...