SlideShare a Scribd company logo
1 of 52
Download to read offline
Динамическая Опердень на Haskell




                 Как за три шага превратить острый гемморой в хронический
Приближение I
Приближение I

Клиент (Браузер)                Сервер приложений                СУБД




   JavaScript
                   HTTP/JSON     Erlang/MochiWeb    SQL
   QooxDoo                                                    PostgreSQL




                               Совершенно типичная, рядовая, унылая опердень
Приближение I
●   Результат: FAIL
●   Разработчики не довели проект...
    ●   Даже до середины

●   Основные причины --- организационные
    ●   И тем не менее
Приближение I
●   QooxDoo
    ●   Сложный дизайн
    ●   Oчень verbose
    ●   Очень много писать руками на JS
    ●   Практическое отсутствие декларативности
    ●   Ручной маппинг данных
    ●   Странные ограничения в виджетах
    ●   Относительно слабая документация
    ●   Довольно симпатично выглядит, впрочем
Приближение I
●   Mochiweb/Erlang
    ●   Динамическая типизация
        –   ОБЯЗАТЕЛЬНО требуются юнит-тесты
             ●   Которые никто не пишет
    ●   Полуживые средства Database Connectivity
        –   Требовалась ручная доработка
    ●   Генерация и парсинг JSON
        –   Очень мало и полуживое
        –   Потребовалась ручная доработка
Приближение I
●   Mochiweb/Erlang
    ●   Автоматический маппинг HTTP на SQL (CRUD)
        –   Оказался слишком сложен
             ●   Достаточно бедный язык
             ●   Динамическая типизация
                  – При этом почти отсутствует метапрограммирование
             ●   Недостаток опыта у разрабатывающих
Приближение I
●   FAIL
    ●   Недостаточная организация
        –   Недостаток времени на организацию
    ●   Недостаток опыта
        –   Овердизайн
    ●   Инструменты увеличивают количество работы
        –   А должны уменьшать
Приближение II
Приближение II
●   Другой разработчик
●   Erlang/MochiWeb
●   ExtJS вместо QooxDoo
    ●   Чуть больше декларативности
    ●   Шаг в сторону --- расстрел
    ●   Мистические глюки
Приближение II
●   FAIL
    ●   Основные причины
        –   Недостаточная организация
        –   Недостаток квалификации
        –   Недостаток опыта
Приближение III




      Если хочешь, что бы что-то было сделано хорошо --- сделай это сам
Приближение III

Клиент (Браузер)            Сервер приложений           СУБД




      ?            HTTP/?
                                  ?             SQL
                                                      PostgreSQL
Лирическое отступление: Дизайн
         “Центр масс” системы



         Клиент            Сервер   СУБД          Вариант I




   Клиент             Сервер               СУБД   Вариант II




Клиент            Сервер
                                       СУБД       Вариант III
Лирическое отступление: Дизайн
    Клиент        Сервер   СУБД   Вариант I




●    Pros                               ●     Cons
       ●     Быстро                           ●   Трэш
             прототипировать                  ●   Угар
             –   Иногда                       ●   Содомия
Лирическое отступление: Дизайн
    Клиент           Сервер    СУБД              Вариант II



●    Pros                                               ●   Cons
      ●   Миграция между СУБД                               ●   Быстро, толькo если держать всю
             –   Как секс у тинейжеров: чаще говорят,           БД в памяти приложения
                 чем делают
                                                                – Страдает D в ACID
      ●   Использование ORM
                                                            ●   Типичные языки для
             –   Хорошо, если не знаете SQL                     манипуляции данными менее
      ●   Возможность строгого                                  удобны, чем SQL + расширения
          типизирования модели
                                                            ●   Все равно отчеты придется
                 Если вы используете типизацию
             –
                                                                делать на SQL
Лирическое отступление: Дизайн
Клиент       Сервер
                        СУБД         Вариант III



    ●    Pros                                ●     Cons
         ●   Просто                                ●   Дорогая смена СУБД
         ●   Быстрая разработка                        –   Но см. предыдущий
         ●   “Горячие” апгрейды                            слайд
             –   Кроме изменения схемы             ●   Отвратительная
         ●   Поддерживать может                        типизация в БД
             любой DBA
                                                       –   Придется с этим жить
             –   И даже немного
                 дорабатывать
Приближение III
        ?          Сервер приложений



●   OCaml/Ocsigen/Eliom                 ●   Haskell/Happstack
    ●   Низкий порог                        ●   Выше качество
        вхождения                               сервера
            –   Верно для OCaml (но         ●   API проще
                не для Ocsigen/Eliom)
                                            ●   Отличные
    ●   Слабые библиотеки                       библиотеки DB
        DB Connectivity                         Connectivity (HDBC)
            –   Пришлось                        –   Все работает
                дорабатывать
Приближение III
        ?             Сервер приложений



●   OCaml/Ocsigen/Eliom                             ●   Haskell/Happstack
    ●   Легкие процессы (Lwt)                           ●   Легкие процессы (ForkIO)
        –   Ручной запуск блокирующих                       –   Прозрачный запуск блокирующих
            вызовов в native threads                            вызовов (GHC 6) в native threads
             ●   Например, SQL запросов                          ●   Не будут блокировать сервер
             ●   Либо блокировка всего сервера                   ●   Без усилий с вашей стороны
             ●   Признанные ошибки Ocsigen для              –   epoll/kqueue IO backend в GHC 7.x
                 этого случая                                    ●   Не блокируют
        –   Реализация на основе монад                           ●   Как в Erlang
             ●   Время удивляться                                ●   C10K / C100K (?)
             ●   Какие еще монады в Окамле?!                –   Естественно вписываются в язык
             ●   End of easy-to-learn Ocaml                      ●   Действительно просто
                  – И это вы еще типов в Eliom не
                    видели
Приближение III
        ?              Сервер приложений



●   OCaml/Ocsigen/Eliom                              ●   Haskell/Happstack
    ●   Инфраструктура                                   ●   Инфраструктура
        –   Стандартная библиотека бедна                     –   Стандартная библиотека
            и неудобна                                           (Prelude как минимум) хороша
             ●   Почти всегда требуются
                 дополнительные библиотеки (ExtLib           –   Немало сторонних библиотек
                 --- как Boost в C++)                             ●   См. apt-cache search haskell
        –   Относительно мало сторонних                           ●   См. cabal list
            библиотек                                        –   Системы сборки / пакетирования
        –   Системы сборки / пакетирования                        ●   Cabal
             ●   Ocamlfind                                        ●   Cabal-dev
             ●   Ocamlbuild                                       ●   Capri
             ●   И другие                                               – Последние две решают
             ●   Package hell присутствует                                проблему package hell
                                                                  ●   В целом, удобнее
Приближение III
                   … And the winner is: Haskell/Happstack




Клиент (Браузер)               Сервер приложений              СУБД




      ?            HTTP/?
                                    Haskell /
                                    Happstack
                                                      SQL
                                                            PostgreSQL
Приближение III
                     ●   QooxDoo
Клиент (Браузер)
                     ●   ExtJs
                     ●   Остальные подобного уровня
                           Такие же или много хуже

     ?               ●   OpenLazslo
                         ●   HTML5 (Canvas) / Flash
                         ●   Не DOM
                         ●   В основном декларативное
                         ●   Layout Engine
                         ●   Декларативный биндинг данных в XML на
                             контролы при помощи Xpath
                              – PostgreSQL умеет отдавать данные в
                                XML
Приближение III


