Перейти к основному содержимому

Синхронизация Google Calendar c MS Outlook

· 1 мин. чтения

Синхронизируем Outlook и Google calendar. Самый недавно вышедший и простой способ - Google Calendar Sync.

Iframe

Для начала самый простой и не настоящий способ. Идём в Outlook под Calendar слайд, и под "My Calendars" жмём правой кнопкой по нужному календарю, ставим на нём Properties->Home Page->Address равным http://www.google.com/calendar/render. Браво, теперь у вас iframe вместо настоящего календарика.

Plug-in RemoteCalendars

  1. Закрываем Outlook
  2. Устанавливаем NET 2.0
  3. Устанавливаем RemoteCalendars (включая файлы O2003PIA.EXE, O2003PIA.MSI, vstor.exe, RemoteCalendarsVSTOSetup.msi)
  4. Открываем Outlook, ставим во вдруг появившемся окошке настроек временную зону и Auto Update.
  5. Видим такую панельку
  6. Добавляем новый календарь. Для этого берём из Google Calendar настроек ссылку . После этого - вводим логин пароль, и вуаля - двусторонняя синхронизация есть.

Читайте также:

RSS generator

· 1 мин. чтения

Все знают про RSS и то как это читать и даже парсить , но как переделать из html-кода статью в валидный RSS для веб-разработчика может быть проблематично.

К типичным проблемам можно отнести присутсвие символов <, >, &. Кроме того сложности с присутсвием тэгов object внутри description приводят к тому что сделать видео объект в rss нельзя.

Пробуем FeedCreator. Громадина, поддерживает всевозможные ATOM, RSS 0.9-RSS 2.0, OPML, MBOX. Надо вручную менять на UTF8 кодировку, объект хочет сразу создать xml файл. Хорошо, это в принципе разумно, кэширование в один час для блога не критично, для новостных сайтов надо уменьшать до пары минут.

$rss = new UniversalFeedCreator();  
$rss->useCached();
$rss->title = "Artjom Kurapov";
$rss->description = "Personal Blog";
$rss->link = "http://kurapov.name/";

Валидатор всё равно ругается на flash (следовательно object не поддерживается) . Кроме того не нравятся относительные пути. Конешно можно изменить WYSIWYG что-бы он сразу генерировал абсолютные пути, но в случае если надо будет менять домен прийдётся много с базой работать. Поэтому мы их генерируем вместе с RSS.

$recEntry->description=preg_replace("//i",'',$recEntry->description);  
$recEntry->description=str_replace("href='/","href='http://kurapov.name/",$recEntry->description);
$recEntry->description=str_replace('href="/','href="http://kurapov.name/',$recEntry->description);
$recEntry->date = date('r',$item->unix_added);
$rss->addItem($recEntry);
echo $rss->saveFeed("RSS2.0", "feed.xml");

И в результате
[Valid RSS]

Шифр Брайля

· 1 мин. чтения

Нет, это не шифр инопланетян, хотя достаточно любопытный, не правда ли? Способы кодирования информации, и криптографии создавались с древнейших времён, но для данный код носит имя француза Брайля и изначально разрабатывался для военных целей для общения ночью в полной тишине, но для обычных солдат это оказалось слишком сложным

Сейчас транскрипцию шифра Брайля используют не только для печати книг для слепых но и для чтения с экранов компьютера. Из-за ограничения размера "буквы" всего существует 26=64 символа. Интересно такой интерфейс как прототип предлагается использовать и на специальных мобильных телефонах, часах

Выбираем полу-профессиональный фотоаппарат

