LINUX.ORG.RU

[haskell] простейшее веб приложение

 


0

2

Добрый вечер.

Хочется сделать простейшее веб-приложение на отдельном поддомене.

Приложение должно состоять из формы - входные данные (несколько цифр), кнопка, выходные данные. Нажали кнопку - получили результат выполнения хаскелевого бинаря

./shit ${ВХОДНЫЕ ДАННЫЕ}
, динамически (без перезагрузки всей страницы) отобразили их в выходных данных.

Собственно, начал с простого nginx'а, но fcgiwrap настроить не удалось. Поэтому пока в форме выходных данных получаю содержимое бинарника.

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

Перемещено hibou из Development

Ответ на: комментарий от Waterlaz

ммм... ок. Зачем ты приперся на ЛОР высказывать свои малограмотные соображения?

Сомневаюсь, что ты может оценивать грамотностью чьих-либо сообщений *вообще* - через пост синдром женской логики во все поля

alienclaster ★★★
()
Ответ на: комментарий от alienclaster

И чем это будет отличаться от всех этих «грязных» именованных ссылок на объекты (в стиле common lisp, python, ruby...)?

Хотя бы тем, что изменения объекта можно выражать чисто

Waterlaz ★★★★★
()
Ответ на: комментарий от alienclaster

Сомневаюсь, что ты может оценивать грамотностью чьих-либо сообщений *вообще* - через пост синдром женской логики во все поля

Ты же тут херню с умным видом пишешь.

Waterlaz ★★★★★
()
Ответ на: комментарий от anonymous

Ты всерьёз считаешь, что в си нет ООП?

Я тоже так считаю.

Ну не знаю, в ядро чтоли посмотри.

Много смотрю. Может, просто приведешь конструкции Си, которые предназначены для поддержки ООП?

tailgunner ★★★★★
()
Ответ на: комментарий от anonymous

Это можно назвать «эмуляцией ооп». На С можно писать и в функциональном стиле, и динамическая типизация там есть - с таким успехом. А еще в С есть лисп, а «хаскель - лучший императивный язык в мире». Я рад, что у нас получился такой познавательный разговор, приходи еще.

alienclaster ★★★
()
Ответ на: комментарий от Waterlaz

Хотя бы тем, что изменения объекта можно выражать чисто

Правда - ложь, добро - зло, а Свет - это Тьма. Рассказы с ах.енно концентрированным внутренним смыслом писать не пробовал?

alienclaster ★★★
()
Ответ на: комментарий от tailgunner

Я тоже так считаю

ООП без наследования уже не ООП?

Много смотрю. Может, просто приведешь конструкции Си, которые предназначены для поддержки ООП?

Грубо говоря [code] struct my_object { ... };

void make_shit(struct my_object *foo){ ... } [/code]

ИМХО мало отличается от того ООП, что практикуют в С++

Waterlaz ★★★★★
()
Ответ на: комментарий от Waterlaz

Сомневаюсь, что ты может оценивать грамотностью чьих-либо сообщений *вообще* - через пост синдром женской логики во все поля

Ты же тут херню с умным видом пишешь.

Ты не подумай, этим постом я ни в коем случае не хотел унизить женщин!

alienclaster ★★★
()
Ответ на: комментарий от alienclaster

Правда - ложь, добро - зло, а Свет - это Тьма. Рассказы с ах.енно концентрированным внутренним смыслом писать не пробовал?

Для людей в теме я написал достаточно.

do
   myVar <- newIORef 666
   modifyIORef myVar (+111)

так вот (+111) - чистая функция

Waterlaz ★★★★★
()
Ответ на: комментарий от Waterlaz

ООП без наследования уже не ООП?

В С *можно* сделать наследование. Можно. Можно! МОЖНО! Муууоооожжноооооооууууээ@#_?*&NO CARRIER

alienclaster ★★★
()
Ответ на: комментарий от alienclaster

ООП без наследования уже не ООП?

В С *можно* сделать наследование. Можно. Можно! МОЖНО! Муууоооожжноооооооууууээ@#_?*&NO CARRIER

А я и не писал, что нельзя. Просто типичный ООП код на Си в таком виде и без наследования.

Waterlaz ★★★★★
()
Ответ на: комментарий от Waterlaz

