Fork me on GitHub
#clojure-russia
<
2016-03-31
>
sasha00:03:49

@batsuev: не подскажешь, где можно подробнее прочесть?

konukhov02:03:25

я как-то спрашивал про библиотеку для конфига – нашел наконец практически идеальный вариант: https://github.com/AvisoNovate/config можно писать в .edn или .yaml; читать из ENV; выставлять разные профайлы по приоритету (типа :profiles [:default :dev :local]), и он грамотно все замерджит, а отсутствующие файлы проигнорирует (например, local.yaml какой-нибудь) + конфиги валидируются schema и еще есть фишки для работы с component. осталось это соединить с фетчилкой конфига из консула simple_smile надеюсь, кому-нибудь тоже пригодится! хотя сейчас понимаю, что это самому написать не проблема.

konukhov02:03:58

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

rmuslimov04:03:42

в последние пару дней смотрел на cider и как бы его заточить по удобнее

rmuslimov04:03:06

нашел по-моему пару хороших решений которые не популярны в инете

rmuslimov04:03:35

1. для clj мега удобно пользоваться биндингом C-c C-x и приконнектить к нему рестарт system-map (если конечно вы пользуетесь component) - что то вроде (setq cider-refresh-before-fn "user/stop-system" cider-refresh-after-fn "user/start-system")

rmuslimov04:03:03

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

rmuslimov04:03:35

сидр умеет из коробки rhino,weasel, и node а вот фигвилл не умеет

rmuslimov04:03:50

но это легко добавляется если сделать что то вроде

rmuslimov04:03:57