· 3 мин. чтения

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

  1. Светосила или отношение чувствительности темноты к выдержке.
    Чем больше светосила, тем больше свободы съемки в ночное время (по шкале ISO) и больше свободы при съемке движущихся предметов (в секундах). Всё это вытекает из зависимости между выдержкой, экспозицией как результат - яркостью картины.
    • 2.0-2.8 профессиональные объективы, тоесть при минимальной и максимальной выдержке яркости будут 2@1/2000 с и 2.8 @ 1/300с
    • 2.8-5 оптика на любителя
  2. Фокусное расстояние объектива.
    • 10-28мм - макросъемка
    • 28-35мм - широкоугольные
    • 50мм - нормальные (человеческий глаз)
    • 80-100мм - портретные
    • 100-300мм - длинно фокусныеОбъективы с меняющимся фокусным расстоянием, т.е. с zoom-возможностью имеют свои пределы. Скажем 50 мм - человеческий глаз, то около 10 мм это уже макро-съемка, а 200мм это уже природа и ландшафт.
  3. Размер матрицы и уровень шума. Из маркетинговых соображений зачастую уровень шума при высоких экспозициях приносится в жертву ради большей матрицы. Если кто-то интересуется что такое шум - сделайте Filter Noise в фотошопе и поймёте.
  4. Класс. В зависимости от требуемых функций фотоаппараты делятся на профессиональные зеркалки, компактные мыльницы и что-то по середине.

Поскольку у меня уже был опыт с мыльницами от Mustek и Olympus C-310, хотелось не столько компактности, сколько качества и оптики. В то же время я не хотел дорогих и строгих профессиональных зеркалок, где видео режима нет. Поэтому выбор пал на "продвинутые незеркалки". Из этого класса на этот момент были

Sony Cyber-shot DSC-H9 Sony Cyber-shot DSC-H9/H7Olympus SP-550 Ultra Zoom Olympus SP-550 Ultra ZoomCanon PowerShot S5 IS Canon PowerShot S5 ISFuji FinePix S6500fd Fuji FinePix S6500fd
- 7990 EEK- 8.1 MP- ISO 3200- AVI- 2.2 к/с- 7690 EEK- 7.1 MP- ISO 5000- RAW- 7690 EEK- 8 MP- ISO 1600- 7250 EEK- 6 MP- ISO 3200- RAW,AVI

Как можно заметить - все умеют записывать видео. Заявленные ISO 5000 у Olympus мало что дают, а отсутсвие USB 2.0 и аскетизм в дизайне только усугубляют положение.

Проблема с Sony - даже если вместо H9 взять практически аналогичную H7 и сэкономить тысячу, то всё-равно можно остаться недовольным отсутсвием AA-батарей и малым циклом аккумулятора - у Canon в два раза больше энергии, и хотя экран пожалуй самый больший из перечисленных, это сказывается также на эргономике - никаких дополнительных кнопок нет.

Про Fuji можно отметить что хотя оптика и хороша, как и в Sony, но матрица меньше, да и процессор старше - нет стабилизатора.

Как вы уже догадались - я выбрал Canon, отчасти и из-за брэнда. Оптика - 36 - 432 mm с F2,7-3,5. Главное преимущество - стабилизатор, видео со стереозвуком, крутящийся дисплей. Пальчиковые батарейки, встроенная вспышка, USB2. В минусы - отсутсвует RAW, хлюпкая крышка объектива. Нет предела человеческой глупости, решившего что искомое найдено - купил в fotoluks и только потом увидел в hinnavaatlus цену на тысячу меньше. Всем советую :)

Магазины в Эстонии - photopointfotoluks.
Обзоры: zoom.

Соединяем блог и Livejournal через XML-RPC

· 2 мин. чтения

XML remote procedure call на самом деле очень простая процедура, при помощи которой я теперь могу писать в своём блоге и копировать статью в livejournal.

С виду, самым простым решением вероятно выглядело бы создание такого процесса, где передача данных на сервер LJ происходил бы браузером. Достаточно создать отдельный iframe, в него поместить форму, в которую копировать содержание из другой формы и в итоге публиковать в LJ. Но - во первых это уродливо, во вторых не факт что так можно исхитриться.

Презентация к диплому

