» Главная
eXcode.ru » Статьи » PHP » Трюки
» Новости
» Опросы
» Файлы
» Журнал



Пользователей: 0
Гостей: 10





TDD: Рефакторинг приложения




Рефакторинг приложения

Отделяем бизнес логику от презентационной

Пожалуй, это самый важный первый шаг, который стоит сделать. Для этого несколько модифицируем index.php, выделив из него разметку в отдельный файл /templates/feedback.html.

index.php

<?php
ob_start();
 
include_once('db.php');
 
$conn = mysql_connect($db_host, $db_user, $db_password);
 
if($conn === FALSE){
    die('db connect error: ' . mysql_error());
}
 
if(!mysql_select_db($db_name, $conn)){
    die('can not use db: ' . mysql_error());
}
 
if(isset($_POST['submit'])) {
    $name = mysql_escape_string($_POST['name']);
    $email = mysql_escape_string($_POST['email']);
    $message = mysql_escape_string($_POST['message']);
    $time = time();
 
    $sql = "INSERT INTO feedback (name, email, message, time) VALUES ('$name', '$email', '$message', '$time')";
 
    $result = mysql_query($sql, $conn);
    if(!$result){
        die('invalid query: ' . mysql_error());
    }
}
 
$limit = 3;
$offset = isset($_GET['offset']) ? $_GET['offset'] : 0;
 
$sql = "SELECT * FROM feedback ORDER BY time DESC LIMIT " . ($offset * $limit) . ", {$limit}";
$fetch_result = mysql_query($sql, $conn);
if(!$fetch_result){
    die('invalid query: ' . mysql_error());
}
 
$sql = "SELECT COUNT(*) as counter FROM feedback";
$count_result = mysql_query($sql, $conn);
if(!$count_result){
    die('invalid query: ' . mysql_error());
}
$row = mysql_fetch_assoc($count_result);
$total = (int)$row['counter'];
 
include_once('templates/feedback.html');
 
ob_end_flush();
?>

templates/feedback.html

<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=windows-1251">
<link rel=stylesheet type='text/css' href='styles/main.css'>
<script language="JavaScript" type="text/javascript" src="js/form.js"></script>
</head>
<body>
<table width="100%" style="height:100%" border="0" cellpadding="0" cellspacing="0">
<tr>
<td width="10%" style="background-color:#7F1A22">
</td>
<td width="90%" style="padding:5px 10px 5px 10px" valign="top">
<h1>Обратная связь</h1>
<p>
  Если у вас есть пожелания или вопросы к сотрудникам нашей компании,<br>
  пожалуйста, заполните поля формы.<br>
</p>
<form action="index.php" method="post" onsubmit="return submit_form(this);">
<table>
  <tr>
    <td align="right">
      Ваше имя:
    </td>
    <td>
      <input name="name" value="" type="text">
    </td>
 </tr>
  <tr>
    <td align="right">
      Email:
    </td>
    <td>
      <input name="email" value="" type="text">
    </td>
 </tr>
    <tr>
     <td align="right">
       Текст вопроса:
     </td>
     <td>
       <textarea name="message" cols="50" rows="4"></textarea>
     </td>
    </tr>
    <tr>
    <td>
    </td>
    <td>
        <input value="Отправить" name="submit" type="submit">
    </td>
    </tr>
</table>
</form>
<?php if($offset > 0) :?><b><a href="?offset=<?=($offset-1)?>">&lt;</a></b><?php endif; ?>
<?php if($total > 0) :?><?=($offset*$limit)+1?> - <?=(($offset+1)*$limit > $total)? $total : ($offset+1)*$limit ?><?php endif; ?>
<?php if(($offset+1)*$limit < $total) :?><b><a href="?offset=<?=($offset+1)?>">&gt;</a></b><?php endif; ?>
<?php
while ($row = mysql_fetch_assoc($fetch_result)) {
?>
<hr/>
<b>Автор:</b> <a href="mailto:<?=htmlspecialchars($row['email']);?>"><?=htmlspecialchars($row['name']);?></a><br/>
<b>Сообщение:</b> <?=htmlspecialchars($row['message']);?><br/>
<b>Время:</b> <?=strftime("%m/%d/%y %H:%M:%S", $row['time'])?><br/>
<?php } ?>
</td>
</tr>
</table>
</body>
</html>

До идела еще далеко, но читается уже намного лучше. Удостоверившись в том, что все функциональные тесты срабатывают, продолжаем дальше.

Используем WACT

WACT предоставляет мощные средства для отделения презентационной и бизнес логики. Помимо гибкой шаблонной системы в WACT присутствуют также инструменты для абстрагирования работы с БД. Т.к. эти инструменты очень гибко интегрируюся с шаблонной системой, имеет смысл остановить на них выбор.