Клиент (Браузер)              Сервер приложений           СУБД




                                 Haskell /
 JS/OpenLaszlo     HTTP/XML                       SQL
                                 Happstack              PostgreSQL
Приближение III
  Опердень: CRUD




    UPDATE
    генерируется   CREATE
                   генерируется




  READ             Businness Logic
  генерируется     (хранимые процедуры)




                                          DELETE
                                          (SOFT)
Приближение III
                       Сервер:
Клиент: JS/OL          Happstack App


                XHR
    Widget
                 XML



                XHR                    SQL
    Widget                                   PostgreSQL
                 XML



    Widget      XHR

                 XML
Приближение III
                                     Happstack App
                                     (generic CRUD + BL)
      HTTP GET/POST                                                       SQL

        /list/entity?col1=...                                    SELECT XMLELEMENT(..)



/query/entity?col=CND(CND2(..))&..                         SELECT .. FROM .. WHERE CONDITIONS



      /create/entity?col1=...                                        INSERT INTO …



 /update/entity?key1=...&col1=...                                 UPDATE … WHERE …




      /delete/entity?key1=...                                   DELETE FROM … WHERE ...




    /fn/function?$0=x1...$n=xn                                  SELECT function(x1, … , xn)
Приближение III
                                            Полная картина




       Клиент                                              Happstack/App
                                                  HTTP
                   HTTP (XHR)
                                                              Node 1           SQL


       JS/OL                     NGINX
                                                                                     PostgreSQL
                      XML                         XML      Happstack/App       XML
                                mod_proxy
                                                              Node N




                                                                           ●Данные
 Раздача статики
                                    ●Generic CRUD
●
                                    ●Вызов бизнес-логики
                                                                           ●View
●Балансирование нагрузки                                                   ●Хранимые процедуры
                                    ●Отчеты (XML → Latex → PDF)
●Failover                                                                  ●Триггеры
                                    ●Аутентификация / Авторизация
●HTTPS                                                                     ●Правила
                                    ●RBAC
                                                                           ●Констрейнты
Приближение III
●   WIN
    ●   Разработка завершена
    ●   Деплоймент произведен
●   Некоторые свойства
    ●   Достаточно универсальный сервер на Happstack
        –   Отсутствует специфичный для приложения код
        –   Можно использовать в другом подобном проекте
             ●   Возможно, даже без перекомпиляции
        –   Можно дорабатывать, не трогая часть на Haskell вообще (только PG и JS)
    ●   Аутентификация / Авторизация / RBAC
        –   Сессии пользователей (кэширование привилегий)
        –   Двухуровневый механизм пермиссий (permissions и metapermissions)
        –   Проверка пермиссий server-side и client-side
        –   Сокрытие элементов UI, к которым нет доступа
    ●   Generic CRUD
    ●   Трансляция HTTP запросов в SQL по определенным правилам
        –   В том числе и для хранимых процедур
    ●   Генерация отчетов: XML → Latex → PDF
Приближение III
●   Некоторые метрики
    ●   Приблизительно сорок экранов/форм
    ●   Свыше пятидесяти таблиц
    ●   Порядка семидесяти VIEW
    ●   Около сорока хранимых процедур
    ●   116 различных веб-методов (CRUD + BL +
        Отчеты + Auth )
        –   Судя по количеству пермиссий
Приближение III




А причем тут вообще Haskell?
    Какая от него польза?
Haskell
●   Сильная типизация
    ●   Как правило, если скомпилировалось, то работает
    ●   Легко и безопасно вносить изменения
        –   Не собирается, пока некорректно (как правило)
●   Компилируется в нативный код
    ●   Работает точно быстрее Erlang, Python, Ruby,
        Javascript, Lua ...
        –   Это не так важно, но довольно приятно
Haskell
●   Компилируется в нативный код
    ●   Легко разворачивать на Production
        –   Как правило, не требуется ничего дополнительно
            устанавливать
Haskell
●   Много готовых к использованию библиотек
    ●   Больше, чем в OСaml или Erlang
    ●   Например
        –   Happstack.Server
             ●   Организация HTTP сервера
             ●   Роутинг и обработка HTTP запросов
        –   HDBC
             ●   Доступ к БД
             ●   Существует множество альтернатив, включая решения с сильной
                 типизацией, генерацией схем из ADT, генерацией запросов, большим
                 выбором бэкенда для хранения данных (аналогов ORM), etc, etc
        –   hdaemonize
             ●   Стандартный демон, понимающий daemon start|stop|restart в несколько
                 строчек кода
Приближение III
●   Haskell
    ●   Много готовых к использованию библиотек
           ●   hslogger
                 – Логгирование с обширными настройками
           ●   ConfigFile
                 – Чтение конфигов
           ●   Parsec
                 – Разбор DSL для не-KV HTTP-запросов:
                   col1 = OR(EQ(“BAR”), LIKE(“%FOO%”))
                   col2 = AND(GREATER(1), LESS(10))
                     ● В неcколько строчек кода
Haskell
●   Много готовых к использованию библиотек
    ●   Регулярные выражения
        –   Различные бэкенды
             ●   POSIX, TDFA, PCRE ...
        –   Наличие произвольных операторов в языке делает их
            практически встроенными в язык, как в Perl:
             ●
                 someString =~   “FOO (BAR)” :: Bool
             ●   someString =~   “FOO (BAR) ALICE (BOB)” :: [[String]]
        –   Работают с UTF8
             ●   someString =~ “Превед (медвед)” :: [[String]]
Haskell
●   Много готовых к использованию библиотек
    ●   STM (Software Transactional Memory)
        –   Атомарный конкурентный доступ к данным в памяти
        –   Для хранения сессионных данных
    ●   Сеreal
        –   Сериализация структур данных
        –   Для сохранения служебной информации в БД
        –   Один из десятков вариантов
Haskell
●   Много готовых к использованию библиотек
    ●   MySQL
    ●   PostgreSQL
    ●   SQLite
    ●   ODBC
    ●   Riak
    ●   Redis
    ●   MongoDB
    ●   Memcached
    ●   MACID
    ●   ...
Haskell
●   Инфраструктура разработки
    ●   Cabal
        –   Централизованная установка пакетов (как CPAN и подобные)
        –   Сборка проекта
        –   Трекинг зависимостей
        –   Запуск тестов
        –   Сборка дистрибутивов
    ●   Cabal-dev
        –   Тот же cabal, но без боли
             ●   Позволяет устанавливать пакеты в локальную песочницу для проекта
             ●   Не трогает остальную систему
             ●   Ликвидирует Package Hell в среде разработки
                  – А в Production его и так нет
Haskell
●   Инфраструктура разработки
    ●   Hlint
         –   Научит вас, как надо писать на Haskell
         –   Находит дублирующий код и предлагает варианты
             исправления
         –   Способен заменить не слишком въедливое Code
             Review
              ●   Каким оно чаще всего и бывает (нехватка времени, лень,
                  усталость, замыленность, нежелание брать ответственность
                  за чужой код на себя)
              ●   В Haskell практически отсутствует тип ошибок, которые может
                  найти Code Review и не может найти компилятор
                    – Использование неинициализированных данных, etc
Haskell
●   Инфраструктура разработки
    ●   QuickCheck
        –   Автоматическая генерация тестов
    ●   Средства автоматического документирования
        –   Haddock
             ●   Просто запустите cabal   haddock
Приближение III




   Заключение