· 2 мин. чтения

Защита диплома в ТТУ дело обыкновенное - достаточно сделать презентацию на 15 минут о том какая проблема решалась. Ввиду специфики области (академическая защита) и ограниченность по времени (всё идёт как по конвейеру), надо постараться выжать самый концентрат сока.

В общем надо ответить на три вопроса

  1. Какая проблема?
  2. На каких теоретических и практических исследованиях работа основывалась, есть ли соавторы
  3. Какие получены новые результаты и какие последствия открываются для будующего поколения учёных

Если презентация делается на 15 минут, то надо не более 15 слайдов где по минимуму будет содержание. Помните, что вы не энциклопедию передаёте поколению, а делаете для себя визуальную помощь. Заранее скажите как вы будете отвечать на вопросы (сразу или в конце).

Календарь на PHP, MySQL и ajax

· 2 мин. чтения

Для корпоративных сайтов зачастую нужен календарь. И ладно бы что-бы он просто показывал дни недели, так зачастую вносится понятие События (Event), а ввиду обширного потенциала этого понятия можно говорить об Event Management System. Поскольку деловым людям свойственно планирование, то такая система должна быть удобной, мобильной и расширяемой. За удобство отвачает ajax, за мобильность - само наличие интернета, а за расширяемость - программист и проектировщик.

А ведь событие ещё может иметь и..

  • повторяемость (с определённым периодом , до бесконечности/определённого числа повторений/конкретной даты )

  • местоположение (для точного - google maps, для неточного - просто текст)

  • привязку к временной зоне

  • неопределённое время или длительность (идёт в todo список?)

  • принадлежать группам или типам событий (деловые встречи, личные встречи, культурные мероприятия)

  • доступ к просмотру для других пользователей (sharing, оповещение)

  • систему оповещения по email/sms/desktop widget


Публичные сервисы

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

Opensource-продукты

Когда дело касается своего сайта, то выбор значительно уже:

  • PlansCalendar на php/mysql, без ajax и видов по дням/неделям

  • phpiCalendar внешне обманчив - работает на файловой системе с .ics файлами

  • monket хоть и на ajax, но скуден

  • thyme платен и по сути чуть лучше чем PlansCalendar

  • jquery fullcalendar - оболочка без серверной части

  • jquery wdcalendar

  • myCalendar

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

На будущее разработчикам - на забудьте что календарь должен быть интегрируем, экспортируем в outlook, ical микроформат , удобен и расширяем.

ЧПУ с mod_rewrite

· 2 мин. чтения

Человеко-понятный URL нужен. Так наглядней видеть где вы находитесь. Реализовать ЧПУ можно несколькими способами.

(Apache) mod_rewrite

В зависимости от архитектуры web-системы, загрузка отдельных модулей происходит как правило если не напрямую через GET запрос, то хотя-бы косвенно. Косвенно это когда создаётся страница, а потом специально для неё создаётся путь, сохраняется в БД, изменяем и красив.

Преобразование разных параметров в папки по-моему самое нужное. Включаем mod_rewrite, создаём или дописываем .htaccess что-бы работало всё так:

http://kurapov.name?**mod**=gallery&**action**=list&page=5
http://kurapov.name/gallery/list/?page=5

Options +FollowSymLinks  
RewriteCond %{REQUEST_FILENAME} !-f
RewriteEngine On
RewriteRule ^([A-Za-z0-9^/]+)/([A-Za-z0-9_^/]+)/$ /index.php?mod=$1&action=$2 [QSA,L]
RewriteRule ^([A-Za-z0-9^/]+)/([A-Za-z0-9_^/]+)/?$ /index.php?mod=$1&action=$2 [QSA,L]