(setq cider-cljs-lein-repl "(do (require 'user) (user/start-cljs) (user/repl-cljs))”)

rmuslimov04:03:54

где методы выглядят примерно так

rmuslimov04:03:32

Не знаю, может быть это тривиально было для всех кто пользуется cider+clojure каждый день

rmuslimov05:03:03

но мне бы это помогло в начале пути

batsuev05:03:57

@sasha а что именно подробнее? пишешь в yesql

-- name: callSmth
CALL procName(:arg)
и все, работаешь как и с остальными запросами

fxposter05:03:17

Эрик на курсере (или удасити, или где-то еще) вел курс о FP с Хаскелем, как базовым языком. можно поискать его.

sasha10:03:21

@batsuev я про multiple result sets

batsuev10:03:39

@sasha что-то типа

(defn call-proc [conn param]
  (log/info (str "connection " conn))
  (with-open [stmt (.prepareCall (:connection conn) "{call proc_name(?)}")]
    (.setString stmt 1 param)
    (loop [res (.execute stmt)
           results []]
      (if res
        (do
          (let [rs (.getResultSet stmt)
                results (conj results (doall (jdbc/result-set-seq rs)))]
            (.close rs)
            (recur (.getMoreResults stmt)
                   results)))
        results))))

batsuev11:03:29

нефункциональненько конечно но работает вполне норм simple_smile

sasha11:03:51

@batsuev: а что-то типа http://ado.net не попадалоись на глаза случайно вам?

batsuev11:03:28

у нас устоялось yesql + в таких кейсах как выше чистый jdbc

batsuev11:03:01

если хочется orm и подобного то тут хз simple_smile

sasha11:03:57

это не орм

sasha11:03:01

орм совсем не хочется

sasha11:03:27

фактически это то же самое что и yesql, только там можно нормально работать с хранимыми процедурами и т.д.

asolovyov12:03:45

user> (type (:quantity z))
java.lang.Integer
user> (type (:cancelled_quantity z))
java.lang.Integer
user> (type (- (:quantity z) (:cancelled_quantity z)))
java.lang.Long
есть идеи, что происходит?

niwinz12:03:27

Is expected

niwinz12:03:40

clojure promotes to long automatically if it needs so

niwinz12:03:55

in fact the default integer type in clojure is Long

asolovyov12:03:35

yeah but docs say:

clojure.core/-
([x] [x y] [x y & more])
  If no ys are supplied, returns the negation of x, else subtracts
  the ys from x and returns the result. Does not auto-promote
  longs, will throw on overflow. See also: -'

asolovyov12:03:40

does not 😮

niwinz12:03:55

it does not promote longs...

niwinz12:03:59

but int yes

asolovyov12:03:02

а, блин, понял

asolovyov12:03:08

ну окей, буду кастовать

niwinz12:03:24

Long is the default integer type

niwinz12:03:32

- does not promote to bigInt

asolovyov12:03:09

не сразу понял фразу, честно говоря

asolovyov12:03:16

еще подумал, что она как-то странно сформулирована simple_smile

niwinz12:03:13

user=> (type (+ Integer/MAX_VALUE 1))
java.lang.Long
user=> (type (+ Long/MAX_VALUE 1))
ArithmeticException integer overflow  clojure.lang.Numbers.throwIntOverflow (Numbers.java:1501)

asolovyov12:03:07

та проще:

user> (type (+ 1 1))
java.lang.Long

niwinz12:03:02

yes but, 1 is already literal for long

niwinz12:03:24

so that example does not shows any promote op

asolovyov12:03:30

user> (type (+ (int 1) (int 1)))
java.lang.Long

asolovyov12:03:04

надо об этом знать, честно говоря, немножко подло оно меня словило simple_smile

andfadeev13:03:52

задублирую сюда тоже, может кто быстрее подскажет hi everyone! I have this problem with compojure and multiple middlewares I use components

:site-handler (handler-component (:site-app config))
:http (jetty-server (:http config))
:site-endpoint (endpoint-component site-endpoint)
:api-endpoint (endpoint-component api-endpoint)
with deps
:http [:site-handler]
:site-handler [:site-endpoint :webhook-endpoint :api-endpoint]
:site-endpoint {:db :db
                :input-chan :notification-worker-in-channel}
:api-endpoint {:db :db
               :channel :notification-worker-in-channel}
in site routes I have something like this:
(defn site-endpoint [{{db :spec} :db input-chan :input-chan}]
  (-> (routes
       ;; more routes
       (POST "/send-message/:channel-id" [channel-id :<< as-int :as request]
         (message-route/send-message db input-chan channel-id request))
       (resources "/"))
      (wrap-routes (fn [handler]
                     (-> handler
                         (wrap-access-rules {:rules rules :on-error on-error})
                         (buddy-middleware/wrap-authorization backend)
                         (buddy-middleware/wrap-authentication backend)
                         (defaults/wrap-defaults defaults/site-defaults)
                         )))))
and in api
(defn api-endpoint [{{db :spec} :db channel :channel}]
  (api
   {:swagger {:ui "/api-docs"
              :spec "/swagger.json"
              :data {:info {:title "PushToTelegram Public API"}}
              }}
   (context "/api" []
     (GET "/send/channelMessage" []
       :return {:channel-id s/Int
                :recipients-count s/Int}
       :query [message ApiChannelMessage]
       (api-route/send-channel-message db channel message))
     )))
and then in handler component they are combined with (routes api-routes site-routes) in post route I have ring antiforgery exception, because of api-middleware, and the only way I can fix it is to wrap api routes with some context, e.x (context "/my-api" [] (api ;; etc)) but then I have swaggers docs broken with wrong api urls What is the right way to split api and site routes in web app?

niquola13:03:33

Do not use defaults stacks, build them one by one

andfadeev14:03:06

да тут не в этом же дело вроде

az17:03:18

народ, какой там аналог https://ocaml.org/learn/tutorials/99problems.html для кложуры?

az17:03:13

нужны просто задачки

az17:03:10

во, первое, не мог вспомнить @rmuslimov: спасибо!

fxposter17:03:31

может кому-то будет интересно - немножко про устройство структур данных в кложурке - http://fxposter.github.io/persistent-data-structures-presentation/

fxposter17:03:52

и не только в кложурке, местами

andmed17:03:00

кстати по 4clojure -- я могу смотреть решения на кого я "подписался" или надо чтобы человек меня тоже зафрендил?

fxposter17:03:29

https://www.youtube.com/watch?v=siUvJN4FoVY&amp;feature=youtu.be ссылка на сам доклад (он немного фейловый, но тем не менее)

sasha18:03:07

господа, а compojure или ring из коробки не умеет query-params нормально в json отобразить?

sasha18:03:35

т.е. чтобы bool рассматривались и numbers

kxepal18:03:26

кажется, это проще закодить т.к. сам по себе query-params не типизированы и все там строки

sasha18:03:22

да проще, я так и сделал, странно очень что этого нет

andfadeev19:03:32

@sasha, а это тебе для апи? я вот вожусь тут с compojure-api

andfadeev19:03:24

@andmed: можешь смотреть кого зафрендил

sasha19:03:10

да ну его, там непонятное раскрытие макросов и куча куда, у меня все гораздо лаконичнее вышло

andfadeev19:03:33

ну зато есть валидация схемы

sasha19:03:55

ну валидация схемы есть у схемы призматика и bouncer и еще куча всего

andfadeev19:03:04

ну там призматик и юзается

sasha19:03:31

в чем заслуга этого апи? simple_smile

andfadeev19:03:37

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

andfadeev19:03:54

ну + генерится в сваггер документация

sasha19:03:24

без сваггера это в 5 строк кода укладывается