Haskell
●   Удобный инструмент                                        ●   Академический язык для маргиналов
    ●   Большое количество библиотек                              ●   Не поддерживается в вашем IDE
    ●   Удобный FFI                                                   –   Простите, не поддерживается в чем?
    ●   Хорошая инфраструктура разработки                         ●   Ленивость
    ●   Выразительный язык                                            –   Так было надо
        –   Пишем меньше                                              –   Иногда, наоборот, полезна
        –   Получаем больше                                           –   Когда она создаст реальные проблемы, я
    ●   Сильная статическая типизация                                     обязательно расскажу (пока просто нет такого
                                                                          опыта)
        –   Безжалостно массово правим код, не боясь что-то
            сломать и не заметить                                 ●   Монады
    ●   Конкурентность                                                –   А что “монады” ?
        –   epoll/kqueue IO                                           –   А вы уверены, что точно знаете, что такое
        –   STM                                                           “объект” и “класс” например?
    ●   Поддержка SMP                                                      ●   Но продолжаете ими пользоваться
                                                                           ●   Либо ваше имя, вероятно, Luca Cardelli
        –   Считай факториал в два раза быстрее на двух
            ядрах вместо одного, просто добавив вызов             ●   Сложная система типов
            функции par                                                   Зато многое позволяет
                                                                      –
    ●   Поддержка UTF-8                                           ●   Ограниченный вывод типов
    ●   Метапрограммирование                                              Местами заставляет расставлять аннотации
                                                                      –
    ●   Хороший REPL                                                       ●   И это правильно
Конец
Haskell
●   Напишем маленький HTTP сервер
    ●   Пусть слушает на порту 10000
    ●   И отвечает HELLO WORLD
         import Happstack.Server

         main = do
             simpleHTTP nullConf { port = 10000 } $ ok "HELLO WORLD"
Haskell
●   Добавим счетчик запросов
      import Happstack.Server

      import Control.Concurrent.STM
      import Control.Concurrent.STM.TVar
      import Control.Monad.Reader

      main = do
          counter <- newTVarIO 0
          simpleHTTP nullConf { port = 10000 } $ do
              cnt <- readCounter counter
              writeCounter counter (cnt+1)
              ok $ "HELLO WORLD: " ++ show cnt

         where readCounter c =
                 liftIO . atomically $ readTVar c

               writeCounter c v =
                 liftIO . atomically $ writeTVar c v
Haskell
●   Демонизируем
      import Happstack.Server

      import   Control.Concurrent.STM
      import   Control.Concurrent.STM.TVar
      import   Control.Monad.Reader
      import   System.Posix.Daemonize

      main = do
          counter <- newTVarIO 0
          let ourHttpDaemon () = do
              simpleHTTP nullConf { port = 10000 } $ do
                  cnt <- readCounter counter
                  writeCounter counter (cnt+1)
                  ok $ "HELLO WORLD: " ++ show cnt

         serviced simpleDaemon { program = ourHttpDaemon }

         where readCounter c =
                 liftIO . atomically $ readTVar c
               writeCounter c v =
                 liftIO . atomically $ writeTVar c v
Haskell
●   Добавим обработку сигналов
    ●   Обнулим счетчик запросов по SIGUSR1
    ●   Напишем что-нибудь в системный лог
             import Happstack.Server

             import   Control.Concurrent.STM
             import   Control.Concurrent.STM.TVar
             import   Control.Monad.Reader
             import   System.Posix.Daemonize
             import   System.Posix.Signals
             import   System.Posix.Syslog

             main = do
                 counter <- newTVarIO 0
                 let ourHttpDaemon () = do
                     simpleHTTP nullConf { port = 10000 } $ do
                         cnt <- readCounter counter
                         writeCounter counter (cnt+1)
                         ok $ "HELLO WORLD: " ++ show cnt

                let onUSR1 = writeCounter counter 0 >> syslog Notice "Counter is set to 0" :: IO ()

                installHandler sigUSR1 (Catch onUSR1) (Just fullSignalSet)

                serviced simpleDaemon { program = ourHttpDaemon }

                where readCounter c =
                        liftIO . atomically $ readTVar c
                      writeCounter c v =
                        liftIO . atomically $ writeTVar c v
Haskell
●   Проверяем
        $ sudo hello start
        $ tail /var/log/daemon.log
        Apr 28 12:39:53 slim hello: starting

        $ ls /var/run/hello.pid
        /var/run/hello.pid

        $ curl 'http://localhost:10000'
        HELLO WORLD: 0$ curl 'http://localhost:10000'
        HELLO WORLD: 1$ curl 'http://localhost:10000'
        HELLO WORLD: 2$ curl 'http://localhost:10000'
        HELLO WORLD: 3$ curl 'http://localhost:10000'
        HELLO WORLD: 4$ curl 'http://localhost:10000'
        HELLO WORLD: 5$ curl 'http://localhost:10000'
        HELLO WORLD: 6$ curl 'http://localhost:10000'

        $ sudo kill -s USR1 `cat /var/run/hello.pid`
        $ tail /var/log/daemon.log
        Apr 28 12:44:11 slim hello: Counter is set to 0

        $ curl 'http://localhost:10000'
        HELLO WORLD: 0
Haskell
●   Запишем что-нибудь в БД
     ●   И постараемся остаться в рамках одного кадра презентации
     ●   Допустим, у нас есть база test и таблица counter (int, timestamp)

    import Happstack.Server

    import   Control.Concurrent.STM
    import   Control.Concurrent.STM.TVar
    import   Control.Monad.Reader
    import   System.Posix.Daemonize
    import   System.Posix.Signals
    import   System.Posix.Syslog
    import   Database.HDBC
    import   Database.HDBC.PostgreSQL

    main = do
        counter <- newTVarIO 0
        let ourHttpDaemon () = do
            simpleHTTP nullConf { port = 10000 } $ do
                cnt <- readCounter counter
                writeCounter counter (cnt+1)
                liftIO $ doInsert cnt
                ok $ "HELLO WORLD: " ++ show cnt

         let onUSR1 = writeCounter counter 0 >> syslog Notice "Counter is set to 0" :: IO ()

         installHandler sigUSR1 (Catch onUSR1) (Just fullSignalSet)
         serviced simpleDaemon { program = ourHttpDaemon }

         where readCounter c =
                 liftIO . atomically $ readTVar c
               writeCounter c v =
                 liftIO . atomically $ writeTVar c v

               insert c conn = quickQuery' conn "INSERT INTO counter VALUES(?)" [toSql (c::Int)]
               doInsert cnt = withPostgreSQL "dbname=test user=dmz" (c -> withTransaction c (insert cnt))
Haskell
●   Проверим
    $sudo hello restart
    $ curl 'http://localhost:10000'
    HELLO WORLD: 0$ curl 'http://localhost:10000'
    HELLO WORLD: 1$ curl 'http://localhost:10000'
    HELLO WORLD: 2$ curl 'http://localhost:10000'
    HELLO WORLD: 3$

    $ cat | psql test
    select * from counter;
     k |              ts
    ---+----------------------------
     0 | 2011-04-28 14:15:58.294183
     1 | 2011-04-28 14:15:59.252331
     2 | 2011-04-28 14:15:59.843991
     3 | 2011-04-28 14:16:00.323366
    (4 rows)
Вот теперь всё. Спасибо за внимание

More Related Content

What's hot

Встраивание Python в мобильные приложения – нюансы interoperation, новые подх...
Встраивание Python в мобильные приложения – нюансы interoperation, новые подх...Встраивание Python в мобильные приложения – нюансы interoperation, новые подх...
Встраивание Python в мобильные приложения – нюансы interoperation, новые подх...Anthony Marchenko
 
