clojure-russia 2018-07-15

видно гитхаб не позволяет делать такие запросы

406 всё-таки

@okilimnik Мне кажется проще завести edn-файл и постепенно наполнять данными. Если нужно много данных, посмотри либу test.check, у нее на борту хороший генератор. Он поддерживает в т.ч. генерацию связанных мам.

👍 1

Господа, а как бы вы делали такую вещь: есть у меня некий компонент (не в смысле com.stuartsierra/component) с состоянием. Чтобы его инициализировать, надо сделать три вещи по очереди (к примеру, создать директорию для временных файлов, открыть сокет к Selenium, создать в Selenium экземпляр браузера). Если какая-то из вещей ломается — надо откатить предыдущие. Если все три получились — надо компонент вернуть для вского разнообразного использования. Для деинициализации нужно все эти три вещи в обратном порядке отменить.

Т.е. хочется чего-то типа

(let [a (open-a)]
    (try
        (let [b (open-b a)]
            (try
                (let [c (open-c a b)]
                    (try
                        (do-some-stuff a b c)
                        (finally
                            (close-c c))))
                (finally
                    (close-b b))))
        (finally
            (close-a a))))

Но менее ужасное: do-some-stuff может быть асинхронным, длинным, и вообще хочется в этом месте точку возврата из функции, которая создаёт компонент.

Придумал нечто, но выглядит дико. Неужели лучше ничего не придумать?

(defn open []
    (let [a (open-a)]
        (try
            (let [b (open-b a)]
                (try
                    (let [c (open-c a b)]
                        {:a a :b b :c c})
                    (finally
                        (close {:a a :b b}))))
            (finally
                (close {:a a}))))

(defn close [{:keys [a b c]}]
    (when c
        (close-c c))
    (when b
        (close-b b))
    (when a
        (close-a a)))

;; usage
(let [session (open)]
    (try
        (do-some-stuff session)
        (finally
            (close session))))

@dottedmag two words: "Integ" "rant" 😉

Integrant для "временной директории" как-то уж слишком монструозно.

Кроме того, у меня эти компоненты создаются и удаляются в runtime.

Открыл один, поработал с ним, закрыл, открыл другой...

ну не знаю... imo integrant в самый раз тут

Интересно, как интегрант работает рекурсивно: получится ли создать компонент, в котором внутри делается (ig/init) / (ig/halt!)?

Да, в интегранте не видно глобального состояния никакого, можно попробовать.

можно инитить ключи по отдельности или всю систему целиком

@dottedmag Мне кажется, mount отлично ляжет в задачу, он поддерживает порядок вызова, но там даже проще все, если сделать defstate зависимыми друг от друга, то порядок запуска и остановки учтется автоматически. Плюс он супер простой, буквально пару функций добавить.