среда, 31 декабря 2008 г.

Free SVN accounts (бесплатный SVN хостинг)

Надеюсь, что большинство из Вас, всё-таки знает, что такое SVN. Если вы серьёзный разработчик программного обеспечения, и до сих пор не знали что такое Subversion Repository, то вам необходимо срочно разобраться и опробовать его пользу на себе.

Subversion — свободная централизованная система управления версиями. Многие считают, что этот инструмент необходим только для контроля версий, если разработку ведёт несколько девелоперов, но это заблуждение. Из собственного опыта могу сказать, даже если разработку ведёт один человек и проект достаточно долгосрочный, то такая вещь, как репозитарий файлов, вас выручит не раз, если придётся восстанавливать версию файла двухнедельной давности, ошибочно затёртого более старым файлом.

В общем, если всё-таки заинтересовал, то есть смысл развернуть у себя Subversion сервер локально на машине и наслаждаться его полезностью. Если разработку ведут несколько человек, причём работают они удалённо, то такой вариант, скорее всего, не подойдёт. Готовы регулярно, каждый месяц, выкладывать от $6, – тогда статья не для вас =), иначе читаем дальше.

В интернете встречается много бесплатных сервисов по предоставлению Subversion-хостинга. Попробую сделать краткий обзор наиболее популярных из них.

Начнём с https://opensvn.csie.org/. Этот хостинг предоставляет бесплатный аккаунт, быстрый процесс регистрации. Но, если в вашем проекте много мультимедийных файлов или большие бинарные файлы, то могут возникнуть проблемы. Здесь без предупреждения может быть удалён ваш аккаунт, при малейшем подозрении, что вы используете его не в целях разработки программного обеспечения.

http://cvsdude.com – неплохой хостинг, с большим количеством планов. Есть бесплатный SVN, предоставляют 2Mb дискового пространства, один репозитарий и один пользователь.

Пожалуй, наиболее распространён и раскручен www.assembla.com. Они предоставляют бесплатный SVN & Trac хостинг и при этом неограниченное дисковое пространство. Главный недостаток, что бесплатные аккаунты видны основной аудитории, если не хочется публичной обозримости, то прийдётся покупать private/professional account.

Для open source проектов Google предоставляет свои услуги по Subversion-хостингу http://code.google.com/hosting/.

https://www.bountysource.com/ – SVN хостинг, вместе с wiki и CMS для управления вашими проектами онлайн. Так же содержит среди своих сервисов tracker для задач.

Широкий спектр бесплатных сервисов по управлению разработкой программного обеспечения предоставляет и http://unfuddle.com/. В бесплатный аккаунт входит 200 Mb дискового пространства, до 2-х пользователей репозитария, Bug Tracking система и ещё несколько приятных мелочей.

http://xp-dev.com/ – как мне кажется, самый большой хостинг, по количеству предоставляемых услуг. Этот сервис предоставляет 1500 Mb бесплатного Subversion пространства под репозитарий, неограниченное количество репозитариев и пользователей для них, а так же полностью бесплатный набор всех необходимых Project Tracking сервисов.

пятница, 26 декабря 2008 г.

Эволюция профессий

Нашёл для подборки пару изображений, как может эволюционировать человек, в зависимости от вида дейтельности.

Эволюция программиста:

Эволюция фотографа:


среда, 24 декабря 2008 г.

Классификация водки в стиле IT

0.1л - demo
0.25л - trial version
0.5л - personal edition
0.7л - professional edition
1.0л - network edition
1.75л - enterprise
3л - for small business
5л - corporate edition
Ведро - home edition
“На посошок” - Service pack
Рассол с утра - Recovery tool
Закуска - plugins
Черти - bugs
Пиво - patch
Coca-Cola, Fanta, 7-UP - trojan viruses

вторник, 23 декабря 2008 г.

Получение списка загруженных модулей сервера на Apache 1 из PHP

Думаю, что многие из вас сталкивались с работой с модулями сервера Apache на PHP. Всегда перед началом использования какого-либо серверного модуля необходимо проверить его активность и доступность. Как оказалось, определение загруженных модулей Apache средствами PHP может стать реальной проблемой, с чем я и столкнулся, потратил уйму времени, чтобы придумать решение.

Итак, обо всём по порядку. В PHP есть специализированная функция apache_get_modules(), работает она на PHP 4 >= 4.3.2, PHP 5. Эта функция позволяет получить список загруженных Apache модулей. Конечно, она идеально подходит для этой задачи. Так думал и я, пока не наступил на «грабли совместимости». Как написано в ChangeLog, функция apache_get_modules() с версии 5.0.0 стала доступна в Apache 1, и в PHP Apache 2 filter API. До того, она была доступна лишь при использовании Apache 2 handler API. Но, как показали тесты на разных серверах, – функция не оправдала надежды, она просто отсутствовала в Apache меньше версии 2.