неприятная правда про язык go
неприятная правда про язык goнеприятная правда про язык go
неприятная правда про язык goDaniel Podolsky
 
Александр Сербул. Прикладное XP в «1С-Битрикс»: как развивать продукт более 1...
Александр Сербул. Прикладное XP в «1С-Битрикс»: как развивать продукт более 1...Александр Сербул. Прикладное XP в «1С-Битрикс»: как развивать продукт более 1...
Александр Сербул. Прикладное XP в «1С-Битрикс»: как развивать продукт более 1...ScrumTrek
 
SDExpo 2007 - Эволюция средств разработки
SDExpo 2007 - Эволюция средств разработкиSDExpo 2007 - Эволюция средств разработки
SDExpo 2007 - Эволюция средств разработкиguest9273776
 
Алексей Туля - А нужен ли вам erlang?
Алексей Туля - А нужен ли вам erlang?Алексей Туля - А нужен ли вам erlang?
Алексей Туля - А нужен ли вам erlang?Minsk Linux User Group
 
"Портирование Web SDK с JS на TS" Петров Григорий, Voximplant
"Портирование Web SDK с JS на TS" Петров Григорий, Voximplant"Портирование Web SDK с JS на TS" Петров Григорий, Voximplant
"Портирование Web SDK с JS на TS" Петров Григорий, Voximplantit-people
 
Цикл разработки и внедрения функционала в Мамбе (Михаил Буйлов)
Цикл разработки и внедрения функционала в Мамбе (Михаил Буйлов)Цикл разработки и внедрения функционала в Мамбе (Михаил Буйлов)
Цикл разработки и внедрения функционала в Мамбе (Михаил Буйлов)Ontico
 
Лев Валкин — Кое-что про Erlang
Лев Валкин — Кое-что про ErlangЛев Валкин — Кое-что про Erlang
Лев Валкин — Кое-что про ErlangYury Yurevich
 
Erlang, который мы потеряли
Erlang, который мы потерялиErlang, который мы потеряли
Erlang, который мы потерялиIvan Grishaev
 
Tk conf daniel-podolsky-sqlvsnosql
Tk conf daniel-podolsky-sqlvsnosqlTk conf daniel-podolsky-sqlvsnosql
Tk conf daniel-podolsky-sqlvsnosqlDaniel Podolsky
 
Erlang мгновенное просветление
Erlang  мгновенное просветлениеErlang  мгновенное просветление
Erlang мгновенное просветлениеMaxim Sokhatsky
 
Антон Довгоброд: Highload и очереди задач на примере PHP + Gearman + Yii2
Антон Довгоброд: Highload и очереди задач на примере PHP + Gearman + Yii2Антон Довгоброд: Highload и очереди задач на примере PHP + Gearman + Yii2
Антон Довгоброд: Highload и очереди задач на примере PHP + Gearman + Yii2Oleg Poludnenko
 
Алексей Воинов — Языки программирования
Алексей Воинов — Языки программированияАлексей Воинов — Языки программирования
Алексей Воинов — Языки программированияYandex
 
My talk on HBase ops engineering at TBD Jun 2016
My talk on HBase ops engineering at TBD Jun 2016My talk on HBase ops engineering at TBD Jun 2016
My talk on HBase ops engineering at TBD Jun 2016Alex Chistyakov
 
Мой modern Perl (весенняя встреча Piter United)
Мой modern Perl (весенняя встреча Piter United)Мой modern Perl (весенняя встреча Piter United)
Мой modern Perl (весенняя встреча Piter United)Alex Chistyakov
 
Страх и ненависть в мире релиз-инжиниринга
Страх и ненависть в мире релиз-инжинирингаСтрах и ненависть в мире релиз-инжиниринга
Страх и ненависть в мире релиз-инжинирингаMikhail Chinkov
 
15 HappyDev-lite-2015 autumn. Анна Тарасенко. Java в современном мире, вторая...
15 HappyDev-lite-2015 autumn. Анна Тарасенко. Java в современном мире, вторая...15 HappyDev-lite-2015 autumn. Анна Тарасенко. Java в современном мире, вторая...
15 HappyDev-lite-2015 autumn. Анна Тарасенко. Java в современном мире, вторая...HappyDev-lite
 
Быстрое расширение Robot Framework под свои нужды с использованием Python
Быстрое расширение Robot Framework под свои нужды с использованием PythonБыстрое расширение Robot Framework под свои нужды с использованием Python
Быстрое расширение Robot Framework под свои нужды с использованием Pythonautomated-testing.info
 
Language oriented programming_(lop)_в_действии_(максим_мазин,_add-2011)
Language oriented programming_(lop)_в_действии_(максим_мазин,_add-2011)Language oriented programming_(lop)_в_действии_(максим_мазин,_add-2011)
Language oriented programming_(lop)_в_действии_(максим_мазин,_add-2011)Sergey Polazhenko
 
Опыт использования Erlang в разработке многопользовательской игры
Опыт использования Erlang в разработке многопользовательской игрыОпыт использования Erlang в разработке многопользовательской игры
Опыт использования Erlang в разработке многопользовательской игрыYuri Zhloba
 

What's hot (20)

Встраивание Python в мобильные приложения – нюансы interoperation, новые подх...
Встраивание Python в мобильные приложения – нюансы interoperation, новые подх...Встраивание Python в мобильные приложения – нюансы interoperation, новые подх...
Встраивание Python в мобильные приложения – нюансы interoperation, новые подх...
 
неприятная правда про язык go
неприятная правда про язык goнеприятная правда про язык go
неприятная правда про язык go
 
Александр Сербул. Прикладное XP в «1С-Битрикс»: как развивать продукт более 1...
Александр Сербул. Прикладное XP в «1С-Битрикс»: как развивать продукт более 1...Александр Сербул. Прикладное XP в «1С-Битрикс»: как развивать продукт более 1...
Александр Сербул. Прикладное XP в «1С-Битрикс»: как развивать продукт более 1...
 
SDExpo 2007 - Эволюция средств разработки
SDExpo 2007 - Эволюция средств разработкиSDExpo 2007 - Эволюция средств разработки
SDExpo 2007 - Эволюция средств разработки
 
Алексей Туля - А нужен ли вам erlang?
Алексей Туля - А нужен ли вам erlang?Алексей Туля - А нужен ли вам erlang?
Алексей Туля - А нужен ли вам erlang?
 
"Портирование Web SDK с JS на TS" Петров Григорий, Voximplant
"Портирование Web SDK с JS на TS" Петров Григорий, Voximplant"Портирование Web SDK с JS на TS" Петров Григорий, Voximplant
"Портирование Web SDK с JS на TS" Петров Григорий, Voximplant
 
Цикл разработки и внедрения функционала в Мамбе (Михаил Буйлов)
Цикл разработки и внедрения функционала в Мамбе (Михаил Буйлов)Цикл разработки и внедрения функционала в Мамбе (Михаил Буйлов)
Цикл разработки и внедрения функционала в Мамбе (Михаил Буйлов)
 
Лев Валкин — Кое-что про Erlang
Лев Валкин — Кое-что про ErlangЛев Валкин — Кое-что про Erlang
Лев Валкин — Кое-что про Erlang
 
Erlang, который мы потеряли
Erlang, который мы потерялиErlang, который мы потеряли
Erlang, который мы потеряли
 
Tk conf daniel-podolsky-sqlvsnosql
Tk conf daniel-podolsky-sqlvsnosqlTk conf daniel-podolsky-sqlvsnosql
Tk conf daniel-podolsky-sqlvsnosql
 
