Multiple packages from the same repo - root level package.json needed?

Hello, we have one private repository in which we would like to keep the code for all our NPM packages. I’ve read the link below but need more detail:

https://help.github.com/en/packages/using-github-packages-with-your-projects-ecosystem/configuring-npm-for-use-with-github-packages#publishing-multiple-packages-to-the-same-repository

Our repo has sub folders for each package code with it’s own package.json listing the url and directory, as per the docs. I tried not having a package.json at root level but Actions didn’t like that. I’m not sure what to put into the root package.json so it is not seen as a package itself?

1 Like

If you’d like to publish multiple packages to same repository, for package.json of each package, should have same URL in ‘repository’ field. Regarding the directory, you can find more details here.

"repository" : {
    "type" : "git",
    "url": "ssh://git@github.com/OWNER/REPOSITORY.git",
    "directory": "packages/name"
  },

You don’t need root level package.json, when you do publish, specify the folder of the package.json.

npm publish [<folder>]

Please refer to doc here for more details.

Hope it helps!

Hello, appreciate the answer. Clears it up a bit for me but I get errors when I remove the root level package.json. I probably have an error somewhere else in my setup. I’ll post if I find a full solution.

OK, progress. I have an action that publishes my repo to Github Registry successfully if it is a ‘normal’ package structure with all files in the root. So I know my environment works.

However, I want to create a monorepo of packages, each in a subfolder. Therefore, I moved my package files (package.json, index.js & README.md) into a subfolder called ‘scroll-to-top’. See image for file structure:

file-structure.png

I also changed the package.json in that file to include the subfolder directory:

"repository": {
    "type": "git",
    "url": "git+https://github.com/patrickgrey/_component-packages.git",
    "directory": "scroll-to-top/"
  },

Now if I push to git, the same action runs but I get an error:

npm ERR! enoent ENOENT: no such file or directory, open 'package.json'

This is my workflow:

name: Publish to Github Package Registry

on: [push]

jobs:
  build:
    runs-on: ubuntu-latest

    steps:
      - uses: actions/checkout@master
      - uses: actions/setup-node@master
        with:
          node-version: 12
          registry-url: https://npm.pkg.github.com/
          scope: "@patrickgrey"
      - name: Publish to GitHub Packages
        run: |
          npm publish
        env:
          NODE_AUTH_TOKEN: ${{secrets.GITHUB_TOKEN }}

Is what I’m attempting to do possible and can anyone see where I’m going wrong? I’m afraid the actual repo has to be private. Many thanks for any help!!!

1 Like

Hi @patrickgrey ,

As your package is in the subfolder ‘scroll-to-top’, please sepecify it for the command ‘npm publish’.

- name: Publish to GitHub Packages
        run: |
          npm publish scroll-to-top
        env:
          NODE_AUTH_TOKEN: ${{secrets.GITHUB_TOKEN }}

npmpackage.png

1 Like

Hi @weide-zhou ,

my apologies, you did say that previously. Doing this works for one package but if I have multiple packages do I need to add an npm publish command for each  new package? E.g.

name: Publish to Github Package Registry

on: [push]

jobs:
  build:
    runs-on: ubuntu-latest

    steps:
      - uses: actions/checkout@master
      - uses: actions/setup-node@master
        with:
          node-version: 12
          registry-url: https://npm.pkg.github.com/
          scope: "@patrickgrey"
      - name: Publish to GitHub Packages
        run: |
          npm publish scroll-to-top
          npm publish test-package-1
          npm publish test-package-2
        env:
          NODE_AUTH_TOKEN: ${{secrets.GITHUB_TOKEN }}

Is there an automatic way of doing this? Also, I then need to check if each package version has been updated before running this command or it will fail (cannot overwrite existing version). Do you have any advice on that please? Sorry for the ongoing questions…

1 Like

In case this helps others, this works (but it’s very ugly!!!) If anyone has a better approach, I’d love to hear it. Thanks @weide-zhou for your help!

name: Publish to Github Package Registry

on: [push]

jobs:
  build:
    runs-on: ubuntu-latest

    steps:
      - uses: actions/checkout@master
      - uses: actions/setup-node@master
        with:
          node-version: 12
          registry-url: https://npm.pkg.github.com/
          scope: "@patrickgrey"

      - name: Check if scroll-to-top version has been updated
        id: checkScroll
        uses: EndBug/version-check@v1
        with:
          diff-search: true
          file-name: scroll-to-top/package.json
          token: ${{ secrets.GITHUB_TOKEN }}
      - name: Publish scroll-to-top to GitHub Packages
        if: steps.checkScroll.outputs.changed == 'true'
        run: npm publish scroll-to-top
        env:
          NODE_AUTH_TOKEN: ${{secrets.GITHUB_TOKEN }}

      - name: Check if test-package-1 version has been updated
        id: checkTest1
        uses: EndBug/version-check@v1
        with:
          diff-search: true
          file-name: test-package-1/package.json
          token: ${{ secrets.GITHUB_TOKEN }}
      - name: Publish test-package-1 to GitHub Packages
        if: steps.checkTest1.outputs.changed == 'true'
        run: npm publish test-package-1
        env:
          NODE_AUTH_TOKEN: ${{secrets.GITHUB_TOKEN }}

      - name: Check if test-package-2 version has been updated
        id: checkTest2
        uses: EndBug/version-check@v1
        with:
          diff-search: true
          file-name: test-package-2/package.json
          token: ${{ secrets.GITHUB_TOKEN }}
      - name: Publish test-package-2 to GitHub Packages
        if: steps.checkTest2.outputs.changed == 'true'
        run: npm publish test-package-2
        env:
          NODE_AUTH_TOKEN: ${{secrets.GITHUB_TOKEN }}
1 Like

Hey @patrickgrey,

Thanks loads for this!

It’s defo got me started with actions, but when I push, and the action runs, it “skips” the publish step.

Do you know why? 

I have already published the packages manually from the command line and they are created on the repo.

Sorry, have to be quick. Did you update the version number in the package.json?

For “simplifying” the management of monorepo JS packages, you could consider something like LernaJS. It has its own one single publish command, for example, and the tool itself then figures out all the packages that are available in the repo and manages publishing each of them.

Alternatively, you can also use Yarn and it’s workspaces feature if you didn’t want to add any additional tooling / dependency to your repo. However, yarn doesn’t support private registries as well as npm's CLI; or at least it isn’t as easy to configure – in my experience anyway.

@patrickgrey - curious if you have tried watching paths for changes instead of the individual package.json file?

IE:

on: 
  push:
    branches:
      - main
    paths:
      - 'scroll-to-top/**'
      - 'test-package-1/**'
      - 'test-package-2/**'
      - 'test-package-3/**'