Функции Firebase с рабочими пространствами Yarn

Мы начинаем внедрять установку monorepo с использованием рабочих пространств yarn, и мы хотели бы, чтобы наши функции firebase были внутри нее. Структура репо выглядит примерно так:

repo
    node_modules <- all dependencies
    packages
        core
        commom
        functions <- firebase functions

Итак, у меня есть 2 проблемы с этой настройкой:

  1. Зависимости функций не находятся в той же папке, что и файл входа из функций.
  2. Функции зависят от других пакетов, таких как core и commom, которые находятся в репо, поэтому пряжите символические ссылки от node_modules к пакетам в репо.

Могу ли я справиться с этим?


person Thiago Nascimento    schedule 21.04.2019    source источник


Ответы (3)


Решение, которое я нашел для этого, - это опция Yarn nohoist в вашем корневом package.json файле.

По умолчанию Yarn поднимает зависимости в корневой каталог, чтобы они могли совместно использоваться вашими пакетами. К сожалению, с Firebase это не сработает. Это означает, что вам нужно указать Yarn не поднимать зависимости, используемые вашими функциями Firebase.

Документация для nohoist далеко не идеальна, но вот официальная запись в блоге об этом здесь: https://yarnpkg.com/blog/2018/02/15/nohoist/

Вероятно, вам нужно что-то вроде этого:

{
  "workspaces": {
    "packages": [
      "packages/*"
    ],
    "nohoist": [
      "functions/core",
      "functions/common",
      "functions/**"
    ]
  }
}

Имейте в виду, что здесь используется поле name, используемое в package.json файлах каждого пакета рабочей области. Итак, в этом примере предполагается, что в каталоге functions есть package.json с «функциями», как это name.

