Навигация
Главная
Поиск
Форум
FAQ's
Ссылки
Карта сайта
Чат программистов

Статьи
-Delphi
-C/C++
-Turbo Pascal
-Assembler
-Java/JS
-PHP
-Perl
-DHTML
-Prolog
-GPSS
-Сайтостроительство
-CMS: PHP Fusion
-Инвестирование

Файлы
-Для программистов
-Компонеты для Delphi
-Исходники на Delphi
-Исходники на C/C++
-Книги по Delphi
-Книги по С/С++
-Книги по JAVA/JS
-Книги по Basic/VB/.NET
-Книги по PHP/MySQL
-Книги по Assembler
-PHP Fusion MOD'ы
-by Kest
Professional Download System
Реклама
Услуги

Автоматическое добавление статей на сайты на Wordpress, Joomla, DLE
Заказать продвижение сайта
Программа для рисования блок-схем
Инженерный калькулятор онлайн
Таблица сложения онлайн
Популярные статьи
OpenGL и Delphi... 65535
Форум на вашем ... 65535
21 ошибка прогр... 65535
HACK F.A.Q 65535
Бип из системно... 65535
Гостевая книга ... 65535
Invision Power ... 65535
Пример работы с... 65535
Содержание сайт... 65535
ТЕХНОЛОГИИ ДОСТ... 65535
Организация зап... 65535
Вызов хранимых ... 65535
Создание отчето... 65535
Имитационное мо... 65535
Программируемая... 65535
Эмулятор микроп... 65535
Подключение Mic... 65535
Создание потоко... 65535
Приложение «Про... 65535
Оператор выбора... 65535
Реклама
Сейчас на сайте
Гостей: 10
На сайте нет зарегистрированных пользователей

Пользователей: 13,370
новичок: dogoco6
Новости
Реклама
Выполняем курсовые и лабораторные по разным языкам программирования
Подробнее - курсовые и лабораторные на заказ
Delphi, Turbo Pascal, Assembler, C, C++, C#, Visual Basic, Java, GPSS, Prolog, 3D MAX, Компас 3D
Заказать программу для Windows Mobile, Symbian

Моделирование литейного цеха на GPSS + Пояснительная записка
Расчет мер близости на отношениях на Delphi + Пояснительная записка
Создание последовательности окон и передвижение окон по экрану на Turbo ...

А сколько человек на сайте?
Автор: Makswell
Источник: http://progers.ru/

Всем доброго времени суток!

Наверняка, гуляя по сети в поисках порн..., т.е. в поисках какой-либо информации, вы натыкались на такую фишку, типа:
На сайте: 100 человек

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

Недавно, по личной надобности, мне захотелось сделать такое для своего сайта и я реализовал все это дело с использованием PHP+MySQL. На нашем портале Progers.ru вы можете видеть (вверху) красующуюся надпись о количестве пользователей On-Line.

Итак, в этой статье я хочу вам рассказать, как сделать такую фичу для сайта. Это на самом деле проще жареной капусты ;=) и вскоре вы убедитесь в этом.

Все что нам нужно, это - хостинг с поддержкой PHP и MySQL и пара минут времени. Может быть, некоторые возразят, зачем здесь база данных, когда все можно реализовать на файлах. Скажу вам , что MySQL в данном конкретном случае подходит как нельзя лучше. С использованием файлов же, пришлось бы писать гораздо больше кода и заниматься в большинстве своем рутиной, которая нам ни к чему; в то время как с помощью базы данных все делается парой-другой запросов...

Я надеюсь, что вы умеете хоть как-то обращаться с сервером MySQL и знаете в целом, что такое базы данных и для чего они служат. В противном случае, не могу ничем помочь, кроме как посоветовать обратиться к друзьям, владеющим искусством составлять SQL-запросы... Хотя, в принципе, вы можете просто скопировать мой код и все. Однако, сама база данных все же должна быть настроена...