Поставленная задача требовала максимальной совместимости разрабатываемого PHP продукта со всеми Apache серверами, начиная с версии 1.3. Поэтому я продолжил поиски решения. Функция phpinfo() выводит довольно много системной и серверной информации не только о сборке PHP, но и об остальных подключенных модулях и библиотеках. Решил воспользоваться этим шансом. Написал простой парсер для информации выводимой phpinfo(), который разбирал информацию из пункта Loaded Modules раздела apache2handler, если это был Apache 2. Или если это был Apache младше 2-й версии, то искал информацию о подключенных модулях в разделе Environment. Это решение, аналогично, успешно работало только на Apache 2, а на остальных сервер не выводил информацию о всех загруженных модулях, а только о тех, что были скомпилированы на этапе сборки.

Два выше расписанных метода определения не давали мне должной совместимости со всеми серверами и сборками. Я перекопал много информации, чтобы найти способ определения loaded Apache modules средствами простого PHP скрипта, но так и не смог найти готового решения.

Раз нельзя определить средствами PHP, какие из модулей сервера загружены, тогда надо заставить сам Apache передавать эту информацию в исполняемый скрипт. Простейший метод реализации, что мне пришёл в голову, это написать .htaccess скприпт, который бы, при исполнении PHP скрипта, передавал в него список загруженных модулей. Список можно передать в качестве $_GET параметра.

В конфигурационном файле .htaccess есть возможность использовать условную директиву . Она проверяет, если подключен указанный модуль Apache, то исполняет ветку, заключённую между директивами. Допускается использование и вложенных директив.

Для передачи дополнительных параметров PHP скрипту, с сохранением его оригинальных GET параметров, нужен как минимум загруженный модуль mod_rewrite. Он будет производить перехват запроса, добавлять необходимые параметры, если модуль активен, и отдавать его обратно в сприпт. Файл .htaccess даёт возможность объявлять переменные окружения и задавать им значения при помощи ключа [E], который мы добавим в RewriteRule.

Приведу фрагмент .htaccess, который написал:

Order deny,allow
allow from all

<IfModule mod_rewrite.c>
RewriteEngine on
RewriteRule .* - [E=MOD_REWRITE_ENABLED:mod_rewrite]
<IfModule mod_env.c>
RewriteRule .* - [E=MOD_ENV_ENABLED:|mod_env]
</IfModule>
<IfModule mod_auth_basic.c>
RewriteRule .* - [E=MOD_AUTH_BASIC_ENABLED:|mod_auth]
</IfModule>
<IfModule mod_proxy.c>
RewriteRule .* - [E=MOD_PROXY_ENABLED:|mod_proxy]
</IfModule>
RewriteRule ^index\.php$ index2.php?modules=%{ENV:MOD_REWRITE_ENABLED}%{ENV:MOD_ENV_ENABLED}​%{ENV:MOD_AUTH_BASIC_ENABLED}%{ENV:MOD_PROXY_ENABLED} [QSA,L]
</IfModule>

Этот файл необходимо положить в одну директорию с файлом index.php. Htaccess перехватит исполнение скрипта index.php. В зависимости от загруженных модулей выставит переменные окружения. Сервер добавит их конкатенацию в качестве переменной $_GET['modules'] к остальным параметрам GET запроса и запустит PHP скрипт на исполнение.

Разобрать строчку modules не составит труда, для этого используем функцию explode("|", $_GET['modules']). В результате получим уже готовый массив с именами загруженных модулей Apache.

Приведенный выше пример .htaccess рассчитан на определение только четырёх модулей Apache: mod_rewrite, mod_env, mod_auth_basic и mod_proxy. Вы довольно легко можете его расширить на любое количество необходимых модулей путём добавления дополнительных директив для проверок. В любом случае, вы ничего не теряете, даже если не загружен основной модуль mod_rewrite.c. Тогда лишь не отработает перенаправление и не будет передан параметр $_GET['modules']).

Надеюсь, вы не потратите столько времени, сколько потратил я, на решение такой, несложной, на первый взгляд, задачи, как детектирование модулей Apache средствами PHP. Если кто-то сталкивался с такой проблемой и смог придумать более оптимальное решение, как это сделать на версии сервера младше Apache 2, то внимательно вас выслушаю.

понедельник, 22 декабря 2008 г.

Сортировка IP адресов на MySQL

Во многих web-приложениях приходится сталкиваться с сортировками данных. Это является несложной задачей, если в качестве данных для сортировки выступают простые фамилии, наименования, даты, суммы, ну и другие строково-числовые данные. Но когда требуется упорядочить более сложные структурные данные, с учётом их логического разбиения, то иногда приходится поломать голову в поисках эффективного и не ресурсоёмкого алгоритма.

Я столкнулся с такой задачей. Нужно было отсортировать ряд IP адресов в порядке убывания или возрастания. Было два инструментария для сортировки, либо сделать это средствами PHP, либо переложить это всё на MySQL сервер. Второй вариант более предпочтителен, так он быстрее и эффективее, потому что выборка всё-равно происходит из базы данных.

