Compare commits
236 Commits
@verdaccio
...
@verdaccio
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
d575eb9356 | ||
|
|
a7745bf9df | ||
|
|
f1d219e48c | ||
|
|
bdd55eacf9 | ||
|
|
22d9802be0 | ||
|
|
e14b064a38 | ||
|
|
1c5106ec6f | ||
|
|
4d9632424d | ||
|
|
e1efd79b60 | ||
|
|
54260206f3 | ||
|
|
851950a0fc | ||
|
|
ddd74ef0fc | ||
|
|
968b59962c | ||
|
|
36cdc5c091 | ||
|
|
869576ae57 | ||
|
|
d32ce71866 | ||
|
|
16cb6348c9 | ||
|
|
f5b9d20859 | ||
|
|
ba7c7577c7 | ||
|
|
fcfa14fa9b | ||
|
|
224ddd91d7 | ||
|
|
297ae86677 | ||
|
|
11a1276281 | ||
|
|
a347c3e934 | ||
|
|
6dba80e3cb | ||
|
|
9e6acdbdcc | ||
|
|
3a0eab511f | ||
|
|
5bec47859c | ||
|
|
2673bccdd8 | ||
|
|
0b5bd2ba92 | ||
|
|
37825bfe77 | ||
|
|
f047cc8c25 | ||
|
|
5f8e361262 | ||
|
|
b537d0d5dd | ||
|
|
56442b8d03 | ||
|
|
34ae4ef638 | ||
|
|
ed5d78e0fe | ||
|
|
922b37f200 | ||
|
|
c8c40a2cf5 | ||
|
|
0d1205c951 | ||
|
|
2e711dabaf | ||
|
|
806bcdf46e | ||
|
|
f2959a370b | ||
|
|
419eb8861b | ||
|
|
6652bbacb3 | ||
|
|
e3b82ae391 | ||
|
|
a9491acbde | ||
|
|
7680323d2d | ||
|
|
7fb1714cb3 | ||
|
|
898abdc714 | ||
|
|
c38a321168 | ||
|
|
d8097b8030 | ||
|
|
a7e0dbb753 | ||
|
|
0f3df248f8 | ||
|
|
7b579b3337 | ||
|
|
fd47fab9a8 | ||
|
|
17cd8d4f36 | ||
|
|
b22a3467c5 | ||
|
|
17e1479be5 | ||
|
|
5e4c768228 | ||
|
|
22cf912483 | ||
|
|
a2343d751b | ||
|
|
88a91bdfc7 | ||
|
|
10be85cb7e | ||
|
|
0ad768d01c | ||
|
|
655bcceb0f | ||
|
|
a730961df7 | ||
|
|
2ecf69cc86 | ||
|
|
c01b9de325 | ||
|
|
b3f12c99b1 | ||
|
|
e885cb126d | ||
|
|
ec895bba79 | ||
|
|
74a8598355 | ||
|
|
8c0058a9cf | ||
|
|
d8ef641c76 | ||
|
|
c456d2e482 | ||
|
|
49aa66e480 | ||
|
|
d68392b102 | ||
|
|
fb53818a47 | ||
|
|
c80d26d926 | ||
|
|
c02f2cb725 | ||
|
|
d6b00b8074 | ||
|
|
1749efbd49 | ||
|
|
56c5e20007 | ||
|
|
e4a0231b6c | ||
|
|
c198c01488 | ||
|
|
2cee1a5801 | ||
|
|
d0b7647443 | ||
|
|
d0ac8155ee | ||
|
|
58cd9fd647 | ||
|
|
7262c10093 | ||
|
|
2f85f85bb0 | ||
|
|
8030e8d5d0 | ||
|
|
34c8e141b7 | ||
|
|
c6e5a67fd8 | ||
|
|
baa3f84e42 | ||
|
|
30d4e59a97 | ||
|
|
df37f5d205 | ||
|
|
31005bc8b9 | ||
|
|
d5f7bdba0a | ||
|
|
c42f2d06bc | ||
|
|
995355f9c7 | ||
|
|
00fb00894c | ||
|
|
e309047a77 | ||
|
|
ba6a098bbe | ||
|
|
2bed2788df | ||
|
|
ccb8317b65 | ||
|
|
6e7c215613 | ||
|
|
beb949e5a6 | ||
|
|
a2b08766a5 | ||
|
|
cda54ec4da | ||
|
|
d4ab275799 | ||
|
|
b593588c02 | ||
|
|
d6bd489129 | ||
|
|
ed3518ee24 | ||
|
|
c3e97fb6dd | ||
|
|
03314c15c5 | ||
|
|
3a47c6d6a9 | ||
|
|
5e49905394 | ||
|
|
9d601c9e34 | ||
|
|
c9b9a84ecb | ||
|
|
9604732736 | ||
|
|
05608eb4e1 | ||
|
|
33530632d6 | ||
|
|
bb83a1a733 | ||
|
|
3c04696dd1 | ||
|
|
fdab6b8c89 | ||
|
|
46915b0d10 | ||
|
|
e5d4e91e21 | ||
|
|
4718b7c2d4 | ||
|
|
f63e216f20 | ||
|
|
843bf8009c | ||
|
|
cf5c359ab9 | ||
|
|
aca5212a4f | ||
|
|
c8c7e5641f | ||
|
|
0abdb8f301 | ||
|
|
6741d7ed80 | ||
|
|
5e83d76b22 | ||
|
|
b92528e1c8 | ||
|
|
0a7b39908a | ||
|
|
c43e1be2c0 | ||
|
|
2f17367d21 | ||
|
|
001896ecfb | ||
|
|
3159458282 | ||
|
|
b8d6311c48 | ||
|
|
ab5bd360e4 | ||
|
|
238f6aeb92 | ||
|
|
8cca64bd4f | ||
|
|
a491baaa4c | ||
|
|
793dcd54c0 | ||
|
|
58daf3c9bd | ||
|
|
c07ed76dc6 | ||
|
|
db83206753 | ||
|
|
e585965389 | ||
|
|
b1e1cfbd8f | ||
|
|
9cffa22bd2 | ||
|
|
541ec22536 | ||
|
|
2af11ee8e3 | ||
|
|
12fd19d3dd | ||
|
|
87f5598070 | ||
|
|
fda7ff26e9 | ||
|
|
b313e56f75 | ||
|
|
667f705c0e | ||
|
|
5e850af59b | ||
|
|
4e31fdf651 | ||
|
|
326ec28930 | ||
|
|
afce58da48 | ||
|
|
277ca7ee71 | ||
|
|
a07ff6350e | ||
|
|
851eb5541f | ||
|
|
c5831f3479 | ||
|
|
7dd4494c2d | ||
|
|
4136fc2e49 | ||
|
|
287983c1c0 | ||
|
|
0b7f5a7e22 | ||
|
|
cc4c113b0d | ||
|
|
56f728c312 | ||
|
|
bf16931eef | ||
|
|
789a2b2020 | ||
|
|
f93a5181f4 | ||
|
|
9395365d65 | ||
|
|
0bda2c6fde | ||
|
|
4912d31387 | ||
|
|
422bf8dba5 | ||
|
|
77764b11a9 | ||
|
|
795df2bf9a | ||
|
|
e5d71046e9 | ||
|
|
22212eeea1 | ||
|
|
faf5895db4 | ||
|
|
0fbc09d7da | ||
|
|
54582b0594 | ||
|
|
a188439abc | ||
|
|
cca9308d0f | ||
|
|
ffbb890600 | ||
|
|
4d53066fac | ||
|
|
98852b400d | ||
|
|
7085c0b075 | ||
|
|
85e640d8d8 | ||
|
|
8d00ca9029 | ||
|
|
6b4603feaa | ||
|
|
8ffdb6623c | ||
|
|
cdeca77f4b | ||
|
|
14f8469d1b | ||
|
|
82d34ae4dc | ||
|
|
400e4e6428 | ||
|
|
c4e89143f3 | ||
|
|
1627957276 | ||
|
|
357f39b78a | ||
|
|
17087ffa97 | ||
|
|
acdf96aa33 | ||
|
|
95674ecf69 | ||
|
|
3a200ee37f | ||
|
|
c6400203cf | ||
|
|
46ef5f0532 | ||
|
|
491c788845 | ||
|
|
e4e7fcea3a | ||
|
|
461d95cef3 | ||
|
|
aedb209520 | ||
|
|
376eb53788 | ||
|
|
c922b83775 | ||
|
|
312bc100ff | ||
|
|
8004ebd445 | ||
|
|
dd551fd110 | ||
|
|
e626f3bc70 | ||
|
|
42660c164d | ||
|
|
eaea6ca2e8 | ||
|
|
4c58a46b43 | ||
|
|
33cf14740d | ||
|
|
56c082ab0a | ||
|
|
6d860074ec | ||
|
|
f04de5103c | ||
|
|
750d4e54fa | ||
|
|
047e2b78b7 | ||
|
|
bf394dd5d1 | ||
|
|
436a639cb1 | ||
|
|
2748471a4b |
7
.changeset/olive-bananas-wink.md
Normal file
7
.changeset/olive-bananas-wink.md
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
---
|
||||||
|
'@verdaccio/store': patch
|
||||||
|
'@verdaccio/tarball': patch
|
||||||
|
---
|
||||||
|
|
||||||
|
- Fixes polynomial regular expression when determining the file name of tarball
|
||||||
|
- Add tests for extracting tarball name
|
||||||
@@ -64,8 +64,12 @@
|
|||||||
"eight-squids-judge",
|
"eight-squids-judge",
|
||||||
"long-jars-collect",
|
"long-jars-collect",
|
||||||
"old-turkeys-heal",
|
"old-turkeys-heal",
|
||||||
|
"olive-bananas-wink",
|
||||||
"perfect-chairs-act",
|
"perfect-chairs-act",
|
||||||
"shiny-worms-retire",
|
"shiny-worms-retire",
|
||||||
"weak-fans-explain"
|
"shy-carrots-compare",
|
||||||
|
"shy-garlics-cry",
|
||||||
|
"weak-fans-explain",
|
||||||
|
"young-donuts-own"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|||||||
14
.changeset/shy-carrots-compare.md
Normal file
14
.changeset/shy-carrots-compare.md
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
---
|
||||||
|
'@verdaccio/server': minor
|
||||||
|
'@verdaccio/test-helper': minor
|
||||||
|
'@verdaccio/types': minor
|
||||||
|
'@verdaccio/middleware': minor
|
||||||
|
'@verdaccio/core': minor
|
||||||
|
'@verdaccio/signature': minor
|
||||||
|
'@verdaccio/url': minor
|
||||||
|
'@verdaccio/config': minor
|
||||||
|
'@verdaccio/auth': minor
|
||||||
|
'@verdaccio/api': minor
|
||||||
|
---
|
||||||
|
|
||||||
|
refactor: auth with legacy sign support
|
||||||
5
.changeset/shy-garlics-cry.md
Normal file
5
.changeset/shy-garlics-cry.md
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
---
|
||||||
|
'@verdaccio/signature': patch
|
||||||
|
---
|
||||||
|
|
||||||
|
chore: export signature options type
|
||||||
5
.changeset/young-donuts-own.md
Normal file
5
.changeset/young-donuts-own.md
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
---
|
||||||
|
'@verdaccio/config': patch
|
||||||
|
---
|
||||||
|
|
||||||
|
chore(config): increase test coverage
|
||||||
4
.github/workflows/changesets.yml
vendored
4
.github/workflows/changesets.yml
vendored
@@ -25,14 +25,14 @@ jobs:
|
|||||||
fetch-depth: 0
|
fetch-depth: 0
|
||||||
|
|
||||||
- name: setup node.js
|
- name: setup node.js
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
env:
|
env:
|
||||||
NODE_AUTH_TOKEN: ${{ secrets.REGISTRY_AUTH_TOKEN }}
|
NODE_AUTH_TOKEN: ${{ secrets.REGISTRY_AUTH_TOKEN }}
|
||||||
|
|
||||||
- name: install pnpm
|
- name: install pnpm
|
||||||
run: npm i pnpm@latest-8 -g
|
run: npm i pnpm@8.9.0 -g
|
||||||
env:
|
env:
|
||||||
NODE_AUTH_TOKEN: ${{ secrets.REGISTRY_AUTH_TOKEN }}
|
NODE_AUTH_TOKEN: ${{ secrets.REGISTRY_AUTH_TOKEN }}
|
||||||
|
|
||||||
|
|||||||
10
.github/workflows/ci-windows.yml
vendored
10
.github/workflows/ci-windows.yml
vendored
@@ -20,7 +20,7 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Node
|
- name: Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
@@ -49,7 +49,7 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Node
|
- name: Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
@@ -73,7 +73,7 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Use Node
|
- name: Use Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
@@ -102,7 +102,7 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Use Node ${{ matrix.node_version }}
|
- name: Use Node ${{ matrix.node_version }}
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version: ${{ matrix.node_version }}
|
node-version: ${{ matrix.node_version }}
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
@@ -127,7 +127,7 @@ jobs:
|
|||||||
name: UI Test E2E
|
name: UI Test E2E
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
- uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
|
|||||||
74
.github/workflows/ci.yml
vendored
74
.github/workflows/ci.yml
vendored
@@ -25,30 +25,30 @@ jobs:
|
|||||||
ports:
|
ports:
|
||||||
- 4873:4873
|
- 4873:4873
|
||||||
env:
|
env:
|
||||||
NODE_ENV: production
|
NODE_ENV: production
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Node
|
- name: Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: |
|
run: |
|
||||||
corepack enable
|
corepack enable
|
||||||
corepack prepare --activate pnpm@latest-8
|
corepack install
|
||||||
- name: set store
|
- name: set store
|
||||||
run: |
|
run: |
|
||||||
mkdir ~/.pnpm-store
|
mkdir ~/.pnpm-store
|
||||||
pnpm config set store-dir ~/.pnpm-store
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
- name: Install
|
- name: Install
|
||||||
run: pnpm install --registry http://localhost:4873
|
run: pnpm install --registry http://localhost:4873
|
||||||
- name: Cache .pnpm-store
|
- name: Cache .pnpm-store
|
||||||
uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
with:
|
with:
|
||||||
path: ~/.pnpm-store
|
path: ~/.pnpm-store
|
||||||
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
||||||
restore-keys: |
|
restore-keys: |
|
||||||
pnpm-
|
pnpm-
|
||||||
lint:
|
lint:
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
name: Lint
|
name: Lint
|
||||||
@@ -56,20 +56,20 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Node
|
- name: Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: |
|
run: |
|
||||||
corepack enable
|
corepack enable
|
||||||
corepack prepare --activate pnpm@latest-8
|
corepack install
|
||||||
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
with:
|
with:
|
||||||
path: ~/.pnpm-store
|
path: ~/.pnpm-store
|
||||||
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
||||||
- name: set store
|
- name: set store
|
||||||
run: |
|
run: |
|
||||||
pnpm config set store-dir ~/.pnpm-store
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
- name: Install
|
- name: Install
|
||||||
run: pnpm install --ignore-scripts
|
run: pnpm install --ignore-scripts
|
||||||
- name: Lint
|
- name: Lint
|
||||||
@@ -81,50 +81,50 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Use Node
|
- name: Use Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: |
|
run: |
|
||||||
corepack enable
|
corepack enable
|
||||||
corepack prepare --activate pnpm@latest-8
|
corepack install
|
||||||
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
with:
|
with:
|
||||||
path: ~/.pnpm-store
|
path: ~/.pnpm-store
|
||||||
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
||||||
- name: set store
|
- name: set store
|
||||||
run: |
|
run: |
|
||||||
pnpm config set store-dir ~/.pnpm-store
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
- name: Install
|
- name: Install
|
||||||
run: pnpm install --ignore-scripts
|
run: pnpm install --ignore-scripts
|
||||||
- name: Lint
|
- name: Lint
|
||||||
run: pnpm format:check
|
run: pnpm format:check
|
||||||
test:
|
test:
|
||||||
needs: [format, lint]
|
needs: [prepare]
|
||||||
strategy:
|
strategy:
|
||||||
fail-fast: true
|
fail-fast: true
|
||||||
matrix:
|
matrix:
|
||||||
os: [ubuntu-latest]
|
os: [ubuntu-latest]
|
||||||
node_version: [18, 20]
|
node_version: [18, 20, 21]
|
||||||
name: ${{ matrix.os }} / Node ${{ matrix.node_version }}
|
name: ${{ matrix.os }} / Node ${{ matrix.node_version }}
|
||||||
runs-on: ${{ matrix.os }}
|
runs-on: ${{ matrix.os }}
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Use Node ${{ matrix.node_version }}
|
- name: Use Node ${{ matrix.node_version }}
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version: ${{ matrix.node_version }}
|
node-version: ${{ matrix.node_version }}
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: |
|
run: |
|
||||||
corepack enable
|
corepack enable
|
||||||
corepack prepare --activate pnpm@latest-8
|
corepack prepare
|
||||||
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
with:
|
with:
|
||||||
path: ~/.pnpm-store
|
path: ~/.pnpm-store
|
||||||
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
||||||
- name: set store
|
- name: set store
|
||||||
run: |
|
run: |
|
||||||
pnpm config set store-dir ~/.pnpm-store
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
- name: Install
|
- name: Install
|
||||||
run: pnpm install --ignore-scripts --registry http://localhost:4873
|
run: pnpm install --ignore-scripts --registry http://localhost:4873
|
||||||
- name: build
|
- name: build
|
||||||
@@ -138,20 +138,20 @@ jobs:
|
|||||||
if: (github.event_name == 'push' && github.ref == 'refs/heads/master') || github.event_name == 'workflow_dispatch'
|
if: (github.event_name == 'push' && github.ref == 'refs/heads/master') || github.event_name == 'workflow_dispatch'
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
- uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: |
|
run: |
|
||||||
corepack enable
|
corepack enable
|
||||||
corepack prepare --activate pnpm@latest-8
|
corepack install
|
||||||
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
with:
|
with:
|
||||||
path: ~/.pnpm-store
|
path: ~/.pnpm-store
|
||||||
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
||||||
- name: set store
|
- name: set store
|
||||||
run: |
|
run: |
|
||||||
pnpm config set store-dir ~/.pnpm-store
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
- name: Install
|
- name: Install
|
||||||
## we need scripts, pupetter downloads aditional content
|
## we need scripts, pupetter downloads aditional content
|
||||||
run: pnpm install --registry http://localhost:4873
|
run: pnpm install --registry http://localhost:4873
|
||||||
|
|||||||
6
.github/workflows/codeql-analysis.yml
vendored
6
.github/workflows/codeql-analysis.yml
vendored
@@ -34,7 +34,7 @@ jobs:
|
|||||||
|
|
||||||
# Initializes the CodeQL tools for scanning.
|
# Initializes the CodeQL tools for scanning.
|
||||||
- name: Initialize CodeQL
|
- name: Initialize CodeQL
|
||||||
uses: github/codeql-action/init@fdcae64e1484d349b3366718cdfef3d404390e85 # v2
|
uses: github/codeql-action/init@1500a131381b66de0c52ac28abb13cd79f4b7ecc # v2
|
||||||
|
|
||||||
# Override language selection by uncommenting this and choosing your languages
|
# Override language selection by uncommenting this and choosing your languages
|
||||||
# with:
|
# with:
|
||||||
@@ -42,7 +42,7 @@ jobs:
|
|||||||
# Autobuild attempts to build any compiled languages (C/C++, C#, or Java).
|
# Autobuild attempts to build any compiled languages (C/C++, C#, or Java).
|
||||||
# If this step fails, then you should remove it and run the build manually (see below)
|
# If this step fails, then you should remove it and run the build manually (see below)
|
||||||
- name: Autobuild
|
- name: Autobuild
|
||||||
uses: github/codeql-action/autobuild@fdcae64e1484d349b3366718cdfef3d404390e85 # v2
|
uses: github/codeql-action/autobuild@1500a131381b66de0c52ac28abb13cd79f4b7ecc # v2
|
||||||
|
|
||||||
# ℹ️ Command-line programs to run using the OS shell.
|
# ℹ️ Command-line programs to run using the OS shell.
|
||||||
# 📚 https://git.io/JvXDl
|
# 📚 https://git.io/JvXDl
|
||||||
@@ -56,4 +56,4 @@ jobs:
|
|||||||
# make release
|
# make release
|
||||||
|
|
||||||
- name: Perform CodeQL Analysis
|
- name: Perform CodeQL Analysis
|
||||||
uses: github/codeql-action/analyze@fdcae64e1484d349b3366718cdfef3d404390e85 # v2
|
uses: github/codeql-action/analyze@1500a131381b66de0c52ac28abb13cd79f4b7ecc # v2
|
||||||
|
|||||||
17
.github/workflows/docker-proxy-apache-e2e.yml
vendored
17
.github/workflows/docker-proxy-apache-e2e.yml
vendored
@@ -12,7 +12,8 @@ jobs:
|
|||||||
docker:
|
docker:
|
||||||
timeout-minutes: 10
|
timeout-minutes: 10
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
|
env:
|
||||||
|
NODE_OPTIONS: --max_old_space_size=4096
|
||||||
steps:
|
steps:
|
||||||
- name: Checkout
|
- name: Checkout
|
||||||
uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
@@ -21,15 +22,21 @@ jobs:
|
|||||||
run: docker-compose -f "./e2e/docker/apache-verdaccio/docker-compose.yaml" up -d --build
|
run: docker-compose -f "./e2e/docker/apache-verdaccio/docker-compose.yaml" up -d --build
|
||||||
|
|
||||||
- name: Install node
|
- name: Install node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version: 18
|
node-version-file: '.nvmrc'
|
||||||
|
- name: npm setup
|
||||||
|
run: |
|
||||||
|
npm config set fetch-retries="10"
|
||||||
|
npm config set fetch-retry-factor="50"
|
||||||
|
npm config set fetch-retry-mintimeout="20000"
|
||||||
|
npm config set fetch-retry-maxtimeout="80000"
|
||||||
- name: verdaccio cli
|
- name: verdaccio cli
|
||||||
run: npm install -g verdaccio --registry http://localhost
|
run: npm install -g verdaccio --registry http://localhost
|
||||||
- name: gastby cli
|
- name: gastby cli
|
||||||
run: npm install -g gatsby-cli --registry http://localhost
|
run: npm install -g gatsby-cli --registry http://localhost
|
||||||
- name: netlify cli
|
# - name: netlify cli
|
||||||
run: npm install -g netlify-cli --registry http://localhost
|
# run: npm install -g netlify-cli --registry http://localhost
|
||||||
- name: angular cli
|
- name: angular cli
|
||||||
run: npm install -g @angular/cli --registry http://localhost
|
run: npm install -g @angular/cli --registry http://localhost
|
||||||
|
|
||||||
|
|||||||
13
.github/workflows/docker-proxy-nginx-e2e.yml
vendored
13
.github/workflows/docker-proxy-nginx-e2e.yml
vendored
@@ -9,7 +9,8 @@ jobs:
|
|||||||
docker:
|
docker:
|
||||||
timeout-minutes: 10
|
timeout-minutes: 10
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
|
env:
|
||||||
|
NODE_OPTIONS: --max_old_space_size=4096
|
||||||
steps:
|
steps:
|
||||||
- name: Checkout
|
- name: Checkout
|
||||||
uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
@@ -18,12 +19,12 @@ jobs:
|
|||||||
run: docker-compose -f "./e2e/docker/proxy-nginx/docker-compose.yaml" up -d --build
|
run: docker-compose -f "./e2e/docker/proxy-nginx/docker-compose.yaml" up -d --build
|
||||||
|
|
||||||
- name: Install node
|
- name: Install node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version: 18
|
node-version-file: '.nvmrc'
|
||||||
- name: npm setup
|
- name: npm setup
|
||||||
run: |
|
run: |
|
||||||
npm config set fetch-retries="5"
|
npm config set fetch-retries="10"
|
||||||
npm config set fetch-retry-factor="50"
|
npm config set fetch-retry-factor="50"
|
||||||
npm config set fetch-retry-mintimeout="20000"
|
npm config set fetch-retry-mintimeout="20000"
|
||||||
npm config set fetch-retry-maxtimeout="80000"
|
npm config set fetch-retry-maxtimeout="80000"
|
||||||
@@ -31,8 +32,8 @@ jobs:
|
|||||||
run: npm install -g verdaccio --registry http://localhost
|
run: npm install -g verdaccio --registry http://localhost
|
||||||
- name: gastby cli
|
- name: gastby cli
|
||||||
run: npm install -g gatsby-cli --registry http://localhost
|
run: npm install -g gatsby-cli --registry http://localhost
|
||||||
- name: netlify cli
|
#- name: netlify cli
|
||||||
run: npm install -g netlify-cli --registry http://localhost
|
# run: npm install -g netlify-cli --registry http://localhost
|
||||||
- name: angular cli
|
- name: angular cli
|
||||||
run: npm install -g @angular/cli --registry http://localhost
|
run: npm install -g @angular/cli --registry http://localhost
|
||||||
|
|
||||||
|
|||||||
164
.github/workflows/e2e-ci.yml
vendored
164
.github/workflows/e2e-ci.yml
vendored
@@ -15,44 +15,48 @@ jobs:
|
|||||||
env:
|
env:
|
||||||
NODE_ENV: production
|
NODE_ENV: production
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Use Node
|
- name: Use Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: npm i pnpm@latest-8 -g
|
run: |
|
||||||
- name: set store
|
corepack enable
|
||||||
run: |
|
corepack prepare
|
||||||
mkdir ~/.pnpm-store
|
- name: set store
|
||||||
pnpm config set store-dir ~/.pnpm-store
|
run: |
|
||||||
- name: Install
|
mkdir ~/.pnpm-store
|
||||||
run: pnpm install --reporter=silence --ignore-scripts --registry http://localhost:4873
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
- name: Cache .pnpm-store
|
- name: Install
|
||||||
uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
run: pnpm install --reporter=silence --ignore-scripts --registry http://localhost:4873
|
||||||
with:
|
- name: Cache .pnpm-store
|
||||||
path: ~/.pnpm-store
|
uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
with:
|
||||||
restore-keys: |
|
path: ~/.pnpm-store
|
||||||
pnpm-
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
|
restore-keys: |
|
||||||
|
pnpm-
|
||||||
build:
|
build:
|
||||||
needs: [prepare]
|
needs: [prepare]
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Use Node 16
|
- name: Use Node 16
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: npm i pnpm@latest-8 -g
|
run: |
|
||||||
|
corepack enable
|
||||||
|
corepack prepare
|
||||||
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
with:
|
with:
|
||||||
path: ~/.pnpm-store
|
path: ~/.pnpm-store
|
||||||
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
- name: set store
|
- name: set store
|
||||||
run: |
|
run: |
|
||||||
pnpm config set store-dir ~/.pnpm-store
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
- name: Install
|
- name: Install
|
||||||
run: pnpm recursive install --reporter=silence --registry http://localhost:4873
|
run: pnpm recursive install --reporter=silence --registry http://localhost:4873
|
||||||
- name: build
|
- name: build
|
||||||
@@ -73,29 +77,38 @@ jobs:
|
|||||||
# key: test-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
# key: test-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
# restore-keys: |
|
# restore-keys: |
|
||||||
# test-
|
# test-
|
||||||
e2e-cli:
|
e2e-cli-npm:
|
||||||
needs: [prepare, build]
|
needs: [prepare, build]
|
||||||
strategy:
|
strategy:
|
||||||
fail-fast: false
|
fail-fast: false
|
||||||
matrix:
|
matrix:
|
||||||
pkg: [npm6, npm7, npm8, npm9, npm10, pnpm6, pnpm7, pnpm8, yarn1, yarn2, yarn3, yarn4]
|
pkg:
|
||||||
node: [16, 18, 19]
|
[
|
||||||
|
npm6,
|
||||||
|
npm7,
|
||||||
|
npm8,
|
||||||
|
npm9,
|
||||||
|
npm10
|
||||||
|
]
|
||||||
|
node: [20, 21]
|
||||||
name: ${{ matrix.pkg }}/ ubuntu-latest / ${{ matrix.node }}
|
name: ${{ matrix.pkg }}/ ubuntu-latest / ${{ matrix.node }}
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
- uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version: ${{ matrix.node }}
|
node-version: ${{ matrix.node }}
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: npm i pnpm@latest-8 -g
|
run: |
|
||||||
|
corepack enable
|
||||||
|
corepack prepare
|
||||||
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
with:
|
with:
|
||||||
path: ~/.pnpm-store
|
path: ~/.pnpm-store
|
||||||
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
- name: set store
|
- name: set store
|
||||||
run: |
|
run: |
|
||||||
pnpm config set store-dir ~/.pnpm-store
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
- name: Install
|
- name: Install
|
||||||
run: pnpm install --offline --reporter=silence --ignore-scripts --registry http://localhost:4873
|
run: pnpm install --offline --reporter=silence --ignore-scripts --registry http://localhost:4873
|
||||||
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
@@ -107,6 +120,97 @@ jobs:
|
|||||||
# path: ./e2e/
|
# path: ./e2e/
|
||||||
# key: test-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
# key: test-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
- name: build e2e
|
- name: build e2e
|
||||||
run: pnpm --filter @verdaccio/test-cli-commons build
|
run: pnpm --filter @verdaccio/test-cli-commons build
|
||||||
- name: Test CLI
|
- name: Test CLI
|
||||||
run: NODE_ENV=production pnpm test --filter ...@verdaccio/e2e-cli-${{matrix.pkg}}
|
run: NODE_ENV=production pnpm test --filter ...@verdaccio/e2e-cli-${{matrix.pkg}}
|
||||||
|
# TODO: fix pnpm setup
|
||||||
|
# e2e-cli-pnpm:
|
||||||
|
# needs: [prepare, build]
|
||||||
|
# strategy:
|
||||||
|
# fail-fast: true
|
||||||
|
# matrix:
|
||||||
|
# pkg:
|
||||||
|
# [
|
||||||
|
# pnpm6,
|
||||||
|
# pnpm7,
|
||||||
|
# pnpm8
|
||||||
|
# ]
|
||||||
|
# node: [20, 21]
|
||||||
|
# name: ${{ matrix.pkg }}/ ubuntu-latest / ${{ matrix.node }}
|
||||||
|
# runs-on: ubuntu-latest
|
||||||
|
# steps:
|
||||||
|
# - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
|
# - uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
|
# with:
|
||||||
|
# node-version: ${{ matrix.node }}
|
||||||
|
# - name: Install pnpm
|
||||||
|
# run: |
|
||||||
|
# corepack enable
|
||||||
|
# corepack prepare
|
||||||
|
# - uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
|
# with:
|
||||||
|
# path: ~/.pnpm-store
|
||||||
|
# key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
|
# - name: set store
|
||||||
|
# run: |
|
||||||
|
# pnpm config set store-dir ~/.pnpm-store
|
||||||
|
# - name: Install
|
||||||
|
# run: pnpm install --loglevel debug --ignore-scripts --registry http://localhost:4873
|
||||||
|
# - uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
|
# with:
|
||||||
|
# path: ./packages/
|
||||||
|
# key: pkg-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
|
# # - uses: actions/cache@9b0c1fce7a93df8e3bb8926b0d6e9d89e92f20a7 # tag=v3
|
||||||
|
# # with:
|
||||||
|
# # path: ./e2e/
|
||||||
|
# # key: test-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
|
# - name: build e2e
|
||||||
|
# run: pnpm --filter @verdaccio/test-cli-commons build
|
||||||
|
# - name: Test CLI
|
||||||
|
# run: NODE_ENV=production pnpm test --filter ...@verdaccio/e2e-cli-${{matrix.pkg}}
|
||||||
|
e2e-cli-yarn:
|
||||||
|
needs: [prepare, build]
|
||||||
|
strategy:
|
||||||
|
fail-fast: false
|
||||||
|
matrix:
|
||||||
|
pkg:
|
||||||
|
[
|
||||||
|
yarn1,
|
||||||
|
yarn2,
|
||||||
|
yarn3,
|
||||||
|
yarn4
|
||||||
|
]
|
||||||
|
node: [20, 21]
|
||||||
|
name: ${{ matrix.pkg }}/ ubuntu-latest / ${{ matrix.node }}
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
|
- uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
|
with:
|
||||||
|
node-version: ${{ matrix.node }}
|
||||||
|
- name: Install pnpm
|
||||||
|
run: |
|
||||||
|
corepack enable
|
||||||
|
corepack prepare
|
||||||
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
|
with:
|
||||||
|
path: ~/.pnpm-store
|
||||||
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
|
- name: set store
|
||||||
|
run: |
|
||||||
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
|
- name: Install
|
||||||
|
run: pnpm install --offline --reporter=silence --ignore-scripts --registry http://localhost:4873
|
||||||
|
- uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
|
with:
|
||||||
|
path: ./packages/
|
||||||
|
key: pkg-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
|
# - uses: actions/cache@9b0c1fce7a93df8e3bb8926b0d6e9d89e92f20a7 # tag=v3
|
||||||
|
# with:
|
||||||
|
# path: ./e2e/
|
||||||
|
# key: test-${{ hashFiles('pnpm-lock.yaml') }}-${{ github.run_id }}-${{ github.sha }}
|
||||||
|
- name: build e2e
|
||||||
|
run: pnpm --filter @verdaccio/test-cli-commons build
|
||||||
|
- name: Test CLI
|
||||||
|
run: NODE_ENV=production pnpm test --filter ...@verdaccio/e2e-cli-${{matrix.pkg}}
|
||||||
|
|
||||||
|
|||||||
6
.github/workflows/e2e-ui.yml
vendored
6
.github/workflows/e2e-ui.yml
vendored
@@ -17,13 +17,13 @@ jobs:
|
|||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
- name: Use Node
|
- name: Use Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: |
|
run: |
|
||||||
corepack enable
|
corepack enable
|
||||||
corepack prepare --activate pnpm@latest-8
|
corepack prepare
|
||||||
- name: Install
|
- name: Install
|
||||||
run: pnpm install --reporter=silence --registry http://localhost:4873
|
run: pnpm install --reporter=silence --registry http://localhost:4873
|
||||||
- name: build
|
- name: build
|
||||||
|
|||||||
2
.github/workflows/static-data.yml
vendored
2
.github/workflows/static-data.yml
vendored
@@ -23,7 +23,7 @@ jobs:
|
|||||||
with:
|
with:
|
||||||
persist-credentials: false
|
persist-credentials: false
|
||||||
fetch-depth: 0
|
fetch-depth: 0
|
||||||
- uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
- uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version: 18.x
|
node-version: 18.x
|
||||||
- name: install pnpm
|
- name: install pnpm
|
||||||
|
|||||||
9
.github/workflows/ui-components.yml
vendored
9
.github/workflows/ui-components.yml
vendored
@@ -3,12 +3,17 @@ name: UI Components
|
|||||||
on:
|
on:
|
||||||
workflow_dispatch:
|
workflow_dispatch:
|
||||||
pull_request:
|
pull_request:
|
||||||
|
branches-ignore:
|
||||||
|
- 'renovate/*'
|
||||||
|
- 'dependabot/*'
|
||||||
paths:
|
paths:
|
||||||
- .github/workflows/ui-components.yml
|
- .github/workflows/ui-components.yml
|
||||||
- 'packages/ui-components/**'
|
- 'packages/ui-components/**'
|
||||||
- 'package.json'
|
- 'package.json'
|
||||||
- 'pnpm-workspace.yaml'
|
- 'pnpm-workspace.yaml'
|
||||||
- 'pnpm-lock.yaml'
|
- 'pnpm-lock.yaml'
|
||||||
|
schedule:
|
||||||
|
- cron: '0 0 * * 1'
|
||||||
|
|
||||||
permissions:
|
permissions:
|
||||||
contents: read # to fetch code (actions/checkout)
|
contents: read # to fetch code (actions/checkout)
|
||||||
@@ -30,7 +35,7 @@ jobs:
|
|||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
|
|
||||||
- name: Use Node
|
- name: Use Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version-file: '.nvmrc'
|
node-version-file: '.nvmrc'
|
||||||
|
|
||||||
@@ -47,7 +52,7 @@ jobs:
|
|||||||
- name: Install pnpm
|
- name: Install pnpm
|
||||||
run: |
|
run: |
|
||||||
corepack enable
|
corepack enable
|
||||||
corepack prepare --activate pnpm@latest-8
|
corepack prepare --activate pnpm@8.9.0
|
||||||
- name: Install
|
- name: Install
|
||||||
run: pnpm install
|
run: pnpm install
|
||||||
- name: Build storybook
|
- name: Build storybook
|
||||||
|
|||||||
45
.github/workflows/website.yml
vendored
45
.github/workflows/website.yml
vendored
@@ -3,6 +3,9 @@ name: Verdaccio Website CI
|
|||||||
on:
|
on:
|
||||||
workflow_dispatch:
|
workflow_dispatch:
|
||||||
pull_request:
|
pull_request:
|
||||||
|
branches-ignore:
|
||||||
|
- 'renovate/*'
|
||||||
|
- 'dependabot/*'
|
||||||
paths:
|
paths:
|
||||||
- 'website/**'
|
- 'website/**'
|
||||||
- './.github/workflows/website.yml'
|
- './.github/workflows/website.yml'
|
||||||
@@ -20,32 +23,40 @@ jobs:
|
|||||||
pull-requests: write # to comment on pull-requests
|
pull-requests: write # to comment on pull-requests
|
||||||
|
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
|
name: setup verdaccio
|
||||||
|
services:
|
||||||
|
verdaccio:
|
||||||
|
image: verdaccio/verdaccio:5
|
||||||
|
ports:
|
||||||
|
- 4873:4873
|
||||||
|
env:
|
||||||
|
NODE_ENV: production
|
||||||
env:
|
env:
|
||||||
NODE_OPTIONS: --max_old_space_size=4096
|
NODE_OPTIONS: --max_old_space_size=4096
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
- uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3
|
||||||
|
|
||||||
- name: Use Node 16
|
- name: Node
|
||||||
uses: actions/setup-node@5e21ff4d9bc1a8cf6de233a3057d20ec6b3fb69d # tag=v3
|
uses: actions/setup-node@b39b52d1213e96004bfcb1c61a8a6fa8ab84f3e8 # v3
|
||||||
with:
|
with:
|
||||||
node-version: 16
|
node-version-file: '.nvmrc'
|
||||||
|
- name: Install pnpm
|
||||||
- name: Cache pnpm modules
|
run: |
|
||||||
|
corepack enable
|
||||||
|
corepack install
|
||||||
|
- name: set store
|
||||||
|
run: |
|
||||||
|
mkdir ~/.pnpm-store
|
||||||
|
pnpm config set store-dir ~/.pnpm-store
|
||||||
|
- name: Install
|
||||||
|
run: pnpm install --registry http://localhost:4873
|
||||||
|
- name: Cache .pnpm-store
|
||||||
uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
uses: actions/cache@88522ab9f39a2ea568f7027eddc7d8d8bc9d59c8 # v3
|
||||||
env:
|
|
||||||
cache-name: cache-pnpm-modules
|
|
||||||
with:
|
with:
|
||||||
path: ~/.pnpm-store
|
path: ~/.pnpm-store
|
||||||
key: ${{ runner.os }}-build-${{ env.cache-name }}-${{ matrix.node-version }}-${{ hashFiles('**/pnpm-lock.yaml') }}
|
key: pnpm-${{ hashFiles('pnpm-lock.yaml') }}
|
||||||
restore-keys: |
|
restore-keys: |
|
||||||
${{ runner.os }}-build-${{ env.cache-name }}-${{ matrix.node-version }}-
|
pnpm-
|
||||||
|
|
||||||
- uses: pnpm/action-setup@d882d12c64e032187b2edb46d3a0d003b7a43598 # tag=v2.4.0
|
|
||||||
with:
|
|
||||||
version: latest-8
|
|
||||||
run_install: |
|
|
||||||
- recursive: true
|
|
||||||
args: [--frozen-lockfile]
|
|
||||||
- name: Build
|
- name: Build
|
||||||
run: pnpm build
|
run: pnpm build
|
||||||
- name: Build Translations percentage
|
- name: Build Translations percentage
|
||||||
@@ -109,7 +120,7 @@ jobs:
|
|||||||
|
|
||||||
- name: Format lighthouse score
|
- name: Format lighthouse score
|
||||||
id: format_lighthouse_score
|
id: format_lighthouse_score
|
||||||
uses: actions/github-script@d7906e4ad0b1822421a7e6a35d5ca353c962f410 # tag=v6
|
uses: actions/github-script@d7906e4ad0b1822421a7e6a35d5ca353c962f410 # v6
|
||||||
with:
|
with:
|
||||||
github-token: ${{secrets.GITHUB_TOKEN}}
|
github-token: ${{secrets.GITHUB_TOKEN}}
|
||||||
script: |
|
script: |
|
||||||
|
|||||||
1
.npmrc
1
.npmrc
@@ -1,3 +1,2 @@
|
|||||||
always-auth = true
|
always-auth = true
|
||||||
loglevel=info
|
|
||||||
fetch-retries="10"
|
fetch-retries="10"
|
||||||
|
|||||||
15
.prettierrc
Normal file
15
.prettierrc
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
{
|
||||||
|
"endOfLine": "lf",
|
||||||
|
"useTabs": false,
|
||||||
|
"printWidth": 100,
|
||||||
|
"tabWidth": 2,
|
||||||
|
"singleQuote": true,
|
||||||
|
"bracketSpacing": true,
|
||||||
|
"trailingComma": "es5",
|
||||||
|
"semi": true,
|
||||||
|
"plugins": ["@trivago/prettier-plugin-sort-imports"],
|
||||||
|
"importOrder": ["^@verdaccio/(.*)$", "^[./]"],
|
||||||
|
"importOrderSeparation": true,
|
||||||
|
"importOrderParserPlugins": ["typescript", "classProperties", "jsx"],
|
||||||
|
"importOrderSortSpecifiers": true
|
||||||
|
}
|
||||||
7
.vscode/settings.json
vendored
7
.vscode/settings.json
vendored
@@ -1,13 +1,10 @@
|
|||||||
// Place your settings in this file to overwrite default and user settings.
|
// Place your settings in this file to overwrite default and user settings.
|
||||||
{
|
{
|
||||||
"files.exclude": {
|
"files.exclude": {
|
||||||
"**/.nyc_output": true,
|
|
||||||
"**/build": false,
|
"**/build": false,
|
||||||
"**/coverage": true,
|
"**/coverage": true,
|
||||||
".idea": true,
|
".idea": true,
|
||||||
"storage_default_storage": true,
|
|
||||||
".yarn": true
|
|
||||||
},
|
},
|
||||||
"editor.formatOnSave": true,
|
"editor.defaultFormatter": "esbenp.prettier-vscode",
|
||||||
"typescript.tsdk": "node_modules/typescript/lib"
|
"editor.formatOnSave": true
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,6 +29,8 @@ The Verdaccio project is split into several areas, the first three hosted in the
|
|||||||
|
|
||||||
## Prepare local setup {#local-setup}
|
## Prepare local setup {#local-setup}
|
||||||
|
|
||||||
|
**Note**: The size of the Verdaccio project is quite significant. Unzipped it is about 33 MB. However, a full build with all node_modules installed takes about **2.8 GB** of disk space (~190k files)!
|
||||||
|
|
||||||
Verdaccio uses [pnpm](https://pnpm.io) as the package manager for development in this repository.
|
Verdaccio uses [pnpm](https://pnpm.io) as the package manager for development in this repository.
|
||||||
|
|
||||||
If you are using pnpm for the first time the [pnpm configuration documentation](https://pnpm.io/configuring) may be useful to avoid any potential problems with the following steps.
|
If you are using pnpm for the first time the [pnpm configuration documentation](https://pnpm.io/configuring) may be useful to avoid any potential problems with the following steps.
|
||||||
@@ -41,61 +43,70 @@ package-lock=false
|
|||||||
|
|
||||||
This setting would cause the `pnpm install` command to install incorrect versions of package dependencies and the subsequent `pnpm build` step would likely fail.
|
This setting would cause the `pnpm install` command to install incorrect versions of package dependencies and the subsequent `pnpm build` step would likely fail.
|
||||||
|
|
||||||
To begin your development setup, please install the latest version of pnpm globally:
|
We use [corepack](https://github.com/nodejs/corepack) to install and use a specific (latest) version of pnpm. Please run the following commands which is use a specific version on Node.js and configure it to use a specific version of pnpm. The version of pnpm is specified in the `package.json` file in `packageManager` field.
|
||||||
|
|
||||||
|
```shell
|
||||||
|
nvm install
|
||||||
|
corepack enable
|
||||||
```
|
```
|
||||||
npm i -g pnpm@latest-8
|
|
||||||
|
`pnpm` version will be updated mainly by the maintainers but if you would like to set it to a specific version, you can do so by running the following command:
|
||||||
|
|
||||||
|
> `packageManager` at the `package.json` defines the default version to be used.
|
||||||
|
|
||||||
|
```shell
|
||||||
|
corepack prepare
|
||||||
```
|
```
|
||||||
|
|
||||||
With pnpm installed, the first step is installing all dependencies:
|
With pnpm installed, the first step is installing all dependencies:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
pnpm install
|
pnpm install
|
||||||
```
|
```
|
||||||
|
|
||||||
### Building the project
|
### Building the project
|
||||||
|
|
||||||
To build the project run
|
Each package is independent, dependencies must be build first, run:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
pnpm build
|
pnpm build
|
||||||
```
|
```
|
||||||
|
|
||||||
### Running test
|
### Running test
|
||||||
|
|
||||||
```
|
```shell
|
||||||
pnpm test
|
pnpm test
|
||||||
```
|
```
|
||||||
|
|
||||||
Verdaccio is a mono repository. To run the tests for for a specific package:
|
Verdaccio is a mono repository. To run the tests for for a specific package:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
cd packages/store
|
cd packages/store
|
||||||
pnpm test
|
pnpm test
|
||||||
```
|
```
|
||||||
|
|
||||||
or an specific test in that package:
|
or an specific test in that package:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
pnpm test test/merge.dist.tags.spec.ts
|
pnpm test test/merge.dist.tags.spec.ts
|
||||||
```
|
```
|
||||||
|
|
||||||
or a single test unit:
|
or a single test unit:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
pnpm test test/merge.dist.tags.spec.ts -- -t 'simple'
|
pnpm test test/merge.dist.tags.spec.ts -- -t 'simple'
|
||||||
```
|
```
|
||||||
|
|
||||||
Coverage reporting is enabled by default, but you can turn it off to speed up
|
Coverage reporting is enabled by default, but you can turn it off to speed up
|
||||||
test runs:
|
test runs:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
pnpm test test/merge.dist.tags.spec.ts -- -t 'simple' --coverage=false
|
pnpm test test/merge.dist.tags.spec.ts -- -t 'simple' --coverage=false
|
||||||
```
|
```
|
||||||
|
|
||||||
You can enable increased [`debug`](https://www.npmjs.com/package/debug) output:
|
You can enable increased [`debug`](https://www.npmjs.com/package/debug) output:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
DEBUG=verdaccio:* pnpm test
|
DEBUG=verdaccio:* pnpm test
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -108,11 +119,22 @@ More details in the debug section
|
|||||||
We use [`debug`](https://www.npmjs.com/package/debug) to add helpful debugging
|
We use [`debug`](https://www.npmjs.com/package/debug) to add helpful debugging
|
||||||
output to the code. Each package has it owns namespace.
|
output to the code. Each package has it owns namespace.
|
||||||
|
|
||||||
#### Useful Scripts
|
#### Developing with local server
|
||||||
|
|
||||||
To run the application from the source code, ensure the project has been built with `pnpm build`, once this is done, there are few commands that helps to run server:
|
To run the application from the source code, ensure the project has been built with `pnpm build`, once this is done, there are few commands that helps to run server:
|
||||||
|
|
||||||
- `pnpm start`: Runs server on port `8000` and UI on port `4873`. This is particularly useful if you want to contribute to the UI, since it runs with hot reload.
|
The command `pnpm start` runs web server on port `8000` and user interface (webpack-server) on port `4873`. This is particularly useful if you want to contribute to the UI, since it runs with hot reload. The request to the server are proxy through webpack proxy support through the port `4873`.
|
||||||
|
|
||||||
|
The user interface is split in two packages, the `/packages/plugins/ui-theme` and the `/packages/ui-components`. The `ui-components` package uses _storybook_ in order to develop component, but if you need to reload ui components with `ui-theme` do the following.
|
||||||
|
|
||||||
|
Go to `/packages/ui-component` and run `pnpm watch` to enable _babel_ in watch mode, every change on the components will be hot reloaded in combination with the `pnpm start` command.
|
||||||
|
|
||||||
|
Any change on the server packages, must be build independently (server do not has hot reload, `pnpm start` should be triggered again).
|
||||||
|
|
||||||
|
Any interaction with the server should be done through the port `8000` eg: `npm login --registry http://localhost:8000` .
|
||||||
|
|
||||||
|
#### Useful commands
|
||||||
|
|
||||||
- `pnpm debug`: Run the server in debug mode `--inspect`. UI runs too but without hot reload. For automatic break use `pnpm debug:break`.
|
- `pnpm debug`: Run the server in debug mode `--inspect`. UI runs too but without hot reload. For automatic break use `pnpm debug:break`.
|
||||||
- `pnpm debug:fastify`: To contribute on the [fastify migration](https://github.com/verdaccio/verdaccio/discussions/2155) this is a temporary command for such purpose.
|
- `pnpm debug:fastify`: To contribute on the [fastify migration](https://github.com/verdaccio/verdaccio/discussions/2155) this is a temporary command for such purpose.
|
||||||
- `pnpm website`: Build the website, for more commands to run the _website_, run `cd website` and then `pnpm serve`, website will run on port `3000`.
|
- `pnpm website`: Build the website, for more commands to run the _website_, run `cd website` and then `pnpm serve`, website will run on port `3000`.
|
||||||
@@ -124,14 +146,14 @@ Currently you can only run pre-compiled packages in debug mode. To enable debug
|
|||||||
while running add the `verdaccio` namespace using the `DEBUG` environment
|
while running add the `verdaccio` namespace using the `DEBUG` environment
|
||||||
variable, like this:
|
variable, like this:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
DEBUG=verdaccio:* node packages/verdaccio/debug/bootstrap.js
|
DEBUG=verdaccio:* node packages/verdaccio/debug/bootstrap.js
|
||||||
```
|
```
|
||||||
|
|
||||||
You can filter this output to just the packages you're interested in using
|
You can filter this output to just the packages you're interested in using
|
||||||
namespaces:
|
namespaces:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
DEBUG=verdaccio:plugin:* node packages/verdaccio/debug/bootstrap.js
|
DEBUG=verdaccio:plugin:* node packages/verdaccio/debug/bootstrap.js
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -144,17 +166,17 @@ of the output is sent to the logger module.
|
|||||||
|
|
||||||
Once you have perform your changes in the code base, the build and tests passes you can publish a local version:
|
Once you have perform your changes in the code base, the build and tests passes you can publish a local version:
|
||||||
|
|
||||||
- Ensure you have build all modules (or the one you have modified)
|
- Ensure you have built all modules by running `pnpm build` (or the one you have modified)
|
||||||
- Run `pnpm local:publish:release` to launch a local registry and publish all packages into it. This command will be alive until server is killed (Control Key + C)
|
- Run `pnpm local:publish:release` to launch a local registry and publish all packages into it. This command will be alive until server is killed (Control Key + C)
|
||||||
|
|
||||||
```
|
```shell
|
||||||
pnpm build
|
pnpm build
|
||||||
pnpm local:publish:release
|
pnpm local:publish:release
|
||||||
```
|
```
|
||||||
|
|
||||||
The last step consist on install globally the package from the local registry which runs on the default port (4873).
|
The last step consist on install globally the package from the local registry which runs on the default port (4873).
|
||||||
|
|
||||||
```
|
```shell
|
||||||
npm i -g verdaccio --registry=http://localhost:4873
|
npm i -g verdaccio --registry=http://localhost:4873
|
||||||
verdaccio
|
verdaccio
|
||||||
```
|
```
|
||||||
@@ -220,7 +242,7 @@ Questions can be asked via [Discord](https://discord.gg/7qWJxBf)
|
|||||||
|
|
||||||
## Development Guidelines {#development-guidelines}
|
## Development Guidelines {#development-guidelines}
|
||||||
|
|
||||||
It's recommended use a UNIX system for local development, Windows should works fine for development, but is not daily tested could not be perfect. To ensure a fast code review and merge, please follow the next guidelines:
|
It's recommended use a UNIX system for local development, Windows dev local support is not being tested and might not work. To ensure a fast code review and merge, please follow the next guidelines:
|
||||||
|
|
||||||
Any contribution gives you the right to be part of this organization as _collaborator_ and your avatar will be automatically added to the [contributors page](https://verdaccio.org/contributors).
|
Any contribution gives you the right to be part of this organization as _collaborator_ and your avatar will be automatically added to the [contributors page](https://verdaccio.org/contributors).
|
||||||
|
|
||||||
@@ -285,7 +307,7 @@ contribution to get merged (unless it does not affect functionality or
|
|||||||
user-facing content, eg: docs, readme, adding test or typo/lint fixes). To
|
user-facing content, eg: docs, readme, adding test or typo/lint fixes). To
|
||||||
create a changeset please run:
|
create a changeset please run:
|
||||||
|
|
||||||
```
|
```shell
|
||||||
pnpm changeset
|
pnpm changeset
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -364,6 +386,8 @@ All translations are provided by the **[crowdin](http://crowdin.com)** platform,
|
|||||||
|
|
||||||
If you want to contribute by adding translations, create an account (GitHub could be used as fast alternative), in the platform you can contribute to two areas, the website or improve User Interface translations.
|
If you want to contribute by adding translations, create an account (GitHub could be used as fast alternative), in the platform you can contribute to two areas, the website or improve User Interface translations.
|
||||||
|
|
||||||
|
> Languages with less the 40% of translations available are excluded by the build system.
|
||||||
|
|
||||||
If a language is not listed, ask for it in the [Discord](https://discord.gg/7qWJxBf) channel #contribute channel.
|
If a language is not listed, ask for it in the [Discord](https://discord.gg/7qWJxBf) channel #contribute channel.
|
||||||
|
|
||||||
For adding a new **language** on the UI follow these steps:
|
For adding a new **language** on the UI follow these steps:
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
FROM --platform=${BUILDPLATFORM:-linux/amd64} node:18-alpine as builder
|
FROM --platform=${BUILDPLATFORM:-linux/amd64} node:21-alpine as builder
|
||||||
|
|
||||||
ENV NODE_ENV=development \
|
ENV NODE_ENV=development \
|
||||||
VERDACCIO_BUILD_REGISTRY=https://registry.npmjs.org
|
VERDACCIO_BUILD_REGISTRY=https://registry.npmjs.org
|
||||||
@@ -11,7 +11,7 @@ RUN apk --no-cache add openssl ca-certificates wget && \
|
|||||||
|
|
||||||
WORKDIR /opt/verdaccio-build
|
WORKDIR /opt/verdaccio-build
|
||||||
COPY . .
|
COPY . .
|
||||||
RUN npm -g i pnpm@latest-8 && \
|
RUN npm -g i pnpm@8.9.0 && \
|
||||||
pnpm config set registry $VERDACCIO_BUILD_REGISTRY && \
|
pnpm config set registry $VERDACCIO_BUILD_REGISTRY && \
|
||||||
pnpm install --frozen-lockfile --ignore-scripts && \
|
pnpm install --frozen-lockfile --ignore-scripts && \
|
||||||
rm -Rf test && \
|
rm -Rf test && \
|
||||||
@@ -20,7 +20,7 @@ RUN npm -g i pnpm@latest-8 && \
|
|||||||
# NODE_ENV=production pnpm install --frozen-lockfile --ignore-scripts
|
# NODE_ENV=production pnpm install --frozen-lockfile --ignore-scripts
|
||||||
# RUN pnpm install --prod --ignore-scripts
|
# RUN pnpm install --prod --ignore-scripts
|
||||||
|
|
||||||
FROM node:18-alpine
|
FROM node:21-alpine
|
||||||
LABEL maintainer="https://github.com/verdaccio/verdaccio"
|
LABEL maintainer="https://github.com/verdaccio/verdaccio"
|
||||||
|
|
||||||
ENV VERDACCIO_APPDIR=/opt/verdaccio \
|
ENV VERDACCIO_APPDIR=/opt/verdaccio \
|
||||||
|
|||||||
2
LICENSE
2
LICENSE
@@ -1,6 +1,6 @@
|
|||||||
MIT License
|
MIT License
|
||||||
|
|
||||||
Copyright (c) 2021 Verdaccio contributors
|
Copyright (c) 2024 Verdaccio contributors
|
||||||
|
|
||||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
of this software and associated documentation files (the "Software"), to deal
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
|||||||
@@ -33,7 +33,6 @@ Google Cloud Storage** or create your own plugin.
|
|||||||
[](https://github.com/verdaccio/verdaccio/blob/master/LICENSE)
|
[](https://github.com/verdaccio/verdaccio/blob/master/LICENSE)
|
||||||
[](https://crowdin.com/project/verdaccio)
|
[](https://crowdin.com/project/verdaccio)
|
||||||
|
|
||||||
[](https://twitter.com/verdaccio_npm)
|
|
||||||
[](https://github.com/verdaccio/verdaccio/stargazers)
|
[](https://github.com/verdaccio/verdaccio/stargazers)
|
||||||
[](https://github.com/vshymanskyy/StandWithUkraine/blob/main/docs/README.md)
|
[](https://github.com/vshymanskyy/StandWithUkraine/blob/main/docs/README.md)
|
||||||
|
|
||||||
|
|||||||
@@ -91,8 +91,8 @@ class LocalMemory {
|
|||||||
(_this$data = this.data) === null || _this$data === void 0
|
(_this$data = this.data) === null || _this$data === void 0
|
||||||
? void 0
|
? void 0
|
||||||
: (_this$data$list = _this$data.list) === null || _this$data$list === void 0
|
: (_this$data$list = _this$data.list) === null || _this$data$list === void 0
|
||||||
? void 0
|
? void 0
|
||||||
: _this$data$list.length
|
: _this$data$list.length
|
||||||
);
|
);
|
||||||
return Promise.resolve(
|
return Promise.resolve(
|
||||||
(_this$data2 = this.data) === null || _this$data2 === void 0 ? void 0 : _this$data2.list
|
(_this$data2 = this.data) === null || _this$data2 === void 0 ? void 0 : _this$data2.list
|
||||||
|
|||||||
@@ -5,16 +5,16 @@
|
|||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "./build/index.d.ts",
|
"types": "./build/index.d.ts",
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/config": "workspace:7.0.0-next.3",
|
"@verdaccio/config": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1",
|
"@verdaccio/types": "workspace:12.0.0-next.2",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"fs-extra": "10.1.0",
|
"fs-extra": "11.2.0",
|
||||||
|
"get-port": "5.1.1",
|
||||||
"got": "11.8.6",
|
"got": "11.8.6",
|
||||||
"js-yaml": "4.1.0",
|
"js-yaml": "4.1.0",
|
||||||
"get-port": "5.1.1",
|
|
||||||
"lodash": "4.17.21",
|
"lodash": "4.17.21",
|
||||||
"verdaccio": "workspace:7.0.0-next.3"
|
"verdaccio": "workspace:7.0.0-next.6"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "jest",
|
"test": "jest",
|
||||||
|
|||||||
@@ -31,12 +31,13 @@ export async function exec(options: SpawnOptions, cmd, args): Promise<ExecOutput
|
|||||||
}
|
}
|
||||||
|
|
||||||
const childProcess = spawn(cmd, args, spawnOptions);
|
const childProcess = spawn(cmd, args, spawnOptions);
|
||||||
// @ts-ignore
|
if (childProcess.stdout) {
|
||||||
const rl = createInterface({ input: childProcess.stdout });
|
const rl = createInterface({ input: childProcess.stdout });
|
||||||
|
|
||||||
rl.on('line', function (line) {
|
rl.on('line', function (line) {
|
||||||
stdout += line;
|
stdout += line;
|
||||||
});
|
});
|
||||||
|
}
|
||||||
|
|
||||||
const err = new Error(`Running "${cmd} ${args.join(' ')}" returned error code `);
|
const err = new Error(`Running "${cmd} ${args.join(' ')}" returned error code `);
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
@@ -45,14 +46,9 @@ export async function exec(options: SpawnOptions, cmd, args): Promise<ExecOutput
|
|||||||
resolve({ stdout, stderr });
|
resolve({ stdout, stderr });
|
||||||
} else {
|
} else {
|
||||||
err.message += `${error}...\n\nSTDOUT:\n${stdout}\n\nSTDERR:\n${stderr}\n`;
|
err.message += `${error}...\n\nSTDOUT:\n${stdout}\n\nSTDERR:\n${stderr}\n`;
|
||||||
return reject({ stdout, stderr: err });
|
const errorObj = { stdout, stderr: err };
|
||||||
|
return reject(errorObj);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
export function silentNpm(...args): Promise<ExecOutput> {
|
|
||||||
debug('run silent npm %o', args);
|
|
||||||
// @ts-ignore
|
|
||||||
return exec({ silent: true }, 'npm', args);
|
|
||||||
}
|
|
||||||
|
|||||||
@@ -5,7 +5,6 @@ import { join } from 'path';
|
|||||||
import { fileUtils } from '@verdaccio/core';
|
import { fileUtils } from '@verdaccio/core';
|
||||||
|
|
||||||
export function createProject(projectName: string) {
|
export function createProject(projectName: string) {
|
||||||
// @ts-ignore
|
|
||||||
const tempRootFolder = global.__namespace.getItem('dir-suite-root');
|
const tempRootFolder = global.__namespace.getItem('dir-suite-root');
|
||||||
const verdaccioInstall = join(tempRootFolder, projectName);
|
const verdaccioInstall = join(tempRootFolder, projectName);
|
||||||
fs.mkdirSync(verdaccioInstall);
|
fs.mkdirSync(verdaccioInstall);
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
"version": "1.0.1",
|
"version": "1.0.1",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
||||||
"npm": "10.1.0"
|
"npm": "10.2.5"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "jest"
|
"test": "jest"
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
"version": "1.0.1",
|
"version": "1.0.1",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
||||||
"npm": "9.7.1"
|
"npm": "9.9.2"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "jest"
|
"test": "jest"
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
"version": "1.0.1",
|
"version": "1.0.1",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
||||||
"npm": "9.7.1"
|
"npm": "9.9.2"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "jest"
|
"test": "jest"
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
"version": "1.0.1",
|
"version": "1.0.1",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
||||||
"npm": "9.7.1"
|
"npm": "9.9.2"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "jest"
|
"test": "jest"
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
"version": "1.0.1",
|
"version": "1.0.1",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
||||||
"npm": "9.7.1"
|
"npm": "9.9.2"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "jest"
|
"test": "jest"
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
"version": "1.0.1",
|
"version": "1.0.1",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
"@verdaccio/test-cli-commons": "workspace:1.1.0",
|
||||||
"yarn": "1.22.19"
|
"yarn": "1.22.21"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "jest"
|
"test": "jest"
|
||||||
|
|||||||
@@ -9,6 +9,10 @@ import { generatePackageMetadata } from '@verdaccio/test-helper';
|
|||||||
|
|
||||||
let registry1;
|
let registry1;
|
||||||
export default defineConfig({
|
export default defineConfig({
|
||||||
|
retries: {
|
||||||
|
runMode: 5,
|
||||||
|
openMode: 0,
|
||||||
|
},
|
||||||
e2e: {
|
e2e: {
|
||||||
setupNodeEvents(on) {
|
setupNodeEvents(on) {
|
||||||
on('before:run', async () => {
|
on('before:run', async () => {
|
||||||
|
|||||||
@@ -3,12 +3,12 @@
|
|||||||
"name": "@verdaccio/e2e-ui",
|
"name": "@verdaccio/e2e-ui",
|
||||||
"version": "2.0.0",
|
"version": "2.0.0",
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"verdaccio": "workspace:7.0.0-next.3",
|
"verdaccio": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/config": "workspace:7.0.0-next.3",
|
"@verdaccio/config": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/test-helper": "workspace:3.0.0-next.0",
|
"@verdaccio/test-helper": "workspace:3.0.0-next.1",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"cypress": "^11.2.0",
|
"cypress": "^13.6.0",
|
||||||
"get-port": "5.1.1"
|
"get-port": "5.1.1"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
|
|||||||
@@ -17,3 +17,11 @@
|
|||||||
|
|
||||||
[[plugins]]
|
[[plugins]]
|
||||||
package = "../.netlify/netlify-plugin-pnpm"
|
package = "../.netlify/netlify-plugin-pnpm"
|
||||||
|
|
||||||
|
[[headers]]
|
||||||
|
for = "/*"
|
||||||
|
[headers.values]
|
||||||
|
X-Frame-Options = "DENY"
|
||||||
|
X-XSS-Protection = "1; mode=block"
|
||||||
|
X-Content-Type-Options = "nosniff"
|
||||||
|
Referrer-Policy = "no-referrer"
|
||||||
|
|||||||
134
package.json
134
package.json
@@ -15,92 +15,90 @@
|
|||||||
"url": "https://opencollective.com/verdaccio"
|
"url": "https://opencollective.com/verdaccio"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@babel/cli": "7.23.0",
|
"@babel/cli": "7.23.4",
|
||||||
"@babel/core": "7.23.0",
|
"@babel/core": "7.23.7",
|
||||||
"@babel/eslint-parser": "7.22.15",
|
"@babel/eslint-parser": "7.23.3",
|
||||||
"@babel/node": "7.22.19",
|
"@babel/node": "7.22.19",
|
||||||
"@babel/plugin-proposal-class-properties": "7.18.6",
|
"@babel/plugin-proposal-class-properties": "7.18.6",
|
||||||
"@babel/plugin-proposal-decorators": "7.23.0",
|
"@babel/plugin-proposal-decorators": "7.23.7",
|
||||||
"@babel/plugin-proposal-export-namespace-from": "7.18.9",
|
"@babel/plugin-proposal-export-namespace-from": "7.18.9",
|
||||||
"@babel/plugin-proposal-function-sent": "7.22.5",
|
"@babel/plugin-proposal-function-sent": "7.23.3",
|
||||||
"@babel/plugin-proposal-json-strings": "7.18.6",
|
"@babel/plugin-proposal-json-strings": "7.18.6",
|
||||||
"@babel/plugin-proposal-nullish-coalescing-operator": "7.18.6",
|
"@babel/plugin-proposal-nullish-coalescing-operator": "7.18.6",
|
||||||
"@babel/plugin-proposal-numeric-separator": "7.18.6",
|
"@babel/plugin-proposal-numeric-separator": "7.18.6",
|
||||||
"@babel/plugin-proposal-object-rest-spread": "7.20.7",
|
"@babel/plugin-proposal-object-rest-spread": "7.20.7",
|
||||||
"@babel/plugin-proposal-optional-chaining": "7.21.0",
|
"@babel/plugin-proposal-optional-chaining": "7.21.0",
|
||||||
"@babel/plugin-proposal-throw-expressions": "7.22.5",
|
"@babel/plugin-proposal-throw-expressions": "7.23.3",
|
||||||
"@babel/plugin-syntax-dynamic-import": "7.8.3",
|
"@babel/plugin-syntax-dynamic-import": "7.8.3",
|
||||||
"@babel/plugin-syntax-import-meta": "7.10.4",
|
"@babel/plugin-syntax-import-meta": "7.10.4",
|
||||||
"@babel/plugin-transform-async-to-generator": "7.22.5",
|
"@babel/plugin-transform-async-to-generator": "7.23.3",
|
||||||
"@babel/plugin-transform-classes": "7.22.15",
|
"@babel/plugin-transform-classes": "7.23.5",
|
||||||
"@babel/plugin-transform-runtime": "7.22.15",
|
"@babel/plugin-transform-runtime": "7.23.7",
|
||||||
"@babel/preset-env": "7.22.20",
|
"@babel/preset-env": "7.23.7",
|
||||||
"@babel/preset-react": "7.22.15",
|
"@babel/preset-react": "7.23.3",
|
||||||
"@babel/preset-typescript": "7.23.0",
|
"@babel/preset-typescript": "7.23.3",
|
||||||
"@babel/register": "7.22.15",
|
"@babel/register": "7.23.7",
|
||||||
"@babel/runtime": "7.23.1",
|
"@babel/runtime": "7.23.7",
|
||||||
"@changesets/changelog-github": "0.4.8",
|
"@changesets/changelog-github": "0.5.0",
|
||||||
"@changesets/cli": "2.24.4",
|
"@changesets/cli": "2.27.1",
|
||||||
"@changesets/get-dependents-graph": "1.3.6",
|
"@changesets/get-dependents-graph": "1.3.6",
|
||||||
"@crowdin/cli": "3.14.0",
|
"@crowdin/cli": "3.16.0",
|
||||||
"@dianmora/contributors": "5.0.0",
|
"@dianmora/contributors": "5.0.0",
|
||||||
"@emotion/react": "11.10.6",
|
"@emotion/react": "11.10.6",
|
||||||
"@emotion/styled": "11.10.6",
|
"@emotion/styled": "11.10.6",
|
||||||
"@testing-library/dom": "9.3.3",
|
"@testing-library/dom": "9.3.3",
|
||||||
"@testing-library/jest-dom": "6.1.3",
|
"@testing-library/jest-dom": "6.2.0",
|
||||||
"@testing-library/react": "14.0.0",
|
"@testing-library/react": "14.1.2",
|
||||||
"@trivago/prettier-plugin-sort-imports": "^4.2.0",
|
"@trivago/prettier-plugin-sort-imports": "4.3.0",
|
||||||
"@types/async": "3.2.21",
|
"@types/body-parser": "1.19.5",
|
||||||
"@types/body-parser": "1.19.2",
|
"@types/connect": "3.4.38",
|
||||||
"@types/connect": "3.4.36",
|
"@types/cookiejar": "2.1.5",
|
||||||
"@types/cookiejar": "2.1.2",
|
"@types/debug": "4.1.12",
|
||||||
"@types/debug": "^4.1.9",
|
"@types/express": "4.17.21",
|
||||||
"@types/express": "4.17.18",
|
"@types/express-serve-static-core": "4.17.41",
|
||||||
"@types/express-serve-static-core": "4.17.37",
|
"@types/http-errors": "2.0.4",
|
||||||
"@types/http-errors": "2.0.2",
|
"@types/jest": "29.5.11",
|
||||||
"@types/jest": "29.5.5",
|
"@types/jsonwebtoken": "9.0.5",
|
||||||
"@types/jsonwebtoken": "9.0.3",
|
"@types/lodash": "4.14.202",
|
||||||
"@types/lodash": "4.14.199",
|
"@types/mime": "3.0.4",
|
||||||
"@types/mime": "3.0.2",
|
|
||||||
"@types/minimatch": "5.1.2",
|
"@types/minimatch": "5.1.2",
|
||||||
"@types/node": "20.8.3",
|
"@types/node": "20.10.6",
|
||||||
"@types/node-fetch": "2.6.6",
|
"@types/node-fetch": "2.6.10",
|
||||||
"@types/qs": "6.9.8",
|
"@types/qs": "6.9.11",
|
||||||
"@types/range-parser": "1.2.5",
|
"@types/range-parser": "1.2.7",
|
||||||
"@types/react": "18.2.25",
|
"@types/react": "18.2.47",
|
||||||
"@types/react-dom": "18.2.11",
|
"@types/react-dom": "18.2.18",
|
||||||
"@types/react-router-dom": "5.3.3",
|
"@types/react-router-dom": "5.3.3",
|
||||||
"@types/react-virtualized": "9.21.23",
|
"@types/react-virtualized": "9.21.29",
|
||||||
"@types/redux": "3.6.0",
|
"@types/redux": "3.6.0",
|
||||||
"@types/request": "2.48.9",
|
"@types/semver": "7.5.6",
|
||||||
"@types/semver": "7.5.3",
|
"@types/send": "0.17.4",
|
||||||
"@types/send": "0.17.2",
|
"@types/serve-static": "1.15.5",
|
||||||
"@types/serve-static": "1.15.3",
|
"@types/superagent": "4.1.24",
|
||||||
"@types/superagent": "4.1.19",
|
"@types/supertest": "2.0.16",
|
||||||
"@types/supertest": "2.0.14",
|
|
||||||
"@types/testing-library__jest-dom": "6.0.0",
|
"@types/testing-library__jest-dom": "6.0.0",
|
||||||
"@types/validator": "13.11.2",
|
"@types/validator": "13.11.7",
|
||||||
"@types/webpack": "5.28.3",
|
"@types/webpack": "5.28.5",
|
||||||
"@types/webpack-env": "1.18.2",
|
"@types/webpack-env": "1.18.4",
|
||||||
"@typescript-eslint/eslint-plugin": "6.7.4",
|
"@typescript-eslint/eslint-plugin": "6.18.0",
|
||||||
"@typescript-eslint/parser": "6.7.4",
|
"@typescript-eslint/parser": "6.18.0",
|
||||||
"@verdaccio/crowdin-translations": "workspace:*",
|
"@verdaccio/crowdin-translations": "workspace:*",
|
||||||
"@verdaccio/eslint-config": "workspace:*",
|
"@verdaccio/eslint-config": "workspace:*",
|
||||||
"@verdaccio/types": "workspace:*",
|
"@verdaccio/types": "workspace:*",
|
||||||
"@verdaccio/ui-theme": "workspace:*",
|
"@verdaccio/ui-theme": "workspace:*",
|
||||||
"@vitest/coverage-v8": "^0.34.6",
|
"@vitest/coverage-v8": "0.34.6",
|
||||||
"babel-core": "7.0.0-bridge.0",
|
"babel-core": "7.0.0-bridge.0",
|
||||||
"babel-jest": "29.7.0",
|
"babel-jest": "29.7.0",
|
||||||
"babel-plugin-dynamic-import-node": "2.3.3",
|
"babel-plugin-dynamic-import-node": "2.3.3",
|
||||||
"babel-plugin-emotion": "11.0.0",
|
"babel-plugin-emotion": "11.0.0",
|
||||||
"concurrently": "6.5.1",
|
"concurrently": "8.2.2",
|
||||||
"cross-env": "7.0.3",
|
"cross-env": "7.0.3",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"detect-secrets": "1.0.6",
|
"detect-secrets": "1.0.6",
|
||||||
"eslint": "8.51.0",
|
"eslint": "8.56.0",
|
||||||
"fs-extra": "10.1.0",
|
"fs-extra": "11.2.0",
|
||||||
"got": "11.8.6",
|
"got": "11.8.6",
|
||||||
"husky": "7.0.4",
|
"husky": "8.0.3",
|
||||||
"in-publish": "2.0.1",
|
"in-publish": "2.0.1",
|
||||||
"jest": "29.7.0",
|
"jest": "29.7.0",
|
||||||
"jest-diff": "29.7.0",
|
"jest-diff": "29.7.0",
|
||||||
@@ -110,23 +108,24 @@
|
|||||||
"jest-junit": "16.0.0",
|
"jest-junit": "16.0.0",
|
||||||
"kleur": "4.1.5",
|
"kleur": "4.1.5",
|
||||||
"lint-staged": "11.2.6",
|
"lint-staged": "11.2.6",
|
||||||
"nock": "13.3.3",
|
"nock": "13.4.0",
|
||||||
"nodemon": "2.0.22",
|
"nodemon": "3.0.2",
|
||||||
"npm-run-all": "4.1.5",
|
"npm-run-all": "4.1.5",
|
||||||
"prettier": "2.8.8",
|
"prettier": "3.1.1",
|
||||||
"react": "18.2.0",
|
"react": "18.2.0",
|
||||||
"react-dom": "18.2.0",
|
"react-dom": "18.2.0",
|
||||||
"rimraf": "3.0.2",
|
"rimraf": "5.0.5",
|
||||||
"selfsigned": "1.10.14",
|
"selfsigned": "2.4.1",
|
||||||
"supertest": "6.3.3",
|
"supertest": "6.3.3",
|
||||||
"ts-node": "10.9.1",
|
"ts-node": "10.9.2",
|
||||||
"typescript": "5.2.2",
|
"typescript": "5.2.2",
|
||||||
"update-ts-references": "2.6.1",
|
"undici-types": "5.28.2",
|
||||||
|
"update-ts-references": "3.2.1",
|
||||||
"verdaccio-audit": "workspace:*",
|
"verdaccio-audit": "workspace:*",
|
||||||
"verdaccio-auth-memory": "workspace:*",
|
"verdaccio-auth-memory": "workspace:*",
|
||||||
"verdaccio-htpasswd": "workspace:*",
|
"verdaccio-htpasswd": "workspace:*",
|
||||||
"verdaccio-memory": "workspace:*",
|
"verdaccio-memory": "workspace:*",
|
||||||
"vitest": "^0.34.3"
|
"vitest": "0.34.6"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"prepare": "husky install",
|
"prepare": "husky install",
|
||||||
@@ -172,12 +171,6 @@
|
|||||||
"local:publish": "cross-env npm_config_registry=http://localhost:4873 changeset publish --no-git-tag",
|
"local:publish": "cross-env npm_config_registry=http://localhost:4873 changeset publish --no-git-tag",
|
||||||
"local:publish:release": "concurrently \"pnpm local:registry\" \"pnpm local:publish\""
|
"local:publish:release": "concurrently \"pnpm local:registry\" \"pnpm local:publish\""
|
||||||
},
|
},
|
||||||
"pnpm": {
|
|
||||||
"overrides": {
|
|
||||||
"got": "11.8.5",
|
|
||||||
"p-cancelable": "2.1.1"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=18"
|
"node": ">=18"
|
||||||
},
|
},
|
||||||
@@ -185,5 +178,6 @@
|
|||||||
"lint-staged": {
|
"lint-staged": {
|
||||||
"*.{js,jsx,ts,tsx,json,yml,yaml,md}": "prettier --write",
|
"*.{js,jsx,ts,tsx,json,yml,yaml,md}": "prettier --write",
|
||||||
"*.{js,jsx,ts,tsx}": "eslint --cache --fix"
|
"*.{js,jsx,ts,tsx}": "eslint --cache --fix"
|
||||||
}
|
},
|
||||||
|
"packageManager": "pnpm@8.14.0+sha256.9cebf61abd83f68177b29484da72da9751390eaad46dfc3072d266bfbb1ba7bf"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,48 @@
|
|||||||
# @verdaccio/api
|
# @verdaccio/api
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [e14b064]
|
||||||
|
- Updated dependencies [4d96324]
|
||||||
|
- @verdaccio/store@7.0.0-next.6
|
||||||
|
- @verdaccio/config@7.0.0-next.6
|
||||||
|
- @verdaccio/auth@7.0.0-next.6
|
||||||
|
- @verdaccio/middleware@7.0.0-next.6
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
- @verdaccio/utils@7.0.0-next.6
|
||||||
|
- @verdaccio/logger@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Minor Changes
|
||||||
|
|
||||||
|
- f047cc8: refactor: auth with legacy sign support
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/middleware@7.0.0-next.5
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
- @verdaccio/config@7.0.0-next.5
|
||||||
|
- @verdaccio/auth@7.0.0-next.5
|
||||||
|
- @verdaccio/store@7.0.0-next.5
|
||||||
|
- @verdaccio/logger@7.0.0-next.5
|
||||||
|
- @verdaccio/utils@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/auth@7.0.0-next.4
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
- @verdaccio/config@7.0.0-next.4
|
||||||
|
- @verdaccio/middleware@7.0.0-next.4
|
||||||
|
- @verdaccio/store@7.0.0-next.4
|
||||||
|
- @verdaccio/utils@7.0.0-next.4
|
||||||
|
- @verdaccio/logger@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/api",
|
"name": "@verdaccio/api",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "loaders logic",
|
"description": "loaders logic",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "build/index.d.ts",
|
"types": "build/index.d.ts",
|
||||||
@@ -38,16 +38,16 @@
|
|||||||
},
|
},
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/auth": "workspace:7.0.0-next.3",
|
"@verdaccio/auth": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/config": "workspace:7.0.0-next.3",
|
"@verdaccio/config": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/logger": "workspace:7.0.0-next.3",
|
"@verdaccio/logger": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/middleware": "workspace:7.0.0-next.3",
|
"@verdaccio/middleware": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/store": "workspace:7.0.0-next.3",
|
"@verdaccio/store": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/utils": "workspace:7.0.0-next.3",
|
"@verdaccio/utils": "workspace:7.0.0-next.6",
|
||||||
"abortcontroller-polyfill": "1.7.5",
|
"abortcontroller-polyfill": "1.7.5",
|
||||||
"body-parser": "1.20.2",
|
"body-parser": "1.20.2",
|
||||||
"cookies": "0.8.0",
|
"cookies": "0.9.0",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"express": "4.18.2",
|
"express": "4.18.2",
|
||||||
"lodash": "4.17.21",
|
"lodash": "4.17.21",
|
||||||
@@ -55,11 +55,10 @@
|
|||||||
"semver": "7.5.4"
|
"semver": "7.5.4"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/server": "workspace:7.0.0-next.3",
|
"@verdaccio/test-helper": "workspace:3.0.0-next.1",
|
||||||
"@verdaccio/test-helper": "workspace:3.0.0-next.0",
|
"@verdaccio/types": "workspace:12.0.0-next.2",
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1",
|
|
||||||
"mockdate": "3.0.5",
|
"mockdate": "3.0.5",
|
||||||
"nock": "13.3.3",
|
"nock": "13.4.0",
|
||||||
"supertest": "6.3.3"
|
"supertest": "6.3.3"
|
||||||
},
|
},
|
||||||
"funding": {
|
"funding": {
|
||||||
|
|||||||
@@ -43,7 +43,6 @@ export default function (config: Config, auth: Auth, storage: Storage): Router {
|
|||||||
app.param('org_couchdb_user', match(/^org\.couchdb\.user:/));
|
app.param('org_couchdb_user', match(/^org\.couchdb\.user:/));
|
||||||
app.use(auth.apiJWTmiddleware());
|
app.use(auth.apiJWTmiddleware());
|
||||||
app.use(express.json({ strict: false, limit: config.max_body_size || '10mb' }));
|
app.use(express.json({ strict: false, limit: config.max_body_size || '10mb' }));
|
||||||
// @ts-ignore
|
|
||||||
app.use(antiLoop(config));
|
app.use(antiLoop(config));
|
||||||
// encode / in a scoped package name to be matched as a single parameter in routes
|
// encode / in a scoped package name to be matched as a single parameter in routes
|
||||||
app.use(encodeScopePackage);
|
app.use(encodeScopePackage);
|
||||||
|
|||||||
@@ -196,10 +196,10 @@ export function publishPackage(storage: Storage): any {
|
|||||||
requestOptions: {
|
requestOptions: {
|
||||||
host: req.hostname,
|
host: req.hostname,
|
||||||
protocol: req.protocol,
|
protocol: req.protocol,
|
||||||
// @ts-ignore
|
headers: req.headers as { [key: string]: string },
|
||||||
headers: req.headers,
|
|
||||||
username,
|
username,
|
||||||
},
|
},
|
||||||
|
uplinksLook: false,
|
||||||
});
|
});
|
||||||
|
|
||||||
res.status(HTTP_STATUS.CREATED);
|
res.status(HTTP_STATUS.CREATED);
|
||||||
|
|||||||
@@ -1,5 +1,48 @@
|
|||||||
# @verdaccio/auth
|
# @verdaccio/auth
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [4d96324]
|
||||||
|
- @verdaccio/config@7.0.0-next.6
|
||||||
|
- @verdaccio/loaders@7.0.0-next.6
|
||||||
|
- verdaccio-htpasswd@12.0.0-next.6
|
||||||
|
- @verdaccio/signature@7.0.0-next.3
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
- @verdaccio/utils@7.0.0-next.6
|
||||||
|
- @verdaccio/logger@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Minor Changes
|
||||||
|
|
||||||
|
- f047cc8: refactor: auth with legacy sign support
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
- @verdaccio/signature@7.0.0-next.3
|
||||||
|
- @verdaccio/config@7.0.0-next.5
|
||||||
|
- @verdaccio/loaders@7.0.0-next.5
|
||||||
|
- @verdaccio/logger@7.0.0-next.5
|
||||||
|
- verdaccio-htpasswd@12.0.0-next.5
|
||||||
|
- @verdaccio/utils@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [312bc100f]
|
||||||
|
- @verdaccio/signature@7.0.0-next.2
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
- @verdaccio/config@7.0.0-next.4
|
||||||
|
- @verdaccio/loaders@7.0.0-next.4
|
||||||
|
- verdaccio-htpasswd@12.0.0-next.4
|
||||||
|
- @verdaccio/utils@7.0.0-next.4
|
||||||
|
- @verdaccio/logger@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/auth",
|
"name": "@verdaccio/auth",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "logger",
|
"description": "logger",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "./build/index.d.ts",
|
"types": "./build/index.d.ts",
|
||||||
@@ -38,19 +38,21 @@
|
|||||||
},
|
},
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/config": "workspace:7.0.0-next.3",
|
"@verdaccio/config": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/loaders": "workspace:7.0.0-next.3",
|
"@verdaccio/loaders": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/logger": "workspace:7.0.0-next.3",
|
"@verdaccio/logger": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/signature": "workspace:7.0.0-next.1",
|
"@verdaccio/signature": "workspace:7.0.0-next.3",
|
||||||
"@verdaccio/utils": "workspace:7.0.0-next.3",
|
"@verdaccio/utils": "workspace:7.0.0-next.6",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"express": "4.18.2",
|
|
||||||
"lodash": "4.17.21",
|
"lodash": "4.17.21",
|
||||||
"verdaccio-htpasswd": "workspace:12.0.0-next.3"
|
"verdaccio-htpasswd": "workspace:12.0.0-next.6"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1"
|
"express": "4.18.2",
|
||||||
|
"supertest": "6.3.3",
|
||||||
|
"@verdaccio/middleware": "workspace:7.0.0-next.6",
|
||||||
|
"@verdaccio/types": "workspace:12.0.0-next.2"
|
||||||
},
|
},
|
||||||
"funding": {
|
"funding": {
|
||||||
"type": "opencollective",
|
"type": "opencollective",
|
||||||
|
|||||||
@@ -1,5 +1,4 @@
|
|||||||
import buildDebug from 'debug';
|
import buildDebug from 'debug';
|
||||||
import { NextFunction, Request, RequestHandler, Response } from 'express';
|
|
||||||
import _ from 'lodash';
|
import _ from 'lodash';
|
||||||
import { HTPasswd } from 'verdaccio-htpasswd';
|
import { HTPasswd } from 'verdaccio-htpasswd';
|
||||||
|
|
||||||
@@ -12,22 +11,36 @@ import {
|
|||||||
VerdaccioError,
|
VerdaccioError,
|
||||||
errorUtils,
|
errorUtils,
|
||||||
pluginUtils,
|
pluginUtils,
|
||||||
|
warningUtils,
|
||||||
} from '@verdaccio/core';
|
} from '@verdaccio/core';
|
||||||
|
import '@verdaccio/core';
|
||||||
import { asyncLoadPlugin } from '@verdaccio/loaders';
|
import { asyncLoadPlugin } from '@verdaccio/loaders';
|
||||||
import { logger } from '@verdaccio/logger';
|
import { logger } from '@verdaccio/logger';
|
||||||
import { aesEncrypt, parseBasicPayload, signPayload } from '@verdaccio/signature';
|
import {
|
||||||
|
aesEncrypt,
|
||||||
|
aesEncryptDeprecated,
|
||||||
|
parseBasicPayload,
|
||||||
|
signPayload,
|
||||||
|
} from '@verdaccio/signature';
|
||||||
import {
|
import {
|
||||||
AllowAccess,
|
AllowAccess,
|
||||||
Callback,
|
Callback,
|
||||||
Config,
|
Config,
|
||||||
JWTSignOptions,
|
JWTSignOptions,
|
||||||
Logger,
|
|
||||||
PackageAccess,
|
PackageAccess,
|
||||||
RemoteUser,
|
RemoteUser,
|
||||||
Security,
|
Security,
|
||||||
} from '@verdaccio/types';
|
} from '@verdaccio/types';
|
||||||
import { getMatchedPackagesSpec, isFunction, isNil } from '@verdaccio/utils';
|
import { getMatchedPackagesSpec, isFunction, isNil } from '@verdaccio/utils';
|
||||||
|
|
||||||
|
import {
|
||||||
|
$RequestExtend,
|
||||||
|
$ResponseExtend,
|
||||||
|
AESPayload,
|
||||||
|
IAuthMiddleware,
|
||||||
|
NextFunction,
|
||||||
|
TokenEncryption,
|
||||||
|
} from './types';
|
||||||
import {
|
import {
|
||||||
convertPayloadToBase64,
|
convertPayloadToBase64,
|
||||||
getDefaultPlugins,
|
getDefaultPlugins,
|
||||||
@@ -40,25 +53,6 @@ import {
|
|||||||
|
|
||||||
const debug = buildDebug('verdaccio:auth');
|
const debug = buildDebug('verdaccio:auth');
|
||||||
|
|
||||||
export interface TokenEncryption {
|
|
||||||
jwtEncrypt(user: RemoteUser, signOptions: JWTSignOptions): Promise<string>;
|
|
||||||
aesEncrypt(buf: string): string | void;
|
|
||||||
}
|
|
||||||
|
|
||||||
// remove
|
|
||||||
export interface AESPayload {
|
|
||||||
user: string;
|
|
||||||
password: string;
|
|
||||||
}
|
|
||||||
export interface IAuthMiddleware {
|
|
||||||
apiJWTmiddleware(): $NextFunctionVer;
|
|
||||||
webUIJWTmiddleware(): $NextFunctionVer;
|
|
||||||
}
|
|
||||||
|
|
||||||
export type $RequestExtend = Request & { remote_user?: any; log: Logger };
|
|
||||||
export type $ResponseExtend = Response & { cookies?: any };
|
|
||||||
export type $NextFunctionVer = NextFunction & any;
|
|
||||||
|
|
||||||
class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
||||||
public config: Config;
|
public config: Config;
|
||||||
public secret: string;
|
public secret: string;
|
||||||
@@ -75,6 +69,7 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
|
|
||||||
public async init() {
|
public async init() {
|
||||||
let plugins = (await this.loadPlugin()) as pluginUtils.Auth<unknown>[];
|
let plugins = (await this.loadPlugin()) as pluginUtils.Auth<unknown>[];
|
||||||
|
|
||||||
debug('auth plugins found %s', plugins.length);
|
debug('auth plugins found %s', plugins.length);
|
||||||
if (!plugins || plugins.length === 0) {
|
if (!plugins || plugins.length === 0) {
|
||||||
plugins = this.loadDefaultPlugin();
|
plugins = this.loadDefaultPlugin();
|
||||||
@@ -226,29 +221,32 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
debug('add user %o', user);
|
debug('add user %o', user);
|
||||||
|
|
||||||
(function next(): void {
|
(function next(): void {
|
||||||
|
let method = 'adduser';
|
||||||
const plugin = plugins.shift() as pluginUtils.Auth<Config>;
|
const plugin = plugins.shift() as pluginUtils.Auth<Config>;
|
||||||
if (typeof plugin.adduser !== 'function') {
|
// @ts-expect-error future major (7.x) should remove this section
|
||||||
|
if (typeof plugin.adduser === 'undefined' && typeof plugin.add_user === 'function') {
|
||||||
|
method = 'add_user';
|
||||||
|
warningUtils.emit(warningUtils.Codes.VERWAR006);
|
||||||
|
}
|
||||||
|
// @ts-ignore
|
||||||
|
if (typeof plugin[method] !== 'function') {
|
||||||
next();
|
next();
|
||||||
} else {
|
} else {
|
||||||
// @ts-expect-error future major (7.x) should remove this section
|
// TODO: replace by adduser whenever add_user deprecation method has been removed
|
||||||
if (typeof plugin.adduser === 'undefined' && typeof plugin.add_user === 'function') {
|
// @ts-ignore
|
||||||
throw errorUtils.getInternalError(
|
plugin[method](
|
||||||
'add_user method not longer supported, rename to adduser'
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
plugin.adduser(
|
|
||||||
user,
|
user,
|
||||||
password,
|
password,
|
||||||
function (err: VerdaccioError | null, ok?: boolean | string): void {
|
function (err: VerdaccioError | null, ok?: boolean | string): void {
|
||||||
if (err) {
|
if (err) {
|
||||||
debug('the user %o could not being added. Error: %o', user, err?.message);
|
debug('the user %o could not being added. Error: %o', user, err?.message);
|
||||||
return cb(err);
|
return cb(err);
|
||||||
}
|
}
|
||||||
if (ok) {
|
if (ok) {
|
||||||
debug('the user %o has been added', user);
|
debug('the user %o has been added', user);
|
||||||
return self.authenticate(user, password, cb);
|
return self.authenticate(user, password, cb);
|
||||||
}
|
}
|
||||||
|
debug('user could not be added, skip to next auth plugin');
|
||||||
next();
|
next();
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
@@ -308,12 +306,11 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
debug('allow unpublish for %o', packageName);
|
debug('allow unpublish for %o', packageName);
|
||||||
|
|
||||||
for (const plugin of this.plugins) {
|
for (const plugin of this.plugins) {
|
||||||
if (_.isNil(plugin) || isFunction(plugin.allow_unpublish) === false) {
|
if (typeof plugin?.allow_unpublish !== 'function') {
|
||||||
debug('allow unpublish for %o plugin does not implement allow_unpublish', packageName);
|
debug('allow unpublish for %o plugin does not implement allow_unpublish', packageName);
|
||||||
continue;
|
continue;
|
||||||
} else {
|
} else {
|
||||||
// @ts-ignore
|
plugin.allow_unpublish(user, pkg, (err, ok): void => {
|
||||||
plugin.allow_unpublish!(user, pkg, (err, ok: boolean): void => {
|
|
||||||
if (err) {
|
if (err) {
|
||||||
debug(
|
debug(
|
||||||
'forbidden publish for %o, it will fallback on unpublish permissions',
|
'forbidden publish for %o, it will fallback on unpublish permissions',
|
||||||
@@ -324,9 +321,7 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
|
|
||||||
if (_.isNil(ok) === true) {
|
if (_.isNil(ok) === true) {
|
||||||
debug('bypass unpublish for %o, publish will handle the access', packageName);
|
debug('bypass unpublish for %o, publish will handle the access', packageName);
|
||||||
// @ts-ignore
|
return this.allow_publish({ packageName, packageVersion }, user, callback);
|
||||||
// eslint-disable-next-line
|
|
||||||
return this.allow_publish(...arguments);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ok) {
|
if (ok) {
|
||||||
@@ -350,7 +345,7 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
const pkg = Object.assign(
|
const pkg = Object.assign(
|
||||||
{ name: packageName, version: packageVersion },
|
{ name: packageName, version: packageVersion },
|
||||||
getMatchedPackagesSpec(packageName, this.config.packages)
|
getMatchedPackagesSpec(packageName, this.config.packages)
|
||||||
) as any;
|
);
|
||||||
debug('allow publish for %o init | plugins: %o', packageName, plugins.length);
|
debug('allow publish for %o init | plugins: %o', packageName, plugins.length);
|
||||||
|
|
||||||
(function next(): void {
|
(function next(): void {
|
||||||
@@ -378,7 +373,7 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
})();
|
})();
|
||||||
}
|
}
|
||||||
|
|
||||||
public apiJWTmiddleware(): RequestHandler {
|
public apiJWTmiddleware(): any {
|
||||||
debug('jwt middleware');
|
debug('jwt middleware');
|
||||||
const plugins = this.plugins.slice(0);
|
const plugins = this.plugins.slice(0);
|
||||||
const helpers = { createAnonymousRemoteUser, createRemoteUser };
|
const helpers = { createAnonymousRemoteUser, createRemoteUser };
|
||||||
@@ -388,11 +383,9 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// @ts-ignore
|
|
||||||
return (req: $RequestExtend, res: $ResponseExtend, _next: NextFunction) => {
|
return (req: $RequestExtend, res: $ResponseExtend, _next: NextFunction) => {
|
||||||
req.pause();
|
req.pause();
|
||||||
|
const next = function (err?: VerdaccioError): NextFunction {
|
||||||
const next = function (err?: VerdaccioError): any {
|
|
||||||
req.resume();
|
req.resume();
|
||||||
// uncomment this to reject users with bad auth headers
|
// uncomment this to reject users with bad auth headers
|
||||||
// return _next.apply(null, arguments)
|
// return _next.apply(null, arguments)
|
||||||
@@ -402,13 +395,14 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
req.remote_user.error = err.message;
|
req.remote_user.error = err.message;
|
||||||
}
|
}
|
||||||
|
|
||||||
return _next();
|
return _next() as unknown as NextFunction;
|
||||||
};
|
};
|
||||||
|
|
||||||
if (this._isRemoteUserValid(req.remote_user)) {
|
// FUTURE: disabled, not removed yet but seems unreacable code
|
||||||
debug('jwt has a valid authentication header');
|
// if (this._isRemoteUserValid(req.remote_user)) {
|
||||||
return next();
|
// debug('jwt has a valid authentication header');
|
||||||
}
|
// return next();
|
||||||
|
// }
|
||||||
|
|
||||||
// in case auth header does not exist we return anonymous function
|
// in case auth header does not exist we return anonymous function
|
||||||
const remoteUser = createAnonymousRemoteUser();
|
const remoteUser = createAnonymousRemoteUser();
|
||||||
@@ -429,20 +423,20 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
|
|
||||||
if (isAESLegacy(security)) {
|
if (isAESLegacy(security)) {
|
||||||
debug('api middleware using legacy auth token');
|
debug('api middleware using legacy auth token');
|
||||||
this._handleAESMiddleware(req, security, secret, authorization, next);
|
this.handleAESMiddleware(req, security, secret, authorization, next);
|
||||||
} else {
|
} else {
|
||||||
debug('api middleware using JWT auth token');
|
debug('api middleware using JWT auth token');
|
||||||
this._handleJWTAPIMiddleware(req, security, secret, authorization, next);
|
this.handleJWTAPIMiddleware(req, security, secret, authorization, next);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
private _handleJWTAPIMiddleware(
|
private handleJWTAPIMiddleware(
|
||||||
req: $RequestExtend,
|
req: $RequestExtend,
|
||||||
security: Security,
|
security: Security,
|
||||||
secret: string,
|
secret: string,
|
||||||
authorization: string,
|
authorization: string,
|
||||||
next: Function
|
next: any
|
||||||
): void {
|
): void {
|
||||||
debug('handle JWT api middleware');
|
debug('handle JWT api middleware');
|
||||||
const { scheme, token } = parseAuthTokenHeader(authorization);
|
const { scheme, token } = parseAuthTokenHeader(authorization);
|
||||||
@@ -479,7 +473,7 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private _handleAESMiddleware(
|
private handleAESMiddleware(
|
||||||
req: $RequestExtend,
|
req: $RequestExtend,
|
||||||
security: Security,
|
security: Security,
|
||||||
secret: string,
|
secret: string,
|
||||||
@@ -489,7 +483,12 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
debug('handle legacy api middleware');
|
debug('handle legacy api middleware');
|
||||||
debug('api middleware secret %o', typeof secret === 'string');
|
debug('api middleware secret %o', typeof secret === 'string');
|
||||||
debug('api middleware authorization %o', typeof authorization === 'string');
|
debug('api middleware authorization %o', typeof authorization === 'string');
|
||||||
const credentials: any = getMiddlewareCredentials(security, secret, authorization);
|
const credentials: any = getMiddlewareCredentials(
|
||||||
|
security,
|
||||||
|
secret,
|
||||||
|
authorization,
|
||||||
|
this.config?.getEnhancedLegacySignature()
|
||||||
|
);
|
||||||
debug('api middleware credentials %o', credentials?.name);
|
debug('api middleware credentials %o', credentials?.name);
|
||||||
if (credentials) {
|
if (credentials) {
|
||||||
const { user, password } = credentials;
|
const { user, password } = credentials;
|
||||||
@@ -519,8 +518,7 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
/**
|
/**
|
||||||
* JWT middleware for WebUI
|
* JWT middleware for WebUI
|
||||||
*/
|
*/
|
||||||
public webUIJWTmiddleware(): RequestHandler {
|
public webUIJWTmiddleware() {
|
||||||
// @ts-ignore
|
|
||||||
return (req: $RequestExtend, res: $ResponseExtend, _next: NextFunction): void => {
|
return (req: $RequestExtend, res: $ResponseExtend, _next: NextFunction): void => {
|
||||||
if (this._isRemoteUserValid(req.remote_user)) {
|
if (this._isRemoteUserValid(req.remote_user)) {
|
||||||
return _next();
|
return _next();
|
||||||
@@ -530,7 +528,7 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
const next = (err: VerdaccioError | void): void => {
|
const next = (err: VerdaccioError | void): void => {
|
||||||
req.resume();
|
req.resume();
|
||||||
if (err) {
|
if (err) {
|
||||||
// req.remote_user.error = err.message;
|
req.remote_user.error = err.message;
|
||||||
res.status(err.statusCode).send(err.message);
|
res.status(err.statusCode).send(err.message);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -581,7 +579,6 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
name,
|
name,
|
||||||
groups: groupedGroups,
|
groups: groupedGroups,
|
||||||
};
|
};
|
||||||
|
|
||||||
const token: string = await signPayload(payload, this.secret, signOptions);
|
const token: string = await signPayload(payload, this.secret, signOptions);
|
||||||
|
|
||||||
return token;
|
return token;
|
||||||
@@ -591,7 +588,17 @@ class Auth implements IAuthMiddleware, TokenEncryption, pluginUtils.IBasicAuth {
|
|||||||
* Encrypt a string.
|
* Encrypt a string.
|
||||||
*/
|
*/
|
||||||
public aesEncrypt(value: string): string | void {
|
public aesEncrypt(value: string): string | void {
|
||||||
return aesEncrypt(value, this.secret);
|
// enhancedLegacySignature enables modern aes192 algorithm signature
|
||||||
|
if (this.config?.getEnhancedLegacySignature()) {
|
||||||
|
debug('signing with enhaced aes legacy');
|
||||||
|
const token = aesEncrypt(value, this.secret);
|
||||||
|
return token;
|
||||||
|
} else {
|
||||||
|
debug('signing with enhaced aes deprecated legacy');
|
||||||
|
// deprecated aes (legacy) signature, only must be used for legacy version
|
||||||
|
const token = aesEncryptDeprecated(Buffer.from(value), this.secret).toString('base64');
|
||||||
|
return token;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,2 +1,3 @@
|
|||||||
export { Auth } from './auth';
|
export { Auth } from './auth';
|
||||||
export * from './utils';
|
export * from './utils';
|
||||||
|
export * from './types';
|
||||||
|
|||||||
66
packages/auth/src/signature-legacy.ts
Normal file
66
packages/auth/src/signature-legacy.ts
Normal file
@@ -0,0 +1,66 @@
|
|||||||
|
import buildDebug from 'debug';
|
||||||
|
import _ from 'lodash';
|
||||||
|
|
||||||
|
import { TOKEN_BASIC, TOKEN_BEARER } from '@verdaccio/core';
|
||||||
|
import { aesDecryptDeprecated as aesDecrypt, parseBasicPayload } from '@verdaccio/signature';
|
||||||
|
import { Security } from '@verdaccio/types';
|
||||||
|
|
||||||
|
import { AuthMiddlewarePayload } from './types';
|
||||||
|
import {
|
||||||
|
convertPayloadToBase64,
|
||||||
|
isAESLegacy,
|
||||||
|
parseAuthTokenHeader,
|
||||||
|
verifyJWTPayload,
|
||||||
|
} from './utils';
|
||||||
|
|
||||||
|
const debug = buildDebug('verdaccio:auth:utils');
|
||||||
|
|
||||||
|
export function parseAESCredentials(authorizationHeader: string, secret: string) {
|
||||||
|
debug('parseAESCredentials');
|
||||||
|
const { scheme, token } = parseAuthTokenHeader(authorizationHeader);
|
||||||
|
|
||||||
|
// basic is deprecated and should not be enforced
|
||||||
|
// basic is currently being used for functional test
|
||||||
|
if (scheme.toUpperCase() === TOKEN_BASIC.toUpperCase()) {
|
||||||
|
debug('legacy header basic');
|
||||||
|
const credentials = convertPayloadToBase64(token).toString();
|
||||||
|
|
||||||
|
return credentials;
|
||||||
|
} else if (scheme.toUpperCase() === TOKEN_BEARER.toUpperCase()) {
|
||||||
|
debug('legacy header bearer');
|
||||||
|
const credentials = aesDecrypt(Buffer.from(token), secret);
|
||||||
|
|
||||||
|
return credentials;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export function getMiddlewareCredentials(
|
||||||
|
security: Security,
|
||||||
|
secretKey: string,
|
||||||
|
authorizationHeader: string
|
||||||
|
): AuthMiddlewarePayload {
|
||||||
|
debug('getMiddlewareCredentials');
|
||||||
|
// comment out for debugging purposes
|
||||||
|
if (isAESLegacy(security)) {
|
||||||
|
debug('is legacy');
|
||||||
|
const credentials = parseAESCredentials(authorizationHeader, secretKey);
|
||||||
|
if (typeof credentials !== 'string') {
|
||||||
|
debug('parse legacy credentials failed');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const parsedCredentials = parseBasicPayload(credentials);
|
||||||
|
if (!parsedCredentials) {
|
||||||
|
debug('parse legacy basic payload credentials failed');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
return parsedCredentials;
|
||||||
|
}
|
||||||
|
const { scheme, token } = parseAuthTokenHeader(authorizationHeader);
|
||||||
|
|
||||||
|
debug('is jwt');
|
||||||
|
if (_.isString(token) && scheme.toUpperCase() === TOKEN_BEARER.toUpperCase()) {
|
||||||
|
return verifyJWTPayload(token, secretKey);
|
||||||
|
}
|
||||||
|
}
|
||||||
66
packages/auth/src/signature.ts
Normal file
66
packages/auth/src/signature.ts
Normal file
@@ -0,0 +1,66 @@
|
|||||||
|
import buildDebug from 'debug';
|
||||||
|
import _ from 'lodash';
|
||||||
|
|
||||||
|
import { TOKEN_BASIC, TOKEN_BEARER } from '@verdaccio/core';
|
||||||
|
import { aesDecrypt, parseBasicPayload } from '@verdaccio/signature';
|
||||||
|
import { Security } from '@verdaccio/types';
|
||||||
|
|
||||||
|
import { AuthMiddlewarePayload } from './types';
|
||||||
|
import {
|
||||||
|
convertPayloadToBase64,
|
||||||
|
isAESLegacy,
|
||||||
|
parseAuthTokenHeader,
|
||||||
|
verifyJWTPayload,
|
||||||
|
} from './utils';
|
||||||
|
|
||||||
|
const debug = buildDebug('verdaccio:auth:utils');
|
||||||
|
|
||||||
|
export function parseAESCredentials(authorizationHeader: string, secret: string) {
|
||||||
|
debug('parseAESCredentials');
|
||||||
|
const { scheme, token } = parseAuthTokenHeader(authorizationHeader);
|
||||||
|
|
||||||
|
// basic is deprecated and should not be enforced
|
||||||
|
// basic is currently being used for functional test
|
||||||
|
if (scheme.toUpperCase() === TOKEN_BASIC.toUpperCase()) {
|
||||||
|
debug('legacy header basic');
|
||||||
|
const credentials = convertPayloadToBase64(token).toString();
|
||||||
|
|
||||||
|
return credentials;
|
||||||
|
} else if (scheme.toUpperCase() === TOKEN_BEARER.toUpperCase()) {
|
||||||
|
debug('legacy header bearer');
|
||||||
|
const credentials = aesDecrypt(token, secret);
|
||||||
|
|
||||||
|
return credentials;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export function getMiddlewareCredentials(
|
||||||
|
security: Security,
|
||||||
|
secretKey: string,
|
||||||
|
authorizationHeader: string
|
||||||
|
): AuthMiddlewarePayload {
|
||||||
|
debug('getMiddlewareCredentials');
|
||||||
|
// comment out for debugging purposes
|
||||||
|
if (isAESLegacy(security)) {
|
||||||
|
debug('is legacy');
|
||||||
|
const credentials = parseAESCredentials(authorizationHeader, secretKey);
|
||||||
|
if (!credentials) {
|
||||||
|
debug('parse legacy credentials failed');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const parsedCredentials = parseBasicPayload(credentials);
|
||||||
|
if (!parsedCredentials) {
|
||||||
|
debug('parse legacy basic payload credentials failed');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
return parsedCredentials;
|
||||||
|
}
|
||||||
|
const { scheme, token } = parseAuthTokenHeader(authorizationHeader);
|
||||||
|
|
||||||
|
debug('is jwt');
|
||||||
|
if (_.isString(token) && scheme.toUpperCase() === TOKEN_BEARER.toUpperCase()) {
|
||||||
|
return verifyJWTPayload(token, secretKey);
|
||||||
|
}
|
||||||
|
}
|
||||||
46
packages/auth/src/types.ts
Normal file
46
packages/auth/src/types.ts
Normal file
@@ -0,0 +1,46 @@
|
|||||||
|
import { NextFunction, Request, Response } from 'express';
|
||||||
|
|
||||||
|
import { VerdaccioError } from '@verdaccio/core';
|
||||||
|
import { AuthPackageAllow, JWTSignOptions, Logger, RemoteUser } from '@verdaccio/types';
|
||||||
|
|
||||||
|
export interface AESPayload {
|
||||||
|
user: string;
|
||||||
|
password: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export type BasicPayload = AESPayload | void;
|
||||||
|
export type AuthMiddlewarePayload = RemoteUser | BasicPayload;
|
||||||
|
|
||||||
|
export interface AuthTokenHeader {
|
||||||
|
scheme: string;
|
||||||
|
token: string;
|
||||||
|
}
|
||||||
|
export type AllowActionCallbackResponse = boolean | undefined;
|
||||||
|
export type AllowActionCallback = (
|
||||||
|
error: VerdaccioError | null,
|
||||||
|
allowed?: AllowActionCallbackResponse
|
||||||
|
) => void;
|
||||||
|
|
||||||
|
export type AllowAction = (
|
||||||
|
user: RemoteUser,
|
||||||
|
pkg: AuthPackageAllow,
|
||||||
|
callback: AllowActionCallback
|
||||||
|
) => void;
|
||||||
|
|
||||||
|
export interface TokenEncryption {
|
||||||
|
jwtEncrypt(user: RemoteUser, signOptions: JWTSignOptions): Promise<string>;
|
||||||
|
aesEncrypt(buf: string): string | void;
|
||||||
|
}
|
||||||
|
|
||||||
|
export type ActionsAllowed = 'publish' | 'unpublish' | 'access';
|
||||||
|
|
||||||
|
// remove
|
||||||
|
export interface IAuthMiddleware {
|
||||||
|
apiJWTmiddleware(): $NextFunctionVer;
|
||||||
|
webUIJWTmiddleware(): $NextFunctionVer;
|
||||||
|
}
|
||||||
|
|
||||||
|
export type $RequestExtend = Request & { remote_user?: any; log: Logger };
|
||||||
|
export type $ResponseExtend = Response & { cookies?: any };
|
||||||
|
export type $NextFunctionVer = NextFunction & any;
|
||||||
|
export { NextFunction };
|
||||||
@@ -7,36 +7,28 @@ import {
|
|||||||
HTTP_STATUS,
|
HTTP_STATUS,
|
||||||
TOKEN_BASIC,
|
TOKEN_BASIC,
|
||||||
TOKEN_BEARER,
|
TOKEN_BEARER,
|
||||||
VerdaccioError,
|
|
||||||
errorUtils,
|
errorUtils,
|
||||||
pluginUtils,
|
pluginUtils,
|
||||||
} from '@verdaccio/core';
|
} from '@verdaccio/core';
|
||||||
import { aesDecrypt, parseBasicPayload, verifyPayload } from '@verdaccio/signature';
|
import {
|
||||||
|
aesDecrypt,
|
||||||
|
aesDecryptDeprecated,
|
||||||
|
parseBasicPayload,
|
||||||
|
verifyPayload,
|
||||||
|
} from '@verdaccio/signature';
|
||||||
import { AuthPackageAllow, Config, Logger, RemoteUser, Security } from '@verdaccio/types';
|
import { AuthPackageAllow, Config, Logger, RemoteUser, Security } from '@verdaccio/types';
|
||||||
|
|
||||||
import { AESPayload, TokenEncryption } from './auth';
|
import {
|
||||||
|
ActionsAllowed,
|
||||||
|
AllowAction,
|
||||||
|
AllowActionCallback,
|
||||||
|
AuthMiddlewarePayload,
|
||||||
|
AuthTokenHeader,
|
||||||
|
TokenEncryption,
|
||||||
|
} from './types';
|
||||||
|
|
||||||
const debug = buildDebug('verdaccio:auth:utils');
|
const debug = buildDebug('verdaccio:auth:utils');
|
||||||
|
|
||||||
export type BasicPayload = AESPayload | void;
|
|
||||||
export type AuthMiddlewarePayload = RemoteUser | BasicPayload;
|
|
||||||
|
|
||||||
export interface AuthTokenHeader {
|
|
||||||
scheme: string;
|
|
||||||
token: string;
|
|
||||||
}
|
|
||||||
export type AllowActionCallbackResponse = boolean | undefined;
|
|
||||||
export type AllowActionCallback = (
|
|
||||||
error: VerdaccioError | null,
|
|
||||||
allowed?: AllowActionCallbackResponse
|
|
||||||
) => void;
|
|
||||||
|
|
||||||
export type AllowAction = (
|
|
||||||
user: RemoteUser,
|
|
||||||
pkg: AuthPackageAllow,
|
|
||||||
callback: AllowActionCallback
|
|
||||||
) => void;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Split authentication header eg: Bearer [secret_token]
|
* Split authentication header eg: Bearer [secret_token]
|
||||||
* @param authorizationHeader auth token
|
* @param authorizationHeader auth token
|
||||||
@@ -48,7 +40,11 @@ export function parseAuthTokenHeader(authorizationHeader: string): AuthTokenHead
|
|||||||
return { scheme, token };
|
return { scheme, token };
|
||||||
}
|
}
|
||||||
|
|
||||||
export function parseAESCredentials(authorizationHeader: string, secret: string) {
|
export function parseAESCredentials(
|
||||||
|
authorizationHeader: string,
|
||||||
|
secret: string,
|
||||||
|
enhanced: boolean
|
||||||
|
) {
|
||||||
debug('parseAESCredentials');
|
debug('parseAESCredentials');
|
||||||
const { scheme, token } = parseAuthTokenHeader(authorizationHeader);
|
const { scheme, token } = parseAuthTokenHeader(authorizationHeader);
|
||||||
|
|
||||||
@@ -61,7 +57,11 @@ export function parseAESCredentials(authorizationHeader: string, secret: string)
|
|||||||
return credentials;
|
return credentials;
|
||||||
} else if (scheme.toUpperCase() === TOKEN_BEARER.toUpperCase()) {
|
} else if (scheme.toUpperCase() === TOKEN_BEARER.toUpperCase()) {
|
||||||
debug('legacy header bearer');
|
debug('legacy header bearer');
|
||||||
const credentials = aesDecrypt(token, secret);
|
debug('legacy header enhanced?', enhanced);
|
||||||
|
const credentials = enhanced
|
||||||
|
? aesDecrypt(token.toString(), secret)
|
||||||
|
: // FUTURE: once deprecated legacy is removed this logic won't be longer need it
|
||||||
|
aesDecryptDeprecated(convertPayloadToBase64(token), secret).toString('utf-8');
|
||||||
|
|
||||||
return credentials;
|
return credentials;
|
||||||
}
|
}
|
||||||
@@ -70,13 +70,14 @@ export function parseAESCredentials(authorizationHeader: string, secret: string)
|
|||||||
export function getMiddlewareCredentials(
|
export function getMiddlewareCredentials(
|
||||||
security: Security,
|
security: Security,
|
||||||
secretKey: string,
|
secretKey: string,
|
||||||
authorizationHeader: string
|
authorizationHeader: string,
|
||||||
|
enhanced: boolean = true
|
||||||
): AuthMiddlewarePayload {
|
): AuthMiddlewarePayload {
|
||||||
debug('getMiddlewareCredentials');
|
debug('getMiddlewareCredentials');
|
||||||
// comment out for debugging purposes
|
// comment out for debugging purposes
|
||||||
if (isAESLegacy(security)) {
|
if (isAESLegacy(security)) {
|
||||||
debug('is legacy');
|
debug('is legacy');
|
||||||
const credentials = parseAESCredentials(authorizationHeader, secretKey);
|
const credentials = parseAESCredentials(authorizationHeader, secretKey, enhanced);
|
||||||
if (!credentials) {
|
if (!credentials) {
|
||||||
debug('parse legacy credentials failed');
|
debug('parse legacy credentials failed');
|
||||||
return;
|
return;
|
||||||
@@ -161,14 +162,15 @@ export function isAuthHeaderValid(authorization: string): boolean {
|
|||||||
export function getDefaultPlugins(logger: Logger): pluginUtils.Auth<Config> {
|
export function getDefaultPlugins(logger: Logger): pluginUtils.Auth<Config> {
|
||||||
return {
|
return {
|
||||||
authenticate(_user: string, _password: string, cb: pluginUtils.AuthCallback): void {
|
authenticate(_user: string, _password: string, cb: pluginUtils.AuthCallback): void {
|
||||||
|
debug('triggered default authenticate method');
|
||||||
cb(errorUtils.getForbidden(API_ERROR.BAD_USERNAME_PASSWORD));
|
cb(errorUtils.getForbidden(API_ERROR.BAD_USERNAME_PASSWORD));
|
||||||
},
|
},
|
||||||
|
|
||||||
adduser(_user: string, _password: string, cb: pluginUtils.AuthUserCallback): void {
|
adduser(_user: string, _password: string, cb: pluginUtils.AuthUserCallback): void {
|
||||||
|
debug('triggered default adduser method');
|
||||||
return cb(errorUtils.getConflict(API_ERROR.BAD_USERNAME_PASSWORD));
|
return cb(errorUtils.getConflict(API_ERROR.BAD_USERNAME_PASSWORD));
|
||||||
},
|
},
|
||||||
|
|
||||||
// FIXME: allow_action and allow_publish should be in the @verdaccio/types
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
allow_access: allow_action('access', logger),
|
allow_access: allow_action('access', logger),
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
@@ -177,8 +179,6 @@ export function getDefaultPlugins(logger: Logger): pluginUtils.Auth<Config> {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export type ActionsAllowed = 'publish' | 'unpublish' | 'access';
|
|
||||||
|
|
||||||
export function allow_action(action: ActionsAllowed, logger: Logger): AllowAction {
|
export function allow_action(action: ActionsAllowed, logger: Logger): AllowAction {
|
||||||
return function allowActionCallback(
|
return function allowActionCallback(
|
||||||
user: RemoteUser,
|
user: RemoteUser,
|
||||||
@@ -187,8 +187,13 @@ export function allow_action(action: ActionsAllowed, logger: Logger): AllowActio
|
|||||||
): void {
|
): void {
|
||||||
logger.trace({ remote: user.name }, `[auth/allow_action]: user: @{remote}`);
|
logger.trace({ remote: user.name }, `[auth/allow_action]: user: @{remote}`);
|
||||||
const { name, groups } = user;
|
const { name, groups } = user;
|
||||||
|
debug('allow_action "%s": groups %s', action, groups);
|
||||||
const groupAccess = pkg[action] as string[];
|
const groupAccess = pkg[action] as string[];
|
||||||
const hasPermission = groupAccess.some((group) => name === group || groups.includes(group));
|
debug('allow_action "%s": groupAccess %s', action, groupAccess);
|
||||||
|
const hasPermission = groupAccess.some((group) => {
|
||||||
|
return name === group || groups.includes(group);
|
||||||
|
});
|
||||||
|
debug('package "%s" has permission "%s"', name, hasPermission);
|
||||||
logger.trace(
|
logger.trace(
|
||||||
{ pkgName: pkg.name, hasPermission, remote: user.name, groupAccess },
|
{ pkgName: pkg.name, hasPermission, remote: user.name, groupAccess },
|
||||||
`[auth/allow_action]: hasPermission? @{hasPermission} for user: @{remote}, package: @{pkgName}`
|
`[auth/allow_action]: hasPermission? @{hasPermission} for user: @{remote}, package: @{pkgName}`
|
||||||
@@ -218,7 +223,8 @@ export function handleSpecialUnpublish(logger: Logger): any {
|
|||||||
return function (user: RemoteUser, pkg: AuthPackageAllow, callback: AllowActionCallback): void {
|
return function (user: RemoteUser, pkg: AuthPackageAllow, callback: AllowActionCallback): void {
|
||||||
const action = 'unpublish';
|
const action = 'unpublish';
|
||||||
// verify whether the unpublish prop has been defined
|
// verify whether the unpublish prop has been defined
|
||||||
const isUnpublishMissing: boolean = _.isNil(pkg[action]);
|
const isUnpublishMissing: boolean = !pkg[action];
|
||||||
|
debug('is unpublish method missing ? %s', isUnpublishMissing);
|
||||||
const hasGroups: boolean = isUnpublishMissing ? false : (pkg[action] as string[]).length > 0;
|
const hasGroups: boolean = isUnpublishMissing ? false : (pkg[action] as string[]).length > 0;
|
||||||
logger.trace(
|
logger.trace(
|
||||||
{ user: user.name, name: pkg.name, hasGroups },
|
{ user: user.name, name: pkg.name, hasGroups },
|
||||||
|
|||||||
@@ -1,47 +1,79 @@
|
|||||||
|
import express from 'express';
|
||||||
import path from 'path';
|
import path from 'path';
|
||||||
|
import supertest from 'supertest';
|
||||||
|
|
||||||
import { Config as AppConfig, ROLES, getDefaultConfig } from '@verdaccio/config';
|
import { Config as AppConfig, ROLES, createRemoteUser, getDefaultConfig } from '@verdaccio/config';
|
||||||
import { errorUtils } from '@verdaccio/core';
|
import {
|
||||||
import { setup } from '@verdaccio/logger';
|
API_ERROR,
|
||||||
|
HEADERS,
|
||||||
|
HTTP_STATUS,
|
||||||
|
SUPPORT_ERRORS,
|
||||||
|
TOKEN_BEARER,
|
||||||
|
errorUtils,
|
||||||
|
} from '@verdaccio/core';
|
||||||
|
import { logger, setup } from '@verdaccio/logger';
|
||||||
|
import { errorReportingMiddleware, final, handleError } from '@verdaccio/middleware';
|
||||||
import { Config } from '@verdaccio/types';
|
import { Config } from '@verdaccio/types';
|
||||||
|
import { buildToken } from '@verdaccio/utils';
|
||||||
|
|
||||||
import { Auth } from '../src';
|
import { $RequestExtend, Auth } from '../src';
|
||||||
import { authPluginFailureConf, authPluginPassThrougConf, authProfileConf } from './helper/plugin';
|
import {
|
||||||
|
authChangePasswordConf,
|
||||||
|
authPluginFailureConf,
|
||||||
|
authPluginPassThrougConf,
|
||||||
|
authProfileConf,
|
||||||
|
} from './helper/plugin';
|
||||||
|
|
||||||
setup({ level: 'debug', type: 'stdout' });
|
setup({});
|
||||||
|
|
||||||
|
// to avoid flaky test generate same ramdom key
|
||||||
|
jest.mock('@verdaccio/utils', () => {
|
||||||
|
return {
|
||||||
|
...jest.requireActual('@verdaccio/utils'),
|
||||||
|
// used by enhanced legacy aes signature (minimum 32 characters)
|
||||||
|
generateRandomSecretKey: () => 'GCYW/3IJzQI6GvPmy9sbMkFoiL7QLVw',
|
||||||
|
// used by legacy aes signature
|
||||||
|
generateRandomHexString: () =>
|
||||||
|
'ff065fcf7a8330ae37d3ea116328852f387ad7aa6defbe47fb68b1ea25f97446',
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
describe('AuthTest', () => {
|
describe('AuthTest', () => {
|
||||||
test('should init correctly', async () => {
|
describe('default', () => {
|
||||||
const config: Config = new AppConfig({ ...authProfileConf });
|
test('should init correctly', async () => {
|
||||||
config.checkSecretKey('12345');
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
|
||||||
const auth: Auth = new Auth(config);
|
const auth: Auth = new Auth(config);
|
||||||
await auth.init();
|
await auth.init();
|
||||||
expect(auth).toBeDefined();
|
expect(auth).toBeDefined();
|
||||||
});
|
|
||||||
|
|
||||||
test('should load default auth plugin', async () => {
|
|
||||||
const config: Config = new AppConfig({ ...authProfileConf, auth: undefined });
|
|
||||||
config.checkSecretKey('12345');
|
|
||||||
|
|
||||||
const auth: Auth = new Auth(config);
|
|
||||||
await auth.init();
|
|
||||||
expect(auth).toBeDefined();
|
|
||||||
});
|
|
||||||
|
|
||||||
test('should load custom algorithm', async () => {
|
|
||||||
const config: Config = new AppConfig({
|
|
||||||
...authProfileConf,
|
|
||||||
auth: { htpasswd: { algorithm: 'sha1', file: './foo' } },
|
|
||||||
});
|
});
|
||||||
config.checkSecretKey('12345');
|
|
||||||
|
|
||||||
const auth: Auth = new Auth(config);
|
test('should load default auth plugin', async () => {
|
||||||
await auth.init();
|
const config: Config = new AppConfig({ ...authProfileConf, auth: undefined });
|
||||||
expect(auth).toBeDefined();
|
config.checkSecretKey('12345');
|
||||||
|
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('test authenticate method', () => {
|
describe('utils', () => {
|
||||||
|
test('should load custom algorithm', async () => {
|
||||||
|
const config: Config = new AppConfig({
|
||||||
|
...authProfileConf,
|
||||||
|
auth: { htpasswd: { algorithm: 'sha1', file: './foo' } },
|
||||||
|
});
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('authenticate', () => {
|
||||||
describe('test authenticate states', () => {
|
describe('test authenticate states', () => {
|
||||||
test('should be a success login', async () => {
|
test('should be a success login', async () => {
|
||||||
const config: Config = new AppConfig({ ...authProfileConf });
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
@@ -163,30 +195,519 @@ describe('AuthTest', () => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('test multiple authenticate methods', () => {
|
||||||
|
test('should skip falsy values', async () => {
|
||||||
|
const config: Config = new AppConfig({
|
||||||
|
...getDefaultConfig(),
|
||||||
|
plugins: path.join(__dirname, './partials/plugin'),
|
||||||
|
auth: {
|
||||||
|
success: {},
|
||||||
|
'fail-invalid-method': {},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
|
||||||
|
return new Promise((resolve) => {
|
||||||
|
auth.authenticate('foo', 'bar', (err, value) => {
|
||||||
|
expect(value).toEqual({
|
||||||
|
name: 'foo',
|
||||||
|
groups: ['test', ROLES.$ALL, '$authenticated', '@all', '@authenticated', 'all'],
|
||||||
|
real_groups: ['test'],
|
||||||
|
});
|
||||||
|
resolve(value);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('test multiple authenticate methods', () => {
|
describe('changePassword', () => {
|
||||||
test('should skip falsy values', async () => {
|
test('should fail if the plugin does not provide implementation', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
const callback = jest.fn();
|
||||||
|
|
||||||
|
auth.changePassword('foo', 'bar', 'newFoo', callback);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(
|
||||||
|
errorUtils.getInternalError(SUPPORT_ERRORS.PLUGIN_MISSING_INTERFACE)
|
||||||
|
);
|
||||||
|
});
|
||||||
|
test('should handle plugin does provide implementation', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authChangePasswordConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
const callback = jest.fn();
|
||||||
|
auth.add_user('foo', 'bar', jest.fn());
|
||||||
|
auth.changePassword('foo', 'bar', 'newFoo', callback);
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(null, true);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('allow_access', () => {
|
||||||
|
describe('no custom allow_access implementation provided', () => {
|
||||||
|
// when allow_access is not implemented, the groups must match
|
||||||
|
// exactly with the packages access group
|
||||||
|
test('should fails if groups do not match exactly', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
const groups = ['test'];
|
||||||
|
|
||||||
|
auth.allow_access(
|
||||||
|
{ packageName: 'foo' },
|
||||||
|
{ name: 'foo', groups, real_groups: groups },
|
||||||
|
callback
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(
|
||||||
|
errorUtils.getForbidden('user foo is not allowed to access package foo')
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should success if groups do not match exactly', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
// $all comes from configuration file
|
||||||
|
const groups = [ROLES.$ALL];
|
||||||
|
|
||||||
|
auth.allow_access(
|
||||||
|
{ packageName: 'foo' },
|
||||||
|
{ name: 'foo', groups, real_groups: groups },
|
||||||
|
callback
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(null, true);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('allow_publish', () => {
|
||||||
|
describe('no custom allow_publish implementation provided', () => {
|
||||||
|
// when allow_access is not implemented, the groups must match
|
||||||
|
// exactly with the packages access group
|
||||||
|
test('should fails if groups do not match exactly', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
const groups = ['test'];
|
||||||
|
|
||||||
|
auth.allow_publish(
|
||||||
|
{ packageName: 'foo' },
|
||||||
|
{ name: 'foo', groups, real_groups: groups },
|
||||||
|
callback
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(
|
||||||
|
errorUtils.getForbidden('user foo is not allowed to publish package foo')
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should success if groups do match exactly', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
// $all comes from configuration file
|
||||||
|
const groups = [ROLES.$AUTH];
|
||||||
|
|
||||||
|
auth.allow_publish(
|
||||||
|
{ packageName: 'foo' },
|
||||||
|
{ name: 'foo', groups, real_groups: groups },
|
||||||
|
callback
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(null, true);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
describe('allow_unpublish', () => {
|
||||||
|
describe('no custom allow_unpublish implementation provided', () => {
|
||||||
|
test('should fails if groups do not match exactly', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
const groups = ['test'];
|
||||||
|
|
||||||
|
auth.allow_unpublish(
|
||||||
|
{ packageName: 'foo' },
|
||||||
|
{ name: 'foo', groups, real_groups: groups },
|
||||||
|
callback
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(
|
||||||
|
errorUtils.getForbidden('user foo is not allowed to unpublish package foo')
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should handle missing unpublish method (special case to handle legacy configurations)', async () => {
|
||||||
|
const config: Config = new AppConfig({
|
||||||
|
...authProfileConf,
|
||||||
|
packages: {
|
||||||
|
...authProfileConf.packages,
|
||||||
|
'**': {
|
||||||
|
access: ['$all'],
|
||||||
|
publish: ['$authenticated'],
|
||||||
|
// it forces publish handle the access
|
||||||
|
unpublish: undefined,
|
||||||
|
proxy: ['npmjs'],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
const groups = ['test'];
|
||||||
|
|
||||||
|
auth.allow_unpublish(
|
||||||
|
{ packageName: 'foo' },
|
||||||
|
{ name: 'foo', groups, real_groups: groups },
|
||||||
|
callback
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(
|
||||||
|
errorUtils.getForbidden('user foo is not allowed to publish package foo')
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should success if groups do match exactly', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
// $all comes from configuration file
|
||||||
|
const groups = [ROLES.$AUTH];
|
||||||
|
|
||||||
|
auth.allow_unpublish(
|
||||||
|
{ packageName: 'foo' },
|
||||||
|
{ name: 'foo', groups, real_groups: groups },
|
||||||
|
callback
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(null, true);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('add_user', () => {
|
||||||
|
describe('error handling', () => {
|
||||||
|
// when allow_access is not implemented, the groups must match
|
||||||
|
// exactly with the packages access group
|
||||||
|
test('should fails with bad password if adduser is not implemented', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
|
||||||
|
auth.add_user('juan', 'password', callback);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(
|
||||||
|
errorUtils.getConflict(API_ERROR.BAD_USERNAME_PASSWORD)
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should fails if adduser fails internally (exception)', async () => {
|
||||||
|
const config: Config = new AppConfig({
|
||||||
|
...getDefaultConfig(),
|
||||||
|
plugins: path.join(__dirname, './partials/plugin'),
|
||||||
|
auth: {
|
||||||
|
adduser: {},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
|
||||||
|
// note: fail uas username make plugin fails
|
||||||
|
auth.add_user('fail', 'password', callback);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(new Error('bad username'));
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should skip to the next plugin and fails', async () => {
|
||||||
|
const config: Config = new AppConfig({
|
||||||
|
...getDefaultConfig(),
|
||||||
|
plugins: path.join(__dirname, './partials/plugin'),
|
||||||
|
auth: {
|
||||||
|
adduser: {},
|
||||||
|
// plugin implement adduser with fail auth
|
||||||
|
fail: {},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
|
||||||
|
// note: fail uas username make plugin fails
|
||||||
|
auth.add_user('skip', 'password', callback);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(
|
||||||
|
errorUtils.getConflict(API_ERROR.BAD_USERNAME_PASSWORD)
|
||||||
|
);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
test('should success if adduser', async () => {
|
||||||
const config: Config = new AppConfig({
|
const config: Config = new AppConfig({
|
||||||
...getDefaultConfig(),
|
...getDefaultConfig(),
|
||||||
plugins: path.join(__dirname, './partials/plugin'),
|
plugins: path.join(__dirname, './partials/plugin'),
|
||||||
auth: {
|
auth: {
|
||||||
success: {},
|
adduser: {},
|
||||||
'fail-invalid-method': {},
|
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
config.checkSecretKey('12345');
|
config.checkSecretKey('12345');
|
||||||
const auth: Auth = new Auth(config);
|
const auth: Auth = new Auth(config);
|
||||||
await auth.init();
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
return new Promise((resolve) => {
|
const callback = jest.fn();
|
||||||
auth.authenticate('foo', 'bar', (err, value) => {
|
|
||||||
expect(value).toEqual({
|
auth.add_user('something', 'password', callback);
|
||||||
name: 'foo',
|
|
||||||
groups: ['test', '$all', '$authenticated', '@all', '@authenticated', 'all'],
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
real_groups: ['test'],
|
expect(callback).toHaveBeenCalledWith(null, {
|
||||||
|
groups: ['test', '$all', '$authenticated', '@all', '@authenticated', 'all'],
|
||||||
|
name: 'something',
|
||||||
|
real_groups: ['test'],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
test('should handle legacy add_user method', async () => {
|
||||||
|
const config: Config = new AppConfig({
|
||||||
|
...getDefaultConfig(),
|
||||||
|
plugins: path.join(__dirname, './partials/plugin'),
|
||||||
|
auth: {
|
||||||
|
'adduser-legacy': {},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
config.checkSecretKey('12345');
|
||||||
|
const auth: Auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
expect(auth).toBeDefined();
|
||||||
|
|
||||||
|
const callback = jest.fn();
|
||||||
|
|
||||||
|
auth.add_user('something', 'password', callback);
|
||||||
|
|
||||||
|
expect(callback).toHaveBeenCalledTimes(1);
|
||||||
|
expect(callback).toHaveBeenCalledWith(null, {
|
||||||
|
groups: ['test', '$all', '$authenticated', '@all', '@authenticated', 'all'],
|
||||||
|
name: 'something',
|
||||||
|
real_groups: ['test'],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
describe('middlewares', () => {
|
||||||
|
describe('apiJWTmiddleware', () => {
|
||||||
|
const secret = '12345';
|
||||||
|
const getServer = async function (auth) {
|
||||||
|
const app = express();
|
||||||
|
app.use(express.json({ strict: false, limit: '10mb' }));
|
||||||
|
// @ts-expect-error
|
||||||
|
app.use(errorReportingMiddleware(logger));
|
||||||
|
app.use(auth.apiJWTmiddleware());
|
||||||
|
app.get('/*', (req, res, next) => {
|
||||||
|
if ((req as $RequestExtend).remote_user.error) {
|
||||||
|
next(new Error((req as $RequestExtend).remote_user.error));
|
||||||
|
} else {
|
||||||
|
// @ts-expect-error
|
||||||
|
next({ user: req?.remote_user });
|
||||||
|
}
|
||||||
|
});
|
||||||
|
// @ts-expect-error
|
||||||
|
app.use(handleError(logger));
|
||||||
|
// @ts-expect-error
|
||||||
|
app.use(final);
|
||||||
|
return app;
|
||||||
|
};
|
||||||
|
describe('legacy signature', () => {
|
||||||
|
describe('error cases', () => {
|
||||||
|
test('should handle invalid auth token', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey(secret);
|
||||||
|
const auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
const app = await getServer(auth);
|
||||||
|
return supertest(app)
|
||||||
|
.get(`/`)
|
||||||
|
.set(HEADERS.AUTHORIZATION, 'Bearer foo')
|
||||||
|
.expect(HTTP_STATUS.INTERNAL_ERROR);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should handle missing auth header', async () => {
|
||||||
|
const config: Config = new AppConfig({ ...authProfileConf });
|
||||||
|
config.checkSecretKey(secret);
|
||||||
|
const auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
const app = await getServer(auth);
|
||||||
|
return supertest(app).get(`/`).expect(HTTP_STATUS.OK);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('deprecated legacy handling forceEnhancedLegacySignature=false', () => {
|
||||||
|
test('should handle valid auth token', async () => {
|
||||||
|
const payload = 'juan:password';
|
||||||
|
// const token = await signPayload(remoteUser, '12345');
|
||||||
|
const config: Config = new AppConfig(
|
||||||
|
{ ...authProfileConf },
|
||||||
|
{ forceEnhancedLegacySignature: false }
|
||||||
|
);
|
||||||
|
// intended to force key generator (associated with mocks above)
|
||||||
|
config.checkSecretKey(undefined);
|
||||||
|
const auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
const token = auth.aesEncrypt(payload) as string;
|
||||||
|
const app = await getServer(auth);
|
||||||
|
const res = await supertest(app)
|
||||||
|
.get(`/`)
|
||||||
|
.set(HEADERS.AUTHORIZATION, buildToken(TOKEN_BEARER, token))
|
||||||
|
.expect(HTTP_STATUS.OK);
|
||||||
|
expect(res.body.user.name).toEqual('juan');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should handle invalid auth token', async () => {
|
||||||
|
const payload = 'juan:password';
|
||||||
|
const config: Config = new AppConfig(
|
||||||
|
{ ...authPluginFailureConf },
|
||||||
|
{ forceEnhancedLegacySignature: false }
|
||||||
|
);
|
||||||
|
// intended to force key generator (associated with mocks above)
|
||||||
|
config.checkSecretKey(undefined);
|
||||||
|
const auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
const token = auth.aesEncrypt(payload) as string;
|
||||||
|
const app = await getServer(auth);
|
||||||
|
return await supertest(app)
|
||||||
|
.get(`/`)
|
||||||
|
.set(HEADERS.AUTHORIZATION, buildToken(TOKEN_BEARER, token))
|
||||||
|
.expect(HTTP_STATUS.INTERNAL_ERROR);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
describe('jwt signature', () => {
|
||||||
|
describe('error cases', () => {
|
||||||
|
test('should handle invalid auth token and return anonymous', async () => {
|
||||||
|
// @ts-expect-error
|
||||||
|
const config: Config = new AppConfig({
|
||||||
|
...authProfileConf,
|
||||||
|
...{ security: { api: { jwt: { sign: { expiresIn: '29d' } } } } },
|
||||||
|
});
|
||||||
|
config.checkSecretKey(secret);
|
||||||
|
const auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
const app = await getServer(auth);
|
||||||
|
const res = await supertest(app)
|
||||||
|
.get(`/`)
|
||||||
|
.set(HEADERS.AUTHORIZATION, 'Bearer foo')
|
||||||
|
.expect(HTTP_STATUS.OK);
|
||||||
|
expect(res.body.user.groups).toEqual([
|
||||||
|
ROLES.$ALL,
|
||||||
|
ROLES.$ANONYMOUS,
|
||||||
|
ROLES.DEPRECATED_ALL,
|
||||||
|
ROLES.DEPRECATED_ANONYMOUS,
|
||||||
|
]);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should handle missing auth header', async () => {
|
||||||
|
// @ts-expect-error
|
||||||
|
const config: Config = new AppConfig({
|
||||||
|
...authProfileConf,
|
||||||
|
...{ security: { api: { jwt: { sign: { expiresIn: '29d' } } } } },
|
||||||
|
});
|
||||||
|
config.checkSecretKey(secret);
|
||||||
|
const auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
const app = await getServer(auth);
|
||||||
|
const res = await supertest(app).get(`/`).expect(HTTP_STATUS.OK);
|
||||||
|
expect(res.body.user.groups).toEqual([
|
||||||
|
ROLES.$ALL,
|
||||||
|
ROLES.$ANONYMOUS,
|
||||||
|
ROLES.DEPRECATED_ALL,
|
||||||
|
ROLES.DEPRECATED_ANONYMOUS,
|
||||||
|
]);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
describe('valid signature handlers', () => {
|
||||||
|
test('should handle valid auth token', async () => {
|
||||||
|
const config: Config = new AppConfig(
|
||||||
|
// @ts-expect-error
|
||||||
|
{
|
||||||
|
...authProfileConf,
|
||||||
|
...{ security: { api: { jwt: { sign: { expiresIn: '29d' } } } } },
|
||||||
|
},
|
||||||
|
{ forceEnhancedLegacySignature: false }
|
||||||
|
);
|
||||||
|
// intended to force key generator (associated with mocks above)
|
||||||
|
config.checkSecretKey(undefined);
|
||||||
|
const auth = new Auth(config);
|
||||||
|
await auth.init();
|
||||||
|
const token = (await auth.jwtEncrypt(
|
||||||
|
createRemoteUser('jwt_user', [ROLES.ALL]),
|
||||||
|
// @ts-expect-error
|
||||||
|
config.security.api.jwt.sign
|
||||||
|
)) as string;
|
||||||
|
const app = await getServer(auth);
|
||||||
|
const res = await supertest(app)
|
||||||
|
.get(`/`)
|
||||||
|
.set(HEADERS.AUTHORIZATION, buildToken(TOKEN_BEARER, token))
|
||||||
|
.expect(HTTP_STATUS.OK);
|
||||||
|
expect(res.body.user.name).toEqual('jwt_user');
|
||||||
});
|
});
|
||||||
resolve(value);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -10,6 +10,14 @@ export const authProfileConf = {
|
|||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const authChangePasswordConf = {
|
||||||
|
...getDefaultConfig(),
|
||||||
|
plugins: path.join(__dirname, '../partials/plugin'),
|
||||||
|
auth: {
|
||||||
|
'change-password': {},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
export const authPluginFailureConf = {
|
export const authPluginFailureConf = {
|
||||||
...getDefaultConfig(),
|
...getDefaultConfig(),
|
||||||
plugins: path.join(__dirname, '../partials/plugin'),
|
plugins: path.join(__dirname, '../partials/plugin'),
|
||||||
|
|||||||
@@ -0,0 +1,9 @@
|
|||||||
|
module.exports = function () {
|
||||||
|
return {
|
||||||
|
authenticate(user, pass, callback) {
|
||||||
|
// https://verdaccio.org/docs/en/dev-plugins#onsuccess
|
||||||
|
// this is a successful login and return a simple group
|
||||||
|
callback(null, ['test']);
|
||||||
|
},
|
||||||
|
};
|
||||||
|
};
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
{
|
||||||
|
"name": "verdaccio-access-ok",
|
||||||
|
"main": "access.js",
|
||||||
|
"version": "1.0.0"
|
||||||
|
}
|
||||||
@@ -0,0 +1,25 @@
|
|||||||
|
module.exports = function () {
|
||||||
|
return {
|
||||||
|
authenticate(user, pass, callback) {
|
||||||
|
// https://verdaccio.org/docs/en/dev-plugins#onsuccess
|
||||||
|
// this is a successful login and return a simple group
|
||||||
|
callback(null, ['test']);
|
||||||
|
},
|
||||||
|
add_user(user, password, cb) {
|
||||||
|
if (user === 'fail') {
|
||||||
|
return cb(Error('bad username'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (user === 'password') {
|
||||||
|
return cb(Error('bad password'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (user === 'skip') {
|
||||||
|
// if wants to the next plugin
|
||||||
|
return cb(null, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
cb(null, true);
|
||||||
|
},
|
||||||
|
};
|
||||||
|
};
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
{
|
||||||
|
"name": "verdaccio-adduser-legacy",
|
||||||
|
"main": "adduser.js",
|
||||||
|
"version": "1.0.0"
|
||||||
|
}
|
||||||
@@ -0,0 +1,25 @@
|
|||||||
|
module.exports = function () {
|
||||||
|
return {
|
||||||
|
authenticate(user, pass, callback) {
|
||||||
|
// https://verdaccio.org/docs/en/dev-plugins#onsuccess
|
||||||
|
// this is a successful login and return a simple group
|
||||||
|
callback(null, ['test']);
|
||||||
|
},
|
||||||
|
adduser(user, password, cb) {
|
||||||
|
if (user === 'fail') {
|
||||||
|
return cb(Error('bad username'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (user === 'password') {
|
||||||
|
return cb(Error('bad password'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (user === 'skip') {
|
||||||
|
// if wants to the next plugin
|
||||||
|
return cb(null, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
cb(null, true);
|
||||||
|
},
|
||||||
|
};
|
||||||
|
};
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
{
|
||||||
|
"name": "verdaccio-adduser",
|
||||||
|
"main": "adduser.js",
|
||||||
|
"version": "1.0.0"
|
||||||
|
}
|
||||||
@@ -0,0 +1,32 @@
|
|||||||
|
module.exports = function () {
|
||||||
|
return {
|
||||||
|
users: [],
|
||||||
|
authenticate(user, pass, callback) {
|
||||||
|
// https://verdaccio.org/docs/en/dev-plugins#onsuccess
|
||||||
|
// this is a successful login and return a simple group
|
||||||
|
callback(null, ['test']);
|
||||||
|
},
|
||||||
|
changePassword(user, password, newPassword, cb) {
|
||||||
|
if (password === newPassword) {
|
||||||
|
return cb(Error('error password equal'));
|
||||||
|
}
|
||||||
|
return cb(null, true);
|
||||||
|
},
|
||||||
|
adduser(user, password, cb) {
|
||||||
|
if (user === 'fail') {
|
||||||
|
return cb(Error('bad username'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (user === 'password') {
|
||||||
|
return cb(Error('bad password'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (user === 'skip') {
|
||||||
|
// if wants to the next plugin
|
||||||
|
return cb(null, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
cb(null, true);
|
||||||
|
},
|
||||||
|
};
|
||||||
|
};
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
{
|
||||||
|
"name": "verdaccio-change-password",
|
||||||
|
"main": "change.js",
|
||||||
|
"version": "1.0.0"
|
||||||
|
}
|
||||||
@@ -7,5 +7,8 @@ module.exports = function () {
|
|||||||
and success types respectively for testing purposes */
|
and success types respectively for testing purposes */
|
||||||
callback(errorUtils.getInternalError(), false);
|
callback(errorUtils.getInternalError(), false);
|
||||||
},
|
},
|
||||||
|
adduser(user, password, cb) {
|
||||||
|
return cb(null, false);
|
||||||
|
},
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,5 +1,34 @@
|
|||||||
# @verdaccio/cli
|
# @verdaccio/cli
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [4d96324]
|
||||||
|
- @verdaccio/config@7.0.0-next.6
|
||||||
|
- @verdaccio/node-api@7.0.0-next.6
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
- @verdaccio/logger@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
- @verdaccio/config@7.0.0-next.5
|
||||||
|
- @verdaccio/node-api@7.0.0-next.5
|
||||||
|
- @verdaccio/logger@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/node-api@7.0.0-next.4
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
- @verdaccio/config@7.0.0-next.4
|
||||||
|
- @verdaccio/logger@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
@@ -169,12 +198,12 @@
|
|||||||
- 8f43bf17d: feat: node api new structure based on promise
|
- 8f43bf17d: feat: node api new structure based on promise
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { runServer } from '@verdaccio/node-api';
|
import { runServer } from "@verdaccio/node-api";
|
||||||
// or
|
// or
|
||||||
import { runServer } from 'verdaccio';
|
import { runServer } from "verdaccio";
|
||||||
|
|
||||||
const app = await runServer(); // default configuration
|
const app = await runServer(); // default configuration
|
||||||
const app = await runServer('./config/config.yaml');
|
const app = await runServer("./config/config.yaml");
|
||||||
const app = await runServer({ configuration });
|
const app = await runServer({ configuration });
|
||||||
app.listen(4000, (event) => {
|
app.listen(4000, (event) => {
|
||||||
// do something
|
// do something
|
||||||
@@ -1020,14 +1049,14 @@
|
|||||||
- 5c5057fc: feat: node api new structure based on promise
|
- 5c5057fc: feat: node api new structure based on promise
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { runServer } from '@verdaccio/node-api';
|
import { runServer } from "@verdaccio/node-api";
|
||||||
// or
|
// or
|
||||||
import { runServer } from 'verdaccio';
|
import { runServer } from "verdaccio";
|
||||||
|
|
||||||
const app = await runServer(); // default configuration
|
const app = await runServer(); // default configuration
|
||||||
const app = await runServer('./config/config.yaml');
|
const app = await runServer("./config/config.yaml");
|
||||||
const app = await runServer({ configuration });
|
const app = await runServer({ configuration });
|
||||||
app.listen(4000, event => {
|
app.listen(4000, (event) => {
|
||||||
// do something
|
// do something
|
||||||
});
|
});
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/cli",
|
"name": "@verdaccio/cli",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"author": {
|
"author": {
|
||||||
"name": "Juan Picado",
|
"name": "Juan Picado",
|
||||||
"email": "juanpicado19@gmail.com"
|
"email": "juanpicado19@gmail.com"
|
||||||
@@ -43,17 +43,17 @@
|
|||||||
"start": "ts-node src/index.ts"
|
"start": "ts-node src/index.ts"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/config": "workspace:7.0.0-next.3",
|
"@verdaccio/config": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/logger": "workspace:7.0.0-next.3",
|
"@verdaccio/logger": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/node-api": "workspace:7.0.0-next.3",
|
"@verdaccio/node-api": "workspace:7.0.0-next.6",
|
||||||
"clipanion": "3.2.1",
|
"clipanion": "3.2.1",
|
||||||
"envinfo": "7.8.1",
|
"envinfo": "7.11.0",
|
||||||
"kleur": "4.1.5",
|
"kleur": "4.1.5",
|
||||||
"semver": "7.5.4"
|
"semver": "7.5.4"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"ts-node": "10.9.1"
|
"ts-node": "10.9.2"
|
||||||
},
|
},
|
||||||
"funding": {
|
"funding": {
|
||||||
"type": "opencollective",
|
"type": "opencollective",
|
||||||
|
|||||||
@@ -1,5 +1,32 @@
|
|||||||
# @verdaccio/config
|
# @verdaccio/config
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- 4d96324: chore(config): increase test coverage
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
- @verdaccio/utils@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Minor Changes
|
||||||
|
|
||||||
|
- f047cc8: refactor: auth with legacy sign support
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
- @verdaccio/utils@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
- @verdaccio/utils@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
@@ -218,12 +245,12 @@
|
|||||||
- 8f43bf17d: feat: node api new structure based on promise
|
- 8f43bf17d: feat: node api new structure based on promise
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { runServer } from '@verdaccio/node-api';
|
import { runServer } from "@verdaccio/node-api";
|
||||||
// or
|
// or
|
||||||
import { runServer } from 'verdaccio';
|
import { runServer } from "verdaccio";
|
||||||
|
|
||||||
const app = await runServer(); // default configuration
|
const app = await runServer(); // default configuration
|
||||||
const app = await runServer('./config/config.yaml');
|
const app = await runServer("./config/config.yaml");
|
||||||
const app = await runServer({ configuration });
|
const app = await runServer({ configuration });
|
||||||
app.listen(4000, (event) => {
|
app.listen(4000, (event) => {
|
||||||
// do something
|
// do something
|
||||||
@@ -993,14 +1020,14 @@
|
|||||||
- 5c5057fc: feat: node api new structure based on promise
|
- 5c5057fc: feat: node api new structure based on promise
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { runServer } from '@verdaccio/node-api';
|
import { runServer } from "@verdaccio/node-api";
|
||||||
// or
|
// or
|
||||||
import { runServer } from 'verdaccio';
|
import { runServer } from "verdaccio";
|
||||||
|
|
||||||
const app = await runServer(); // default configuration
|
const app = await runServer(); // default configuration
|
||||||
const app = await runServer('./config/config.yaml');
|
const app = await runServer("./config/config.yaml");
|
||||||
const app = await runServer({ configuration });
|
const app = await runServer({ configuration });
|
||||||
app.listen(4000, event => {
|
app.listen(4000, (event) => {
|
||||||
// do something
|
// do something
|
||||||
});
|
});
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -3,8 +3,7 @@ const config = require('../../jest/config');
|
|||||||
module.exports = Object.assign({}, config, {
|
module.exports = Object.assign({}, config, {
|
||||||
coverageThreshold: {
|
coverageThreshold: {
|
||||||
global: {
|
global: {
|
||||||
// FIXME: increase to 90
|
lines: 90,
|
||||||
lines: 85,
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/config",
|
"name": "@verdaccio/config",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "logger",
|
"description": "logger",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "build/index.d.ts",
|
"types": "build/index.d.ts",
|
||||||
@@ -38,8 +38,8 @@
|
|||||||
"build": "pnpm run build:js && pnpm run build:types"
|
"build": "pnpm run build:js && pnpm run build:types"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/utils": "workspace:7.0.0-next.3",
|
"@verdaccio/utils": "workspace:7.0.0-next.6",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"js-yaml": "4.1.0",
|
"js-yaml": "4.1.0",
|
||||||
"lodash": "4.17.21",
|
"lodash": "4.17.21",
|
||||||
@@ -48,7 +48,7 @@
|
|||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@types/minimatch": "5.1.2",
|
"@types/minimatch": "5.1.2",
|
||||||
"@types/yup": "0.29.14"
|
"@types/yup": "0.32.0"
|
||||||
},
|
},
|
||||||
"funding": {
|
"funding": {
|
||||||
"type": "opencollective",
|
"type": "opencollective",
|
||||||
|
|||||||
@@ -63,6 +63,10 @@ class Config implements AppConfig {
|
|||||||
private configOptions: { forceEnhancedLegacySignature: boolean };
|
private configOptions: { forceEnhancedLegacySignature: boolean };
|
||||||
public constructor(
|
public constructor(
|
||||||
config: ConfigYaml & { config_path: string },
|
config: ConfigYaml & { config_path: string },
|
||||||
|
// forceEnhancedLegacySignature is a property that
|
||||||
|
// allows switch a new legacy aes signature token signature
|
||||||
|
// for older versions do not want to have this new signature model
|
||||||
|
// this property must be false
|
||||||
configOptions = { forceEnhancedLegacySignature: true }
|
configOptions = { forceEnhancedLegacySignature: true }
|
||||||
) {
|
) {
|
||||||
const self = this;
|
const self = this;
|
||||||
@@ -131,6 +135,16 @@ class Config implements AppConfig {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public getEnhancedLegacySignature() {
|
||||||
|
if (typeof this?.security.enhancedLegacySignature !== 'undefined') {
|
||||||
|
if (this.security.enhancedLegacySignature === true) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return this.configOptions.forceEnhancedLegacySignature;
|
||||||
|
}
|
||||||
|
|
||||||
public getConfigPath() {
|
public getConfigPath() {
|
||||||
return this.configPath;
|
return this.configPath;
|
||||||
}
|
}
|
||||||
@@ -156,24 +170,23 @@ class Config implements AppConfig {
|
|||||||
}
|
}
|
||||||
// generate a new a secret key
|
// generate a new a secret key
|
||||||
// FUTURE: this might be an external secret key, perhaps within config file?
|
// FUTURE: this might be an external secret key, perhaps within config file?
|
||||||
debug('generate a new key');
|
debug('generating a new secret key');
|
||||||
//
|
|
||||||
if (this.configOptions.forceEnhancedLegacySignature) {
|
if (this.getEnhancedLegacySignature()) {
|
||||||
|
debug('key generated with "enhanced" legacy signature user config');
|
||||||
this.secret = generateRandomSecretKey();
|
this.secret = generateRandomSecretKey();
|
||||||
} else {
|
} else {
|
||||||
this.secret =
|
debug('key generated with legacy signature user config');
|
||||||
this.security.enhancedLegacySignature === true
|
this.secret = generateRandomHexString(32);
|
||||||
? generateRandomSecretKey()
|
}
|
||||||
: generateRandomHexString(32);
|
// set this to false allow use old token signature and is not recommended
|
||||||
// set this to false allow use old token signature and is not recommended
|
// only use for migration reasons, major release will remove this property and
|
||||||
// only use for migration reasons, major release will remove this property and
|
// set it by default
|
||||||
// set it by default
|
if (this.security?.enhancedLegacySignature === false) {
|
||||||
if (this.security.enhancedLegacySignature === false) {
|
warningUtils.emit(Codes.VERWAR005);
|
||||||
warningUtils.emit(Codes.VERWAR005);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
debug('generated a new secret key %s', this.secret?.length);
|
debug('generated a new secret key length %s', this.secret?.length);
|
||||||
return this.secret;
|
return this.secret;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -27,7 +27,7 @@ export const PACKAGE_ACCESS = {
|
|||||||
|
|
||||||
export function normalizeUserList(groupsList: any): any {
|
export function normalizeUserList(groupsList: any): any {
|
||||||
const result: any[] = [];
|
const result: any[] = [];
|
||||||
if (_.isNil(groupsList)) {
|
if (_.isNil(groupsList) || _.isEmpty(groupsList)) {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
42
packages/config/test/agent.spec.ts
Normal file
42
packages/config/test/agent.spec.ts
Normal file
@@ -0,0 +1,42 @@
|
|||||||
|
import { getUserAgent } from '../src';
|
||||||
|
|
||||||
|
describe('getUserAgent', () => {
|
||||||
|
test('should return custom user agent when customUserAgent is true', () => {
|
||||||
|
const customUserAgent = true;
|
||||||
|
const version = '1.0.0';
|
||||||
|
const name = 'MyAgent';
|
||||||
|
|
||||||
|
const result = getUserAgent(customUserAgent, version, name);
|
||||||
|
|
||||||
|
expect(result).toBe('MyAgent/1.0.0');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should return custom user agent when customUserAgent is a non-empty string', () => {
|
||||||
|
const customUserAgent = 'CustomAgent/1.0.0';
|
||||||
|
const version = '1.0.0';
|
||||||
|
const name = 'MyAgent';
|
||||||
|
|
||||||
|
const result = getUserAgent(customUserAgent, version, name);
|
||||||
|
|
||||||
|
expect(result).toBe('CustomAgent/1.0.0');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should return "hidden" when customUserAgent is false', () => {
|
||||||
|
const customUserAgent = false;
|
||||||
|
const version = '1.0.0';
|
||||||
|
const name = 'MyAgent';
|
||||||
|
|
||||||
|
const result = getUserAgent(customUserAgent, version, name);
|
||||||
|
|
||||||
|
expect(result).toBe('hidden');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should return default user agent when customUserAgent is undefined', () => {
|
||||||
|
const version = '1.0.0';
|
||||||
|
const name = 'MyAgent';
|
||||||
|
|
||||||
|
const result = getUserAgent(undefined, version, name);
|
||||||
|
|
||||||
|
expect(result).toBe('MyAgent/1.0.0');
|
||||||
|
});
|
||||||
|
});
|
||||||
@@ -13,6 +13,7 @@ describe('Config builder', () => {
|
|||||||
proxy: 'some',
|
proxy: 'some',
|
||||||
})
|
})
|
||||||
.addLogger({ level: 'info', type: 'stdout', format: 'json' })
|
.addLogger({ level: 'info', type: 'stdout', format: 'json' })
|
||||||
|
.addAuth({ htpasswd: { file: '.htpasswd' } })
|
||||||
.addStorage('/tmp/verdaccio')
|
.addStorage('/tmp/verdaccio')
|
||||||
.addSecurity({ api: { legacy: true } });
|
.addSecurity({ api: { legacy: true } });
|
||||||
expect(config.getConfig()).toEqual({
|
expect(config.getConfig()).toEqual({
|
||||||
@@ -21,6 +22,11 @@ describe('Config builder', () => {
|
|||||||
legacy: true,
|
legacy: true,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
auth: {
|
||||||
|
htpasswd: {
|
||||||
|
file: '.htpasswd',
|
||||||
|
},
|
||||||
|
},
|
||||||
storage: '/tmp/verdaccio',
|
storage: '/tmp/verdaccio',
|
||||||
packages: {
|
packages: {
|
||||||
'upstream/*': {
|
'upstream/*': {
|
||||||
|
|||||||
@@ -106,6 +106,20 @@ describe('checkSecretKey', () => {
|
|||||||
const config = new Config(parseConfigFile(resolveConf('default')));
|
const config = new Config(parseConfigFile(resolveConf('default')));
|
||||||
expect(typeof config.checkSecretKey('') === 'string').toBeTruthy();
|
expect(typeof config.checkSecretKey('') === 'string').toBeTruthy();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test('with enhanced legacy signature', () => {
|
||||||
|
const config = new Config(parseConfigFile(resolveConf('default')));
|
||||||
|
config.security.enhancedLegacySignature = true;
|
||||||
|
expect(typeof config.checkSecretKey() === 'string').toBeTruthy();
|
||||||
|
expect(config.secret.length).toBe(32);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('without enhanced legacy signature', () => {
|
||||||
|
const config = new Config(parseConfigFile(resolveConf('default')));
|
||||||
|
config.security.enhancedLegacySignature = false;
|
||||||
|
expect(typeof config.checkSecretKey() === 'string').toBeTruthy();
|
||||||
|
expect(config.secret.length).toBe(64);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('getMatchedPackagesSpec', () => {
|
describe('getMatchedPackagesSpec', () => {
|
||||||
@@ -159,3 +173,18 @@ describe('VERDACCIO_STORAGE_PATH', () => {
|
|||||||
delete process.env.VERDACCIO_STORAGE_PATH;
|
delete process.env.VERDACCIO_STORAGE_PATH;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('configPath', () => {
|
||||||
|
test('should set configPath in config', () => {
|
||||||
|
const defaultConfig = parseConfigFile(resolveConf('default'));
|
||||||
|
const config = new Config(defaultConfig);
|
||||||
|
expect(config.getConfigPath()).toBe(path.join(__dirname, '../src/conf/default.yaml'));
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should throw an error if configPath is not provided', () => {
|
||||||
|
const defaultConfig = parseConfigFile(resolveConf('default'));
|
||||||
|
defaultConfig.configPath = '';
|
||||||
|
defaultConfig.config_path = '';
|
||||||
|
expect(() => new Config(defaultConfig)).toThrow('configPath property is required');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import _ from 'lodash';
|
import _ from 'lodash';
|
||||||
|
|
||||||
import { parseConfigFile } from '../src';
|
import { parseConfigFile } from '../src';
|
||||||
import { PACKAGE_ACCESS, normalisePackageAccess } from '../src/package-access';
|
import { PACKAGE_ACCESS, normalisePackageAccess, normalizeUserList } from '../src/package-access';
|
||||||
import { parseConfigurationFile } from './utils';
|
import { parseConfigurationFile } from './utils';
|
||||||
|
|
||||||
describe('Package access utilities', () => {
|
describe('Package access utilities', () => {
|
||||||
@@ -123,4 +123,30 @@ describe('Package access utilities', () => {
|
|||||||
expect(_.isArray(all.publish)).toBeTruthy();
|
expect(_.isArray(all.publish)).toBeTruthy();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
describe('normaliseUserList', () => {
|
||||||
|
test('should normalize user list', () => {
|
||||||
|
const groupsList = 'admin superadmin';
|
||||||
|
const result = normalizeUserList(groupsList);
|
||||||
|
expect(result).toEqual(['admin', 'superadmin']);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should normalize empty user list', () => {
|
||||||
|
const groupsList = '';
|
||||||
|
const result = normalizeUserList(groupsList);
|
||||||
|
expect(result).toEqual([]);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should normalize user list array', () => {
|
||||||
|
const groupsList = ['admin', 'superadmin'];
|
||||||
|
const result = normalizeUserList(groupsList);
|
||||||
|
expect(result).toEqual(['admin', 'superadmin']);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('should throw error for invalid user list', () => {
|
||||||
|
const groupsList = { group: 'admin' };
|
||||||
|
expect(() => {
|
||||||
|
normalizeUserList(groupsList);
|
||||||
|
}).toThrow('CONFIG: bad package acl (array or string expected): {"group":"admin"}');
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,5 +1,15 @@
|
|||||||
# @verdaccio/core
|
# @verdaccio/core
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Minor Changes
|
||||||
|
|
||||||
|
- f047cc8: refactor: auth with legacy sign support
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/core",
|
"name": "@verdaccio/core",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "core utilities",
|
"description": "core utilities",
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"private",
|
"private",
|
||||||
@@ -34,17 +34,17 @@
|
|||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"http-errors": "2.0.0",
|
"http-errors": "2.0.0",
|
||||||
"http-status-codes": "2.2.0",
|
"http-status-codes": "2.3.0",
|
||||||
"semver": "7.5.4",
|
"semver": "7.5.4",
|
||||||
"ajv": "8.12.0",
|
"ajv": "8.12.0",
|
||||||
"process-warning": "1.0.0",
|
"process-warning": "1.0.0",
|
||||||
"core-js": "3.30.2"
|
"core-js": "3.35.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"lodash": "4.17.21",
|
"lodash": "4.17.21",
|
||||||
"typedoc": "0.23.25",
|
"typedoc": "0.23.25",
|
||||||
"typedoc-plugin-missing-exports": "latest",
|
"typedoc-plugin-missing-exports": "latest",
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1"
|
"@verdaccio/types": "workspace:12.0.0-next.2"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"clean": "rimraf ./build",
|
"clean": "rimraf ./build",
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ export enum Codes {
|
|||||||
VERWAR005 = 'VERWAR005',
|
VERWAR005 = 'VERWAR005',
|
||||||
// deprecation warnings
|
// deprecation warnings
|
||||||
VERDEP003 = 'VERDEP003',
|
VERDEP003 = 'VERDEP003',
|
||||||
|
VERWAR006 = 'VERWAR006',
|
||||||
}
|
}
|
||||||
|
|
||||||
warningInstance.create(
|
warningInstance.create(
|
||||||
@@ -52,6 +53,12 @@ warningInstance.create(
|
|||||||
'multiple addresses will be deprecated in the next major, only use one'
|
'multiple addresses will be deprecated in the next major, only use one'
|
||||||
);
|
);
|
||||||
|
|
||||||
|
warningInstance.create(
|
||||||
|
verdaccioDeprecation,
|
||||||
|
Codes.VERWAR006,
|
||||||
|
'the auth plugin method "add_user" in the auth plugin is deprecated and will be removed in next major release, rename to "adduser"'
|
||||||
|
);
|
||||||
|
|
||||||
export function emit(code: string, a?: string, b?: string, c?: string) {
|
export function emit(code: string, a?: string, b?: string, c?: string) {
|
||||||
warningInstance.emit(code, a, b, c);
|
warningInstance.emit(code, a, b, c);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -39,7 +39,7 @@
|
|||||||
"lockfile": "1.0.4"
|
"lockfile": "1.0.4"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1"
|
"@verdaccio/types": "workspace:12.0.0-next.2"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"clean": "rimraf ./build",
|
"clean": "rimraf ./build",
|
||||||
|
|||||||
@@ -1,5 +1,32 @@
|
|||||||
# Change Log
|
# Change Log
|
||||||
|
|
||||||
|
## 12.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- e14b064: - Fixes polynomial regular expression when determining the file name of tarball
|
||||||
|
- Add tests for extracting tarball name
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
- @verdaccio/url@12.0.0-next.6
|
||||||
|
- @verdaccio/utils@7.0.0-next.6
|
||||||
|
|
||||||
|
## 12.0.0-next.5
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
- @verdaccio/url@12.0.0-next.5
|
||||||
|
- @verdaccio/utils@7.0.0-next.5
|
||||||
|
|
||||||
|
## 12.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
- @verdaccio/url@12.0.0-next.4
|
||||||
|
- @verdaccio/utils@7.0.0-next.4
|
||||||
|
|
||||||
## 12.0.0-next.3
|
## 12.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/tarball",
|
"name": "@verdaccio/tarball",
|
||||||
"version": "12.0.0-next.3",
|
"version": "12.0.0-next.6",
|
||||||
"description": "tarball utilities resolver",
|
"description": "tarball utilities resolver",
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"private",
|
"private",
|
||||||
@@ -34,14 +34,14 @@
|
|||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/url": "workspace:12.0.0-next.3",
|
"@verdaccio/url": "workspace:12.0.0-next.6",
|
||||||
"@verdaccio/utils": "workspace:7.0.0-next.3",
|
"@verdaccio/utils": "workspace:7.0.0-next.6",
|
||||||
"lodash": "4.17.21"
|
"lodash": "4.17.21"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1",
|
"@verdaccio/types": "workspace:12.0.0-next.2",
|
||||||
"node-mocks-http": "1.13.0"
|
"node-mocks-http": "1.14.1"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"clean": "rimraf ./build",
|
"clean": "rimraf ./build",
|
||||||
|
|||||||
@@ -4,6 +4,6 @@ export {
|
|||||||
convertDistRemoteToLocalTarballUrls,
|
convertDistRemoteToLocalTarballUrls,
|
||||||
convertDistVersionToLocalTarballsUrl,
|
convertDistVersionToLocalTarballsUrl,
|
||||||
} from './convertDistRemoteToLocalTarballUrls';
|
} from './convertDistRemoteToLocalTarballUrls';
|
||||||
export { getLocalRegistryTarballUri } from './getLocalRegistryTarballUri';
|
export { extractTarballFromUrl, getLocalRegistryTarballUri } from './getLocalRegistryTarballUri';
|
||||||
|
|
||||||
export { RequestOptions };
|
export { RequestOptions };
|
||||||
|
|||||||
@@ -0,0 +1,36 @@
|
|||||||
|
import { extractTarballFromUrl } from '../src';
|
||||||
|
|
||||||
|
describe('extractTarballFromUrl', () => {
|
||||||
|
const metadata: any = {
|
||||||
|
name: 'npm_test',
|
||||||
|
versions: {
|
||||||
|
'1.0.0': {
|
||||||
|
dist: {
|
||||||
|
tarball: 'http://registry.org/npm_test/-/npm_test-1.0.0.tgz',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
'1.0.1': {
|
||||||
|
dist: {
|
||||||
|
tarball: 'npm_test-1.0.1.tgz',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
'1.0.2': {
|
||||||
|
dist: {
|
||||||
|
tarball: 'https://localhost/npm_test-1.0.2.tgz',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
test('should return only name of tarball', () => {
|
||||||
|
expect(extractTarballFromUrl(metadata.versions['1.0.0'].dist.tarball)).toEqual(
|
||||||
|
'npm_test-1.0.0.tgz'
|
||||||
|
);
|
||||||
|
expect(extractTarballFromUrl(metadata.versions['1.0.1'].dist.tarball)).toEqual(
|
||||||
|
'npm_test-1.0.1.tgz'
|
||||||
|
);
|
||||||
|
expect(extractTarballFromUrl(metadata.versions['1.0.2'].dist.tarball)).toEqual(
|
||||||
|
'npm_test-1.0.2.tgz'
|
||||||
|
);
|
||||||
|
});
|
||||||
|
});
|
||||||
@@ -1,5 +1,11 @@
|
|||||||
# Change Log
|
# Change Log
|
||||||
|
|
||||||
|
## 12.0.0-next.2
|
||||||
|
|
||||||
|
### Minor Changes
|
||||||
|
|
||||||
|
- f047cc8: refactor: auth with legacy sign support
|
||||||
|
|
||||||
## 12.0.0-next.1
|
## 12.0.0-next.1
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
@@ -211,12 +217,12 @@
|
|||||||
- 8f43bf17d: feat: node api new structure based on promise
|
- 8f43bf17d: feat: node api new structure based on promise
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { runServer } from '@verdaccio/node-api';
|
import { runServer } from "@verdaccio/node-api";
|
||||||
// or
|
// or
|
||||||
import { runServer } from 'verdaccio';
|
import { runServer } from "verdaccio";
|
||||||
|
|
||||||
const app = await runServer(); // default configuration
|
const app = await runServer(); // default configuration
|
||||||
const app = await runServer('./config/config.yaml');
|
const app = await runServer("./config/config.yaml");
|
||||||
const app = await runServer({ configuration });
|
const app = await runServer({ configuration });
|
||||||
app.listen(4000, (event) => {
|
app.listen(4000, (event) => {
|
||||||
// do something
|
// do something
|
||||||
@@ -808,14 +814,14 @@
|
|||||||
- 5c5057fc: feat: node api new structure based on promise
|
- 5c5057fc: feat: node api new structure based on promise
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { runServer } from '@verdaccio/node-api';
|
import { runServer } from "@verdaccio/node-api";
|
||||||
// or
|
// or
|
||||||
import { runServer } from 'verdaccio';
|
import { runServer } from "verdaccio";
|
||||||
|
|
||||||
const app = await runServer(); // default configuration
|
const app = await runServer(); // default configuration
|
||||||
const app = await runServer('./config/config.yaml');
|
const app = await runServer("./config/config.yaml");
|
||||||
const app = await runServer({ configuration });
|
const app = await runServer({ configuration });
|
||||||
app.listen(4000, event => {
|
app.listen(4000, (event) => {
|
||||||
// do something
|
// do something
|
||||||
});
|
});
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/types",
|
"name": "@verdaccio/types",
|
||||||
"version": "12.0.0-next.1",
|
"version": "12.0.0-next.2",
|
||||||
"description": "verdaccio types definitions",
|
"description": "verdaccio types definitions",
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"private",
|
"private",
|
||||||
|
|||||||
@@ -296,7 +296,7 @@ export interface Config extends Omit<ConfigYaml, 'packages' | 'security' | 'conf
|
|||||||
// security object defaults is added by the config file but optional in the yaml file
|
// security object defaults is added by the config file but optional in the yaml file
|
||||||
security: Security;
|
security: Security;
|
||||||
// @deprecated (pending adding the replacement)
|
// @deprecated (pending adding the replacement)
|
||||||
checkSecretKey(token: string): string;
|
checkSecretKey(token: string | void): string;
|
||||||
getMatchedPackagesSpec(storage: string): PackageAccess | void;
|
getMatchedPackagesSpec(storage: string): PackageAccess | void;
|
||||||
// TODO: verify how to handle this in the future
|
// TODO: verify how to handle this in the future
|
||||||
[key: string]: any;
|
[key: string]: any;
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ export interface PackageAccess {
|
|||||||
publish?: string[];
|
publish?: string[];
|
||||||
proxy?: string[];
|
proxy?: string[];
|
||||||
access?: string[];
|
access?: string[];
|
||||||
unpublish: string[];
|
unpublish?: string[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface PackageList {
|
export interface PackageList {
|
||||||
|
|||||||
@@ -1,5 +1,28 @@
|
|||||||
# Change Log
|
# Change Log
|
||||||
|
|
||||||
|
## 12.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
|
||||||
|
## 12.0.0-next.5
|
||||||
|
|
||||||
|
### Minor Changes
|
||||||
|
|
||||||
|
- f047cc8: refactor: auth with legacy sign support
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
|
||||||
|
## 12.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
|
||||||
## 12.0.0-next.3
|
## 12.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/url",
|
"name": "@verdaccio/url",
|
||||||
"version": "12.0.0-next.3",
|
"version": "12.0.0-next.6",
|
||||||
"description": "url utilities resolver",
|
"description": "url utilities resolver",
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"private",
|
"private",
|
||||||
@@ -33,14 +33,14 @@
|
|||||||
"access": "public"
|
"access": "public"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"lodash": "4.17.21",
|
"lodash": "4.17.21",
|
||||||
"validator": "13.9.0"
|
"validator": "13.11.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1",
|
"@verdaccio/types": "workspace:12.0.0-next.2",
|
||||||
"node-mocks-http": "1.13.0"
|
"node-mocks-http": "1.14.1"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"clean": "rimraf ./build",
|
"clean": "rimraf ./build",
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import buildDebug from 'debug';
|
import buildDebug from 'debug';
|
||||||
import { URL } from 'url';
|
import { URL } from 'url';
|
||||||
import isURLValidator from 'validator/lib/isURL';
|
import validator from 'validator';
|
||||||
|
|
||||||
import { HEADERS } from '@verdaccio/core';
|
import { HEADERS } from '@verdaccio/core';
|
||||||
|
|
||||||
@@ -17,7 +17,7 @@ export function isURLhasValidProtocol(uri: string): boolean {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function isHost(url: string = '', options = {}): boolean {
|
export function isHost(url: string = '', options = {}): boolean {
|
||||||
return isURLValidator(url, {
|
return validator.isURL(url, {
|
||||||
require_host: true,
|
require_host: true,
|
||||||
allow_trailing_dot: false,
|
allow_trailing_dot: false,
|
||||||
require_valid_protocol: false,
|
require_valid_protocol: false,
|
||||||
@@ -130,3 +130,5 @@ export function getPublicUrl(url_prefix: string = '', requestOptions: RequestOpt
|
|||||||
return '/';
|
return '/';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export const isURL = validator.isURL;
|
||||||
|
|||||||
@@ -1,5 +1,27 @@
|
|||||||
# @verdaccio/hooks
|
# @verdaccio/hooks
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
- @verdaccio/logger@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
- @verdaccio/logger@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
- @verdaccio/logger@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/hooks",
|
"name": "@verdaccio/hooks",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "loaders logic",
|
"description": "loaders logic",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "build/index.d.ts",
|
"types": "build/index.d.ts",
|
||||||
@@ -29,18 +29,18 @@
|
|||||||
"node": ">=18"
|
"node": ">=18"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/logger": "workspace:7.0.0-next.3",
|
"@verdaccio/logger": "workspace:7.0.0-next.6",
|
||||||
"core-js": "3.30.2",
|
"core-js": "3.35.0",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"got-cjs": "12.5.4",
|
"got-cjs": "12.5.4",
|
||||||
"handlebars": "4.7.7"
|
"handlebars": "4.7.8"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/auth": "workspace:7.0.0-next.3",
|
"@verdaccio/auth": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/config": "workspace:7.0.0-next.3",
|
"@verdaccio/config": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1",
|
"@verdaccio/types": "workspace:12.0.0-next.2",
|
||||||
"nock": "13.3.3"
|
"nock": "13.4.0"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"clean": "rimraf ./build",
|
"clean": "rimraf ./build",
|
||||||
|
|||||||
@@ -1,5 +1,23 @@
|
|||||||
# @verdaccio/loaders
|
# @verdaccio/loaders
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/loaders",
|
"name": "@verdaccio/loaders",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "loaders logic",
|
"description": "loaders logic",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "build/index.d.ts",
|
"types": "build/index.d.ts",
|
||||||
@@ -13,14 +13,14 @@
|
|||||||
"url": "https://github.com/verdaccio/verdaccio"
|
"url": "https://github.com/verdaccio/verdaccio"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/logger": "workspace:7.0.0-next.3",
|
"@verdaccio/logger": "workspace:7.0.0-next.6",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"lodash": "4.17.21"
|
"lodash": "4.17.21"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/config": "workspace:7.0.0-next.3",
|
"@verdaccio/config": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1",
|
"@verdaccio/types": "workspace:12.0.0-next.2",
|
||||||
"@verdaccio-scope/verdaccio-auth-foo": "0.0.2",
|
"@verdaccio-scope/verdaccio-auth-foo": "0.0.2",
|
||||||
"verdaccio-auth-memory": "workspace:*",
|
"verdaccio-auth-memory": "workspace:*",
|
||||||
"customprefix-auth": "2.0.0-next.0"
|
"customprefix-auth": "2.0.0-next.0"
|
||||||
|
|||||||
@@ -1,5 +1,23 @@
|
|||||||
# @verdaccio/logger-7
|
# @verdaccio/logger-7
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger-commons@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger-commons@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger-commons@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Minor Changes
|
### Minor Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/logger-7",
|
"name": "@verdaccio/logger-7",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "logger for verdaccio 5.x version",
|
"description": "logger for verdaccio 5.x version",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "./build/index.d.ts",
|
"types": "./build/index.d.ts",
|
||||||
@@ -38,11 +38,11 @@
|
|||||||
"build": "pnpm run build:js && pnpm run build:types"
|
"build": "pnpm run build:js && pnpm run build:types"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/logger-commons": "workspace:7.0.0-next.3",
|
"@verdaccio/logger-commons": "workspace:7.0.0-next.6",
|
||||||
"pino": "7.11.0"
|
"pino": "7.11.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1"
|
"@verdaccio/types": "workspace:12.0.0-next.2"
|
||||||
},
|
},
|
||||||
"funding": {
|
"funding": {
|
||||||
"type": "opencollective",
|
"type": "opencollective",
|
||||||
|
|||||||
@@ -1,5 +1,24 @@
|
|||||||
# @verdaccio/logger-commons
|
# @verdaccio/logger-commons
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/logger-commons",
|
"name": "@verdaccio/logger-commons",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "logger",
|
"description": "logger",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "./build/index.d.ts",
|
"types": "./build/index.d.ts",
|
||||||
@@ -38,14 +38,14 @@
|
|||||||
"build": "pnpm run build:js && pnpm run build:types"
|
"build": "pnpm run build:js && pnpm run build:types"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/logger-prettify": "workspace:7.0.0-next.1",
|
"@verdaccio/logger-prettify": "workspace:7.0.0-next.1",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"colorette": "2.0.20"
|
"colorette": "2.0.20"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"pino": "7.11.0",
|
"pino": "7.11.0",
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1"
|
"@verdaccio/types": "workspace:12.0.0-next.2"
|
||||||
},
|
},
|
||||||
"funding": {
|
"funding": {
|
||||||
"type": "opencollective",
|
"type": "opencollective",
|
||||||
|
|||||||
@@ -38,14 +38,14 @@
|
|||||||
"build": "pnpm run build:js && pnpm run build:types"
|
"build": "pnpm run build:js && pnpm run build:types"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"dayjs": "1.11.7",
|
"dayjs": "1.11.10",
|
||||||
"pino-abstract-transport": "1.0.0",
|
"pino-abstract-transport": "1.1.0",
|
||||||
"colorette": "2.0.20",
|
"colorette": "2.0.20",
|
||||||
"lodash": "4.17.21",
|
"lodash": "4.17.21",
|
||||||
"sonic-boom": "3.3.0"
|
"sonic-boom": "3.7.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"pino": "8.12.1"
|
"pino": "8.17.2"
|
||||||
},
|
},
|
||||||
"funding": {
|
"funding": {
|
||||||
"type": "opencollective",
|
"type": "opencollective",
|
||||||
|
|||||||
@@ -1,5 +1,23 @@
|
|||||||
# @verdaccio/logger
|
# @verdaccio/logger
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger-commons@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger-commons@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/logger-commons@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
@@ -129,12 +147,12 @@
|
|||||||
- 8f43bf17d: feat: node api new structure based on promise
|
- 8f43bf17d: feat: node api new structure based on promise
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { runServer } from '@verdaccio/node-api';
|
import { runServer } from "@verdaccio/node-api";
|
||||||
// or
|
// or
|
||||||
import { runServer } from 'verdaccio';
|
import { runServer } from "verdaccio";
|
||||||
|
|
||||||
const app = await runServer(); // default configuration
|
const app = await runServer(); // default configuration
|
||||||
const app = await runServer('./config/config.yaml');
|
const app = await runServer("./config/config.yaml");
|
||||||
const app = await runServer({ configuration });
|
const app = await runServer({ configuration });
|
||||||
app.listen(4000, (event) => {
|
app.listen(4000, (event) => {
|
||||||
// do something
|
// do something
|
||||||
@@ -546,14 +564,14 @@
|
|||||||
- 5c5057fc: feat: node api new structure based on promise
|
- 5c5057fc: feat: node api new structure based on promise
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { runServer } from '@verdaccio/node-api';
|
import { runServer } from "@verdaccio/node-api";
|
||||||
// or
|
// or
|
||||||
import { runServer } from 'verdaccio';
|
import { runServer } from "verdaccio";
|
||||||
|
|
||||||
const app = await runServer(); // default configuration
|
const app = await runServer(); // default configuration
|
||||||
const app = await runServer('./config/config.yaml');
|
const app = await runServer("./config/config.yaml");
|
||||||
const app = await runServer({ configuration });
|
const app = await runServer({ configuration });
|
||||||
app.listen(4000, event => {
|
app.listen(4000, (event) => {
|
||||||
// do something
|
// do something
|
||||||
});
|
});
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/logger",
|
"name": "@verdaccio/logger",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "logger",
|
"description": "logger",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "./build/index.d.ts",
|
"types": "./build/index.d.ts",
|
||||||
@@ -38,11 +38,11 @@
|
|||||||
"build": "pnpm run build:js && pnpm run build:types"
|
"build": "pnpm run build:js && pnpm run build:types"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/logger-commons": "workspace:7.0.0-next.3",
|
"@verdaccio/logger-commons": "workspace:7.0.0-next.6",
|
||||||
"pino": "8.14.1"
|
"pino": "8.17.2"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/types": "workspace:12.0.0-next.1"
|
"@verdaccio/types": "workspace:12.0.0-next.2"
|
||||||
},
|
},
|
||||||
"funding": {
|
"funding": {
|
||||||
"type": "opencollective",
|
"type": "opencollective",
|
||||||
|
|||||||
@@ -1,5 +1,38 @@
|
|||||||
# @verdaccio/middleware
|
# @verdaccio/middleware
|
||||||
|
|
||||||
|
## 7.0.0-next.6
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [4d96324]
|
||||||
|
- @verdaccio/config@7.0.0-next.6
|
||||||
|
- @verdaccio/core@7.0.0-next.6
|
||||||
|
- @verdaccio/url@12.0.0-next.6
|
||||||
|
- @verdaccio/utils@7.0.0-next.6
|
||||||
|
|
||||||
|
## 7.0.0-next.5
|
||||||
|
|
||||||
|
### Minor Changes
|
||||||
|
|
||||||
|
- f047cc8: refactor: auth with legacy sign support
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- Updated dependencies [f047cc8]
|
||||||
|
- @verdaccio/core@7.0.0-next.5
|
||||||
|
- @verdaccio/url@12.0.0-next.5
|
||||||
|
- @verdaccio/config@7.0.0-next.5
|
||||||
|
- @verdaccio/utils@7.0.0-next.5
|
||||||
|
|
||||||
|
## 7.0.0-next.4
|
||||||
|
|
||||||
|
### Patch Changes
|
||||||
|
|
||||||
|
- @verdaccio/core@7.0.0-next.4
|
||||||
|
- @verdaccio/config@7.0.0-next.4
|
||||||
|
- @verdaccio/url@12.0.0-next.4
|
||||||
|
- @verdaccio/utils@7.0.0-next.4
|
||||||
|
|
||||||
## 7.0.0-next.3
|
## 7.0.0-next.3
|
||||||
|
|
||||||
### Major Changes
|
### Major Changes
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@verdaccio/middleware",
|
"name": "@verdaccio/middleware",
|
||||||
"version": "7.0.0-next.3",
|
"version": "7.0.0-next.6",
|
||||||
"description": "express middleware utils",
|
"description": "express middleware utils",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"types": "build/index.d.ts",
|
"types": "build/index.d.ts",
|
||||||
@@ -38,10 +38,10 @@
|
|||||||
"build": "pnpm run build:js && pnpm run build:types"
|
"build": "pnpm run build:js && pnpm run build:types"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@verdaccio/core": "workspace:7.0.0-next.3",
|
"@verdaccio/core": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/utils": "workspace:7.0.0-next.3",
|
"@verdaccio/utils": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/config": "workspace:7.0.0-next.3",
|
"@verdaccio/config": "workspace:7.0.0-next.6",
|
||||||
"@verdaccio/url": "workspace:12.0.0-next.3",
|
"@verdaccio/url": "workspace:12.0.0-next.6",
|
||||||
"debug": "4.3.4",
|
"debug": "4.3.4",
|
||||||
"lru-cache": "7.18.3",
|
"lru-cache": "7.18.3",
|
||||||
"express": "4.18.2",
|
"express": "4.18.2",
|
||||||
@@ -54,7 +54,7 @@
|
|||||||
"url": "https://opencollective.com/verdaccio"
|
"url": "https://opencollective.com/verdaccio"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@verdaccio/logger": "workspace:7.0.0-next.3",
|
"@verdaccio/logger": "workspace:7.0.0-next.6",
|
||||||
"body-parser": "1.20.2",
|
"body-parser": "1.20.2",
|
||||||
"supertest": "6.3.3"
|
"supertest": "6.3.3"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ import { $NextFunctionVer, $RequestExtend, $ResponseExtend } from '../types';
|
|||||||
* @param config
|
* @param config
|
||||||
* @returns
|
* @returns
|
||||||
*/
|
*/
|
||||||
export function antiLoop(config: Config): Function {
|
export function antiLoop(config: Config) {
|
||||||
return function (req: $RequestExtend, res: $ResponseExtend, next: $NextFunctionVer): void {
|
return function (req: $RequestExtend, res: $ResponseExtend, next: $NextFunctionVer): void {
|
||||||
if (req?.headers?.via != null) {
|
if (req?.headers?.via != null) {
|
||||||
const arr = req.get('via')?.split(',');
|
const arr = req.get('via')?.split(',');
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user