Самое главное это конечно же RewriteRule, которое построено на регулярных выражениях , поэтому многие веб-разработчики и не прошли через этот участок. В данном примере в URL ищется в начале (знак ^) две папки, названия которых состоят из букв и цифр. Первая папка становится значением $1, вторая соответсвенно $2. В итоге запрос передаётся в обработку в index.php с GET параметрами. Параметр QSA=query string append добавляет в конец ещё параметры которые запрашивал пользователь.

Установка ЧПУ на существующую систему

Какой получается минус? Если есть файл resources/thumbs/generator.php , то получится что обращение тоже будет перезаписываться, и в действительности будет всё идти на index.php. Более того, если система была спроектирована по относительным путям, где все картинки, фреймы, ссылки не велись от корня, то возникнет проблема с новой адрессацией.

404 перезапись

Как очень быстрое и простое решение можно вместо mod_rewrite использовать перенаправление 404 ошибки

ErrorDocument 404 /index.php

Теперь достаточно в index.php обратится к массиву и вызвать нужный модуль:

header("HTTP/1.1 200 OK");  
header("Status: 200 OK");

$arrURL=explode('/',$_SERVER['REQUEST_URI']);

Не забудьте проверять существует ли такой модуль в системе, и сделать обработку ошибок, в том числе и на уровне header-ов, иначе поисковики могут посчитать что у вас всюду брак.

Введение в Foreign keys

· 1 мин. чтения

Foreign keys это движущая сила реляционных БД. Выборка по нескольким таблицам по прежнему формируется при помощи JOIN-конструкций, но FK создаёт логические связи между таблицами, понятные человеку. Очень полезно в больших проектах, где уследить за всеми связями нелегко, а такие программки как MySQL Workbench хорошо могут эти связи показать.

Создание связей начинается с создания тех таблиц, на которые надо ссылаться. Дальше в ссылающихся таблицах делается поле типа refID. Теперь создаётся уникальный FK который и связывает поля. Ключ может иметь дополнительные свойства, например каскадное удаление или update.

Для удобства создания таких структур можно воспользоваться SQLyog-ом. Типы таблиц естественно только InnoDB. К примеру таблица events ссылающаяся через FK на events_groups выглядит так..

CREATE TABLE `events` (  
`ID` int(11) NOT NULL auto_increment,
`groupID` int(11) default NULL,
UNIQUE KEY `ID` (`ID`),
KEY `FK_events` (`groupID`),
CONSTRAINT `FK_events` FOREIGN KEY (`groupID`) REFERENCES `events_groups` (`ID`) ON DELETE CASCADE,
) ENGINE=InnoDB DEFAULT CHARSET=latin1

OpenUP

· 1 мин. чтения

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

OpenUP - бесплатная методика ( тогда как некоторые более 700$ стоят) и ориентирована на развитие небольших проектов в небольших фирмах (до 36 человеко-месяцев). Вполне подходит для IT, поскольку текучка кадров большая, а проекты стоять не хотят.

Ради достижения успешности проекта, группа разделяется на 3-6 ролей (вспоминаем сразу классы в RPG?):

  • клиент
  • управляющий проектом
  • аналитик
  • архитектор
  • тестер
  • разработчик

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

Pangalink

· 5 мин. чтения

Банковская ссылка (pangalink) — способ обмена данных купли-продажи между клиентом, банком и магазином, очень распространённая в Эстонии. Эта услуга предоставляется банками в виде услуги магазинам, которым надо платить

WSDL

· 1 мин. чтения

Никогда не задумывались как работает гениальный copy/paste? Правильно, благодаря всяким OLE и COM, которые продвигал Microsoft. В чём же гениальность этой функции? Interoperability, о как!

WSDL это формальный стандарт для описания сервизов сервисов. Под сервисом естественно подразумевается какой-то сайт, портал или просто скрипт. А зачем его описывать? Затем что-бы использовать в других таких же скриптах, программах и сайтах, а это и есть interoperability.