Итак, постепенно переходим от теории к практической ипостаси. В PHP, к сожалению (да и в других серверных языках веб-программирования), отсутствует такая, на мой взгляд, полезная технология, которая позволяла бы определять момент времени, в который человек покинул сайт. Неважно, каким способом, он это сделал: закрыл окно браузера или перешел по другой ссылке. Раз PHP пасует, сами сделаем кое-какую подобную технологию; естественно, о точности и отсутствии погрешностей здесь не говорю... Однако, все так делают и мы так сделаем. Далее опишу, как мы будем, собственно, определять кол-во юзеров на линии теоретически (не касаясь MySql и PHP конкретно). Если вы уловите мысль, то тотчас же реализуете эту возможность на любом языке веб-программирования и любым доступным для вас методом (файлы, к примеру)...

Для начала, нам нужно установить переменную Точность - время, в течении которого посетитель будет считаться на линии, т.е. бродящем по сайту. Значит, при заходе на страницу, мы должны определить сперва-наперво IP-адрес зашедшего и его timestamp. Никакой экзотики, TimeStamp - это представление времени, которое равняется "кол-ву секунд, прошедших с полуночи 1 января 1970 года по Гринвичу до настоящего момента". Это весьма универсальное представление времени и, в частности, именно с этим форматом работает большинство PHP-х ф-й для работы с "датой-временем". Весьма удобная метка, поверьте мне на слово. Т.е., чем больше число TimeStamp, чем дольше "мы живем" и чем больше "сейчас времени", извиняюсь за сумбурность. После, мы открываем какое-либо хранилище (файлы, базы данных, сессионный массив и т.п.) и удаляем из него все записи (каждая запись - информация об одном зашедшем на страничку пользователе), в которых TimeStamp + Точность меньше текущего TimeStamp'а, или где IP-адрес совпадает с текущим Ip'м. Т.е., уничтожаем старые записи. Далее записываем данные о зашедшем пользователе (оставляем запись): IP и timestamp. Все, подсчитываем количество записей - это и есть кол-во человек на сайте в данное время.

Честно говоря, получилось так, что ориентир все равно велся на MySQL, а не на файлы. В самом деле, наше ли это дело, сначала лезть в файл и удалять там-то, потом опять лезть в него, чтобы записать, а потом только считывать. Куда проще сначала считать файл в массив, удалить из массива старые записи и добавить запись о юзере, если это требуется и уж потом записать массив обратно в файл. При выводе данных же руководствоваться кол-м значений в массиве.

Надеюсь, основную мысль вы все же уловили. Мы просто подсчитываем кол-во юзверей, со времени захода которых не прошло время, которое мы установили (Точность).

Итак, переходим наконец-то к практике. Повторюсь, для хранения информации будет юзаться база MySQL. Для всего этого дела мы создадим отдельную таблицу. Назовем её online. В таблице создадим 3 поля:
id - ключевое авто_инкрементирующееся поле типа INT с максимальным размеров в 10 символов. Нужно для более оптимизированной работы с таблицей, хотя его можно и опустить. При каждом заходе человека на сайт, поле будет увеличивать свое значение на 1.
ip - поле символьного типа VARCHAR с максимальным значением 20 cсимволов (лично я не видел еще IP-адреса, размером больше 15 символов, но на всякий случай =). В нем хранятся, соответственно, IP'ы людей. Значение по умолчанию - 0.
unix - поле символьного типа VARCHAR с максимальным значением 60 символов. Поле, в котором будет храниться timestamp пользователя. Такое странное название выражено скорее моими личными пристрастиями, чем истинным его предназначением. Хотя скажу, что timestamp-формат принят в операционных системах UNIX, как стандартный. Можете поле назвать как угодно (только мой пример с этим именами полей). По дефолту пустое значение.

Замечу, что поле unix будет иметь тип VARCHAR, а не встроенный разработчиками MySQL тип TIMESTAMP. Это связано с тем, что этот тип слишком неудобен для хранения данных даты\времени в базе, как это может показаться на первый взгляд.