Херня - это IORef и STМ для «поддержки» ООП.

разве тут это кто-то утверждал?

Что IORef для поддержки ООП является херней? Это утверждаю я. Использовать для этого IORef посоветовал кто-то выше по топику. С умным видом, да.

tailgunner ★★★★★
()
Ответ на: комментарий от alienclaster

А modifyIORef чистая? А в myVar значение не изменилось? ... Хм, а что же тогда ты здесь продемонстрировал?

Еще раз прочитай то, что я написал.

Waterlaz ★★★★★
()
Ответ на: комментарий от Waterlaz

ООП без наследования уже не ООП?

Да.

ИМХО мало отличается от того ООП, что практикуют в С++

Бгг. Ну тогда не-ООП языков вообще не существует.

tailgunner ★★★★★
()
Ответ на: комментарий от tailgunner

Бгг. Ну тогда не-ООП языков вообще не существует.

ООП язык - это так же как и функциональный язык, хрен пойми что такое. Просто на одном языке писать принято/удобно в ООП стиле, на другом в функциональном. Так вот на Си (ИМХО) принято писать в ООП стиле.

Waterlaz ★★★★★
()
Ответ на: комментарий от Waterlaz

Мы здесь не обсуждаем чистоту 3,2301 функций хацкеле, а говорим о чистоте фп (а не отдельных функций) и совместимости этого подхода с изменяемыми структурами данных. А совместиться они могут только на горизонте событий, никак не раньше, при условии что грибный самосбор - читерство.

alienclaster ★★★
()
Ответ на: комментарий от alienclaster

Мы здесь не обсуждаем чистоту 3,2301 функций хацкеле, а говорим о чистоте фп (а не отдельных функций) и совместимости этого подхода с изменяемыми структурами данных. А совместиться они могут только на горизонте событий, никак не раньше, при условии что грибный самосбор - читерство.

Ну... ты спросил в чем разница, я ответил. В том, что функции, которые описывают как изменяются объекты, определяются чисто.

Waterlaz ★★★★★
()
Ответ на: комментарий от Waterlaz

Ну... ты спросил в чем разница, я ответил

Ничего подобного я не спрашивал

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

О да, ломающие новости

alienclaster ★★★
()
Ответ на: комментарий от tailgunner

IORef и STM для мутабельности же.

тут 2 наезда было, (1) нет ооп, (2) нет состояний.

qnikst ★★★★★
()
Ответ на: комментарий от alienclaster

1). IORef ничем, STM ­— тем, что это транзакционная память с возможностями синхронизации, блокировки, откатов.

2). не чистые, т.е. ST монада

3). если не поленюсь — попробую сделать.

qnikst ★★★★★
()
Ответ на: комментарий от alienclaster

состояние же в БД меняется, при чём тут иммутабельность структур в программе? ORM-ы для haskell вполне есть. аналогий я не понял.

qnikst ★★★★★
()
Ответ на: комментарий от qnikst

состояние же в БД меняется, при чём тут иммутабельность структур в программе?

Состояние меняется в sql-таблицах. ORM - представление таблиц с помощью языка программирования + связанные с таблицами операции + связанные операции уже с языковыми структурами (которые одновременно и являются таблицами). Чтобы абстракция протекала минимально, мы *добавляем* некоторые возможности к таблицам, а не *отнимаем*.

Кроме того, на уровне View - происходит обработка данных. Как только мы с ними поработали - они становятся не «данными для обрабоки», а «данными для записи». Утиная типизация во все поля.

ORM-ы для haskell вполне есть.

В аббревиатуре ORM есть буквы О и M. Понимая под объектами такие, у которых есть изменяемые состояния, я хотел узнать каким образом это реализуется в haskell или чем замещается?

аналогий я не понял.

Дырявые абстракции - не аналогия.

alienclaster ★★★
()
Ответ на: комментарий от tailgunner

ООП без наследования уже не ООП?

Да.

Выходит, Smalltalk и CLOS - недообъектные недосистемки.

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

Примерно то же самое и с CLOS

yoghurt ★★★★★
()
Ответ на: комментарий от yoghurt

ну да.. особенно если сразу рассматривать не ephemerical, а persistent структуры данных :)

qnikst ★★★★★
()
Ответ на: комментарий от alienclaster