Этот стандарт выглядит как обычный XML файл, разрабатывается W3C и всевозможными корпорациями. Файл состоит из 4 основных тэгов:

  • types в котором под-тэги elements описывают "переменные"

  • interface в котором operations описывают возможные "функции"

  • binding в котором детально объясняется каждая operation

  • service в целом описывает местонахождение конкретного сервиса и используемые им операции

Более старые версии WSDL 1.1 имели иную структуру с portType тэгами.

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

См. также SOAP, типы wsdl операций

Mysql prepared statements

· 2 мин. чтения

воскресенье, 22 апреля 2007 г. в 14:10:12

Подготовленные запросы имеются в MySQL начиная с 4.1 и нужны по трём причинам.

  1. Скорость. Если вы выполняете однообразные запросы, то mysql парсеру каждый раз приходится выполнять распознавание - какой тип запроса, какие данные передаются и тому подобное. Если сделать прототип запроса, а в последствии передавать только данные, то ясное дело что это скажется на скорости.
  2. Передача данных. Мало того что для подобных запросов передача бинарных данных не нуждается в конвертировании в строку, так и то что стандартное ограничение на один запрос имеет около 1 мб можно подвинуть благодаря тому что каждый кусок данных передаётся отдельным запросом, а не одним общим (INSERT скажем).
  3. Безопасность. Благодаря отделению данных от запроса вы можете обезопасить себя от SQL injection .
PREPARE some_statement_1 FROM "INSERT INTO my_table (`some_HTML`, `some_title`) VALUES ('?','?')";  
SET @someparam_1 = "HTML SOURCE";
SET @someparam_2 = "TITLE HERE";
EXECUTE some_stament_1 USING @someparam_1,@someparam_2;
DEALLOCATE PREPARE some_statement_1;

Всё достаточно просто - объявил запрос, вместо переменных поставил символы вопросов, потом по порядку этих символов объявил переменные , выполнил запрос и удалил кэширование (которое только планируется сделать).

Использование подобной техники через PHP на низком уровне занимается PDO extension и mysqli правда порой не совсем удобным способом, ну а если хочется по-старинке эти запросы генерировать самому, то можно попробовать огромную PEAR:DB или DbSimple

Случайная сортировка

· 1 мин. чтения

Mysql позволяет сортировать случайным образом

SELECT * FROM my_table ORDER BY RAND()

Проблема в том, что такая сортировка зачастую вовсе не нужна для всей выборки - хочется просто достать случайный элемент из определённого множества, к тому же ORDER BY RAND() достаточно медленный выход из ситуации.

Можно попробовать делать выборку основываясь на числе элементов в целом и функции RAND():

SELECT name FROM my_table JOIN (  
SELECT CEIL(RAND() * (
SELECT MAX(id) FROM my_table
)) AS randomID
) AS random_table ON random_table.randomID=my_table.ID

На 50000 рядов такой запрос занимает 0.00086 сек.. Сравните с 1.56356 сек обычного варианта ORDER BY RAND().

Недавно натолкнулся на один интересный вариант:

select G.*, rand() as RO from GOODS G order by RO

Вероятно вас заинтересует случайная сортировка в Postgre, где рассматриваются и другие способы.

Сортировка матрицы

· 1 мин. чтения

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

Средствами PHP насколько мне известно пока невозможно нормально отсортировать - функции uksort и ksort сортируют по ключам массива, но просто вписать данные столбца в качестве ключа нельзя если могут появится одинаковые ключи.

Небольшая функция на будущее.

  /**
* Sorts matrix by column
*
* @param array $arrMatrix
* @param mixed $col
* @param boolean $direction
* @return array
*/
function sort_matrix($arrMatrix,$col=0,$direction=1){
$result=array();
foreach($arrMatrix as $var => $val){
$set=false;
foreach($result as $var2 => $val2){
if($set==false){
if($val[$col]>$val2[$col] && $direction || $val[$col]<$val2[$col] && !$direction){
$temp=array();
foreach($result as $var3 => $val3){
if($var3==$var2) $set=true;
if($set){
$temp[$var3]=$val3;
unset($result[$var3]);
}
}
$result[$var]=$val;
foreach($temp as $var3 => $val3)
$result[$var3]=$val3;
}
}
}
if(!$set) $result[$var]=$val;
}
return $result;
}