Далее привожу запрос, выполнив который, вы создадите соответствующую таблицу с нужными полями. Запрос можно выполнить функцией PHP mysql_query(), либо в какой-нибудь удобной оболочке для работы с MySQL. Например в PHPMyAdmin.
CREATE TABLE `online` (
`id` int(10) NOT NULL auto_increment,
`ip` varchar(20) NOT NULL default '0',
`unix` varchar(60) NOT NULL default '',
KEY `id` (`id`)
)

Выполнили? Молодцы. Напомню, что команды синтаксиса MySQL лучше всего привыкать писать в верхнем регистре и не для понта, как думают некоторые, а для повышении удобочитаемости кода и просто потому, что так принято.

После выполнения запроса, нам остается только написать код, который будет заниматься, собственно, подсчетом кол-а человек на линии. Этот код я запихнул в отдельную функцию, которая хранится у меня в файле, а сам файл инклюдится ( include(), require() ) на каждой странице моего сайта где-нибудь в самом начале. Я привожу вам пример функции точь-в-точь, какую я написал для своего сайта, разве только немного измененную в целях публичного использования. При наличии необходимых знаний, вы легко сможете отредактировать её под себя.
#------ Файл online.php

/* ф-я подсчитывает пользователей на линии; возвращает кол-во пользователей в
отформатированном виде, т.е. для вывода результата нужно лишь прописать в
нужном месте типа: echo on_line(); */
function on_line() {
$host = "localhost"; // хост, где расположена база данных MySql
$db_name = ""; // имя базы данных; как правило совпадает с именем юзера
// (переменная ниже), хотя я категорически против одинаковых
// имен, ориентируясь на защиту...
$db_user = ""; // пользователь, которому разрешен доступ к базе
$db_password = ""; // пароль пользователя
$wine = 300; // точность он-лайн (секунды); время, в течении которого
// пользователя, зашедшего на страничку, мы считаем находящимся
// на сайте
$table_online = "online"; // имя таблицы
// делаем доступной глобальную переменную ИП-адреса
global $REMOTE_ADDR;
// соединяемся с сервером MySQL и выбираем нужную базу
mysql_connect($host,$db_user,$db_password) or die(mysql_error());
mysql_select_db($db_name) or die(mysql_error());

// удаляем всех, кто уже пробыл $wine секунд или у кого ИП текущий
$sql_update = "DELETE FROM $table_online WHERE `unix`+$wine < ".time().
" OR `ip` = '$REMOTE_ADDR'";
$result_update = mysql_query($sql_update) or die(mysql_error());

// вставляем свою запись
$sql_insert = "INSERT INTO $table_online VALUES ('','$REMOTE_ADDR','".time()."')";
$result_insert = mysql_query($sql_insert) or die(mysql_error());

// считаем уников он-лайн
$sql_sel = "SELECT `id` FROM $table_online";
$result_sel = mysql_query($sql_sel) or die(mysql_error());

$online_people = mysql_num_rows($result_sel); // кол-во On-Line пользователей
$online_people = (string) $online_people; // приводим к строковому типу
// (так надо.. см. дальше)

$rain = strlen($online_people) - 1; // номер последнего символа в числе
// on-line юзеров

// форматирование вывода (я все сделал за вас =)
if($online_people[$rain]==2||$online_people[$rain]==3
||$online_people[$rain]==4
||(strlen($online_people)!=1&&$online_people[strlen($online_people)-2]!=1))
// $line - переменная, определяющая формат вывода
$line = "человека"; else $line = "человек";
// возвращаем результат
return "На сайте ".$online_people."$line";
}

Вот такая вот функция. Где-нибудь в начале файла вам надо будет вставлять её как-нибудь по типу:
include 'online.php';

А в том месте, где нужно вывести кол-во пользователей, писать:
echo on_line();

Теперь разъясню немного код функции, так как в ней самой я все подробно откомментировал. Сначала идут переменные, нужные для удачного коннекта к базе, а также переменная $wine - наша точность. Также делается доступной из функции глобальная переменная $REMOTE_ADDR, которая возвращает IP-адрес клиентского компьютера. После происходит соединение с сервером MySQL. И уже после начинается самое интересное.