functions/** сообщает yarn не поднимать ни одну из зависимостей, указанных в packages/functions/package.json. Однако это не работает для ваших общих пакетов пряжи, поэтому functions/core и functions/common нужно указывать отдельно.

Вам также необходимо включить свои рабочие области в качестве зависимостей в ваш functions проект, поэтому добавьте их в свой package.json:

{
  "name": "functions",
  "dependencies": {
    "core": "*",
    "common": "*",
  }
}

После того, как вы все это добавили, удалите каталог packages/functions/node_modules и запустите yarn install. После этого вы должны увидеть все свои зависимости, включенные в packages/functions/node_modules (не символические ссылки).

person twiz    schedule 04.01.2020
comment
Я пробовал этот подход, но не смог развернуть функции. Процесс firebase не может установить зависимости (поскольку они локальные) - person Thiago Nascimento; 05.01.2020
comment
@ThiagoNascimento хммм. Я сделал это некоторое время назад и забыл опубликовать этот ответ. Возможно, я забываю еще об одном шаге в этом процессе. Я взгляну. Спасибо, что дал мне знать. Обновлю, если что-нибудь разберусь. - person twiz; 05.01.2020
comment
Я создал репозиторий, чтобы продемонстрировать использование этого метода, однако у меня, похоже, возникают проблемы при развертывании функций в Firebase, хотя аспект веб-хостинга работает нормально. Любая помощь будет принята с благодарностью - я добавил ошибки в файл Readme github.com/cjmyles/firebase- монорепо - person Craig Myles; 03.04.2020
comment
Мне также не удалось заставить это работать с облачными функциями. Хотя node_modules содержит пакет общего ядра, при развертывании облачных функций node_modules не используется. Итак, мне осталось создать упакованную версию моей общей зависимости и затем обновить packages.json. - person R. Wright; 06.05.2020

При использовании Пряжа 2 node_modules не извлекаются и не помещаются в соответствующий functions каталог (как это было бы в случае вызова npm i в каталоге functions). Поэтому при вызове firebase deploy --project default --only function папка node_modules отсутствует, и firebase пожалуется на это и прервет процесс развертывания со следующей ошибкой (или аналогичной):

Error parsing triggers: Cannot find module [...]
Try running "npm install" in your functions directory before deploying.

На данный момент есть две проблемы с github, которые отслеживают эту проблему:

В двух вышеупомянутых проблемах пользователи firebase предлагают несколько умных обходных путей, например использование webpack для создания сборки, содержащей все локальные пакеты в выпуске, или использование rsync или других инструментов, которые перенаправляют пакеты перед выпуском.

Другое решение - не поднимать пакеты проекта, если это возможно. Вы можете сделать это, добавив следующие две директивы в ваш .yarnrc.yml файл.

# yarnrc.yml

# disables yarn's plugnplay style and uses node_modules instead
nodeLinker: node-modules
# makes sure the node_modules are not hoisted to the (monorepo) project root
nmHoistingLimits: "dependencies"

Две приведенные выше директивы объясняются в документации по конфигурации yarnrc следующим образом:

nmHoistingLimits Определяет наивысшую точку, откуда можно поднять пакеты. Одно из рабочих пространств (не поднимать пакеты за пределы рабочего пространства, которое от них зависит), зависимостей (пакеты не поднимаются за пределы прямых зависимостей для каждого рабочего пространства) или нет (по умолчанию пакеты поднимаются в максимально возможной степени). Этот параметр можно изменить для каждой рабочей области с помощью поля installConfig.hoistingLimits.

nodeLinker Определяет, какой компоновщик следует использовать для установки пакетов Node (полезно для включения подключаемого модуля node-modules), один из: pnp, node-modules.

person B12Toaster    schedule 06.05.2021

Я не уверен, что правильно понимаю вопрос, но я мог бы дать вам свои два цента на рабочие области пряжи, основываясь на том, что я понял из вашего вопроса и из моего опыта его использования.

Рабочие области Yarn объединяют все ваши зависимости в node_modules, присутствующие в корне проекта, а также в один package-lock.json, чтобы уменьшить конфликты и позволяют yarn оптимизировать процесс установки, давая ты быстрее yarn install. И еще одно его преимущество: за один проход yarn install можно установить зависимости всех пакетов в рабочей области.

Изменить: я думаю, что по какой-то причине yarn link не вызывается, а вместо этого выполняется только yarn install, который будет искать в реестрах npm и выдает ошибку, указанную в комментарии, поскольку он не может найти упомянутый пакет на реестр npm. Итак, для решения попробуйте создать запись в package.json firebase, например

"dependencies": {
  "a": "file:../dependency-package-name/",
}
person PrivateOmega    schedule 10.06.2019
comment
Я знаю, как работают рабочие области пряжи, и сейчас использую в проекте. Проблема, с которой я сталкиваюсь, заключается в том, что при импорте другого локального пакета из того же проекта yarn заботится о его символической ссылке, поэтому вместо того, чтобы указывать на node_modules, он фактически импортирует из локального пакета. И в этом проблема, функции firebase, похоже, не работают с пакетами с символическими ссылками, которых нет в node_modules - person Thiago Nascimento; 18.06.2019
comment
Теперь вопрос для меня стал более ясным. Да пряжи символические ссылки на пакет в той же рабочей области. Но с какой именно проблемой вы столкнулись? Он должен работать так же, как установленный пакет npm. - person PrivateOmega; 18.06.2019
comment
при развертывании в функции firebase я получаю сообщение об ошибке, что некоторый пакет X (который является локальным) не был найден - person Thiago Nascimento; 19.06.2019
comment
Я предполагаю, что в проекте есть файл yarn.lock, потому что в противном случае облако Google устанавливается с использованием npm, который, как я полагаю, может не выполнять символические ссылки. - person PrivateOmega; 19.06.2019
comment
Да, yarn.lock есть. Облако Google вообще поддерживает пряжу? Может быть, в этом суть - person Thiago Nascimento; 19.06.2019
comment
Да, Google Cloud поддерживает пряжу. Хотя, возможно, мы что-то упускаем. Вы проверяли журналы выполнения команд. Может быть, это прольет свет на то, что происходит под ним, когда вы его развернете. - person PrivateOmega; 19.06.2019
comment
Ошибка следующая: Module @local/XXXX not found in npm registry. Я проверил, что файл yarn.lock находится в корне каталога, а не в папке функций. Может быть, в этом проблема? - person Thiago Nascimento; 19.06.2019
comment
@ThiagoNascimento Я думаю, что у меня проблема, попробуйте решение, которое я упомянул в Edit. - person PrivateOmega; 20.06.2019