Comments 52
Если вам нужно написать какую-то фичу, вы не обязаны смотреть какие зависимости уже используются в проекте. Вы не ограничены ими. Вы используете то, что вам нужно.
Это, конечно, удобно если в одном файле можно использовать некий libjs 1.x, а в соседнем libjs 2.x — но исключительно на стадии прототипирования. В долгосрочной поддержке это только головная боль.
Линтер это хорошо, но по факту далеко не во всех проектах он есть.
Еще один момент это аудит кода. В npm или yarn очень легко получить ответ на вопросы:
- Какие пакеты являются моими прямыми / транзитивными зависимостями?
- Какие из моих зависимостей устарели и нуждаются в обновлении?
- Зачем нужна эта конкретная транзитивная зависимость? (
yarn why
) - Какие лицензии у моих зависимостей?
Для этого не нужно парсить никакой код, загрузил один json-файл и всё. Работает быстро в проекте любого размера.
А еще бывают devDependencies и peerDependencies, которые не присутствуют в рантайме — как это в Deno реализовано я не знаю, поэтому ничего утверждать не стану, кроме того, что это очень нужная на практике штука.
Deno как и NodeJs — это среда исполнения. Для NodeJs существует отдельная утилита — пакетный менеджер — npm. Она берет на себя роль управления всеми зависимостями, не только для рантайма, а в целом по проекту, их обновлением и всё в таком духе.
Deno не поставляется со своим аналогом npm. И хотя возможно устанавливать отдельные утилиты в директорию проекта, это сложно назвать полноценным пакетным менеджером.
Но, народные умельци уже написали несколько утилит:
- velociraptor — An alternative to npm scripts for Deno
- denox — Script runner and workspace configuration for Deno
- dpm — deno package manager
- dem — A module version manager for Deno.
- Trex — package management like npm for deno
Поймите правильно, мне нравится Deno. TypeScript это клёво, настройки безопасности это клёво. Но вот эта штука с импортами — не пришей нигде рукав.
Одно из преимуществ Deno, которые мы тут обсуждаем — отказ от npm, package.json
Ну, не совсем.
npm — менеджер пакетов. Ряд озвученных вами вопросов, действительно стоит остро, и утилиты, для анализа всей кодовой базы или какой-то части и вывода статистики по всем зависимостям по модульно действительно не хватает. И, если будет потребность, то такие появятся. Но текущие реализации, я думаю, жертвы привычки.
package.json — Можно назвать глобальным конфигом для всего проекта. В нем и название, и версия, и зависимости, и инструкции по сборке, и имена авторов и все все все. Deno предлагает перенести список зависимостей из глобального реестра непосредственно в кодовую базу. Но, это не означает, полный отказ от глобального файла с конфигурацией проекта. Вполне может существовать какой-то package.json с названием, списком авторов, какими-то ссылками на документацию, репозиторий, лицензию, списком точек входа для запуска тестов или самого приложения.
Сейчас Deno и его сообщество в зародыше. Лучшие практики ещё не выработаны, инструменты не написаны.
Но вот эта штука с импортами — не пришей нигде рукав.
Может и так. Лично я пока не вижу тут проблем. Но, справедливости ради, я и не искал особо. Мне видится тут больше гибкости. Вы пишите что-то простое? Вам не нужно заворачиваться с установкой зависимостей локально. Просто пишите код. Работаете над чем то побольше? Создайте свой реестр зависимостей. Со временем появятся инструменты для их анализа.
А зачем что-то разрешать, что потом ещё нужно запрещать отдельными линтерами?
Весь JavaScript так работает :)
У JS тяжёлое прошлое. Меня больше удивляет, когда сейчас разрабатывают новый язык позволяющий писать и так и эдак и тут же к нему прикладывают линтер, который не позволяет писать эдак, и форматтер, который форматирует именно так. Привет, Go.
А я вот понимаю такой подход. Сделать гибкий язык который может работать как угодно и предоставить инструмент, чтобы каждая команда могла "донастроить" его для своих нужд. Мне больше нравится когда всё строго, когда имена файлов и структура директорий жестко регламентирована интерпретатором. Но, как ты не крути, это нужно не всегда и часто в разном виде.
Да никто не занимается такой ерундой, как форканье гоформатера с целью "донастройки" для "своих нужд" (будто в них есть что-то особенное). Никому такой бардак не нужен.
Я имел в виде существование линтера в целом. то о чем вы писали
Меня больше удивляет, когда сейчас разрабатывают новый язык позволяющий писать и так и эдак и тут же к нему прикладывают линтер, который не позволяет писать эдак
Есть, язык, который может работать как угодно. И есть инструмент, который можно настроить так, чтобы он ограничивал разработчика и принуждал его писать только эдак.
А вот настроить эти ограничения каждый может так как нужно именно ему. Что гораздо гибче.
Идея в том, чтобы отказаться от глобального списка зависимостей на весь проект. Чтобы вместо одного большого package.json у вас в каждом вашем модуле/файле был свой, независимый список зависимостей. Я вижу в этом несколько плюсов.
В этом просто нет ни одного плюса, если у вас одно приложение — у него должен быть список зависимостей. В противном случае появляется хаос в месте, в котором, казалось, наступить на грабли нельзя, но люди (тот же Go) регулярно умудряются.
Но для такого подхода нужна возможность описывать зависимости для каждого модуля. Название, версию и откуда эту зависимость взять. Как следствие — import с указанием URL.
Но это могут быть десятки и сотни зависимостей!!! Всё вручную прописывать?!
Представим ситуацию, что какой-то сервис деплоится автоматом в полночь. Использует Deno. Итак, проект используется import по URL. Владелец этого URL ровно в полночь подменяет контент по этому URL на вердоносный. В момент деплоя пакеты скачиваются заново, качается вредоносная версия. На бой также попадает пакет с плохим кодом. Через. 5 минут, владелец URL меняет код обратно на хороший.
На каком этапе Deno защитит от такой атаки?
Deno, как и Node, умеет создавать lock.json
. В нем будет список ссылок и хэш. Если при восстановлении зависимостей, хэш измененного файла не будет соответствовать сохраненному — Deno выдаст ошибку "Subresource integrity check failed"
https://deno.land/manual/linking_to_external_code/integrity_checking
Если подытожить, deno создан для криворуких copy-paste девелоперов. Нашёл на стаковерфлоу кусок кода, скопировал себе в проект и дальше пошёл. А то, что в 10 файлах будет 10 импортов разных версий одной либы — да кого это волнует?
Да уж, я как-то думал, что go достаточно ясно показал всем, как бывает плохо, когда создатели языка делают кривой менеджер зависимостей. Ан нет, на те же грабли ступают, только другого цвета.
Единственный плюс deno — возможность явно указывать разрешения при запуске скрипта.
Но для такого подхода нужна возможность описывать зависимости для каждого модуля. Название, версию и откуда эту зависимость взять. Как следствие — import с указанием URL. И это даже не придумка Deno. Это часть стандарта. Просто все привыкли работать так как привыкли. Но это не единственный путь.
Возьмем maven. Вот хочу я скачать новую зависимость: указываю название (в двух частях), версию, и откуда скачать (активирую нужный репозиторий — вот вам и import maps, кстати).
Если я клепаю код сам по себе — так с центрального репозитория и буду качать. Если я решу создать свой артефакт, то опубликовать его на любом из репозиториев — вопрос одного вечера, чтоб разобраться как правильно оформлять пакет. Если я устроюсь в секьюрную контору, то девопсы заменят центральный репозиторий на свой, внутренний, содержащий только проверенные или кэшированные библиотеки, из них и буду выбирать.
Мне такой подход кажется максимально логичным, так как позволяет как делать что угодно, так и разделять обязанности и ответственности. При скачивании же модулей по URL у нас получается какая-то каша в которой зависимости качаются как попало, откуда попало, по совету левых чуваков со stackoverflow, и никто на это не сможет повлиять без дополнительных усилий. Соответственно, вопрос: а нафига такое надо, и в чем польза такого подхода.
У меня ушло много времени, чтоб заставить npm работать в изолированной от интернета среде.
Нет, справедливости ради — заставить сам npm это одна переменная окружения или один параметр к нему. Но вот подготовить зеркало репозиториев NPM и так чтоб он был не кеширующим самостоятельно бегающим в интернет, а нормальным зеркалом с ручным управлением — это была боль.
А если разработчику на той же ноде с тем же NPM задать вопрос «как с этим работать без интернета?» у них картина мироздания рушится.
И это глобальная проблема современного менеджмента зависимостей. Тот же мавен с одной стороны да, легко раздаётся любым веб сервером из списка файлов. С другой стороны сформировать этот список файлов по списку зависимостей, так чтоб собрать зависимости зависимостей задача уже не такая простая.
Это какая-то глобальная тенденция современной разработки. Системы управления зависимостями не представляют современный мир без интернета.
А если нужен новый модуль, тогда да, или интернет, или настроенное зеркало. Но так работают любые репозитории, JS из общей массы по-моему не выделяется.
Откуда информация что он начинает выстреливать? Пока Deno просто хайпит на том что "это как года только лучше". Интерес к нему у большинства (имхо) скорее академический, интересно посмотреть что да как.
Выстреливать он начнет (если начнет) когда выйдет полноценный релиз и на нем будут делать коммерческие проекты.
А вообще конкуренция это хорошо
Не понимаю, почему npm надо избегать…
Да, npm — это очень удобный инструмент. Но, я вижу некоторое недопонимание у сообщества. Хотя, не исключено, что ошибаюсь именно я.
Deno — это "переосмысление" Node. Именно Node. Не смешивайте с npm. Node — это среда исполнения, npm — менеджер пакетов и появился он примерно через пол года после первых выпусков Node. Сейчас они поставляются вместе из-за исторической необходимости. Ну, и вы сами видите реакцию сообщества на идею работы среды исполнения без комплектного менеджера пакетов.
Deno — именно прокачанная среда исполнения. Разница в том, что во времена создания модульной системы Node в языке не было ничего. А в Deno просто реализованы все современные возможности языка. Даже больше чем сейчас поддерживается в Node или в браузерах. Даже компиляторы по типу babel или typescript ограничены возможностями той среды в которой будет запускаться итоговый код.
Аналогия: использование функции require
без необходимости предварительно вызывать установку пакета. Просто пишете название пакета, версию если нужно, или ссылку на другой источник. А резолвер модулей в Node сам найдет и кэширует необходимые пакеты. При таком раскладе, вам не нужен npm для установки или удаления пакетов.
Поймите, никто не говорит, что npm это зло и не призывает отказываться от него. Просто автор, сделал в свою новую среду исполнения с улучшенным резолвером модулей, что сделало не обязательным шаг по предварительной инициализации проекта и установке пакетов. Но никто не говорит что не появятся инструменты для анализа кода и сложного аудита всех зависимостей, или для запуска пресетов команд Deno и для всего остального что сегодня умеет npm.
Deno ж и с .js спокойно работает, разве нет?:D
для go надо мозг свой переделывать.
Я, как и многие, всё таки не оценил новую систему с модулями.
Вот например мне понадобились 5 часто используемых пакетов. В npm я прописал их имена, которые я помню наизусть, попил чаю, и пакеты уже ждут меня. В deno я должен помнить URL этих пакетов? И из проекта в проект либо руками копировать эти URL, либо сидеть и тратить n времени на повторный поиск этих URL?
Как обычно работаю я. Я просто пишу код. Когда использую какую-то функцию — моя IDE сама вставляет import. Если бы я работал с Deno, то этого было бы достаточно. Но работая с node, моя IDE должна ещё проверить установлен ли нужный пакет, и если нет — установить.
Я думаю, что большинство подобных вопросов — это дело привычки и отсутствия инструментов.
5 претензий к Deno