Если решать сортировку в лоб, и отсортировать просто в алфавитно-числовом порядке, то IP адрес 135.x.x.x будет стоять перед 88.x.x.x, хотя это логически неправильно. Здесь надо учитывать не строку целиком, а разбивать на четыре отдельных байта – составляющие IP адреса.

Первое что пришло на ум – поискать специализированные функции для работы с IP адресами. Нашёл в manual по MySQL функцию для перевода строки с IP address-ом в числовое значение, то есть в integer, – это функция inet_aton().

SELECT ip, inet_aton(ip) as `IPvINT`
FROM ip_address
ORDER BY `IPvINT` ASC;

Этот метод работает безотказно, но если у вас данные в таблице были проверены и не содержат никаких больше символов, не относящихся к IP адресу.

Передо мной стояла задача немного сложнее, у меня мало того значением выступает IP адрес, он может содержать и маску вида 192.168.1.*, и даже диапазон адресов вида 192.168.1.0-192.168.230.14. Тогда выше приведенный метод не будет работать, потому что функция inet_aton() всегда будет возвращать неправильное значение для масок и диапазонов, и эти адреса будут кучей сбиваться в конце или начале отсортированного списка.

Приведённый ниже SQL запрос сможет отсортировать список значений IP адресов содержащих маски адресов вида 192.168.1.*, или диапазон адресов вида 192.168.1.0-192.168.230.14:

SELECT ip, (SUBSTRING_INDEX(ip, '.', 1)<<24) +
  (SUBSTRING_INDEX(SUBSTRING_INDEX(ip, '.', 2), '.', -1)<<16) +
  (SUBSTRING_INDEX(SUBSTRING_INDEX(ip, '.', -2), '.', 1)<<8) +
  SUBSTRING_INDEX(ip, '.', -1) as `IPvINT`
FROM ip_address
ORDER BY `IPvINT` ASC;

Я думаю, что эта реализация выглядит довольно элегантно и при этом будет быстро вычисляться, если кто-то знает более мудрое и оптимальное решение, с радостью выслушаю в комментариях.

Более эффективный поиск картинок от Google

Google ввёл ещё одну инновацию в свой поисковый сервис. Теперь поиск картинок стал ещё более эффективным. Теперь можно фильтровать поиск выбором категории. Сейчас из доступных категорий есть «Новости», «Лица», «Фотографии».

Чтобы сделать поиск ещё более релевантным, компания Mountain View недавно добавила ещё две опции – клипарт (clip art) и штриховой рисунок (line drawings).

Таким образом, компания Google добавила ещё один штрих к своей поисковой системе и сделала поиск информации ещё быстрее и доступнее.

суббота, 20 декабря 2008 г.

Domain names и совместимость с браузерами

Ко мне обратился программист, говорит, мол, не могу понять, почему не работает система авторизации на странице и не запоминает данные логин и пароль после ввода пользователем. Причём не работает, только в отдельных браузерах.

Столкнулся с такой проблемой – на одном и том же PHP-скрипте, но при заходе с разных браузеров, не работал механизм сессий. Так как программное обеспечение пишем кроссбраузерное, то и проверяем один и тот же функционал на разных браузерах и различных конфигурациях сервера. Я вылил на свой хост его скрипт и начал разбираться, в чём дело, но у меня всё работало отлично, данные авторизации успешно сохранялись. Тогда попробовал на другом виртуальном хосте, где были проблемы, и обнаружил, что у меня тоже не работает в Internet Explorer и Safari, хотя при этом Firefox, а так же Opera успешно держали сессию.

Решил, что дело просто в разных настройках браузеров, и что они не сохраняют для отдельных хостов cookie. Всё тщательно перепроверил, но дело было не в этом. Установил себе сниффер и перехватил HTTP заголовки запросов к серверу и его ответов для каждого из браузеров. Для всех вариантов заголовок Set-Cookie имел правильное значение идентификатора сессии PHPSESSID, но IE и Safari упорно не хотели его держать и каждый раз при обращении к серверу он выдавал им новый идентификатор.

Так как сервер был один и тот же для тестирования и стоял у нас локально, а различие было лишь в именах виртуальных хостов, то пошёл к нашему системному администратору, на что тот пожал плечами и сказал что настройки для обоих виртуальных хостов одинаковые. И тут меня осенило, я увидел, что доменное имя виртуального хоста в первом случае содержит подчёркивание «_» в имени, а во втором нет. Это доменное имя было составлено не по стандарту RFC1035 (Domain names - implementation and specification). Отсюда и нерабочий механизм сессий, и отсутствие сохранения cookies в браузере.

Мораль сей басни такова. Этот яркий пример ещё раз показывает, что браузеры Firefox и Opera жёстко соблюдают стандарты, но при этом умеют работать даже в нештатных ситуациях. А Internet Explorer и Safari жутко капризны, перестают работать или интерпретируют код неправильно, даже при малейших отклонениях от стандартов. Будьте внимательны.

Рекоммендую

Попробуйте надёжный хостинг от Scala Hosting