Первым запросом к базе ( запросы выполняются ф-й mysql_query() ) мы удаляем все записи, в которых timestamp + $wine меньше текущего timestamp или в которых ИП-адрес совпадает с нашим. Т.е. мы удаляем из таблицы либо старых пользователей, либо самих себя, чтобы не повторяться.

Вторым запросом мы вставляем свою запись со своим IP'м и timestamp'м. Обратите внимание ,что значение первого поля мы оставляем пустым, так как оно инкрементируется от вставки к вставке и само собой заполнится (увеличенным на 1 предыдущим значением).

После всех манипуляций с таблицей, в ней остается действительно истинное кол-во человек на сайте, с момента прихода которых не прошло $wine секунд. Нам остается лишь простым запросом выбрать все записи и подсчитать их кол-во. Это и будет кол-во пользователей в Он-Лайне. Обратите внимание, что мы с вами, как люди умные, не выбираем сразу все поля из всех записей (зачем нам лишние данные, если нужно только подсчитать количество записей), а выбираем только поле id. Это тоже прием для оптимизации запросов, хотя многие о нем забывают или не знают.

А вот потом идет, собственно, форматирование данных. На мой взгляд, я сделал его очень лаконичным и элегантным. Смотреть приятно, хотя с первого раза и не совсем понятно, как происходит процесс. Возможно, такое форматирование вам не понадобится. Вдруг вы захотите как-либо по-другому выводить информацию о кол-во юзверей. Тогда вам остается или убрать форматирование, или подредактировать его (в том числе и под свой дизайн). Так или иначе, переменная $online_people хранит кол-во пользователей и дальше вы вольны делать с ней все, что хотите. Можете просто возвратить её ( return $online_people; ) и сам формат данных осуществлять при непосредственном выводе, а не в теле функции, либо вообще, как я уже говорил, не осуществлять форматирования:
echo "On-Line: ".on_line();

Возможно, так будет даже красивее.
Важные замечания:
Переменная $wine на моем сайте равна 300 секундам, т.е. 5 минутам. Вы можете произвольно выставить её значение.
При коннекте к базе и выполнении запросов мы используем конструкцию or die(), которая в случае неудачного действия завершает сценарий, но перед этим выводит в выходной поток (браузер) какую-либо строку. В нашем случае мы применяем ф-ю mysql_error(), которая возвращает в строковом виде ошибку, случившуюся во время манипуляции с базой\таблицей. Если вы не хотите завершать сценарий (в самом деле, зачем это надо: ведь из-за одной ошибки в ф-и сайт перестанет работать!), то просто не используйте эту конструкцию. Тем более что при какой-либо ошибке и наличии этой конструкции, пользователь, возможно (если ошибка при соединении с сервером), сможет узнать некоторые данные вашего сервера MySQL, а именно хост, логин пользователя и имя базы, что чревато взломом сайта (я пессимист по натуре - не верьте мне).
Переменную $online_people мы приводим к строковому типу, так при формате информации (проверке, что выводить: "человек" или "человека") мы "крутим строкой"! Как мы крутим - думаю, разберетесь сами, после некоторого брожения мозгов :-). Возможно, можно было сделать все элегантнее и написать меньше кода - не знаю... Если вы так считаете, то пишите на Е-мэйл с кодом, который, на ваш взгляд, лучше моего... или оставляйте комментарии к этой статье. Я их просматриваю иногда (периодически раз в полгода ...=)
Ф-я time() занимается тем, что возвращает время в секундах, прошедшее с полуночи 1 января 1970 года по Гринвичу до настоящего момента. Но мы то знаем, что по научному это называется TimeStamp... $-)
Форматирование я разделил символами перехода строки, т.к. строка проверок (где много знаков || =) очень длинная, а это приводит к растяжению статьи в ширину, в результате чего становится очень неудобно производить чтении статьи, т.к. глаза бегают туда-сюда-обратно (я не о том, что вы подумали). Вообщем вы меня поняли.
Код рабочий - у меня такой же =) Но: несколько дополнений были сделаны только при написании статьи, в частности:
Добавлены переменные для коннекта к базе и коннект происходит внутри функции. Естественно, у меня на сайте он происходит задолго до этого и ф-я, используя открытое соединение с MySQL-демоном, выполняет запросы.
Форматирование я разделил символом перевода строки (причину см. выше), так что, если сценарий не заработает и выдаст тупую ошибку, типа parse error in ..., то преобразуйте строку проверок в единое целое (чтобы на одной строчке все было). Но, я думаю, вы меня поняли.
Ошибки маловероятны, но возможны, так как я правил комменты и т.п. при написании статьи, вдруг какой-нибудь символ точки с запятой забыл. Исправляйте все сами 5=).