В аббревиатуре ORM есть буквы О и M. Понимая под объектами такие, у которых есть изменяемые состояния, я хотел узнать каким образом это реализуется в haskell или чем замещается?

аааа.... изменяемость интересна только для скорости/экономии места и расшаривания объектов, т.е. в одном месте foo+=1, то в другом foo тоже инкрементируется, для последнего есть STM,IO,ST..

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

let newObject = update oldObject

нужно, чтобы это было изменение и в ORM, то тогда это скорее всего внутри монады и будет new <- orm update ... old.

Дырявые абстракции - не аналогия.

базворды базвордами, но лучше говорите конкретно.

qnikst ★★★★★
()
Ответ на: комментарий от yoghurt

В CLOS наследование есть, но оно реализуется на самом языке, а не является его фичей, я вот о чём

О лиспе сложно так сказать - ввиду отсутствия семантики, его формы могут означать что угодно. Вот и было принято соглашение в определенных местах придавать им смысл наследования. С таким же успехом можно сказать, что в лиспе - ооп встроенное... И даже уровнем ниже, чем объекты.

alienclaster ★★★
()
Ответ на: комментарий от alienclaster

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

В какой-то степени - да, но это все-же не отменяет того факта, что defclass - макрос.

SBCL:

(macroexpand '(defclass foo () ()))

(PROGN
 (EVAL-WHEN (:COMPILE-TOPLEVEL)
   (SB-PCL::%COMPILER-DEFCLASS 'FOO 'NIL 'NIL 'NIL))
 (EVAL-WHEN (:LOAD-TOPLEVEL :EXECUTE)
   (LET ()
     (SB-PCL::LOAD-DEFCLASS 'FOO 'STANDARD-CLASS 'NIL (LIST)
                            (LIST :DIRECT-DEFAULT-INITARGS NIL) 'NIL 'NIL 'NIL
                            (SB-C:SOURCE-LOCATION) 'NIL))))

CLISP:

(macroexpand '(defclass foo () ()))

(LET NIL
 (EVAL-WHEN (COMPILE LOAD EVAL)
  (LET* ((#:G3232 CLOS::<STANDARD-CLASS>))
   (APPLY #'ENSURE-CLASS 'FOO :DIRECT-SUPERCLASSES (LIST) :DIRECT-SLOTS (LIST)
    :METACLASS #:G3232
    (APPEND '(:FIXED-SLOT-LOCATIONS NIL)
     (LIST :DIRECT-DEFAULT-INITARGS NIL :DOCUMENTATION NIL :GENERIC-ACCESSORS
      'T)))))
 (FIND-CLASS 'FOO))

Вот это уже чем-то напоминает референсную реализацию из AMOP

yoghurt ★★★★★
()
Ответ на: комментарий от qnikst

аааа.... изменяемость интересна только для скорости/экономии места и расшаривания объектов

Меня производительность интересует в _последнюю_ очередь.

let newObject = update oldObject

И сколько ты готов героически плодить новых имен в программе, которая предполагает частую модификацию структуры данных? И в чем смысл, объяснишь?

Тема как-то исхудала, новый вброс: мое мнение, что из чистого функционального языка (это естественно будет не хаскель, он слишком уродлив) может получиться хороший инструмент для легкопараллелящихся алгоритмов, то есть он станет числодробилкой (заменит С). Но, конечно же это потребует существенного роста производительности вычислительных систем.

Дырявые абстракции - не аналогия.

базворды базвордами, но лучше говорите конкретно.

Не позорься

alienclaster ★★★
()
Ответ на: комментарий от yoghurt

В какой-то степени - да, но это все-же не отменяет того факта, что defclass - макрос.

А кто говорил об отменяет? defclass мог бы как реализовывать наследование, так и нет - всем плевать^W^W семантика достаточно гибка.

alienclaster ★★★
()

Кстати,

Перемещено hibou из Development

имхо зря. В треде обсуждаются общие вопросы, не имеющие отношения к вебу. Казалось бы, какая разница? Просто многие могут быть подписаны на Development, но при этом обходить Web-development стороной, либо не заглядывать в трекер, и т.о. пропустить (имхо) интересный тредик

yoghurt ★★★★★
()
Ответ на: комментарий от yoghurt

Изначально топик о вебдеве. Хотя на лоре все топики с упоминанием кивордов lisp и haskell можно было бы автоматически переносить в development ;)

alienclaster ★★★
()
Ответ на: комментарий от alienclaster

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

garmonbozia
() автор топика
Ответ на: комментарий от garmonbozia

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

Итак, garmonbozia:
1) Берешь любой ЯП, который знаешь.
2*) Пишешь простую функцию, которая при отсутствии POST-запроса выводит HTML-предствление формы. Если же есть POST-запрос к странице, осуществляешь валидацию данных, и в случае успеха вызываешь внешную программу на Haskell`e и береше из нее данные и аяксом посылаешь ответ клиенту.
3) То, что fcgiwrap не работает, это отдельный вопрос, который решается изучением логов.

* Если тебе нужно из Haskell`я прочитать ответ форкнутого процесса, то делается так:

import System.Process
...
output <- readProcess "/путь/к/программе" [] []

beka
()
Ответ на: комментарий от yoghurt

ООП без наследования уже не ООП?

Да

Выходит, Smalltalk и CLOS - недообъектные недосистемки.

Выходит, у тебя какие-то свои Smalltalk и CLOS, потому что в обоих есть наследование.

Ведь в синтаксисе первого нет специальных конструкций для наследования

Примерно то же самое и с CLOS

Итак, в обоих языках есть поддержка наследования (да, именно в языках - думаю, про Smalltalk ты и сам знаешь, про CLOS могу процитировать). То, что для нее не требуются специальные синтаксические формы - всего лишь особенности этих языков.

И, зная, что кто-то обязательно доебется до столба, я написал «конструкции Си» - не обязательно специальный синтаксис.

tailgunner ★★★★★
()
Ответ на: комментарий от yoghurt

Выходит, Smalltalk и CLOS - недообъектные недосистемки.

За CLOS не ручаюсь, а вот в смаллтолковском Blue Book ты термина «объектно-ориентированный» не встретишь. Смаллтолк родился несколько раньше этого термина, по крайней мере его повального употребления в дискурсе.

Кроме того, ты задаешь некорректные вопросы, да еще и пытаешься на них ответить.

Определись, сначала, что ты понимаешь под наследованием. Грубо говоря, наследование ЧЕГО именно ты имеешь в виду.

Macil ★★★★★
()
Ответ на: комментарий от tailgunner

Так и в Си есть поддержка наследования:

struct Foo {
    Bar parent;

    /* Foo's data */
    /* ... */
    /* ... */
};

Выглядит, правда, как агрегация, и ещё этот пример не иллюстрирует работу с поздней диспетчеризацией, но ведь есть же!

yoghurt ★★★★★
()
Ответ на: комментарий от yoghurt

Перестань прикидываться шлангом. Это было бы подержкой наследования, если бы преобразование Foo* в Bar* выполнялось языком автоматически.

tailgunner ★★★★★
()
Ответ на: комментарий от yoghurt

Структуры и поведения

Ну вот ты и сам ответил на свой вопрос. Ежику же ясно, что поведение наследуется *всегда*, иначе какого же хрена тогда все затевать?

Со структурой несколько сложнее. Если понимать под структурой физическую структуру, то в C это правило может и не соблюдаться. Ассемблер, он и в африке ассемблер, что с него взять?

А если понимать под структурой интерфейс, то все намного интереснее. Во-первых, интерфейс может существовать и в рантайме, ИЧХ во многих ипостасях, начиная от множества сообщений, которые принимает объект, заканчивая определением на IDL. И правила наследования ты можешь задавать как тебе будет угодно. Во-вторых, в том же С есть прекрасные механизмы определения интерфейсоов. Да, там в упор нет возможности задания интерфейса через иерархию наследования, но если вдуматься, то нахрен оно нужно? Все-равно в менйстрим-ООП это наследование вылилось в банальности вроде переопределения методов.

Так что можно сказать что и структура наследуется всегда. Поэтому, говорить что «наследования нет», вместо «наследование осуществляется не по правилам мейнстрим-ООП» не совсем корректно.

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

Из-за этого же существуют всякие велосипеды на С, когда как это не парадоксально, методологическая сложность предложенных решений намного ниже, чем решений на том же C++.

Macil ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.