Erlang мгновенное просветление
Erlang  мгновенное просветлениеErlang  мгновенное просветление
Erlang мгновенное просветление
 
Антон Довгоброд: Highload и очереди задач на примере PHP + Gearman + Yii2
Антон Довгоброд: Highload и очереди задач на примере PHP + Gearman + Yii2Антон Довгоброд: Highload и очереди задач на примере PHP + Gearman + Yii2
Антон Довгоброд: Highload и очереди задач на примере PHP + Gearman + Yii2
 
Алексей Воинов — Языки программирования
Алексей Воинов — Языки программированияАлексей Воинов — Языки программирования
Алексей Воинов — Языки программирования
 
My talk on HBase ops engineering at TBD Jun 2016
My talk on HBase ops engineering at TBD Jun 2016My talk on HBase ops engineering at TBD Jun 2016
My talk on HBase ops engineering at TBD Jun 2016
 
Мой modern Perl (весенняя встреча Piter United)
Мой modern Perl (весенняя встреча Piter United)Мой modern Perl (весенняя встреча Piter United)
Мой modern Perl (весенняя встреча Piter United)
 
Страх и ненависть в мире релиз-инжиниринга
Страх и ненависть в мире релиз-инжинирингаСтрах и ненависть в мире релиз-инжиниринга
Страх и ненависть в мире релиз-инжиниринга
 
15 HappyDev-lite-2015 autumn. Анна Тарасенко. Java в современном мире, вторая...
15 HappyDev-lite-2015 autumn. Анна Тарасенко. Java в современном мире, вторая...15 HappyDev-lite-2015 autumn. Анна Тарасенко. Java в современном мире, вторая...
15 HappyDev-lite-2015 autumn. Анна Тарасенко. Java в современном мире, вторая...
 
Быстрое расширение Robot Framework под свои нужды с использованием Python
Быстрое расширение Robot Framework под свои нужды с использованием PythonБыстрое расширение Robot Framework под свои нужды с использованием Python
Быстрое расширение Robot Framework под свои нужды с использованием Python
 
Language oriented programming_(lop)_в_действии_(максим_мазин,_add-2011)
Language oriented programming_(lop)_в_действии_(максим_мазин,_add-2011)Language oriented programming_(lop)_в_действии_(максим_мазин,_add-2011)
Language oriented programming_(lop)_в_действии_(максим_мазин,_add-2011)
 
Опыт использования Erlang в разработке многопользовательской игры
Опыт использования Erlang в разработке многопользовательской игрыОпыт использования Erlang в разработке многопользовательской игры
Опыт использования Erlang в разработке многопользовательской игры
 

Similar to Operden1

My talk on Salt and Ansible from DevConf 2014
My talk on Salt and Ansible from DevConf 2014My talk on Salt and Ansible from DevConf 2014
My talk on Salt and Ansible from DevConf 2014Alex Chistyakov
 
специализированные http-демона (Сергей Боченков, Александр Панков)
специализированные http-демона (Сергей Боченков, Александр Панков)специализированные http-демона (Сергей Боченков, Александр Панков)
специализированные http-демона (Сергей Боченков, Александр Панков)Ontico
 
"How to build powerful CI / CD based on GitLab and Docker", Aleksandr Matkovs...
"How to build powerful CI / CD based on GitLab and Docker", Aleksandr Matkovs..."How to build powerful CI / CD based on GitLab and Docker", Aleksandr Matkovs...
"How to build powerful CI / CD based on GitLab and Docker", Aleksandr Matkovs...Provectus
 
ORM battle. MyBatis vs Hibernate
ORM battle. MyBatis vs HibernateORM battle. MyBatis vs Hibernate
ORM battle. MyBatis vs HibernateAlexey Zinoviev
 
2012-12-01 03 Битва ORM: Hibernate vs MyBatis. Давайте жить дружно!
2012-12-01 03 Битва ORM: Hibernate vs MyBatis. Давайте жить дружно!2012-12-01 03 Битва ORM: Hibernate vs MyBatis. Давайте жить дружно!
2012-12-01 03 Битва ORM: Hibernate vs MyBatis. Давайте жить дружно!Омские ИТ-субботники
 
Gobblin как ETL-фреймворк / Иван Ахлестин (Rambler&Co)
Gobblin как ETL-фреймворк / Иван Ахлестин (Rambler&Co)Gobblin как ETL-фреймворк / Иван Ахлестин (Rambler&Co)
Gobblin как ETL-фреймворк / Иван Ахлестин (Rambler&Co)Ontico
 
Devconf 2011 - PHP - Как разрабатывается фреймворк Yii
Devconf 2011 - PHP - Как разрабатывается фреймворк YiiDevconf 2011 - PHP - Как разрабатывается фреймворк Yii
Devconf 2011 - PHP - Как разрабатывается фреймворк YiiAlexander Makarov
 
Там, где Rails не справляются
Там, где Rails не справляютсяТам, где Rails не справляются
Там, где Rails не справляютсяMax Lapshin
 
Опыт эксплуатации большого проекта на Ruby
Опыт эксплуатации большого проекта на RubyОпыт эксплуатации большого проекта на Ruby
Опыт эксплуатации большого проекта на RubyAlex Chistyakov
 
Кирилл Комлев. О реализации continuous integration для web проектов
Кирилл Комлев. О реализации continuous integration для web проектовКирилл Комлев. О реализации continuous integration для web проектов
Кирилл Комлев. О реализации continuous integration для web проектовOlesya_V
 
Docker-контейнеризация: от local до production
Docker-контейнеризация: от local до productionDocker-контейнеризация: от local до production
Docker-контейнеризация: от local до productionRoman Kudlay
 
My talk on Hadoop stack operations engineering at OSPCon
My talk on Hadoop stack operations engineering at OSPConMy talk on Hadoop stack operations engineering at OSPCon
My talk on Hadoop stack operations engineering at OSPConAlex Chistyakov
 
16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Эксплуат...
16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Эксплуат...16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Эксплуат...
16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Эксплуат...IT-Portfolio
 
CodeFest 2012. Сидельников А. — Опыт создания DSL на Ruby. Где применить, как...
CodeFest 2012. Сидельников А. — Опыт создания DSL на Ruby. Где применить, как...CodeFest 2012. Сидельников А. — Опыт создания DSL на Ruby. Где применить, как...
CodeFest 2012. Сидельников А. — Опыт создания DSL на Ruby. Где применить, как...CodeFest
 
Gradle. Новый уровень автоматизации для Android
Gradle. Новый уровень автоматизации для AndroidGradle. Новый уровень автоматизации для Android
Gradle. Новый уровень автоматизации для AndroidSQALab
 
Meet Magento Belarus - Andriy Samilyak
Meet Magento Belarus - Andriy SamilyakMeet Magento Belarus - Andriy Samilyak
Meet Magento Belarus - Andriy SamilyakAmasty
 

Similar to Operden1 (20)

My talk on Salt and Ansible from DevConf 2014
My talk on Salt and Ansible from DevConf 2014My talk on Salt and Ansible from DevConf 2014
My talk on Salt and Ansible from DevConf 2014
 
специализированные http-демона (Сергей Боченков, Александр Панков)
специализированные http-демона (Сергей Боченков, Александр Панков)специализированные http-демона (Сергей Боченков, Александр Панков)
специализированные http-демона (Сергей Боченков, Александр Панков)
 
