Когда пользователь щелкает на кнопке перехода к окончательному расчету (Перейти в кассу), вызывается сценарий checkout.php. Доступ к странице окончательного расчета и связанным с ней страницам должен осуществляться через SSL-соединение, однако наше демонстрационное приложение этого не требует.
Внешний вид страницы окончательного расчета показан ниже.
Данный сценарий требует, чтобы клиент ввел свой почтовый адрес (а также адрес доставки, если они отличаются).
checkout.php — сценарий принимающий детальную информацию о клиенте
<?php
// Включить наш набор функций
require ('book_sc_fns.php');
// Для покупательской тележки необходимо запустить сеанс
session_start();
$pagename = "Окончательный расчет";
$keywords= "";
$description="Окончательный расчет";
do_html_header($pagename, $keywords, $description);
echo "<section class=blok>";
echo "<div class=col1>";
echo "<header>";
echo "<h5>Категория книг</h5>";
echo "</header>";
echo "<nav>";
// Извлечь категории из базы данных
$cat_array = get_categories();
display_categories($cat_array);
echo "</nav>";
echo "</div>";
echo "<div class=col2>";
echo "<header>";
echo "<h2>$pagename</h2>";
echo "</header>";
echo "<article class=checkout>";
if($_SESSION['cart']&&array_count_values($_SESSION['cart']))
{
display_cart($_SESSION['cart'], false, 0);
display_checkout_form
();}
else
echo '<p>Ваша тележка пуста</p>';
display_button('show_cart.php', 'continue-shopping', 'Продолжить покупки');
echo "</article>";
echo "</div>";
echo"</section>";
do_html_footer();
?>
Сценарий не содержит ничего особо примечательного. Если тележка пуста, об этом выводится соответствующее уведомление. В противном случает отображается форма, показанная выше.
display_checkout_form()— функция из библиотеки output_fns.php, которая запрашивает ФИО и почтовый адрес клиента
<?php
function display_checkout_form
(){
// Выводит форму, которая запрашивает ФИО и адрес
?>
<br>
<table border = 0 width = '100%' cellspacing = 0>
<form action = 'purchase.php' method = 'post'>
<tr><th colspan = 2 bgcolor='#cccccc'>Информация о вас</th></tr>
<tr>
<td>ФИО</td>
<td><input type = 'text' name = 'name' value = "" maxlength = 40 size = 40></td>
</tr>
<tr>
<td>Адрес</td>
<td><input type = 'text' name = 'address' value = "" maxlength = 40 size = 40></td>
</tr>
<tr>
<td>Город/село</td>
<td><input type = 'text' name = 'city' value = "" maxlength = 20 size = 40></td>
</tr>
<tr>
<td>Область</td>
<td><input type = 'text' name = 'state' value = "" maxlength = 20 size = 40></td>
</tr>
<tr>
<td>Почтовый индекс</td>
<td><input type = 'text' name = 'zip' value = "" maxlength = 10 size = 40></td>
</tr>
<tr>
<td>Страна</td>
<td><input type = 'text' name = 'country' value = "" maxlength = 20 size = 40></td>
</tr>
<tr><th colspan = 2 bgcolor='#cccccc'>Адрес для доставки (не заполняйте поля, если совпадает с указанным выше)</th></tr>
<tr>
<td>ФИО</td>
<td><input type = 'text' name = 'ship_name' value = "" maxlength = 40 size = 40></td>
</tr>
<tr>
<td>Адрес</td>
<td><input type = 'text' name = 'ship_address' value = "" maxlength = 40 size = 40></td>
</tr>
<tr>
<td>Город/село</td>
<td><input type = 'text' name = 'ship_city' value = "" maxlength = 20 size = 40></td>
</tr>
<tr>
<td>Область</td>
<td><input type = 'text' name = 'ship_state' value = "" maxlength = 20 size = 40></td>
</tr>
<tr>
<td>Почтовый индекс</td>
<td><input type = 'text' name = 'ship_zip' value = "" maxlength = 10 size = 40></td>
</tr>
<tr>
<td>Страна</td>
<td><input type = 'text' name = 'ship_country' value = "" maxlength = 20 size = 40></td>
</tr>
<tr>
<td colspan = 2 align = 'center'>
<b>Пожалуйста, щелкните на кнопке "Купить" для того, чтобы подтвердить покупку,
либо на кнопке "Продолжить покупки" для продолжения покупок.</b>
<?php display_form_button('purchase', 'Приобрести выбранное'); ?>
</td>
</tr>
</form>
</table><hr>
<?php
}
?>
Когда пользователь продолжает работу, щелкнув на кнопке Купить в нижней части формы, запускается сценарий purchase.php.
По сравнению с checkout.php этот сценарий немного сложнее.
purchase.php — сценарий сохраняющий заказ в базе данных и принимающий данные, касающиеся платежа
<?php
// Включить наш набор функций
require_once('book_sc_fns.php');
// Для покупательской тележки необходимо запустить сеанс
session_start();
$pagename = "Окончательный расчет";
$keywords= "";
$description="Интернет-магазин ABC-Book. Книги традиционные и на электронных носителях";
do_html_header($pagename, $keywords, $description);
echo "<section class=blok>";
echo "<div class=col1>";
echo "<header>";
echo "<h5>Категория книг</h5>";
echo "</header>";
echo "<nav>";
// Извлечь категории из базы данных
$cat_array = get_categories();
display_categories($cat_array);
echo "</nav>";
echo "</div>";
echo "<div class=col2>";
echo "<header>";
echo "<h2>$pagename</h2>";
echo "</header>";
echo "<article>";
// Создать короткие имена переменных
$name = $_POST['name'];
$address = $_POST['address'];
$city = $_POST['city'];
$zip = $_POST['zip'];
$country = $_POST['country'];
// Если форма заполнена
if($_SESSION['cart']&&$name&&$address&&$city&&$zip&&$country)
{
// Можно ли вставлять в базу данных?
if( insert_order($_POST)!=false )
{
// Вывести тележку без изображений товаров и не разрешая изменения
display_cart($_SESSION['cart'], false, 0);
display_shipping(calculate_shipping_cost());
// Получить информацию по кредитной карточке
display_card_form
($name);display_button('show_cart.php', 'continue-shopping', 'Продолжить покупки');
}
else
{
echo 'Невозможно сохранить данные. Пожалуйста, повторите попытку позже.';
display_button('checkout.php', 'back', 'Назад');
}
}
else
{
echo 'Вы заполнили не все поля. Пожалуйста, повторите попытку.<hr />';
display_button('checkout.php', 'back', 'Назад');
}
echo "</article>";
echo "</div>";
echo"</section>";
do_html_footer();
?>
Логика сценария довольно-таки проста: выполняется проверка, что клиент заполнил все поля формы, после чего в базе данных сохраняется введенная информация путем вызова функции insert_order(). Эта функция вставляет сведения о клиенте в базу данных.
Функция insert_order() из библиотеки order_fns.php — вставляет в базу данных детальную информацию о заказе
<?php
function insert_order($order_details)
{
// Извлечь детальную информацию о заказе и поместить ее в переменные
extract($order_details);
// Установить адрес доставки равным почтовому адресу
if(!$ship_name&&!$ship_address&&!$ship_city&&
!$ship_state&&!$ship_zip&&!$ship_country)
{
$ship_name = $name;
$ship_address = $address;
$ship_city = $city;
$ship_state = $state;
$ship_zip = $zip;
$ship_country = $country;
}
$conn = db_connect();
// Вставка заказа должна выполняться в виде транзакции,
// поэтому необходимо отключить autocommit
$conn->autocommit(FALSE);
// Вставить почтовый адрес клиента
$query = "select customerid from customers where
name = '$name' and address = '$address'
and city = '$city' and state = '$state'
and zip = '$zip' and country = '$country'";
$result = $conn->query($query);
if($result->num_rows>0)
{
$customer = $result->fetch_object();
$customerid = $customer->customerid;
}
else
{
$query= "INSERT INTO customers VALUES(NULL, '$name', '$address', '$city', '$state', '$zip', '$country')";
$result = $conn->query($query);
if (!$result)
return false;
}
$customerid = $conn->insert_id;
$date = date('Y-m-d');
$query = "INSERT INTO orders VALUES(NULL, $customerid, ".$_SESSION['total_price'].", '$date',
'PARTIAL', '$ship_name','$ship_address', '$ship_city', '$ship_state', '$ship_zip', '$ship_country')";
$result = $conn->query($query) ;
if (!$result)
return false;
$query = "select orderid from orders where
customerid = $customerid and
amount > ".$_SESSION['total_price']."-.001 and
amount < ".$_SESSION['total_price']."+.001 and
date = '$date' and
order_status = 'PARTIAL' and
ship_name = '$ship_name' and
ship_address = '$ship_address' and
ship_city = '$ship_city' and
ship_state = '$ship_state' and
ship_zip = '$ship_zip' and
ship_country = '$ship_country'";
$result = $conn->query($query);
if($result->num_rows>0)
{
$order = $result->fetch_object();
$orderid = $order->orderid;
}
else
return false;
// Вставить каждую книгу из числа заказанных
foreach($_SESSION['cart'] as $isbn => $quantity)
{
$detail = get_book_details($isbn);
$query = "DELETE FROM order_items WHERE orderid =$orderid and isbn =$isbn";
$result = $conn->query($query);
$query = "INSERT INTO order_items VALUES($orderid, $isbn, ".$detail['price'].", $quantity)";
$result = $conn->query($query);
if(!$result)
return false;
}
// конец транзакции
$conn->commit();
$conn->autocommit(TRUE);
return $orderid;
}
?>
Код функции insert_order() достаточно длинный, поскольку необходимо выполнить вставку данных о клиенте, заказе, а также информацию о каждой приобретаемой книге.
Следует отметить, что различные части вставки оформлены как транзакция, которая начинается с оператора
$conn->autocommit(FALSE);
и заканчивается операторами
$conn->commit();
$conn->autocommit(TRUE);
Это единственное место в приложении, где должна применяться транзакция. Как избежать их? Посмотрите на код функции db_connect():
<?php
function db_connect()
{
$result = new mysqli('localhost', 'root', 'admin', 'book_sc');
$result->set_charset("utf8");
if (!$result)
return false;
$result->autocommit(TRUE);
return $result;
}
?>
Очевидно, что этот код отличается от применяемого в функции insert_order().
После создания соединения с MySQL включается режим автоматического сохранения транзакций (autocommit). Это гарантирует автоматическое сохранение результатов любого SQL-оператора. Однако если необходимо выдать целую последовательность взаимосвязанных SQL-операторов в виде единственной транзакции, потребуется отключить режим autocommit, выполнить серию вставок, сохранить данные и вновь включить режим autocommit.
Затем определяется стоимость доставки по адресу клиента, которая выводится на экран с помощью строки кода:
display_shipping(calculate_shipping_cost());
function calculate_shipping_cost()
{
// Поскольку доставка осуществляется по всему миру
// посредством телепортирования, стоимость доставки фиксирована
return 200.00;
}
Код вычисления стоимости доставки, оформленный в виде функции calculate_shipping_cost(), всегда возвращает значение 200 рублей. В реальном сайте, реализующем онлайновую торговлю, потребуется предоставить клиенту выбор способа доставки, подсчитать затраты на доставку по разным адресам и соответствующим образом вычислить стоимость доставки.
Далее отображается форма для ввода клиентом данных о кредитной карточке с помощью функции display_card_form() из библиотеки output_fns.php.
Функция display_card_form() из библиотеки output_fns.php
<?php
function display_card_form
($name){
// Выводит форму, запрашивающую сведения о кредитной карточке
?>
<div class="table_cart">
<table>
<form action = 'process.php' method = 'post'>
<tr><th colspan = 2 bgcolor="#cccccc">Сведения о кредитной карточке</th></tr>
<tr>
<td>Вид</td>
<td><select name = 'card_type'><option>VISA<option>MasterCard<option>American Express</select></td>
</tr>
<tr>
<td>Номер</td>
<td><input type = 'text' name = 'card_number' value = "" maxlength = 16 size = 40></td>
</tr>
<tr>
<td>AMEX-код (если необходим)</td>
<td><input type = 'text' name = 'amex_code' value = "" maxlength = 4 size = 4></td>
</tr>
<tr>
<td>Дата истечения</td>
<td>Месяц <select name = 'card_month'><option>01<option>02<option>03<option>04<option>05<option>06<option>07<option>08<option>09<option>10<option>11<option>12</select>
Год <select name = 'card_year'><option>12<option>13<option>14<option>15<option>16<option>17<option>18<option>19<option>20<option>21<option>22</select></td>
</tr>
<tr>
<td>Держатель карточки</td>
<td><input type = 'text' name = 'card_name' value = "<?php echo $name; ?>" maxlength = 40 size = 40></td>
</tr>
<tr>
<td colspan = 2 align = 'center'>
<b>Пожалуйста, щелкните на кнопке "Купить" для того, чтобы подтвердить покупку,
либо на кнопке "Продолжить покупки" для продолжения покупок.</b>
<?php display_form_button('purchase', 'Приобрести выбранное'); ?>
</td>
</tr>
</table>
</div>
<?php
}
?>
Комментарии(0)
Для добавления комментариев надо войти в систему и авторизоватьсяКомментирование статей доступно только для зарегистрированных пользователей:Зарегистрироваться