Сохраняющаяся сортировка

· 1 мин. чтения

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

Представляю небольшой вариант такого решения..

$_SESSION['Sorting'][get_class($this)]= array_merge( $_SESSION['Sorting'][get_class($this)], $_REQUEST);

В сессии кэшируются все параметры некогда используемые, причём новые параметры перезаписывают более старые. С такой техникой можно делать много параметровую сортировку ( ORDER BY param1, param2, param3..) причём передавать через GET только по одному параметру, т.е. не надо делать

?sort[]=param1&sort[]=param2

Введение в Postgre

· 2 мин. чтения

PostgreSQL - крутая СУБД, потому что..

  1. Она не принадлежит какой-либо компании, как например Oracle или mysql и распространяется по BSD-лицензии

  2. Имеет поддержку продвинутых фишек - PL/pgSQL, триггеров. Теоретически это очень полезно при создании очень масштабной системы.

  3. Транзакции по принципам ACID придают скорости - несколько запросов в одной транзакции выполняются как одна атомарная операция. А мультиверсионность помогает избежать блокировки таблиц.

  4. Объектность. Таблица выступает фактически в виде класса, а ряды - в виде объектов, так же как классы могут наследоваться, так и таблицы могут наследоваться.

  5. Система привилегий операций с таблицами, схожа с системой по принципу с Oracle.

  6. Репликации, т.е. использование нескольких серверов даёт масштабируемость.

Переход на PostgreSQL как правило связан с обработкой больших объемов данных - когда число рядов переваливает миллион, то mysql начинает испытывать трудности, а Natural Join нескольких таких таблиц может привести вообще к падению сервера. Да и тесты на параллельность поддерживают Postgre. Энтузиастам может быть интересна же не столь масштабируемость, сколько объектность, позволяющая большую свободу, или если хотите - сложность, по сравнению с mysql.

При переходе из mysql, следует отметить различия, которые естественно следует предусмотреть:

  • Различные типы данных. Нет datetime, зато есть возможность создать тучу своих типов.
  • Отсутсвие autoincrement. Такая функция заменена наличием sequence, и в упрощённом виде может использоваться так:
    CREATE TABLE mynewtable ( id SERIAL }
  • pgAdmin III очень удобная консольная программа, а в качестве замены phpMyAdmin есть phpPgAdmin
  • Аналогом DATE_FORMAT является to_char
  • Заглавные буквы в названиях таблиц и полей по умолчанию переводятся в нижний регистр, это можно обойти используя двойные кавычки
  • Форматом для LIMIT конструкции стал также поддерживаемый с mysql 4LIMIT # OFFSET #
  • Просмотр запущенных процессов реализуется аналогом
    --show processlisе``SELECT * from pg_stat_activity ;

Читайте также:

Excel через javascript

· 2 мин. чтения

Microsoft Excel - незаменимый spreadsheet-редактор, попробуем сделать нечто похожее уже в web-середе.

Выбираем Simple spreadsheet, который уже умеет достаточно много, немного его исправим и создадим возможность сохранять все данные в БД. GPL лицензия также радует.

Прежде всего - изменить размеры редактируемого окна, которое запускается из spreadsheet.php. Для этого изменяем styles.css и при необходимости - spreadsheet.js, где делаются собственно таблицы.

Дальше - сделаем сохранение данных. Для этого надо весь код поместить в форму, добавить submit, к которому приписать onclick='save();'

Simple spreadsheet хранит все данные в своём "javascript" формате который фактически просто переменные инициализации, поэтому сохранять данные мы будем не только их, но и данные в csv формате. Для этого есть функция saveCSV, которую достаточно немного изменить и добавить спрятанный textarea c id='csv'.