"How to build powerful CI / CD based on GitLab and Docker", Aleksandr Matkovs...
"How to build powerful CI / CD based on GitLab and Docker", Aleksandr Matkovs..."How to build powerful CI / CD based on GitLab and Docker", Aleksandr Matkovs...
"How to build powerful CI / CD based on GitLab and Docker", Aleksandr Matkovs...
 
ORM battle. MyBatis vs Hibernate
ORM battle. MyBatis vs HibernateORM battle. MyBatis vs Hibernate
ORM battle. MyBatis vs Hibernate
 
2012-12-01 03 Битва ORM: Hibernate vs MyBatis. Давайте жить дружно!
2012-12-01 03 Битва ORM: Hibernate vs MyBatis. Давайте жить дружно!2012-12-01 03 Битва ORM: Hibernate vs MyBatis. Давайте жить дружно!
2012-12-01 03 Битва ORM: Hibernate vs MyBatis. Давайте жить дружно!
 
Gobblin как ETL-фреймворк / Иван Ахлестин (Rambler&Co)
Gobblin как ETL-фреймворк / Иван Ахлестин (Rambler&Co)Gobblin как ETL-фреймворк / Иван Ахлестин (Rambler&Co)
Gobblin как ETL-фреймворк / Иван Ахлестин (Rambler&Co)
 
Devconf 2011 - PHP - Как разрабатывается фреймворк Yii
Devconf 2011 - PHP - Как разрабатывается фреймворк YiiDevconf 2011 - PHP - Как разрабатывается фреймворк Yii
Devconf 2011 - PHP - Как разрабатывается фреймворк Yii
 
Там, где Rails не справляются
Там, где Rails не справляютсяТам, где Rails не справляются
Там, где Rails не справляются
 
Sivko
SivkoSivko
Sivko
 
Опыт эксплуатации большого проекта на Ruby
Опыт эксплуатации большого проекта на RubyОпыт эксплуатации большого проекта на Ruby
Опыт эксплуатации большого проекта на Ruby
 
Кирилл Комлев. О реализации continuous integration для web проектов
Кирилл Комлев. О реализации continuous integration для web проектовКирилл Комлев. О реализации continuous integration для web проектов
Кирилл Комлев. О реализации continuous integration для web проектов
 
Docker-контейнеризация: от local до production
Docker-контейнеризация: от local до productionDocker-контейнеризация: от local до production
Docker-контейнеризация: от local до production
 
My talk on Hadoop stack operations engineering at OSPCon
My talk on Hadoop stack operations engineering at OSPConMy talk on Hadoop stack operations engineering at OSPCon
My talk on Hadoop stack operations engineering at OSPCon
 
HBase on Dev{Highload}
HBase on Dev{Highload}HBase on Dev{Highload}
HBase on Dev{Highload}
 
16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Эксплуат...
16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Эксплуат...16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Эксплуат...
16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Эксплуат...
 
CodeFest 2012. Сидельников А. — Опыт создания DSL на Ruby. Где применить, как...
CodeFest 2012. Сидельников А. — Опыт создания DSL на Ruby. Где применить, как...CodeFest 2012. Сидельников А. — Опыт создания DSL на Ruby. Где применить, как...
CodeFest 2012. Сидельников А. — Опыт создания DSL на Ruby. Где применить, как...
 
2 bdw.key
2 bdw.key2 bdw.key
2 bdw.key
 
Gradle. Новый уровень автоматизации для Android
Gradle. Новый уровень автоматизации для AndroidGradle. Новый уровень автоматизации для Android
Gradle. Новый уровень автоматизации для Android
 
Meet Magento Belarus - Andriy Samilyak
Meet Magento Belarus - Andriy SamilyakMeet Magento Belarus - Andriy Samilyak
Meet Magento Belarus - Andriy Samilyak
 
Migrate!
Migrate!Migrate!
Migrate!
 