WACT требует наличие config.ini файла, в котором описываются глобальные конфигурационные настройки приложения. Перенесем данные из db.php в config.ini.

[templates]
forcecompile = TRUE

[database]
driver = mysql
mysql.database = "feedback"
mysql.user = "root"
mysql.password = "test"
mysql.host = "localhost" 

Создадим также файл tests/config.ini, в котором мы будем хранить настройки для тестов.

[templates]
forcecompile = TRUE

[database]
driver = mysql
mysql.database = "feedback-web-tests"
mysql.user = "root"
mysql.password = "test"
mysql.host = "localhost" 

Заставим WACT также пользоваться этим конфигурационным файлом при вызове из тестов. Для этого добавим следующую строку в /tests/setup.php:

<?php
define('WACT_CONFIG_DIRECTORY', dirname(__FILE__) . '/'); 
?>

Нам необходимо заменять config.ini на /tests/config.ini на время выполнения тестов, как мы это делали с db.php, для этого несколько изменим фикстуру:

<?php
class AcceptanceTestOfFeedbackProject extends WebTestCase {
    function setUp() {
        DBC :: execute('DELETE FROM feedback');
        $this->_switchToWebTestingConfig();
    }
 
    function tearDown() {
        $this->_switchToProductionConfig();
    } 
 
    function _switchToWebTestingConfig() {
        $project_dir = dirname(__FILE__) . '/../';
        $tests_dir = dirname(__FILE__) . '/';
 
        if(!file_exists($project_dir . 'config.ini~')) {
            rename($project_dir . 'config.ini', $project_dir . 'config.ini~');
        }
        copy($tests_dir . 'config.ini', $project_dir . 'config.ini');
    }
 