Из добавлений, пожалуй, все. Да и статье приходит Зе Енд. Рад, что вы дочитали пособие до этого места, а еще большее эстетического наслаждение мне принесет тот факт, что статья показалось вам занимательной и оставила хорошие впечатления и знания в баш... голове. Если вы заметили ошибки\неточности\баги в статье или у вас что-то не получилось, то оставляйте комменты ниже или пишите на мыло. Я обязательно вас выслушаю и отвечу. Естественно, буду рад и добрым пожеланиям. Как же без них. Хотя критика принесет мне большую пользу...
Опубликовал Kest November 06 2008 16:38:40 · 0 Комментариев · 7256 Прочтений · Для печати

• Не нашли ответ на свой вопрос? Тогда задайте вопрос в комментариях или на форуме! •


Комментарии
Нет комментариев.
Добавить комментарий
Имя:



smiley smiley smiley smiley smiley smiley smiley smiley smiley
Запретить смайлики в комментариях

Введите проверочный код:* =
Рейтинги
Рейтинг доступен только для пользователей.

Пожалуйста, залогиньтесь или зарегистрируйтесь для голосования.

Нет данных для оценки.
Гость
Имя

Пароль



Вы не зарегистрированны?
Нажмите здесь для регистрации.

Забыли пароль?
Запросите новый здесь.
Поделиться ссылкой
Фолловь меня в Твиттере! • Смотрите канал о путешествияхКак приготовить мидии в тайланде?
Загрузки
Новые загрузки
iChat v.7.0 Final...
iComm v.6.1 - выв...
Visual Studio 200...
CodeGear RAD Stud...
Шаблон для новост...

Случайные загрузки
MPTools
Ведение справочны...
TmxOutlookBarPro
Web Регистрация
PHP 5
EditNew
IPAddresseEdit
Программирование ...
Exe in exe
CwstatusBar
C++ Стандартная б...
Geo-Whois
RAS
Современное проек...
Основы Delphi. Пр...
WebReg v1.3
C++ Builder: Книг...
VksButton
Animation (Пример...
IpEditAdress

Топ загрузок
Приложение Клие... 100774
Delphi 7 Enterp... 97836
Converter AMR<-... 20268
GPSS World Stud... 17014
Borland C++Buil... 14191
Borland Delphi ... 10291
Turbo Pascal fo... 7374
Калькулятор [Ис... 5984
Visual Studio 2... 5207
Microsoft SQL S... 3661
Случайные статьи
Pointer type Ident...
Технология NetFlow
Переработка
ДОПУСТИМЫЕ СПОСОБЫ...
Практический Перл ...
Операции управлени...
Широкие возможност...
Тестирование, поис...
Игры
Выбор режима экспо...
«Это не моя ошибка!»
ПРИЛОЖЕНИЕ Е. МИК...
OpenGL. Шесть куби...
Загрузка объекта W...
Метаданные. Исполь...
REALLOCATE (ПЕРЕРА...
ChatSession.cpp
Подход к реализаци...
Лог версий php-fus...
Случайное рехеширо...
Максимально свобод...
VW Polo
Бесплатный игровой...
Глава 14. Разде...
Работа с MySQL в P...
Статистика



Друзья сайта
Программы, игры


Полезно
В какую объединенную сеть входит классовая сеть? Суммирование маршрутов Занимают ли таблицы память маршрутизатора?