Operden1

  • 1. Динамическая Опердень на Haskell Как за три шага превратить острый гемморой в хронический
  • 3. Приближение I Клиент (Браузер) Сервер приложений СУБД JavaScript HTTP/JSON Erlang/MochiWeb SQL QooxDoo PostgreSQL Совершенно типичная, рядовая, унылая опердень
  • 4. Приближение I ● Результат: FAIL ● Разработчики не довели проект... ● Даже до середины ● Основные причины --- организационные ● И тем не менее
  • 5. Приближение I ● QooxDoo ● Сложный дизайн ● Oчень verbose ● Очень много писать руками на JS ● Практическое отсутствие декларативности ● Ручной маппинг данных ● Странные ограничения в виджетах ● Относительно слабая документация ● Довольно симпатично выглядит, впрочем
  • 6. Приближение I ● Mochiweb/Erlang ● Динамическая типизация – ОБЯЗАТЕЛЬНО требуются юнит-тесты ● Которые никто не пишет ● Полуживые средства Database Connectivity – Требовалась ручная доработка ● Генерация и парсинг JSON – Очень мало и полуживое – Потребовалась ручная доработка
  • 7. Приближение I ● Mochiweb/Erlang ● Автоматический маппинг HTTP на SQL (CRUD) – Оказался слишком сложен ● Достаточно бедный язык ● Динамическая типизация – При этом почти отсутствует метапрограммирование ● Недостаток опыта у разрабатывающих
  • 8. Приближение I ● FAIL ● Недостаточная организация – Недостаток времени на организацию ● Недостаток опыта – Овердизайн ● Инструменты увеличивают количество работы – А должны уменьшать
  • 10. Приближение II ● Другой разработчик ● Erlang/MochiWeb ● ExtJS вместо QooxDoo ● Чуть больше декларативности ● Шаг в сторону --- расстрел ● Мистические глюки
  • 11. Приближение II ● FAIL ● Основные причины – Недостаточная организация – Недостаток квалификации – Недостаток опыта
  • 12. Приближение III Если хочешь, что бы что-то было сделано хорошо --- сделай это сам
  • 13. Приближение III Клиент (Браузер) Сервер приложений СУБД ? HTTP/? ? SQL PostgreSQL
  • 14. Лирическое отступление: Дизайн “Центр масс” системы Клиент Сервер СУБД Вариант I Клиент Сервер СУБД Вариант II Клиент Сервер СУБД Вариант III
  • 15. Лирическое отступление: Дизайн Клиент Сервер СУБД Вариант I ● Pros ● Cons ● Быстро ● Трэш прототипировать ● Угар – Иногда ● Содомия
  • 16. Лирическое отступление: Дизайн Клиент Сервер СУБД Вариант II ● Pros ● Cons ● Миграция между СУБД ● Быстро, толькo если держать всю – Как секс у тинейжеров: чаще говорят, БД в памяти приложения чем делают – Страдает D в ACID ● Использование ORM ● Типичные языки для – Хорошо, если не знаете SQL манипуляции данными менее ● Возможность строгого удобны, чем SQL + расширения типизирования модели ● Все равно отчеты придется Если вы используете типизацию – делать на SQL
  • 17. Лирическое отступление: Дизайн Клиент Сервер СУБД Вариант III ● Pros ● Cons ● Просто ● Дорогая смена СУБД ● Быстрая разработка – Но см. предыдущий ● “Горячие” апгрейды слайд – Кроме изменения схемы ● Отвратительная ● Поддерживать может типизация в БД любой DBA – Придется с этим жить – И даже немного дорабатывать
  • 18. Приближение III ? Сервер приложений ● OCaml/Ocsigen/Eliom ● Haskell/Happstack ● Низкий порог ● Выше качество вхождения сервера – Верно для OCaml (но ● API проще не для Ocsigen/Eliom) ● Отличные ● Слабые библиотеки библиотеки DB DB Connectivity Connectivity (HDBC) – Пришлось – Все работает дорабатывать
  • 19. Приближение III ? Сервер приложений ● OCaml/Ocsigen/Eliom ● Haskell/Happstack ● Легкие процессы (Lwt) ● Легкие процессы (ForkIO) – Ручной запуск блокирующих – Прозрачный запуск блокирующих вызовов в native threads вызовов (GHC 6) в native threads ● Например, SQL запросов ● Не будут блокировать сервер ● Либо блокировка всего сервера ● Без усилий с вашей стороны ● Признанные ошибки Ocsigen для – epoll/kqueue IO backend в GHC 7.x этого случая ● Не блокируют – Реализация на основе монад ● Как в Erlang ● Время удивляться ● C10K / C100K (?) ● Какие еще монады в Окамле?! – Естественно вписываются в язык ● End of easy-to-learn Ocaml ● Действительно просто – И это вы еще типов в Eliom не видели
  • 20. Приближение III ? Сервер приложений ● OCaml/Ocsigen/Eliom ● Haskell/Happstack ● Инфраструктура ● Инфраструктура – Стандартная библиотека бедна – Стандартная библиотека и неудобна (Prelude как минимум) хороша ● Почти всегда требуются дополнительные библиотеки (ExtLib – Немало сторонних библиотек --- как Boost в C++) ● См. apt-cache search haskell – Относительно мало сторонних ● См. cabal list библиотек – Системы сборки / пакетирования – Системы сборки / пакетирования ● Cabal ● Ocamlfind ● Cabal-dev ● Ocamlbuild ● Capri ● И другие – Последние две решают ● Package hell присутствует проблему package hell ● В целом, удобнее
  • 21. Приближение III … And the winner is: Haskell/Happstack Клиент (Браузер) Сервер приложений СУБД ? HTTP/? Haskell / Happstack SQL PostgreSQL
  • 22. Приближение III ● QooxDoo Клиент (Браузер) ● ExtJs ● Остальные подобного уровня Такие же или много хуже ? ● OpenLazslo ● HTML5 (Canvas) / Flash ● Не DOM ● В основном декларативное ● Layout Engine ● Декларативный биндинг данных в XML на контролы при помощи Xpath – PostgreSQL умеет отдавать данные в XML
  • 23. Приближение III Клиент (Браузер) Сервер приложений СУБД Haskell / JS/OpenLaszlo HTTP/XML SQL Happstack PostgreSQL
  • 24. Приближение III Опердень: CRUD UPDATE генерируется CREATE генерируется READ Businness Logic генерируется (хранимые процедуры) DELETE (SOFT)
  • 25. Приближение III Сервер: Клиент: JS/OL Happstack App XHR Widget XML XHR SQL Widget PostgreSQL XML Widget XHR XML
  • 26. Приближение III Happstack App (generic CRUD + BL) HTTP GET/POST SQL /list/entity?col1=... SELECT XMLELEMENT(..) /query/entity?col=CND(CND2(..))&.. SELECT .. FROM .. WHERE CONDITIONS /create/entity?col1=... INSERT INTO … /update/entity?key1=...&col1=... UPDATE … WHERE … /delete/entity?key1=... DELETE FROM … WHERE ... /fn/function?$0=x1...$n=xn SELECT function(x1, … , xn)
  • 27. Приближение III Полная картина Клиент Happstack/App HTTP HTTP (XHR) Node 1 SQL JS/OL NGINX PostgreSQL XML XML Happstack/App XML mod_proxy Node N ●Данные Раздача статики ●Generic CRUD ● ●Вызов бизнес-логики ●View ●Балансирование нагрузки ●Хранимые процедуры ●Отчеты (XML → Latex → PDF) ●Failover ●Триггеры ●Аутентификация / Авторизация ●HTTPS ●Правила ●RBAC ●Констрейнты
  • 28. Приближение III ● WIN ● Разработка завершена ● Деплоймент произведен ● Некоторые свойства ● Достаточно универсальный сервер на Happstack – Отсутствует специфичный для приложения код – Можно использовать в другом подобном проекте ● Возможно, даже без перекомпиляции – Можно дорабатывать, не трогая часть на Haskell вообще (только PG и JS) ● Аутентификация / Авторизация / RBAC – Сессии пользователей (кэширование привилегий) – Двухуровневый механизм пермиссий (permissions и metapermissions) – Проверка пермиссий server-side и client-side – Сокрытие элементов UI, к которым нет доступа ● Generic CRUD ● Трансляция HTTP запросов в SQL по определенным правилам – В том числе и для хранимых процедур ● Генерация отчетов: XML → Latex → PDF
  • 29. Приближение III ● Некоторые метрики ● Приблизительно сорок экранов/форм ● Свыше пятидесяти таблиц ● Порядка семидесяти VIEW ● Около сорока хранимых процедур ● 116 различных веб-методов (CRUD + BL + Отчеты + Auth ) – Судя по количеству пермиссий
  • 30. Приближение III А причем тут вообще Haskell? Какая от него польза?
  • 31. Haskell ● Сильная типизация ● Как правило, если скомпилировалось, то работает ● Легко и безопасно вносить изменения – Не собирается, пока некорректно (как правило) ● Компилируется в нативный код ● Работает точно быстрее Erlang, Python, Ruby, Javascript, Lua ... – Это не так важно, но довольно приятно
  • 32. Haskell ● Компилируется в нативный код ● Легко разворачивать на Production – Как правило, не требуется ничего дополнительно устанавливать
  • 33. Haskell ● Много готовых к использованию библиотек ● Больше, чем в OСaml или Erlang ● Например – Happstack.Server ● Организация HTTP сервера ● Роутинг и обработка HTTP запросов – HDBC ● Доступ к БД ● Существует множество альтернатив, включая решения с сильной типизацией, генерацией схем из ADT, генерацией запросов, большим выбором бэкенда для хранения данных (аналогов ORM), etc, etc – hdaemonize ● Стандартный демон, понимающий daemon start|stop|restart в несколько строчек кода
  • 34. Приближение III ● Haskell ● Много готовых к использованию библиотек ● hslogger – Логгирование с обширными настройками ● ConfigFile – Чтение конфигов ● Parsec – Разбор DSL для не-KV HTTP-запросов: col1 = OR(EQ(“BAR”), LIKE(“%FOO%”)) col2 = AND(GREATER(1), LESS(10)) ● В неcколько строчек кода
  • 35. Haskell ● Много готовых к использованию библиотек ● Регулярные выражения – Различные бэкенды ● POSIX, TDFA, PCRE ... – Наличие произвольных операторов в языке делает их практически встроенными в язык, как в Perl: ● someString =~ “FOO (BAR)” :: Bool ● someString =~ “FOO (BAR) ALICE (BOB)” :: [[String]] – Работают с UTF8 ● someString =~ “Превед (медвед)” :: [[String]]
  • 36. Haskell ● Много готовых к использованию библиотек ● STM (Software Transactional Memory) – Атомарный конкурентный доступ к данным в памяти – Для хранения сессионных данных ● Сеreal – Сериализация структур данных – Для сохранения служебной информации в БД – Один из десятков вариантов
  • 37. Haskell ● Много готовых к использованию библиотек ● MySQL ● PostgreSQL ● SQLite ● ODBC ● Riak ● Redis ● MongoDB ● Memcached ● MACID ● ...
  • 38. Haskell ● Инфраструктура разработки ● Cabal – Централизованная установка пакетов (как CPAN и подобные) – Сборка проекта – Трекинг зависимостей – Запуск тестов – Сборка дистрибутивов ● Cabal-dev – Тот же cabal, но без боли ● Позволяет устанавливать пакеты в локальную песочницу для проекта ● Не трогает остальную систему ● Ликвидирует Package Hell в среде разработки – А в Production его и так нет
  • 39. Haskell ● Инфраструктура разработки ● Hlint – Научит вас, как надо писать на Haskell – Находит дублирующий код и предлагает варианты исправления – Способен заменить не слишком въедливое Code Review ● Каким оно чаще всего и бывает (нехватка времени, лень, усталость, замыленность, нежелание брать ответственность за чужой код на себя) ● В Haskell практически отсутствует тип ошибок, которые может найти Code Review и не может найти компилятор – Использование неинициализированных данных, etc
  • 40. Haskell ● Инфраструктура разработки ● QuickCheck – Автоматическая генерация тестов ● Средства автоматического документирования – Haddock ● Просто запустите cabal haddock
  • 41. Приближение III Заключение
  • 42. Haskell ● Удобный инструмент ● Академический язык для маргиналов ● Большое количество библиотек ● Не поддерживается в вашем IDE ● Удобный FFI – Простите, не поддерживается в чем? ● Хорошая инфраструктура разработки ● Ленивость ● Выразительный язык – Так было надо – Пишем меньше – Иногда, наоборот, полезна – Получаем больше – Когда она создаст реальные проблемы, я ● Сильная статическая типизация обязательно расскажу (пока просто нет такого опыта) – Безжалостно массово правим код, не боясь что-то сломать и не заметить ● Монады ● Конкурентность – А что “монады” ? – epoll/kqueue IO – А вы уверены, что точно знаете, что такое – STM “объект” и “класс” например? ● Поддержка SMP ● Но продолжаете ими пользоваться ● Либо ваше имя, вероятно, Luca Cardelli – Считай факториал в два раза быстрее на двух ядрах вместо одного, просто добавив вызов ● Сложная система типов функции par Зато многое позволяет – ● Поддержка UTF-8 ● Ограниченный вывод типов ● Метапрограммирование Местами заставляет расставлять аннотации – ● Хороший REPL ● И это правильно
  • 44.
  • 45. Haskell ● Напишем маленький HTTP сервер ● Пусть слушает на порту 10000 ● И отвечает HELLO WORLD import Happstack.Server main = do simpleHTTP nullConf { port = 10000 } $ ok "HELLO WORLD"
  • 46. Haskell ● Добавим счетчик запросов import Happstack.Server import Control.Concurrent.STM import Control.Concurrent.STM.TVar import Control.Monad.Reader main = do counter <- newTVarIO 0 simpleHTTP nullConf { port = 10000 } $ do cnt <- readCounter counter writeCounter counter (cnt+1) ok $ "HELLO WORLD: " ++ show cnt where readCounter c = liftIO . atomically $ readTVar c writeCounter c v = liftIO . atomically $ writeTVar c v
  • 47. Haskell ● Демонизируем import Happstack.Server import Control.Concurrent.STM import Control.Concurrent.STM.TVar import Control.Monad.Reader import System.Posix.Daemonize main = do counter <- newTVarIO 0 let ourHttpDaemon () = do simpleHTTP nullConf { port = 10000 } $ do cnt <- readCounter counter writeCounter counter (cnt+1) ok $ "HELLO WORLD: " ++ show cnt serviced simpleDaemon { program = ourHttpDaemon } where readCounter c = liftIO . atomically $ readTVar c writeCounter c v = liftIO . atomically $ writeTVar c v
  • 48. Haskell ● Добавим обработку сигналов ● Обнулим счетчик запросов по SIGUSR1 ● Напишем что-нибудь в системный лог import Happstack.Server import Control.Concurrent.STM import Control.Concurrent.STM.TVar import Control.Monad.Reader import System.Posix.Daemonize import System.Posix.Signals import System.Posix.Syslog main = do counter <- newTVarIO 0 let ourHttpDaemon () = do simpleHTTP nullConf { port = 10000 } $ do cnt <- readCounter counter writeCounter counter (cnt+1) ok $ "HELLO WORLD: " ++ show cnt let onUSR1 = writeCounter counter 0 >> syslog Notice "Counter is set to 0" :: IO () installHandler sigUSR1 (Catch onUSR1) (Just fullSignalSet) serviced simpleDaemon { program = ourHttpDaemon } where readCounter c = liftIO . atomically $ readTVar c writeCounter c v = liftIO . atomically $ writeTVar c v
  • 49. Haskell ● Проверяем $ sudo hello start $ tail /var/log/daemon.log Apr 28 12:39:53 slim hello: starting $ ls /var/run/hello.pid /var/run/hello.pid $ curl 'http://localhost:10000' HELLO WORLD: 0$ curl 'http://localhost:10000' HELLO WORLD: 1$ curl 'http://localhost:10000' HELLO WORLD: 2$ curl 'http://localhost:10000' HELLO WORLD: 3$ curl 'http://localhost:10000' HELLO WORLD: 4$ curl 'http://localhost:10000' HELLO WORLD: 5$ curl 'http://localhost:10000' HELLO WORLD: 6$ curl 'http://localhost:10000' $ sudo kill -s USR1 `cat /var/run/hello.pid` $ tail /var/log/daemon.log Apr 28 12:44:11 slim hello: Counter is set to 0 $ curl 'http://localhost:10000' HELLO WORLD: 0
  • 50. Haskell ● Запишем что-нибудь в БД ● И постараемся остаться в рамках одного кадра презентации ● Допустим, у нас есть база test и таблица counter (int, timestamp) import Happstack.Server import Control.Concurrent.STM import Control.Concurrent.STM.TVar import Control.Monad.Reader import System.Posix.Daemonize import System.Posix.Signals import System.Posix.Syslog import Database.HDBC import Database.HDBC.PostgreSQL main = do counter <- newTVarIO 0 let ourHttpDaemon () = do simpleHTTP nullConf { port = 10000 } $ do cnt <- readCounter counter writeCounter counter (cnt+1) liftIO $ doInsert cnt ok $ "HELLO WORLD: " ++ show cnt let onUSR1 = writeCounter counter 0 >> syslog Notice "Counter is set to 0" :: IO () installHandler sigUSR1 (Catch onUSR1) (Just fullSignalSet) serviced simpleDaemon { program = ourHttpDaemon } where readCounter c = liftIO . atomically $ readTVar c writeCounter c v = liftIO . atomically $ writeTVar c v insert c conn = quickQuery' conn "INSERT INTO counter VALUES(?)" [toSql (c::Int)] doInsert cnt = withPostgreSQL "dbname=test user=dmz" (c -> withTransaction c (insert cnt))
  • 51. Haskell ● Проверим $sudo hello restart $ curl 'http://localhost:10000' HELLO WORLD: 0$ curl 'http://localhost:10000' HELLO WORLD: 1$ curl 'http://localhost:10000' HELLO WORLD: 2$ curl 'http://localhost:10000' HELLO WORLD: 3$ $ cat | psql test select * from counter; k | ts ---+---------------------------- 0 | 2011-04-28 14:15:58.294183 1 | 2011-04-28 14:15:59.252331 2 | 2011-04-28 14:15:59.843991 3 | 2011-04-28 14:16:00.323366 (4 rows)
  • 52. Вот теперь всё. Спасибо за внимание