    function _switchToProductionConfig() {
        $project_dir = dirname(__FILE__) . '/../';
        if(file_exists($project_dir . 'config.ini~')) {
            unlink($project_dir . 'config.ini');
            rename($project_dir . 'config.ini~', $project_dir . 'config.ini');
        }
    } 
    [...]
?>

Имеет смысл также пользоваться в тесте средствами WACT для работы с БД. Как можно видеть, вызов DBC :: execute('DELETE FROM feedback') - пришел на смену жесткой привязке к mysql_ функциям.

Все готово к тому, чтобы полностью отделить бизнес логику от презентационной. Начинаем с index.php:

<?php
ob_start();
 
require_once(dirname(__FILE__) . '/external/wact/framework/common.inc.php');
require_once(WACT_ROOT . '/db/db.inc.php');
require_once(WACT_ROOT . '/template/template.inc.php');
 
function &getList(&$pager) {
    return DBC::NewPagedRecordSet('SELECT * FROM feedback ORDER BY time DESC', $pager);
}
 
function insertFeedback($arr) {
    $dataspace = new DataSpace();
    $dataspace->import($arr);
    $record =& DBC::NewRecord($dataspace);
    return $record->insert('feedback', array('name', 'email', 'message', 'time'));
}
 
if(isset($_POST['submit'])) {
    insertFeedback(array('name' => $_POST['name'],
                 'email' => $_POST['email'],
                 'message' => $_POST['message'],
                 'time' => time()));
}
 
$page = new Template('/feedback.html');
$pager =& $page->getChild('pager');
 
$feedback =& $page->findChild('feedback');
$feedback->registerDataSet(getList($pager));
 
$page->display();
 
ob_end_flush();
?>

WACT ищет по-умолчанию шаблоны в директории /templates/source, модифицируем и перенесем feedback.html.

<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=windows-1251">
<link rel=stylesheet type='text/css' href='styles/main.css'>
<script language="JavaScript" type="text/javascript" src="js/form.js"></script>
</head>
<body>
<table width="100%" style="height:100%" border="0" cellpadding="0" cellspacing="0">
<tr>
<td width="10%" style="background-color:#7F1A22">
</td>
<td width="90%" style="padding:5px 10px 5px 10px" valign="top">
<h1>Обратная связь</h1>
<p>
  Если у вас есть пожелания или вопросы к сотрудникам нашей компании,<br>
  пожалуйста, заполните поля формы.<br>
</p>
<form action="index.php" method="post" onsubmit="return submit_form(this);">
<table>
  <tr>
    <td align="right">
      Ваше имя:
    </td>
    <td>
      <input name="name" value="" type="text">
    </td>
 </tr>
  <tr>
    <td align="right">
      Email:
    </td>
    <td>
      <input name="email" value="" type="text">
    </td>
 </tr>
    <tr>
     <td align="right">
       Текст вопроса:
     </td>
     <td>
       <textarea name="message" cols="50" rows="4"></textarea>
     </td>
    </tr>
    <tr>
    <td>
    </td>
    <td>
        <input value="Отправить" name="submit" type="submit">
    </td>
    </tr>
</table>
</form>
<list:LIST id="feedback">
<page:navigator id="pager" items="3">
Страница: {$PageNumber} из {$TotalPages}
    <page:first>&lt;&lt;</page:first> <page:prev>&lt;</page:prev>
    <page:list>
        <page:number>
        <page:elipses>...</page:elipses>
        <page:separator> </page:separator>
    </page:list>
    <page:next>&gt;</page:next> <page:last>&gt;&gt;</page:last>
</page:navigator>
<list:ITEM>
<hr>
<b>Автор:</b> <a href="mailto:{$email}">{$name}</a><br>
<b>Сообщение:</b> {$message}<br>
<b>Время:</b> {$time|date:"H:i:s m/d/Y"}<br>
</list:ITEM>
</list:LIST>
</td>
</tr>
</table>
</body>
</html>

WACT предоставляет набор компонентов, позволяющих заметно облегчить жизнь верстальщика. При помощи <list:LIST> компонента организуется итерация по сообщениям в шаблоне. <page:navigator> компонент берет полностью на себя всю рутину по организации и выводу пейджера. При этом содержимое index.php и feedback.html заметно упростилось и приобрело более логический вид.

Конечно, мы сделали очень много измненений, но выполняющиеся функциональные тесты позволили нам неустанно держать руку на пульсе разработки.

Далее - Шаг третий - внедряем паттерн ActiveRecord.

К началу статьи





Добавил: PIXELДата публикации: 2008-03-05 08:58:31
Рейтинг статьи:4.00 [Голосов 1]Кол-во просмотров: 26171

Комментарии читателей

Всего комментариев: 79

2019-06-03 14:06:50
Raymondsok

<a href=https://www.youtube.com/watch?v=f2nCVvKcXS0&list=PLnzw9EuFoSBmLO4djI4GCHKBjaGqjKOcS&index=5&t=0s>комплектная трансформаторная подстанция</a>

2019-01-20 02:09:31
Denniswat

Реклоузер 6-10кв, КТП КОМПЛЕКТНЫЕ ТРАНСФОРМАТОРНЫЕ ПОДСТАНЦИИ москва, Производство ктп москва, а также многое другое Вы найдете на нашем специализированном сайте: http://sviloguzov.ru/ - Это то, что Вам нужно!

2018-09-15 12:51:01
Justin
Вам нужен кредит для вашего бизнеса или личных целей? Мы оказываем финансовую помощь компаниям и частным лицам с удобной для кармана процентной ставкой в размере 3% годовых. Наши условия дешевы и понятны.

Свяжитесь с нами сегодня и будет финансироваться в течение 2-4 рабочих дней. E-mail: unique2aal@gmail.com

2018-08-24 07:09:26
RebaCarrasco
Все компоненты в креме действуют по принципу синергии – повышают эффективность друг друга. Уникальное действие крема Bioretin объясняется огромным количеством питательных веществ в составе. При регулярном применении вам удастся добиться следующих результатов: запустить внутреннее обновление клеток; усилить подкожное кровообращение; улучшить подкожный обмен веществ; нормализовать восстановительные процессы; сделать лицо более свежим и подтянутым; восстановить водный баланс; избавиться от шелушения; уменьшить отечность и сухость кожи; избавиться от многочисленных морщинок. <a href=http://otzyvy-vrachej.com/protivogribkovyy-krem-mitsinorm-otzyvy-pokupateley-kupit-sredstvo-v-aptekah.php>противогрибковый крем мицинорм</a> Оставьте заявку, менеджер с Вами свяжется и проконсультирует по любым вопросам. Xtrazеx для потeнции: улучшает вcе aспекты сексуaльнoй жизни. Усилить мужскую силу и раскрыть весь сексуальный потенциал помогут шипучие таблетки Xtrazex для потенции. Благодаря нетоксичности препарата его можно применять в любом возрасте, не опасаясь побочных эффектов. Разрешен совместный прием с алкоголем и другими медикаментами. Уже многие мужчины благодаря средству теперь занимаются сексом в 2-3 раза чаще, испытывают мощные оргазмы и полностью свободны в своих сексуальных фантазиях. Это уникальное средство, которое поддерживает потенцию даже при стрессах и нервных перегрузках.

2018-04-17 01:20:46
kawanboni.com
沒有醫生的處方
cialis 5 mg para diabeticos
<a href="http://cialisvipsale.com/#">viagra vs cialis</a>
can you purchase viagra online
<a href=http://viagrayosale.com/#>Viagra 20 mg</a>

2018-01-21 20:12:52
WalterPem
АЛКОВЕРИН АКТИВИРУЕТ РЕЖИМ АЛКОГОЛЬНОГО ОТТОРЖЕНИЯ
С ALCOVIRIN выпить ПРОСТО НЕ УДАСТСЯ!

Это первый биогенный растительный комплекс, способствующий выработке непереносимости алкоголя при совместном приеме капель и спиртных напитков, вызывая тошноту и его полное отторжение организмом!

Кроме того, он оказывает мощное оздоровительное действие, устраняя алкогольную интоксикацию и способствуя восстановлению правильной работы органов и систем.

Официальный сайт: http://alcovirin.bxox.info

2018-01-21 12:09:40
CraigVet
Приобрести можно на веб-сайте http://tedsjkpb.bestseller-super.ru

Рады предложить вам удивительное средство для снижения веса сироп Мангустина. С его помощью реально избавиться от 15 кг за 14 дней.

Дерево мангостан произрастает на Шри-Ланке. Плоды растения обладают удивительными особенностями, которые были положены в основу препарата Мангустина. В баночке содержится более 25 плодов этого замечательного растения. Плоды с растения мангостан помогают сжечь чрезмерную жировую ткань. И отлично влияют на организм в комплексе. Технология производства средства, и уникальная упаковка позволяют сберечь все полезные свойства мангостина.

Основным действующим веществом сиропа Мангустина являются фрукты с дерева мангкут, в которых имеется большое число полезных элементов. Благодаря компоненту окиси дифениленкетона, которое в больших количествах содержатся в плодах, сильно тормозятся процессы окисления в организме. Ксантон считается одним из наиболее мощных антиоксидантов. В плодах растения мангкут также есть разные группы витаминов и элементы. Купить сироп Mangoosteen возможно на веб-сайте http://tedsjkpb.bestseller-super.ru.


2017-12-23 18:55:03
MiLaskinaunwig
Какую выбрать шлейку для собаки? Открытый вопрос

Наверняка <a href=https://www.murzoo.ru/>купить щенка</a> у Вас уже получилось и Вы начали ухаживать за ним. Для комфортного ношения шлейка должна быть правильно подобрана по размерам собаки, <a href=https://www.murzoo.ru/component/djclassifieds/?view=items&cid=0&se=1&option=com_djclassifieds&view=items&Itemid=&search=шлейка&se_regs=0&se_cats=&se_price_f=&se_price_t=>купить шлейку</a> можно какую угодно, но нужно внимательно подойти к этому вопросу для обеспечения комфорта вашему питомцу. Существуют размерные таблицы, выкройки, облегчающие выбор. Чтобы воспользоваться таблицей, вы должны снять со своей собачки несколько мерок:
Главная мерка: от костей холки до основания хвоста измеряется длина спины.
Обхват груди: измеряется в самом широком месте сразу за локтями. К результату добавляется для мелких пород 1 см, для крупных — 2 см.
Обхват шеи в том месте, где должен быть ошейник.
Мерки для определения размеров ездовой шлейки снимаются иначе из-за конструктивных особенностей амуниции. Ездовая шлейка требует таких измерений собак:
расстояние между началом грудной кости и холкой;
длина грудины;
расстояние от окончания грудной кости до основания хвоста.
Правильно подобранная по размеру шлейка не болтается на корпусе собаки, но и не давит нигде. Под ремни должна входить ваша ладонь. Правильный замер позволит <a href=https://www.murzoo.ru/tovary-dlya-zhivotnykh,165>купить шлейку</a> не выходя из дома, что с экономит вам время.

Ну и в заключении хотелось бы пригласить Вас в нашу группу ВКОНТАКТЕ: <a href=https://vk.com/murzooru>Купить щенка / купить котёнка - murzoo.ru</a>

2017-11-16 21:38:54
JosephGlima
Здравствуйте, скорее http://vulkan-cazino24.com .

Все хиты Вулкана в двух турнирах – присоединяйтесь! Давайте вспомним все самые приятные события уходящего 2017 года




Гарантии, акции, победа ждут тебя


Ниже сайт:
http://vulkan-cazino24.com
<a href=vulkan-cazino24.com> Игровые автоматы бесплатно </a>

2017-09-12 08:49:04
Robertbix
гостиная Роза
http://1stbest.info/

----------
Ваше имя: *
Текст записи: *
Имя:

Пароль:



Регистрация

Какой марки ваш мобильник?
Nokia
40% (146)
Samsung
8% (29)
Siemens
16% (59)
Motorola
13% (49)
Sony Ericsson
13% (49)
LG
1% (4)
Pantech
0% (0)
Alcatel
2% (6)
Другой
3% (10)
Нет у меня мобилы
4% (15)

Проголосовало: 367
Звонит один мужик своему интернет-провайдеру и говорит оператору:
- Алло, здраствуйте, у меня проблема! Я не могу зайти в интернет!
- А в чем, собственно говоря, дело?
- А у меня нет компьютера.
Рейтинг: 0/10 (0)
Посмотреть все анекдоты