getObj("csv").value = out;

Данные сохраняются в таблицу БД. Что-бы их обратно показать в таблице для изменений, достаточно в spreadsheet.php сохранённые данные передать в $init_data

Для чтения CSV надо выдавать заголовок типа

header("Pragma: public"); header('Content-Type: text/csv'); //header('Content-Type: application/vnd.ms-excel'); header('Cache-Control: must-revalidate, post-check=0, pre-check=0'); header("Content-Description: downloaded from iunu.net as an example"); header('Content-Disposition: attachment; filename="'.MD5(time()).'.csv"');

Код достаточно понятен, например что-бы при нажатии Tab фокус переходил на соседнюю клетку, я добавил в функцию keypress практически в самый конец

if (keyCode==9) { saveCell(); ret=false; editCell(currRow,currCol+1,keyCode); }

Если csv не подходящий вариант, и хочется создания xls, можно воспользоваться портированным с perl, writeexcel 'ем, а для импорта xls есть spreadsheet_excel_reader однако проблемы с utf8 всё ещё не имеются..

Многоязычность Smarty

· 3 мин. чтения

Многоязычность сайта - важный фактор для корпоративных сайтов. Какие существуют подходы?

  1. Разные языки - разные сайты. Такое решение очень простое и используется для международных фирм. Каждый регион владеет своим доменом, хостинг как правило делается на одном защищённом сервере, где все данные доступны для всех доменов, либо же раздельно, что в принципе не играет большой роли, главное то - что платформа под каждый язык своя.
  2. Разные языки - разные темплейты. Решение так же простое - для каждого языка свой темплейт. Контроллер всё же один и сам выбирает какие данные из БД выбирать. Большой минус в том, что при изменении дизайна, надо менять темплейты во всех языках, поэтому может случится что языки с разными дизайнами.
  3. Разные языки - разные данные. Неудобен тем, что для каждой мелкой системной надписи надо лезть и добавлять строчки переводов. Кроме того возникают вопросы при составлении структур типа дерева - зависит ли структура от языка или нет. Например при составлении каталога продуктов, в случае если необходимо добавить новый язык, надо отдельно составлять всю структуру, или достаточно перевести уже созданную?

CVS и SVN

· 2 мин. чтения

CVS и SVN (Subversion) это программы хранения истории изменения проекта в файловой системе разными пользователями в результате одновременной совместной работы. Существует клиентская и серверная часть.

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

SVN это наследник CVS, впрочем если вы испытываете большую симпатию к Microsoft, вы можете использовать Visual SourceSafe. Из себя это представляет сетевую программу, где центральный сервер хранит все вносимые изменения, а клиенты уже производят операции над этими изменениями. Поэтому если вы работаете в фирме, и сервер уже имеется, то вам достаточно установить клиентскую программу.


Для windows можно посоветовать tortoiseSVN. В настройках устанавливается связь с localhost:3690, где висит SSH-тунненель putty (настраивается в Connection/SSH/Tunnels) или SSH tunnel client. Если хочется платного, то есть SmartSVN.

После настроек - создаём папку под проект и работаю полностью из контексного меню эксплорера делаем операцию checkout (копирование working copy в локальную папку). Что-бы сохранить свои изменения в файлах делаем операцию update (копирование изменений из svn в локальную папку) и commit (сохранение своих изменений в svn). В случае если файлы были изменены одновременно, то svn не позволит вам сохранить файл и отметит его как конфликт, который надо решить либо через diff (сравнение svn и локальной версии), либо через solved (перезаписать версию svn своей). В особо запущенных случаях, когда файлы переименовываются или удаляются не используя функции svn, вам прийдётся запускать cleanup.

Из дополнительных функций есть функция вины (blame), благодаря которой можно найти кто какую строчку написал. Удачи в проектах!