Compare commits
1003 Commits
@nhost/das
...
auth@0.42.
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
3b107a386e | ||
|
|
b5ed48a832 | ||
|
|
363730ab20 | ||
|
|
9c77c4be51 | ||
|
|
c7c6de5258 | ||
|
|
1e7f4df883 | ||
|
|
0c8e5ac55f | ||
|
|
5b809f6ac9 | ||
|
|
0cadc0e5ba | ||
|
|
4c53f4a83b | ||
|
|
9607e9fbad | ||
|
|
19506d5dd8 | ||
|
|
ac4132ec5d | ||
|
|
2e09723d70 | ||
|
|
25ef074a7f | ||
|
|
6ad1cd1900 | ||
|
|
5c5223d871 | ||
|
|
57a69c16dc | ||
|
|
21856df37b | ||
|
|
183bd83ad7 | ||
|
|
ccbc12f952 | ||
|
|
d070758ce3 | ||
|
|
3672af6f2e | ||
|
|
19de48095d | ||
|
|
d064a2fe23 | ||
|
|
c618a7a359 | ||
|
|
6c3ed7ba55 | ||
|
|
c575700f96 | ||
|
|
736fc8584f | ||
|
|
ea1537122a | ||
|
|
2a65455d44 | ||
|
|
c42e65b54f | ||
|
|
fa456fb7b1 | ||
|
|
c7e577b513 | ||
|
|
92b594c523 | ||
|
|
0b316c95bc | ||
|
|
6f3778f18f | ||
|
|
d34d23aa69 | ||
|
|
3f8cafe6d6 | ||
|
|
35fb1197d0 | ||
|
|
3643bec04f | ||
|
|
4d56ac937b | ||
|
|
f300de5cc4 | ||
|
|
48269c3d2e | ||
|
|
984c2733a0 | ||
|
|
c9b0829936 | ||
|
|
50f7376c07 | ||
|
|
7ba5584369 | ||
|
|
5bee6de6bd | ||
|
|
c1b4d5abc5 | ||
|
|
74396856ef | ||
|
|
0a79a92f45 | ||
|
|
87f3c7fcf8 | ||
|
|
a941e237b5 | ||
|
|
9ba3c6c326 | ||
|
|
0f9adf9698 | ||
|
|
9aa6b02523 | ||
|
|
c5f7101432 | ||
|
|
f93014dbfe | ||
|
|
1495588cd7 | ||
|
|
7d06c4ed2a | ||
|
|
595b024b54 | ||
|
|
82fb906577 | ||
|
|
26d264e506 | ||
|
|
457de9a89a | ||
|
|
b566ae9676 | ||
|
|
bfb7cab2ca | ||
|
|
9cd0aa0e81 | ||
|
|
3e2ffd373e | ||
|
|
f1f4ae2cd3 | ||
|
|
664df61518 | ||
|
|
21de1e1e00 | ||
|
|
ff724cdb04 | ||
|
|
d8fbbcf43a | ||
|
|
a199f4ede3 | ||
|
|
7a092cad77 | ||
|
|
cc4eff69cd | ||
|
|
c552ad14fd | ||
|
|
c8e63c31ee | ||
|
|
194970bcf4 | ||
|
|
d9e55890cc | ||
|
|
eee3d0554c | ||
|
|
bbb97d4a2f | ||
|
|
58dc72420d | ||
|
|
6e160faf7a | ||
|
|
4e4adee643 | ||
|
|
2813bd6299 | ||
|
|
9cbe270238 | ||
|
|
91bb815043 | ||
|
|
d37fbb0056 | ||
|
|
ed7fc85791 | ||
|
|
da87fba3d0 | ||
|
|
45c3a792e7 | ||
|
|
b7b6a34753 | ||
|
|
f02b109c00 | ||
|
|
05ba244030 | ||
|
|
1e6c29f606 | ||
|
|
bdccfffc16 | ||
|
|
b2df24adb6 | ||
|
|
4f749fad08 | ||
|
|
36837b13d1 | ||
|
|
66bab982fb | ||
|
|
74803d46ef | ||
|
|
189ea758be | ||
|
|
4993f9e548 | ||
|
|
c98a3beaad | ||
|
|
20ccc6cde0 | ||
|
|
4dd8c52cb7 | ||
|
|
63130b84f5 | ||
|
|
8e8275240c | ||
|
|
c48e722676 | ||
|
|
4f5b2e124b | ||
|
|
f8ca298012 | ||
|
|
3bc6703f17 | ||
|
|
05ab45b5b8 | ||
|
|
067dd7b761 | ||
|
|
78701f6521 | ||
|
|
316e0efaa0 | ||
|
|
23273dec3f | ||
|
|
eccc7dcd3d | ||
|
|
155357345a | ||
|
|
6d2fcaf751 | ||
|
|
dc5d3748ae | ||
|
|
a893f8e093 | ||
|
|
d0b75b6d87 | ||
|
|
f1ecd32104 | ||
|
|
43889c9809 | ||
|
|
1978f4f8d8 | ||
|
|
3456123991 | ||
|
|
8bb4dcfe83 | ||
|
|
72d7e29a0f | ||
|
|
16d336d6ac | ||
|
|
a6d3f8e9e5 | ||
|
|
4e7dcc98eb | ||
|
|
7b6c5fbbb0 | ||
|
|
5bf4a95dfe | ||
|
|
94dbc53159 | ||
|
|
afab4da826 | ||
|
|
5ed6f9acf3 | ||
|
|
e08950cfff | ||
|
|
ed8edf338a | ||
|
|
cf82693dd5 | ||
|
|
b7903c69ca | ||
|
|
5cadff514f | ||
|
|
5523fec2b6 | ||
|
|
642e82d35c | ||
|
|
243efd12c7 | ||
|
|
dd03035898 | ||
|
|
307873fec2 | ||
|
|
5472bedaa1 | ||
|
|
04b75ab193 | ||
|
|
b69719720c | ||
|
|
f3a9283461 | ||
|
|
6302971947 | ||
|
|
5406876129 | ||
|
|
a56642846d | ||
|
|
a094a463e7 | ||
|
|
a7f507ab94 | ||
|
|
ca3a2087f1 | ||
|
|
88038fbade | ||
|
|
45315c7de1 | ||
|
|
d8915e54a3 | ||
|
|
2373bd72cd | ||
|
|
8a471a7a77 | ||
|
|
ef2cc0810d | ||
|
|
4484269204 | ||
|
|
8311fa9af2 | ||
|
|
6534613393 | ||
|
|
0c52594654 | ||
|
|
b865c27d05 | ||
|
|
27aeca6a0f | ||
|
|
61aa87dbd2 | ||
|
|
fcec7fabdf | ||
|
|
93abd359a9 | ||
|
|
8d454973d8 | ||
|
|
68aa985498 | ||
|
|
011516e5d9 | ||
|
|
00b3994ae1 | ||
|
|
19316ad884 | ||
|
|
634f2bfe2d | ||
|
|
2e3096cc9f | ||
|
|
b6b1afd2cf | ||
|
|
cd8c786751 | ||
|
|
15459a92fe | ||
|
|
003cfd6bff | ||
|
|
ffba7d8402 | ||
|
|
377a846708 | ||
|
|
b727ab9f0e | ||
|
|
eef9c803c9 | ||
|
|
024258cc12 | ||
|
|
c3fcb7f5c4 | ||
|
|
044ed00fcf | ||
|
|
5663eecea7 | ||
|
|
e1ec543853 | ||
|
|
2aa0d6d6ca | ||
|
|
59e588ae4a | ||
|
|
962e7b7561 | ||
|
|
4eff7f4958 | ||
|
|
44c7d9e1ab | ||
|
|
ca5010d5bc | ||
|
|
87fee13f4e | ||
|
|
840d730ad7 | ||
|
|
072d25fd3e | ||
|
|
1706c37051 | ||
|
|
7a07b50939 | ||
|
|
60dcbf417a | ||
|
|
ceaca45112 | ||
|
|
0a4e4b315d | ||
|
|
0cc9d36f2c | ||
|
|
fe87694e88 | ||
|
|
d412a931f2 | ||
|
|
3b1fbcec52 | ||
|
|
50a1b1d60c | ||
|
|
b2a1dbb8fc | ||
|
|
b156b1d712 | ||
|
|
5529f7de3f | ||
|
|
29eff81383 | ||
|
|
005e259ff6 | ||
|
|
bc73097f1b | ||
|
|
9a7e02791a | ||
|
|
6fd10dca14 | ||
|
|
08c2fbb80f | ||
|
|
11e1eb3788 | ||
|
|
171aa8e659 | ||
|
|
73b7642a37 | ||
|
|
993ca5720b | ||
|
|
42e14c855c | ||
|
|
2eadfa97d2 | ||
|
|
f7ec32fe02 | ||
|
|
55d4c66c72 | ||
|
|
fff9d1f4a0 | ||
|
|
de0b16325f | ||
|
|
4f7cb06c67 | ||
|
|
aea5d198ee | ||
|
|
87a3e96687 | ||
|
|
1c89e2d781 | ||
|
|
5bdb917d5e | ||
|
|
8b7a4b158d | ||
|
|
e538807b47 | ||
|
|
27bd02f691 | ||
|
|
de38369235 | ||
|
|
e0b9f13429 | ||
|
|
a038291eae | ||
|
|
c5c82506cd | ||
|
|
e4daa58f96 | ||
|
|
829ebd8fd9 | ||
|
|
5a224e69ca | ||
|
|
3080132752 | ||
|
|
b398ae2302 | ||
|
|
9ffb459d9a | ||
|
|
1d413fb871 | ||
|
|
30bcd09cc6 | ||
|
|
cb5d650c50 | ||
|
|
8e3d49b9c8 | ||
|
|
45afb45ebc | ||
|
|
14af6229b2 | ||
|
|
bb864f1d66 | ||
|
|
ec38a08017 | ||
|
|
015a7a00d4 | ||
|
|
5e2bb6368f | ||
|
|
893a30127b | ||
|
|
f669c5c737 | ||
|
|
9448b7e7e8 | ||
|
|
2e15427ec2 | ||
|
|
8b9f249031 | ||
|
|
b1077ed1db | ||
|
|
e91d667587 | ||
|
|
1c7ffedaf9 | ||
|
|
8d49471051 | ||
|
|
f53b7409b3 | ||
|
|
92830004a7 | ||
|
|
577570a14a | ||
|
|
a9dfb173b2 | ||
|
|
696fcb0593 | ||
|
|
db3b7a979e | ||
|
|
d5eed8fa5b | ||
|
|
5107e7c254 | ||
|
|
6be99f06a8 | ||
|
|
9bcd66f362 | ||
|
|
97023e12e7 | ||
|
|
9695ca57d7 | ||
|
|
d11cabf8d3 | ||
|
|
1e48c9f63f | ||
|
|
ee81d85a91 | ||
|
|
17b2418e22 | ||
|
|
d209e3c6e0 | ||
|
|
2ec1393900 | ||
|
|
f85e92d5c4 | ||
|
|
02da92a585 | ||
|
|
a4517f6877 | ||
|
|
fc9dba4887 | ||
|
|
f6a80a00cc | ||
|
|
61c76dd256 | ||
|
|
3a080b8ba9 | ||
|
|
c752050f41 | ||
|
|
a3bf06aa16 | ||
|
|
6acc71c7bb | ||
|
|
ecd969b345 | ||
|
|
74c1c1bd27 | ||
|
|
601259805c | ||
|
|
48f01ed8cb | ||
|
|
e1a7507473 | ||
|
|
e5b2836215 | ||
|
|
8ff315e7a5 | ||
|
|
f328846852 | ||
|
|
d3fe853b6b | ||
|
|
e32f1fb3f6 | ||
|
|
a511353bf9 | ||
|
|
951349bc34 | ||
|
|
9c25b1fedc | ||
|
|
113ed2743d | ||
|
|
7baab1c83f | ||
|
|
b93ecac587 | ||
|
|
e0949d72dd | ||
|
|
1caca158ab | ||
|
|
164ba34789 | ||
|
|
d2e6f4b98b | ||
|
|
01bcdbb17a | ||
|
|
42d7ce8fd9 | ||
|
|
b5ae0fe2e1 | ||
|
|
c167964a97 | ||
|
|
85b3ac0e53 | ||
|
|
d4f6a92097 | ||
|
|
7d28373c6c | ||
|
|
4ad88ce9a8 | ||
|
|
73c0307bb5 | ||
|
|
ef9caac8df | ||
|
|
3395e2460b | ||
|
|
0577ae8435 | ||
|
|
8482976c29 | ||
|
|
00a7327309 | ||
|
|
09478c4718 | ||
|
|
949c0b5a65 | ||
|
|
f44c6f6164 | ||
|
|
fd411579ca | ||
|
|
4d16514950 | ||
|
|
0904444355 | ||
|
|
b82bfb8318 | ||
|
|
c6daab9122 | ||
|
|
61da856b13 | ||
|
|
412ab229c2 | ||
|
|
0071a55b3e | ||
|
|
8d40d15f9f | ||
|
|
5e63d8d1b4 | ||
|
|
42a76fcba0 | ||
|
|
b1c6eb69c0 | ||
|
|
c85a4d5e6b | ||
|
|
62beaf4cd2 | ||
|
|
24fcc609fa | ||
|
|
daf3429d6d | ||
|
|
abc91fd2f4 | ||
|
|
75a486fca7 | ||
|
|
90afa95210 | ||
|
|
f623d341fe | ||
|
|
8e3199a7bb | ||
|
|
f104076de2 | ||
|
|
6889347930 | ||
|
|
5dc415b06b | ||
|
|
93bf34ab9a | ||
|
|
3f397cd7ed | ||
|
|
114df9b884 | ||
|
|
ec13fea58f | ||
|
|
5238bf8b0e | ||
|
|
1570ed4ff4 | ||
|
|
6abc99f731 | ||
|
|
a94ca9a0b3 | ||
|
|
1ead391321 | ||
|
|
5034848e86 | ||
|
|
f9b51c3cb2 | ||
|
|
55ad462398 | ||
|
|
629ed73dc1 | ||
|
|
54f12d8cac | ||
|
|
a2cdb71187 | ||
|
|
80d93299cb | ||
|
|
e40a613e98 | ||
|
|
e83359a8af | ||
|
|
8221458311 | ||
|
|
0d54500f16 | ||
|
|
49ffdf8013 | ||
|
|
8244eafccd | ||
|
|
76337388a7 | ||
|
|
026f48f77b | ||
|
|
b01b60bf62 | ||
|
|
b6cb7f7a77 | ||
|
|
dc0bb3756e | ||
|
|
ebb218ed57 | ||
|
|
98f40cf5ab | ||
|
|
22ac10156c | ||
|
|
258015208f | ||
|
|
347ee4db92 | ||
|
|
9ab33cdc1b | ||
|
|
d47bffbb7a | ||
|
|
741d324c79 | ||
|
|
e508bb3911 | ||
|
|
73db3aa659 | ||
|
|
4af169ef05 | ||
|
|
df01cbe148 | ||
|
|
1fd1170342 | ||
|
|
5859077e0c | ||
|
|
5a26fc953d | ||
|
|
179d96ad93 | ||
|
|
e0024ba91b | ||
|
|
5a4f35f2d8 | ||
|
|
2159f19bac | ||
|
|
93b659f11f | ||
|
|
34404c23e4 | ||
|
|
b081676f92 | ||
|
|
728f35bc6b | ||
|
|
8606ed3040 | ||
|
|
6906ee797e | ||
|
|
637a48eb10 | ||
|
|
40ecd77001 | ||
|
|
f452c46899 | ||
|
|
8972912034 | ||
|
|
7493ad2663 | ||
|
|
c7247ccd0b | ||
|
|
370baa12e9 | ||
|
|
c1f82c4503 | ||
|
|
4bccab8794 | ||
|
|
c90629e66a | ||
|
|
3005ac148d | ||
|
|
5939bd81c1 | ||
|
|
cd1d83566a | ||
|
|
374415289b | ||
|
|
4d7f19fb98 | ||
|
|
bc9282bc23 | ||
|
|
8cae5dc1d5 | ||
|
|
598819aba2 | ||
|
|
031246d627 | ||
|
|
0318f21898 | ||
|
|
31543a6993 | ||
|
|
cf5ff651cc | ||
|
|
2371fdc917 | ||
|
|
3d78c64c45 | ||
|
|
b49d4f70c7 | ||
|
|
76ea376794 | ||
|
|
c5c7d4ca2d | ||
|
|
a7af5ed39e | ||
|
|
6e0a27695d | ||
|
|
9236d0a6f1 | ||
|
|
c96879e933 | ||
|
|
9600923c11 | ||
|
|
8982a497df | ||
|
|
fac7337b5c | ||
|
|
fd04a9f7bc | ||
|
|
bd3279a42e | ||
|
|
4067c03385 | ||
|
|
4418bd0b28 | ||
|
|
3e55b9e11c | ||
|
|
7a129f6cf0 | ||
|
|
664e5b143e | ||
|
|
8c1ce75d07 | ||
|
|
719fb221cd | ||
|
|
e99ec64bca | ||
|
|
fd1aacec79 | ||
|
|
d1ed7eafda | ||
|
|
c89b224349 | ||
|
|
50126b483a | ||
|
|
088cde56f2 | ||
|
|
71c858e4c6 | ||
|
|
b055c575bf | ||
|
|
6a690601f5 | ||
|
|
ab359713a2 | ||
|
|
ee0ad52e73 | ||
|
|
af5d2c2b94 | ||
|
|
7f3944d0ad | ||
|
|
4f166b9259 | ||
|
|
b95b4c458a | ||
|
|
a02fc72288 | ||
|
|
a943c423d5 | ||
|
|
224e9902b4 | ||
|
|
f2cb098136 | ||
|
|
1d21706fb4 | ||
|
|
457fafd6a0 | ||
|
|
b5933359ce | ||
|
|
b750784c57 | ||
|
|
bdff4fec24 | ||
|
|
0c2a48ca63 | ||
|
|
db8e3a2832 | ||
|
|
bc416fda76 | ||
|
|
d06eee5f2d | ||
|
|
6b776eb9f0 | ||
|
|
4857063b14 | ||
|
|
142f2460dc | ||
|
|
1f8ee0c688 | ||
|
|
4533b0834a | ||
|
|
5e7b6e0e14 | ||
|
|
6daeeee1ef | ||
|
|
dec3247e32 | ||
|
|
7bd478194d | ||
|
|
e26f5b7e84 | ||
|
|
6feeb0b1a5 | ||
|
|
81fe46d6bf | ||
|
|
9707c06dae | ||
|
|
8656add8f6 | ||
|
|
686a85ea77 | ||
|
|
6d859a61c8 | ||
|
|
6f7be225d1 | ||
|
|
876fda6655 | ||
|
|
fdd3d02ac5 | ||
|
|
3a5bb8ed77 | ||
|
|
575c0f8073 | ||
|
|
605cbcf62f | ||
|
|
f979f1b953 | ||
|
|
4e0c4bffdc | ||
|
|
50ba9e4403 | ||
|
|
17ef26d1ad | ||
|
|
b22820b6a2 | ||
|
|
30002238fa | ||
|
|
067748987e | ||
|
|
8e14d051c4 | ||
|
|
11eba3381a | ||
|
|
65cf1f8c10 | ||
|
|
9de2fbed47 | ||
|
|
676d6cade5 | ||
|
|
c2a1615dc6 | ||
|
|
077bd17182 | ||
|
|
21820234c7 | ||
|
|
2d79782a88 | ||
|
|
02a8febe98 | ||
|
|
cce39ef820 | ||
|
|
3a375135a6 | ||
|
|
cb9b7fbf7c | ||
|
|
5c9625a246 | ||
|
|
113a9a96e9 | ||
|
|
c08167dd73 | ||
|
|
7294c87d29 | ||
|
|
90c3b55932 | ||
|
|
ba96e0e467 | ||
|
|
d5ca328ceb | ||
|
|
48c812cea7 | ||
|
|
4d17a8763d | ||
|
|
534552e788 | ||
|
|
15debef72c | ||
|
|
84d969d3cd | ||
|
|
d6261688dd | ||
|
|
8d821b3c37 | ||
|
|
0b926e3d16 | ||
|
|
facec9771c | ||
|
|
aeea1d3359 | ||
|
|
dc429cb5b6 | ||
|
|
35bf1863f3 | ||
|
|
a7072d96c9 | ||
|
|
71cff8ac0a | ||
|
|
942c0c7936 | ||
|
|
57bae7fe5c | ||
|
|
91e0fbf6f3 | ||
|
|
d8ac10a673 | ||
|
|
a23849a948 | ||
|
|
9b12c67a4e | ||
|
|
65a10f623d | ||
|
|
2a30399653 | ||
|
|
3ae8731a8d | ||
|
|
70e1926aeb | ||
|
|
340134de91 | ||
|
|
adb021f7c5 | ||
|
|
1717185a74 | ||
|
|
8a104c5b04 | ||
|
|
cbe86e31b2 | ||
|
|
0ae3db9a09 | ||
|
|
2e18108961 | ||
|
|
16d5b57d60 | ||
|
|
0b0efc947d | ||
|
|
064b15be7d | ||
|
|
355d5ca8cf | ||
|
|
5653a4eecd | ||
|
|
cf51d23935 | ||
|
|
38e9e596fd | ||
|
|
fde36e203c | ||
|
|
acb9e3907f | ||
|
|
7d24e55d3a | ||
|
|
1f12a5351d | ||
|
|
d764826dd3 | ||
|
|
9f5cbbcd14 | ||
|
|
d2235e9f54 | ||
|
|
ca0fff0a4f | ||
|
|
73b1569af3 | ||
|
|
856640128e | ||
|
|
2979ca3c5b | ||
|
|
e6fff04154 | ||
|
|
de55ad787d | ||
|
|
a9b2359b48 | ||
|
|
70edaca1e4 | ||
|
|
9a9ccae34e | ||
|
|
ad521551ab | ||
|
|
73c02629bb | ||
|
|
299ff8da2c | ||
|
|
fd836232c1 | ||
|
|
098730fd60 | ||
|
|
85d7cf19d8 | ||
|
|
dddac91ac2 | ||
|
|
4c9641b71b | ||
|
|
627ad24f5b | ||
|
|
ae61717db7 | ||
|
|
d2b6406237 | ||
|
|
996f3f411c | ||
|
|
b31b230a63 | ||
|
|
74087dda41 | ||
|
|
e2eac3897a | ||
|
|
043657441c | ||
|
|
b0cddaa74e | ||
|
|
1a36115912 | ||
|
|
228a24b996 | ||
|
|
0a3457a100 | ||
|
|
7583997e45 | ||
|
|
c77e965c10 | ||
|
|
ade6087f27 | ||
|
|
363bbbceb3 | ||
|
|
d26259b860 | ||
|
|
36938960e8 | ||
|
|
39cc32902e | ||
|
|
478af9fb62 | ||
|
|
2ee4aa68f5 | ||
|
|
9c6d0f4ded | ||
|
|
e6296fec49 | ||
|
|
09007c5c73 | ||
|
|
af8ea5097c | ||
|
|
b9ea3e527a | ||
|
|
5c3107e08e | ||
|
|
9b88a91274 | ||
|
|
3bf88d8a44 | ||
|
|
d89561ac7f | ||
|
|
11ffb96356 | ||
|
|
d1c4c9bcb1 | ||
|
|
249a156dd5 | ||
|
|
96f9f41779 | ||
|
|
62d7f597e7 | ||
|
|
98fc05ff6a | ||
|
|
6b1b5a493d | ||
|
|
be85edb75a | ||
|
|
127824c0c4 | ||
|
|
577f8bfb87 | ||
|
|
7f5f6b2a54 | ||
|
|
dac0332a04 | ||
|
|
8bb351d55f | ||
|
|
2e1819d65a | ||
|
|
99fd7603c5 | ||
|
|
80b4a3984c | ||
|
|
be9d6bb81f | ||
|
|
bd9b3618e9 | ||
|
|
f420693f34 | ||
|
|
c172c8a55b | ||
|
|
b8811d1e16 | ||
|
|
e00c073d55 | ||
|
|
cacce97573 | ||
|
|
9f4ef56b8e | ||
|
|
1c7c18fac8 | ||
|
|
b79cc458ec | ||
|
|
97b2caa4a1 | ||
|
|
fcce09f63d | ||
|
|
ba8fcd18d8 | ||
|
|
02754a9312 | ||
|
|
c86ab0c216 | ||
|
|
6ae1a58783 | ||
|
|
739dc833f4 | ||
|
|
a4ca42e780 | ||
|
|
093b47f08d | ||
|
|
4d452d7d0b | ||
|
|
6ce9d73046 | ||
|
|
43161af21d | ||
|
|
6a0856a9e6 | ||
|
|
4938b9fb51 | ||
|
|
a2e0d2a677 | ||
|
|
def75bdfd8 | ||
|
|
fdfa097f23 | ||
|
|
b4dfc35a71 | ||
|
|
143af704f5 | ||
|
|
dc4a4126cd | ||
|
|
ddba4b39f6 | ||
|
|
5304e3b0fc | ||
|
|
2483b78e19 | ||
|
|
71b84905bb | ||
|
|
4c2150822b | ||
|
|
6834e2d1f9 | ||
|
|
3a29707329 | ||
|
|
a14d7a9389 | ||
|
|
b7b19d919b | ||
|
|
6e4196dbed | ||
|
|
ba1c9c0588 | ||
|
|
4f611a4143 | ||
|
|
d473b3e07f | ||
|
|
dd7b4db3e8 | ||
|
|
735d71a8c8 | ||
|
|
213e09db89 | ||
|
|
4f903332f4 | ||
|
|
7f9e2706de | ||
|
|
16df3e84b6 | ||
|
|
8bbc6a3c08 | ||
|
|
06162b6571 | ||
|
|
b7acdbc0fa | ||
|
|
485dc1df55 | ||
|
|
666b411b6f | ||
|
|
e2d34e0ecd | ||
|
|
ebb19f8cea | ||
|
|
9a140056e8 | ||
|
|
aab9637586 | ||
|
|
94511cecfc | ||
|
|
0024aa16f7 | ||
|
|
02e75cfd93 | ||
|
|
06ec31fbac | ||
|
|
09af005345 | ||
|
|
fcd3e10468 | ||
|
|
0dcb37028e | ||
|
|
068f9c0d65 | ||
|
|
b573c9cc4b | ||
|
|
dbfc0bef86 | ||
|
|
1cd992602b | ||
|
|
1b3ed7cdfb | ||
|
|
815bd9a3e0 | ||
|
|
2a4669286e | ||
|
|
7b10e1e57d | ||
|
|
ab23184e7c | ||
|
|
c09b857f5c | ||
|
|
f6c29b0e38 | ||
|
|
00665eb92a | ||
|
|
f5fe85b401 | ||
|
|
1298c97579 | ||
|
|
aef86ca2d7 | ||
|
|
b6add5891f | ||
|
|
249461bbce | ||
|
|
e0d5658734 | ||
|
|
6b92546928 | ||
|
|
c4ff6d8f2e | ||
|
|
f022cb5a73 | ||
|
|
9208abf73d | ||
|
|
c917188d96 | ||
|
|
b5dac663d0 | ||
|
|
5a367d7cfb | ||
|
|
6a8f1f268e | ||
|
|
445ecb4879 | ||
|
|
26fb2ffdef | ||
|
|
b257b692ad | ||
|
|
35623d7d11 | ||
|
|
c75dfeaaf1 | ||
|
|
c00bff8283 | ||
|
|
3c95d18cbd | ||
|
|
3a5b11ca0c | ||
|
|
cbece99fd2 | ||
|
|
12a9800ad5 | ||
|
|
d6f887a4d9 | ||
|
|
8e9b9736fd | ||
|
|
27b3888302 | ||
|
|
b94cdf2097 | ||
|
|
5c6dbf503f | ||
|
|
2458651a41 | ||
|
|
bca5b63af9 | ||
|
|
5504c6c2ba | ||
|
|
16c50d01b7 | ||
|
|
db25b319b1 | ||
|
|
70d656671b | ||
|
|
e710986232 | ||
|
|
6c8f81fb1b | ||
|
|
0e859057e6 | ||
|
|
ba9d829e34 | ||
|
|
b6390fc5e2 | ||
|
|
671adb560d | ||
|
|
53a286a74f | ||
|
|
353010308a | ||
|
|
a5b5cf474d | ||
|
|
8761d442c5 | ||
|
|
01c0207fd1 | ||
|
|
a8550d7798 | ||
|
|
ee43fe374f | ||
|
|
b997dc880f | ||
|
|
e99535cacc | ||
|
|
a595941332 | ||
|
|
aef2cb8630 | ||
|
|
3ec9c763f1 | ||
|
|
6a70c103df | ||
|
|
31d4a89d58 | ||
|
|
294073d76a | ||
|
|
aaef1971a3 | ||
|
|
ba324c005e | ||
|
|
52a3da805e | ||
|
|
f41fae00e2 | ||
|
|
bb7c9d1bbc | ||
|
|
8da32a54a4 | ||
|
|
e991f00bd2 | ||
|
|
9a425b18e8 | ||
|
|
80349c2812 | ||
|
|
3317ff213b | ||
|
|
540bb36bbc | ||
|
|
94efc5494e | ||
|
|
b081be9d39 | ||
|
|
c48ad52150 | ||
|
|
29cc800ca0 | ||
|
|
80c1794f5f | ||
|
|
94850207be | ||
|
|
8b85a158a7 | ||
|
|
eadfafb3ef | ||
|
|
d9eff08121 | ||
|
|
e2dab11743 | ||
|
|
56211c4d39 | ||
|
|
78a7e60f98 | ||
|
|
68108258fd | ||
|
|
5f4d2b2415 | ||
|
|
7bb4763b8c | ||
|
|
ebe00fa824 | ||
|
|
48b85ecf08 | ||
|
|
6e53c1235a | ||
|
|
963099c099 | ||
|
|
841775ea4c | ||
|
|
f149cd3a4f | ||
|
|
1c5bbb0dd0 | ||
|
|
4eb09abd01 | ||
|
|
4e121d2d4b | ||
|
|
e1a52bdb1c | ||
|
|
761677a604 | ||
|
|
76ae0f5a12 | ||
|
|
8f9bb8e96d | ||
|
|
1777c106bd | ||
|
|
71e2bb3abe | ||
|
|
67265de4f2 | ||
|
|
78bc4c85e1 | ||
|
|
634d4b2d28 | ||
|
|
f16be31f98 | ||
|
|
109695f0da | ||
|
|
c7eb721f11 | ||
|
|
aaa413beb2 | ||
|
|
0b764255e0 | ||
|
|
3cafdf9e20 | ||
|
|
394d4ae5e2 | ||
|
|
994af31935 | ||
|
|
c328aa71ef | ||
|
|
b4a74567bb | ||
|
|
c34e55eb63 | ||
|
|
0a1fca4126 | ||
|
|
b0d04e8bf8 | ||
|
|
cd333849f0 | ||
|
|
c33924e61e | ||
|
|
86f942edee | ||
|
|
104da12e4a | ||
|
|
cc30a60f7d | ||
|
|
932baf8b1c | ||
|
|
c3d4167e52 | ||
|
|
780641bf84 | ||
|
|
68dea05653 | ||
|
|
632f6c38ee | ||
|
|
252f50300a | ||
|
|
d6838305ec | ||
|
|
f51bb26490 | ||
|
|
6ebfe2b134 | ||
|
|
c3de66dedd | ||
|
|
6197878b80 | ||
|
|
c916151b71 | ||
|
|
d62afdea8b | ||
|
|
9397db8087 | ||
|
|
85b9fd8bbd | ||
|
|
4b31f30806 | ||
|
|
6c2f0f570d | ||
|
|
1a2cfa71ba | ||
|
|
4863c05b4a | ||
|
|
3bb3ee2100 | ||
|
|
1d10ac8192 | ||
|
|
6b91d04589 | ||
|
|
ab41a398ec | ||
|
|
a894134062 | ||
|
|
786220f2f9 | ||
|
|
386f6f1da0 | ||
|
|
df71598ab6 | ||
|
|
c68cd71f83 | ||
|
|
234f47899c | ||
|
|
d73153ea76 | ||
|
|
f2c7b1bf3e | ||
|
|
979a3d1da1 | ||
|
|
b481ea9dc6 | ||
|
|
c58b462e33 | ||
|
|
a65696c75a | ||
|
|
0f237d2a8f | ||
|
|
4027100063 | ||
|
|
f92401a11d | ||
|
|
5d8989bec9 | ||
|
|
56d887ffb1 | ||
|
|
281344771d | ||
|
|
6e0eed6879 | ||
|
|
dd027722ee | ||
|
|
9dfa082d12 | ||
|
|
e3f363558a | ||
|
|
e4f89b5d88 | ||
|
|
a1a4c14baf | ||
|
|
bc09758fd7 | ||
|
|
6da3a0d9fc | ||
|
|
9f66f4d239 | ||
|
|
8371a2c8f4 | ||
|
|
17c6760916 | ||
|
|
26e02fb119 | ||
|
|
2477572cff | ||
|
|
0a1ed11c04 | ||
|
|
c75c21aeee | ||
|
|
67d24211c2 | ||
|
|
c7fb045698 | ||
|
|
9388cbab0d | ||
|
|
5dea03825b | ||
|
|
f26189b27c | ||
|
|
97139b684b | ||
|
|
c86cef5f63 | ||
|
|
8907eee2ed | ||
|
|
f212784e39 | ||
|
|
43ed2b03c3 | ||
|
|
5ef5d43cb6 | ||
|
|
48cf7aa09f | ||
|
|
e0d6e976fe | ||
|
|
997c561275 | ||
|
|
517d8044e9 | ||
|
|
554b3d5ce3 | ||
|
|
5439ff81c9 | ||
|
|
bfcbf22b7b | ||
|
|
8c31a5c6a1 | ||
|
|
66b56b0dce | ||
|
|
d912177ee8 | ||
|
|
d43bdc0d8f | ||
|
|
4ec7c8c7df | ||
|
|
3ef2020a26 | ||
|
|
9415942a53 | ||
|
|
5369e9624f | ||
|
|
20b55d5fba | ||
|
|
dfc8d5f51f | ||
|
|
2c0aafac68 | ||
|
|
c2a83a954f | ||
|
|
5d69d31b16 | ||
|
|
4236653586 | ||
|
|
65dd8beb33 | ||
|
|
0493990e57 | ||
|
|
849d842c32 | ||
|
|
abaf40cd04 | ||
|
|
a333c8fc74 | ||
|
|
7b2fee36b6 | ||
|
|
8a9a32ce97 | ||
|
|
61ead1199c | ||
|
|
ed986ed7ba | ||
|
|
1b07f11843 | ||
|
|
17d8a3ac4e | ||
|
|
b7af7d4618 | ||
|
|
6e3c26d4f7 | ||
|
|
5797f8830b | ||
|
|
57c709ed96 | ||
|
|
811a1054ee | ||
|
|
dadeb672c6 | ||
|
|
81ff2d1aaf | ||
|
|
c1a94dd21f | ||
|
|
408ab151fd | ||
|
|
a3c897aada | ||
|
|
b8213f2fdd | ||
|
|
228f39da1d | ||
|
|
d8e260eaa7 | ||
|
|
9329cd4ec3 | ||
|
|
36726fef52 | ||
|
|
76fa4ad6e3 | ||
|
|
7183c3f240 | ||
|
|
3c90b55958 | ||
|
|
ee340f8683 | ||
|
|
0250773fbc | ||
|
|
3390f45cea | ||
|
|
d823235084 | ||
|
|
8456bb0eaa | ||
|
|
4de6e2d3ac | ||
|
|
97c437760a | ||
|
|
be2212c8dd | ||
|
|
bc8d790eb9 | ||
|
|
cebd3399a6 | ||
|
|
a4dbc79a1a | ||
|
|
b27646357d | ||
|
|
0d8c7d9e55 | ||
|
|
1aca6b4f5b | ||
|
|
129248847b | ||
|
|
da8c954ffd | ||
|
|
0aa0a6d1e7 | ||
|
|
ce4d289438 | ||
|
|
0c67a703d4 | ||
|
|
3952718811 | ||
|
|
e9b08db88f | ||
|
|
871858c753 | ||
|
|
6fc15b80e3 | ||
|
|
2ea24bd44d | ||
|
|
fb671f5860 | ||
|
|
dd9c32d526 | ||
|
|
d650a7bcca | ||
|
|
a03412fe87 | ||
|
|
1276ec26ba | ||
|
|
f7b235c24f | ||
|
|
fdf4ad31ee | ||
|
|
dd00098668 | ||
|
|
348cc06164 | ||
|
|
790c9ca9cc | ||
|
|
6da801eb9c | ||
|
|
6bf6c5770b | ||
|
|
bdd45ead8e | ||
|
|
5958f67305 | ||
|
|
50a19da4f7 | ||
|
|
d0503ee0f0 | ||
|
|
961e806a28 | ||
|
|
3780233d87 | ||
|
|
8a068def25 | ||
|
|
6742e8da4f | ||
|
|
e1aaecaecc | ||
|
|
8468cc3e59 | ||
|
|
fd87888334 | ||
|
|
34451f7a57 | ||
|
|
6fd920aa49 | ||
|
|
ea088f39ba | ||
|
|
67916eb0cd | ||
|
|
8bc01ad8cb | ||
|
|
5c155e86e5 |
3
.github/PULL_REQUEST_TEMPLATE.md
vendored
3
.github/PULL_REQUEST_TEMPLATE.md
vendored
@@ -22,6 +22,7 @@ Where `TYPE` is:
|
||||
|
||||
Where `PKG` is:
|
||||
|
||||
- `auth`: For changes to the Nhost Auth service
|
||||
- `ci`: For general changes to the build and/or CI/CD pipeline
|
||||
- `cli`: For changes to the Nhost CLI
|
||||
- `codegen`: For changes to the code generator
|
||||
@@ -32,7 +33,7 @@ Where `PKG` is:
|
||||
- `mintlify-openapi`: For changes to the Mintlify OpenAPI tool
|
||||
- `nhost-js`: For changes to the Nhost JavaScript SDK
|
||||
- `nixops`: For changes to the NixOps
|
||||
- `storage`: For changes to the Nhost Storage
|
||||
- `storage`: For changes to the Nhost Storage service
|
||||
|
||||
Where `SUMMARY` is a short description of what the PR does.
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@ runs:
|
||||
|
||||
# Define valid types and packages
|
||||
VALID_TYPES="feat|fix|chore"
|
||||
VALID_PKGS="ci|cli|codegen|dashboard|deps|docs|examples|mintlify-openapi|nhost-js|nixops|storage"
|
||||
VALID_PKGS="auth|ci|cli|codegen|dashboard|deps|docs|examples|mintlify-openapi|nhost-js|nixops|storage"
|
||||
|
||||
# Check if title matches the pattern TYPE(PKG): SUMMARY
|
||||
if [[ ! "$PR_TITLE" =~ ^(${VALID_TYPES})\((${VALID_PKGS})\):\ .+ ]]; then
|
||||
@@ -31,11 +31,11 @@ runs:
|
||||
echo " - chore: mark this pull request as a maintenance item"
|
||||
echo ""
|
||||
echo "Valid PKGs:"
|
||||
echo " - ci, cli, codegen, dashboard, deps, docs, examples,"
|
||||
echo " - auth, ci, cli, codegen, dashboard, deps, docs, examples,"
|
||||
echo " - mintlify-openapi, nhost-js, nixops, storage"
|
||||
echo ""
|
||||
echo "Example: feat(cli): add new command for database migrations"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
echo "✅ PR title is valid!"
|
||||
echo "✅ PR title is valid!"
|
||||
|
||||
84
.github/workflows/auth_checks.yaml
vendored
Normal file
84
.github/workflows/auth_checks.yaml
vendored
Normal file
@@ -0,0 +1,84 @@
|
||||
---
|
||||
name: "auth: check and build"
|
||||
on:
|
||||
# pull_request_target:
|
||||
pull_request:
|
||||
paths:
|
||||
- '.github/workflows/auth_checks.yaml'
|
||||
- '.github/workflows/wf_check.yaml'
|
||||
- '.github/workflows/wf_build_artifacts.yaml'
|
||||
|
||||
# common build
|
||||
- 'flake.nix'
|
||||
- 'flake.lock'
|
||||
- 'nixops/**'
|
||||
- 'build/**'
|
||||
|
||||
# common go
|
||||
- '.golangci.yaml'
|
||||
- 'go.mod'
|
||||
- 'go.sum'
|
||||
- 'vendor/**'
|
||||
|
||||
# auth
|
||||
- 'services/auth/**'
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.event_name == 'pull_request' && format('pr-{0}', github.event.pull_request.number) || format('push-{0}', github.sha) }}
|
||||
cancel-in-progress: ${{ github.event_name == 'pull_request' }}
|
||||
|
||||
jobs:
|
||||
check-permissions:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- run: |
|
||||
echo "github.event_name: ${{ github.event_name }}"
|
||||
echo "github.event.pull_request.author_association: ${{ github.event.pull_request.author_association }}"
|
||||
- name: "This task will run and fail if user has no permissions and label safe_to_test isn't present"
|
||||
if: "github.event_name == 'pull_request_target' && ! ( contains(github.event.pull_request.labels.*.name, 'safe_to_test') || contains(fromJson('[\"OWNER\", \"MEMBER\", \"COLLABORATOR\"]'), github.event.pull_request.author_association) )"
|
||||
run: |
|
||||
exit 1
|
||||
|
||||
tests:
|
||||
uses: ./.github/workflows/wf_check.yaml
|
||||
needs:
|
||||
- check-permissions
|
||||
with:
|
||||
NAME: auth
|
||||
PATH: services/auth
|
||||
GIT_REF: ${{ github.sha }}
|
||||
|
||||
secrets:
|
||||
AWS_ACCOUNT_ID: ${{ secrets.AWS_PRODUCTION_CORE_ACCOUNT_ID }}
|
||||
NIX_CACHE_PUB_KEY: ${{ secrets.NIX_CACHE_PUB_KEY }}
|
||||
NIX_CACHE_PRIV_KEY: ${{ secrets.NIX_CACHE_PRIV_KEY }}
|
||||
NHOST_PAT: ${{ secrets.NHOST_PAT }}
|
||||
|
||||
build_artifacts:
|
||||
uses: ./.github/workflows/wf_build_artifacts.yaml
|
||||
needs:
|
||||
- check-permissions
|
||||
with:
|
||||
NAME: auth
|
||||
PATH: services/auth
|
||||
GIT_REF: ${{ github.sha }}
|
||||
VERSION: 0.0.0-dev # we use a fixed version here to avoid unnecessary rebuilds
|
||||
DOCKER: true
|
||||
secrets:
|
||||
AWS_ACCOUNT_ID: ${{ secrets.AWS_PRODUCTION_CORE_ACCOUNT_ID }}
|
||||
NIX_CACHE_PUB_KEY: ${{ secrets.NIX_CACHE_PUB_KEY }}
|
||||
NIX_CACHE_PRIV_KEY: ${{ secrets.NIX_CACHE_PRIV_KEY }}
|
||||
|
||||
remove_label:
|
||||
runs-on: ubuntu-latest
|
||||
needs:
|
||||
- check-permissions
|
||||
steps:
|
||||
- uses: actions-ecosystem/action-remove-labels@v1
|
||||
with:
|
||||
labels: |
|
||||
safe_to_test
|
||||
if: contains(github.event.pull_request.labels.*.name, 'safe_to_test')
|
||||
60
.github/workflows/auth_wf_release.yaml
vendored
Normal file
60
.github/workflows/auth_wf_release.yaml
vendored
Normal file
@@ -0,0 +1,60 @@
|
||||
---
|
||||
name: "auth: release"
|
||||
on:
|
||||
workflow_call:
|
||||
inputs:
|
||||
GIT_REF:
|
||||
required: true
|
||||
type: string
|
||||
VERSION:
|
||||
required: true
|
||||
type: string
|
||||
secrets:
|
||||
AWS_ACCOUNT_ID:
|
||||
required: true
|
||||
NIX_CACHE_PUB_KEY:
|
||||
required: true
|
||||
NIX_CACHE_PRIV_KEY:
|
||||
required: true
|
||||
DOCKER_USERNAME:
|
||||
required: true
|
||||
DOCKER_PASSWORD:
|
||||
required: true
|
||||
|
||||
jobs:
|
||||
build_artifacts:
|
||||
uses: ./.github/workflows/wf_build_artifacts.yaml
|
||||
with:
|
||||
NAME: auth
|
||||
PATH: services/auth
|
||||
GIT_REF: ${{ inputs.GIT_REF }}
|
||||
VERSION: ${{ inputs.VERSION }}
|
||||
DOCKER: true
|
||||
secrets:
|
||||
AWS_ACCOUNT_ID: ${{ secrets.AWS_ACCOUNT_ID }}
|
||||
NIX_CACHE_PUB_KEY: ${{ secrets.NIX_CACHE_PUB_KEY }}
|
||||
NIX_CACHE_PRIV_KEY: ${{ secrets.NIX_CACHE_PRIV_KEY }}
|
||||
|
||||
push-docker-hub:
|
||||
uses: ./.github/workflows/wf_docker_push_image.yaml
|
||||
needs:
|
||||
- build_artifacts
|
||||
with:
|
||||
NAME: auth
|
||||
PATH: services/auth
|
||||
VERSION: ${{ inputs.VERSION }}
|
||||
secrets:
|
||||
DOCKER_USERNAME: ${{ secrets.DOCKER_USERNAME }}
|
||||
DOCKER_PASSWORD: ${{ secrets.DOCKER_PASSWORD }}
|
||||
|
||||
push-docker-ecr:
|
||||
uses: ./.github/workflows/wf_docker_push_image_ecr.yaml
|
||||
needs:
|
||||
- build_artifacts
|
||||
with:
|
||||
NAME: auth
|
||||
PATH: services/auth
|
||||
VERSION: ${{ inputs.VERSION }}
|
||||
secrets:
|
||||
AWS_ACCOUNT_ID: ${{ secrets.AWS_ACCOUNT_ID }}
|
||||
CONTAINER_REGISTRY: ${{ secrets.AWS_ACCOUNT_ID }}.dkr.ecr.eu-central-1.amazonaws.com
|
||||
14
.github/workflows/ci_release.yaml
vendored
14
.github/workflows/ci_release.yaml
vendored
@@ -33,6 +33,20 @@ jobs:
|
||||
echo "version=$VERSION" >> $GITHUB_OUTPUT
|
||||
echo "Extracted project: $PROJECT, version: $VERSION"
|
||||
|
||||
auth:
|
||||
needs: extract-project
|
||||
if: needs.extract-project.outputs.project == 'auth'
|
||||
uses: ./.github/workflows/auth_wf_release.yaml
|
||||
with:
|
||||
GIT_REF: ${{ github.sha }}
|
||||
VERSION: ${{ needs.extract-project.outputs.version }}
|
||||
secrets:
|
||||
AWS_ACCOUNT_ID: ${{ secrets.AWS_PRODUCTION_CORE_ACCOUNT_ID }}
|
||||
NIX_CACHE_PUB_KEY: ${{ secrets.NIX_CACHE_PUB_KEY }}
|
||||
NIX_CACHE_PRIV_KEY: ${{ secrets.NIX_CACHE_PRIV_KEY }}
|
||||
DOCKER_USERNAME: ${{ secrets.DOCKER_USERNAME }}
|
||||
DOCKER_PASSWORD: ${{ secrets.DOCKER_PASSWORD }}
|
||||
|
||||
cli:
|
||||
needs: extract-project
|
||||
if: needs.extract-project.outputs.project == 'cli'
|
||||
|
||||
2
.github/workflows/ci_update_changelog.yaml
vendored
2
.github/workflows/ci_update_changelog.yaml
vendored
@@ -13,7 +13,7 @@ jobs:
|
||||
|
||||
strategy:
|
||||
matrix:
|
||||
project: [cli, dashboard, packages/nhost-js, services/storage]
|
||||
project: [cli, dashboard, packages/nhost-js, services/auth, services/storage]
|
||||
|
||||
permissions:
|
||||
id-token: write
|
||||
|
||||
4
.github/workflows/dashboard_checks.yaml
vendored
4
.github/workflows/dashboard_checks.yaml
vendored
@@ -126,8 +126,10 @@ jobs:
|
||||
NHOST_TEST_USER_EMAIL: ${{ secrets.NHOST_TEST_USER_EMAIL }}
|
||||
NHOST_TEST_USER_PASSWORD: ${{ secrets.NHOST_TEST_USER_PASSWORD }}
|
||||
NHOST_TEST_PROJECT_ADMIN_SECRET: ${{ secrets.NHOST_TEST_PROJECT_ADMIN_SECRET }}
|
||||
NHOST_TEST_FREE_USER_EMAILS: ${{ secrets.NHOST_TEST_FREE_USER_EMAILS }}
|
||||
NHOST_TEST_ONBOARDING_USER: ${{ secrets.NHOST_TEST_ONBOARDING_USER }}
|
||||
PLAYWRIGHT_REPORT_ENCRYPTION_KEY: ${{ secrets.PLAYWRIGHT_REPORT_ENCRYPTION_KEY }}
|
||||
NHOST_TEST_STAGING_SUBDOMAIN: ${{ secrets.NHOST_TEST_STAGING_SUBDOMAIN }}
|
||||
NHOST_TEST_STAGING_REGION: ${{ secrets.NHOST_TEST_STAGING_REGION }}
|
||||
|
||||
remove_label:
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
13
.github/workflows/dashboard_wf_e2e_staging.yaml
vendored
13
.github/workflows/dashboard_wf_e2e_staging.yaml
vendored
@@ -52,12 +52,16 @@ on:
|
||||
required: true
|
||||
NHOST_TEST_USER_PASSWORD:
|
||||
required: true
|
||||
NHOST_TEST_ONBOARDING_USER:
|
||||
required: true
|
||||
NHOST_TEST_PROJECT_ADMIN_SECRET:
|
||||
required: true
|
||||
NHOST_TEST_FREE_USER_EMAILS:
|
||||
required: true
|
||||
PLAYWRIGHT_REPORT_ENCRYPTION_KEY:
|
||||
required: true
|
||||
NHOST_TEST_STAGING_SUBDOMAIN:
|
||||
required: true
|
||||
NHOST_TEST_STAGING_REGION:
|
||||
required: true
|
||||
|
||||
concurrency:
|
||||
group: dashboard-e2e-staging
|
||||
@@ -77,7 +81,10 @@ env:
|
||||
NHOST_TEST_USER_EMAIL: ${{ secrets.NHOST_TEST_USER_EMAIL }}
|
||||
NHOST_TEST_USER_PASSWORD: ${{ secrets.NHOST_TEST_USER_PASSWORD }}
|
||||
NHOST_TEST_PROJECT_ADMIN_SECRET: ${{ secrets.NHOST_TEST_PROJECT_ADMIN_SECRET }}
|
||||
NHOST_TEST_FREE_USER_EMAILS: ${{ secrets.NHOST_TEST_FREE_USER_EMAILS }}
|
||||
NHOST_TEST_ONBOARDING_USER: ${{ secrets.NHOST_TEST_ONBOARDING_USER }}
|
||||
NHOST_TEST_STAGING_SUBDOMAIN: ${{ secrets.NHOST_TEST_STAGING_SUBDOMAIN }}
|
||||
NHOST_TEST_STAGING_REGION: ${{ secrets.NHOST_TEST_STAGING_REGION }}
|
||||
|
||||
|
||||
jobs:
|
||||
tests:
|
||||
|
||||
1
.github/workflows/dashboard_wf_release.yaml
vendored
1
.github/workflows/dashboard_wf_release.yaml
vendored
@@ -88,6 +88,7 @@ jobs:
|
||||
- name: Bump version in source code
|
||||
run: |
|
||||
find cli -type f -exec sed -i 's/"nhost\/dashboard:[^"]*"/"nhost\/dashboard:${{ inputs.VERSION }}"/g' {} +
|
||||
sed -i 's/"nhost\/dashboard:[^"]*"/"nhost\/dashboard:${{ inputs.VERSION }}"/g' docs/reference/cli/commands.mdx
|
||||
|
||||
- name: "Create Pull Request"
|
||||
uses: peter-evans/create-pull-request@v7
|
||||
|
||||
4
.github/workflows/docs_checks.yaml
vendored
4
.github/workflows/docs_checks.yaml
vendored
@@ -28,6 +28,10 @@ on:
|
||||
# nhost-js
|
||||
- packages/nhost-js/**
|
||||
|
||||
# apis
|
||||
- 'services/auth/docs/openapi.yaml'
|
||||
- 'services/storage/controller/openapi.yaml'
|
||||
|
||||
# cli
|
||||
- cli/**
|
||||
push:
|
||||
|
||||
4
.github/workflows/nhost-js_checks.yaml
vendored
4
.github/workflows/nhost-js_checks.yaml
vendored
@@ -34,6 +34,10 @@ on:
|
||||
|
||||
# nhost-js
|
||||
- 'packages/nhost-js/**'
|
||||
|
||||
# apis
|
||||
- 'services/auth/docs/openapi.yaml'
|
||||
- 'services/storage/controller/openapi.yaml'
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
|
||||
2
.github/workflows/nixops_checks.yaml
vendored
2
.github/workflows/nixops_checks.yaml
vendored
@@ -56,7 +56,7 @@ jobs:
|
||||
PATH: nixops
|
||||
GIT_REF: ${{ github.sha }}
|
||||
VERSION: 0.0.0-dev # we use a fixed version here to avoid unnecessary rebuilds
|
||||
DOCKER: false
|
||||
DOCKER: true
|
||||
secrets:
|
||||
AWS_ACCOUNT_ID: ${{ secrets.AWS_PRODUCTION_CORE_ACCOUNT_ID }}
|
||||
NIX_CACHE_PUB_KEY: ${{ secrets.NIX_CACHE_PUB_KEY }}
|
||||
|
||||
35
.github/workflows/nixops_wf_release.yaml
vendored
Normal file
35
.github/workflows/nixops_wf_release.yaml
vendored
Normal file
@@ -0,0 +1,35 @@
|
||||
---
|
||||
name: "nixops: release"
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
paths:
|
||||
- 'flake.lock'
|
||||
- 'nixops/project.nix'
|
||||
|
||||
jobs:
|
||||
build_artifacts:
|
||||
uses: ./.github/workflows/wf_build_artifacts.yaml
|
||||
with:
|
||||
NAME: nixops
|
||||
PATH: nixops
|
||||
GIT_REF: ${{ inputs.GIT_REF }}
|
||||
VERSION: latest
|
||||
DOCKER: true
|
||||
secrets:
|
||||
AWS_ACCOUNT_ID: ${{ secrets.AWS_PRODUCTION_CORE_ACCOUNT_ID }}
|
||||
NIX_CACHE_PUB_KEY: ${{ secrets.NIX_CACHE_PUB_KEY }}
|
||||
NIX_CACHE_PRIV_KEY: ${{ secrets.NIX_CACHE_PRIV_KEY }}
|
||||
|
||||
push-docker:
|
||||
uses: ./.github/workflows/wf_docker_push_image.yaml
|
||||
needs:
|
||||
- build_artifacts
|
||||
with:
|
||||
NAME: nixops
|
||||
PATH: nixops
|
||||
VERSION: latest
|
||||
secrets:
|
||||
DOCKER_USERNAME: ${{ secrets.DOCKER_USERNAME }}
|
||||
DOCKER_PASSWORD: ${{ secrets.DOCKER_PASSWORD }}
|
||||
@@ -32,6 +32,7 @@ linters:
|
||||
- linters:
|
||||
- funlen
|
||||
- ireturn
|
||||
- goconst
|
||||
path: _test\.go
|
||||
- linters:
|
||||
- lll
|
||||
|
||||
@@ -24,28 +24,20 @@ If you find an Issue that addresses the problem you're having, please add your r
|
||||
|
||||
### Pull Requests
|
||||
|
||||
Please have a look at our [developers guide](https://github.com/nhost/nhost/blob/main/DEVELOPERS.md) to start coding!
|
||||
|
||||
PRs to our libraries are always welcome and can be a quick way to get your fix or improvement slated for the next release. In general, PRs should:
|
||||
|
||||
- Only fix/add the functionality in question **OR** address wide-spread whitespace/style issues, not both.
|
||||
- Add unit or integration tests for fixed or changed functionality (if a test suite exists).
|
||||
- Address a single concern in the least number of changed lines as possible.
|
||||
- Include documentation in the repo or on our [docs site](https://docs.nhost.io).
|
||||
- Be accompanied by a complete Pull Request template (loaded automatically when a PR is created).
|
||||
## Monorepo Structure
|
||||
|
||||
For changes that address core functionality or require breaking changes (e.g., a major release), it's best to open an Issue to discuss your proposal first. This is not required but can save time creating and reviewing changes.
|
||||
This repository is a monorepo that contains multiple packages and applications. The structure is as follows:
|
||||
|
||||
In general, we follow the ["fork-and-pull" Git workflow](https://github.com/susam/gitpr)
|
||||
- `cli` - The Nhost CLI
|
||||
- `dashboard` - The Nhost Dashboard
|
||||
- `docs` - Documentation
|
||||
- `examples` - Various example projects
|
||||
- `packages/nhost-js` - The Nhost JavaScript/TypeScript SDK
|
||||
- `services/auth` - Nhost Authentication service
|
||||
- `services/storage` - Nhost Storage service
|
||||
- `tools/codegen` - Internal code generation tool to build the SDK
|
||||
- `tools/mintlify-openapi` - Internal tool to generate reference documentation for Mintlify from an OpenAPI spec.
|
||||
|
||||
1. Fork the repository to your own Github account
|
||||
2. Clone the project to your machine
|
||||
3. Create a branch locally with a succinct but descriptive name. All changes should be part of a branch and submitted as a pull request - your branches should be prefixed with one of:
|
||||
- `bug/` for bug fixes
|
||||
- `feat/` for features
|
||||
- `chore/` for configuration changes
|
||||
- `docs/` for documentation changes
|
||||
4. Commit changes to the branch
|
||||
5. Following any formatting and testing guidelines specific to this repo
|
||||
6. Push changes to your fork
|
||||
7. Open a PR in our repository and follow the PR template to review the changes efficiently.
|
||||
For details about those projects and how to contribure, please refer to their respective `README.md` and `CONTRIBUTING.md` files.
|
||||
|
||||
100
DEVELOPERS.md
100
DEVELOPERS.md
@@ -1,100 +0,0 @@
|
||||
# Developer Guide
|
||||
|
||||
## Requirements
|
||||
|
||||
### Node.js v20 or later
|
||||
|
||||
### [pnpm](https://pnpm.io/) package manager
|
||||
|
||||
The easiest way to install `pnpm` if it's not installed on your machine yet is to use `npm`:
|
||||
|
||||
```sh
|
||||
$ npm install -g pnpm
|
||||
```
|
||||
|
||||
### [Nhost CLI](https://docs.nhost.io/platform/cli/local-development)
|
||||
|
||||
- The CLI is primarily used for running the E2E tests
|
||||
- Please refer to the [installation guide](https://docs.nhost.io/platform/cli/local-development) if you have not installed it yet
|
||||
|
||||
## File Structure
|
||||
|
||||
The repository is organized as a monorepo, with the following structure (only relevant folders are shown):
|
||||
|
||||
```
|
||||
assets/ # Assets used in the README
|
||||
config/ # Configuration files for the monorepo
|
||||
dashboard/ # Dashboard
|
||||
docs/ # Documentation website
|
||||
examples/ # Example projects
|
||||
packages/ # Core packages
|
||||
integrations/ # These are packages that rely on the core packages
|
||||
```
|
||||
|
||||
## Get started
|
||||
|
||||
### Installation
|
||||
|
||||
First, clone this repository:
|
||||
|
||||
```sh
|
||||
git clone https://github.com/nhost/nhost
|
||||
```
|
||||
|
||||
Then, install the dependencies with `pnpm`:
|
||||
|
||||
```sh
|
||||
$ cd nhost
|
||||
$ pnpm install
|
||||
```
|
||||
|
||||
### Development
|
||||
|
||||
Although package references are correctly updated on the fly for TypeScript, example projects and the dashboard won't see the changes because they are depending on the build output. To fix this, you can run packages in development mode.
|
||||
|
||||
Running packages in development mode from the root folder is as simple as:
|
||||
|
||||
```sh
|
||||
$ pnpm dev
|
||||
```
|
||||
|
||||
Our packages are linked together using [PNPM's workspace](https://pnpm.io/workspaces) feature. Next.js and Vite automatically detect changes in the dependencies and rebuild everything, so the changes will be reflected in the examples and the dashboard.
|
||||
|
||||
**Note:** It's possible that Next.js or Vite throw an error when you run `pnpm dev`. Restarting the process should fix it.
|
||||
|
||||
### Use Examples
|
||||
|
||||
Examples are a great way to test your changes in practice. Make sure you've `pnpm dev` running in your terminal and then run an example.
|
||||
|
||||
Let's follow the instructions to run [react-apollo example](https://github.com/nhost/nhost/blob/main/examples/react-apollo/README.md).
|
||||
|
||||
## Edit Documentation
|
||||
|
||||
The easier way to contribute to our documentation is to go to the `docs` folder and follow the [instructions to start local development](https://github.com/nhost/nhost/blob/main/docs/README.md):
|
||||
|
||||
```sh
|
||||
$ cd docs
|
||||
# not necessary if you've already done this step somewhere in the repository
|
||||
$ pnpm install
|
||||
$ pnpm start
|
||||
```
|
||||
|
||||
## Run Test Suites
|
||||
|
||||
### Unit Tests
|
||||
|
||||
You can run the unit tests with the following command from the repository root:
|
||||
|
||||
```sh
|
||||
$ pnpm test
|
||||
```
|
||||
|
||||
### E2E Tests
|
||||
|
||||
Each package that defines end-to-end tests embeds their own Nhost configuration, that will be automatically when running the tests. As a result, you must make sure you are not running the Nhost CLI before running the tests.
|
||||
|
||||
You can run the e2e tests with the following command from the repository root:
|
||||
|
||||
```sh
|
||||
$ pnpm e2e
|
||||
```
|
||||
16
Makefile
Normal file
16
Makefile
Normal file
@@ -0,0 +1,16 @@
|
||||
.PHONY: envrc-install
|
||||
envrc-install: ## Copy envrc.sample to all project folders
|
||||
@for f in $$(find . -name "project.nix"); do \
|
||||
echo "Copying envrc.sample to $$(dirname $$f)/.envrc"; \
|
||||
cp ./envrc.sample $$(dirname $$f)/.envrc; \
|
||||
done
|
||||
|
||||
.PHONY: nixops-container-env
|
||||
nixops-container-env: ## Enter a NixOS container environment
|
||||
docker run \
|
||||
-it \
|
||||
-v /var/run/docker.sock:/var/run/docker.sock \
|
||||
-v ./:/build \
|
||||
-w /build \
|
||||
nixops:0.0.0-dev \
|
||||
bash
|
||||
@@ -12,7 +12,7 @@
|
||||
<span> • </span>
|
||||
<a href="https://nhost.io/blog">Blog</a>
|
||||
<span> • </span>
|
||||
<a href="https://twitter.com/nhost">Twitter</a>
|
||||
<a href="https://x.com/nhost">X</a>
|
||||
<span> • </span>
|
||||
<a href="https://nhost.io/discord">Discord</a>
|
||||
<span> • </span>
|
||||
@@ -33,10 +33,10 @@ Nhost consists of open source software:
|
||||
|
||||
- Database: [PostgreSQL](https://www.postgresql.org/)
|
||||
- Instant GraphQL API: [Hasura](https://hasura.io/)
|
||||
- Authentication: [Hasura Auth](https://github.com/nhost/hasura-auth/)
|
||||
- Storage: [Hasura Storage](https://github.com/nhost/hasura-storage)
|
||||
- Authentication: [Auth](https://github.com/nhost/nhost/tree/main/services/auth)
|
||||
- Storage: [Storage](https://github.com/nhost/nhost/tree/main/services/storage)
|
||||
- Serverless Functions: Node.js (JavaScript and TypeScript)
|
||||
- [Nhost CLI](https://docs.nhost.io/platform/cli/local-development) for local development
|
||||
- [Nhost CLI](https://github.com/nhost/nhost/tree/main/cli) for local development
|
||||
|
||||
## Architecture of Nhost
|
||||
|
||||
@@ -107,7 +107,6 @@ Nhost is frontend agnostic, which means Nhost works with all frontend frameworks
|
||||
# Resources
|
||||
|
||||
- Start developing locally with the [Nhost CLI](https://docs.nhost.io/platform/cli/local-development)
|
||||
|
||||
## Nhost Clients
|
||||
|
||||
- [JavaScript/TypeScript](https://docs.nhost.io/reference/javascript/nhost-js/main)
|
||||
|
||||
@@ -54,6 +54,11 @@ get-version: ## Return version
|
||||
@echo $(VERSION)
|
||||
|
||||
|
||||
.PHONY: develop
|
||||
develop: ## Start a nix develop shell
|
||||
nix develop .\#$(NAME)
|
||||
|
||||
|
||||
.PHONY: _check-pre
|
||||
_check-pre: ## Pre-checks before running nix flake check
|
||||
|
||||
@@ -105,6 +110,11 @@ build-docker-image: ## Build docker container for native architecture
|
||||
skopeo copy --insecure-policy dir:./result docker-daemon:$(NAME):$(VERSION)
|
||||
|
||||
|
||||
.PHONY: build-docker-image-import-bare
|
||||
build-docker-image-import-bare:
|
||||
skopeo copy --insecure-policy dir:./result docker-daemon:$(NAME):$(VERSION)
|
||||
|
||||
|
||||
.PHONY: dev-env-up
|
||||
dev-env-up: _dev-env-build _dev-env-up ## Starts development environment
|
||||
|
||||
|
||||
@@ -2,6 +2,39 @@
|
||||
|
||||
All notable changes to this project will be documented in this file.
|
||||
|
||||
## [cli@1.34.1] - 2025-10-13
|
||||
|
||||
### 🐛 Bug Fixes
|
||||
|
||||
- *(cli)* Remove references to mcp-nhost (#3575)
|
||||
- *(cli)* Workaround os.Rename issues when src and dst are on different partitions (#3599)
|
||||
|
||||
|
||||
### ⚙️ Miscellaneous Tasks
|
||||
|
||||
- *(auth)* Change some references to deprecated hasura-auth (#3584)
|
||||
- *(docs)* Udpated README.md and CONTRIBUTING.md (#3587)
|
||||
|
||||
## [cli@1.34.0] - 2025-10-09
|
||||
|
||||
### 🚀 Features
|
||||
|
||||
- *(cli)* Added mcp server functionality from mcp-nhost (#3550)
|
||||
- *(cli)* Mcp: move configuration to .nhost folder and integrate cloud credentials (#3555)
|
||||
- *(cli)* Mcp: added support for environment variables in the configuration (#3556)
|
||||
- *(cli)* MCP refactor and documentation prior to official release (#3571)
|
||||
|
||||
|
||||
### 🐛 Bug Fixes
|
||||
|
||||
- *(dashboard)* Remove NODE_ENV from restricted env vars (#3573)
|
||||
|
||||
|
||||
### ⚙️ Miscellaneous Tasks
|
||||
|
||||
- *(nixops)* Update nhost-cli (#3554)
|
||||
- *(cli)* Bump nhost/dashboard to 2.38.4 (#3539)
|
||||
|
||||
## [cli@1.33.0] - 2025-10-02
|
||||
|
||||
### 🚀 Features
|
||||
|
||||
84
cli/CONTRIBUTING.md
Normal file
84
cli/CONTRIBUTING.md
Normal file
@@ -0,0 +1,84 @@
|
||||
# Developer Guide
|
||||
|
||||
## Requirements
|
||||
|
||||
We use nix to manage the development environment, the build process and for running tests.
|
||||
|
||||
### With Nix (Recommended)
|
||||
|
||||
Run `nix develop \#cli` to get a complete development environment.
|
||||
|
||||
### Without Nix
|
||||
|
||||
Check `project.nix` (checkDeps, buildInputs, buildNativeInputs) for manual dependency installation. Alternatively, you can run `make nixops-container-env` in the root of the repository to enter a Docker container with nix and all dependencies pre-installed (note it is a large image).
|
||||
|
||||
## Development Workflow
|
||||
|
||||
### Running Tests
|
||||
|
||||
**With Nix:**
|
||||
```bash
|
||||
make dev-env-up
|
||||
make check
|
||||
```
|
||||
|
||||
**Without Nix:**
|
||||
```bash
|
||||
# Start development environment
|
||||
make dev-env-up
|
||||
|
||||
# Lint Go code
|
||||
golangci-lint run ./...
|
||||
|
||||
# Run tests
|
||||
go test -v ./...
|
||||
```
|
||||
|
||||
### Formatting
|
||||
|
||||
Format code before committing:
|
||||
```bash
|
||||
golines -w --base-formatter=gofumpt .
|
||||
```
|
||||
|
||||
## Building
|
||||
|
||||
### Local Build
|
||||
|
||||
Build the project (output in `./result`):
|
||||
```bash
|
||||
make build
|
||||
```
|
||||
|
||||
### Docker Image
|
||||
|
||||
Build and import Docker image with skopeo:
|
||||
```bash
|
||||
make build-docker-image
|
||||
```
|
||||
|
||||
If you run the command above inside the dockerized nixops-container-env and you get an error like:
|
||||
|
||||
```
|
||||
FATA[0000] writing blob: io: read/write on closed pipe
|
||||
```
|
||||
|
||||
then you need to run the following command outside of the container (needs skopeo installed on the host):
|
||||
|
||||
```bash
|
||||
cd cli
|
||||
make build-docker-image-import-bare
|
||||
```
|
||||
|
||||
### Multi-Platform Builds
|
||||
|
||||
Build for multiple platforms (Darwin/Linux, ARM64/AMD64):
|
||||
```bash
|
||||
make build-multiplatform
|
||||
```
|
||||
|
||||
This produces binaries for:
|
||||
- darwin/arm64
|
||||
- darwin/amd64
|
||||
- linux/arm64
|
||||
- linux/amd64
|
||||
@@ -56,7 +56,7 @@ func CommandCloud() *cli.Command {
|
||||
&cli.StringFlag{ //nolint:exhaustruct
|
||||
Name: flagDashboardVersion,
|
||||
Usage: "Dashboard version to use",
|
||||
Value: "nhost/dashboard:2.38.0",
|
||||
Value: "nhost/dashboard:2.38.4",
|
||||
Sources: cli.EnvVars("NHOST_DASHBOARD_VERSION"),
|
||||
},
|
||||
&cli.StringFlag{ //nolint:exhaustruct
|
||||
|
||||
@@ -111,7 +111,7 @@ func CommandUp() *cli.Command { //nolint:funlen
|
||||
&cli.StringFlag{ //nolint:exhaustruct
|
||||
Name: flagDashboardVersion,
|
||||
Usage: "Dashboard version to use",
|
||||
Value: "nhost/dashboard:2.38.0",
|
||||
Value: "nhost/dashboard:2.38.4",
|
||||
Sources: cli.EnvVars("NHOST_DASHBOARD_VERSION"),
|
||||
},
|
||||
&cli.StringFlag{ //nolint:exhaustruct
|
||||
|
||||
@@ -17,7 +17,7 @@ func actionDump(_ context.Context, cmd *cli.Command) error {
|
||||
|
||||
cfg, err := config.Load(configPath)
|
||||
if err != nil {
|
||||
fmt.Println("Please, run `mcp-nhost config` to configure the service.") //nolint:forbidigo
|
||||
fmt.Println("Please, run `nhost mcp config` to configure the service.") //nolint:forbidigo
|
||||
return cli.Exit("failed to load config file "+err.Error(), 1)
|
||||
}
|
||||
|
||||
|
||||
@@ -137,7 +137,7 @@ func getConfig(cmd *cli.Command) (*config.Config, error) {
|
||||
|
||||
cfg, err := config.Load(configPath)
|
||||
if err != nil {
|
||||
fmt.Println("Please, run `mcp-nhost config` to configure the service.") //nolint:forbidigo
|
||||
fmt.Println("Please, run `nhost mcp config` to configure the service.") //nolint:forbidigo
|
||||
return nil, cli.Exit("failed to load config file "+err.Error(), 1)
|
||||
}
|
||||
|
||||
|
||||
@@ -131,7 +131,7 @@ func initInit(
|
||||
|
||||
getclient := &getter.Client{} //nolint:exhaustruct
|
||||
if _, err := getclient.Get(ctx, &getter.Request{ //nolint:exhaustruct
|
||||
Src: "git::https://github.com/nhost/hasura-auth.git//email-templates",
|
||||
Src: "git::https://github.com/nhost/nhost.git//services/auth/email-templates",
|
||||
Dst: "nhost/emails",
|
||||
DisableSymlinks: true,
|
||||
}); err != nil {
|
||||
|
||||
@@ -2,10 +2,13 @@ package software
|
||||
|
||||
import (
|
||||
"context"
|
||||
"errors"
|
||||
"fmt"
|
||||
"io"
|
||||
"os"
|
||||
"runtime"
|
||||
"strings"
|
||||
"syscall"
|
||||
|
||||
"github.com/nhost/nhost/cli/clienv"
|
||||
"github.com/nhost/nhost/cli/software"
|
||||
@@ -92,8 +95,8 @@ func install(cmd *cli.Command, ce *clienv.CliEnv, tmpFile string) error {
|
||||
|
||||
ce.Infoln("Copying to %s...", curBin)
|
||||
|
||||
if err := os.Rename(tmpFile, curBin); err != nil {
|
||||
return fmt.Errorf("failed to rename %s to %s: %w", tmpFile, curBin, err)
|
||||
if err := moveOrCopyFile(tmpFile, curBin); err != nil {
|
||||
return fmt.Errorf("failed to move %s to %s: %w", tmpFile, curBin, err)
|
||||
}
|
||||
|
||||
ce.Infoln("Setting permissions...")
|
||||
@@ -104,3 +107,55 @@ func install(cmd *cli.Command, ce *clienv.CliEnv, tmpFile string) error {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func moveOrCopyFile(src, dst string) error {
|
||||
if err := os.Rename(src, dst); err != nil {
|
||||
var linkErr *os.LinkError
|
||||
// this happens when moving across different filesystems
|
||||
if errors.As(err, &linkErr) && errors.Is(linkErr.Err, syscall.EXDEV) {
|
||||
if err := hardMove(src, dst); err != nil {
|
||||
return fmt.Errorf("failed to hard move: %w", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
return fmt.Errorf("failed to rename: %w", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func hardMove(src, dst string) error {
|
||||
srcFile, err := os.Open(src)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to open source file: %w", err)
|
||||
}
|
||||
defer srcFile.Close()
|
||||
|
||||
dstFile, err := os.Create(dst)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to create destination file: %w", err)
|
||||
}
|
||||
defer dstFile.Close()
|
||||
|
||||
if _, err := io.Copy(dstFile, srcFile); err != nil {
|
||||
return fmt.Errorf("failed to copy file contents: %w", err)
|
||||
}
|
||||
|
||||
fi, err := os.Stat(src)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to stat source file: %w", err)
|
||||
}
|
||||
|
||||
err = os.Chmod(dst, fi.Mode())
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to set file permissions: %w", err)
|
||||
}
|
||||
|
||||
if err := os.Remove(src); err != nil {
|
||||
return fmt.Errorf("failed to remove source file: %w", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -47,7 +47,7 @@ func auth( //nolint:funlen
|
||||
&model.ConfigSmtp{
|
||||
User: "user",
|
||||
Password: "password",
|
||||
Sender: "hasura-auth@example.com",
|
||||
Sender: "auth@example.com",
|
||||
Host: "mailhog",
|
||||
Port: 1025, //nolint:mnd
|
||||
Secure: false,
|
||||
|
||||
@@ -143,7 +143,7 @@ func expectedAuth() *Service {
|
||||
"AUTH_SMTP_PASS": "password",
|
||||
"AUTH_SMTP_PORT": "1025",
|
||||
"AUTH_SMTP_SECURE": "false",
|
||||
"AUTH_SMTP_SENDER": "hasura-auth@example.com",
|
||||
"AUTH_SMTP_SENDER": "auth@example.com",
|
||||
"AUTH_SMTP_USER": "user",
|
||||
"AUTH_USER_DEFAULT_ALLOWED_ROLES": "user,admin",
|
||||
"AUTH_USER_DEFAULT_ROLE": "user",
|
||||
|
||||
@@ -459,7 +459,7 @@ func mailhog(subdomain, volumeName string, useTLS bool) *Service {
|
||||
"SMTP_PASS": "password",
|
||||
"SMTP_PORT": "1025",
|
||||
"SMTP_SECURE": "false",
|
||||
"SMTP_SENDER": "hasura-auth@example.com",
|
||||
"SMTP_SENDER": "auth@example.com",
|
||||
"SMTP_USER": "user",
|
||||
},
|
||||
ExtraHosts: extraHosts(subdomain),
|
||||
|
||||
@@ -12,7 +12,7 @@ import (
|
||||
const (
|
||||
ToolGraphqlQueryName = "cloud-graphql-query"
|
||||
//nolint:lll
|
||||
ToolGraphqlQueryInstructions = `Execute a GraphQL query against the Nhost Cloud to perform operations on projects and organizations. It also allows configuring projects hosted on Nhost Cloud. Make sure you got the schema before attempting to execute any query. If you get an error while performing a query refresh the schema in case something has changed or you did something wrong. If you get an error indicating mutations are not allowed the user may have disabled them in the server, don't retry and ask the user they need to pass --with-cloud-mutations when starting mcp-nhost to enable them. Projects are apps.`
|
||||
ToolGraphqlQueryInstructions = `Execute a GraphQL query against the Nhost Cloud to perform operations on projects and organizations. It also allows configuring projects hosted on Nhost Cloud. Make sure you got the schema before attempting to execute any query. If you get an error while performing a query refresh the schema in case something has changed or you did something wrong. If you get an error indicating mutations are not allowed the user may have disabled them in the server, don't retry and ask the user they need to pass --with-cloud-mutations when starting nhost's mcp to enable them. Projects are apps.`
|
||||
)
|
||||
|
||||
func ptr[T any](v T) *T {
|
||||
|
||||
@@ -14,7 +14,7 @@ import (
|
||||
const (
|
||||
ToolGraphqlQueryName = "graphql-query"
|
||||
//nolint:lll
|
||||
ToolGraphqlQueryInstructions = `Execute a GraphQL query against a Nhost project. This tool is useful to query and mutate data. If you run into issues executing queries, retrieve the schema again in case the schema has changed. If you get an error indicating the query or mutation is not allowed the user may have disabled them in the server, don't retry and tell the user they need to enable them when starting mcp-nhost`
|
||||
ToolGraphqlQueryInstructions = `Execute a GraphQL query against a Nhost project. This tool is useful to query and mutate data. If you run into issues executing queries, retrieve the schema again in case the schema has changed. If you get an error indicating the query or mutation is not allowed the user may have disabled them in the server, don't retry and tell the user they need to enable them when starting nhost's mcp`
|
||||
)
|
||||
|
||||
func ptr[T any](v T) *T {
|
||||
|
||||
@@ -105,8 +105,8 @@ test('should create a table with nullable columns', async ({
|
||||
.locator(`li:has-text("${tableName}") #table-management-menu button`)
|
||||
.click();
|
||||
await page.getByText('Edit Table').click();
|
||||
expect(page.locator('h2:has-text("Edit Table")')).toBeVisible();
|
||||
expect(page.locator('div[data-testid="id"]')).toBeVisible();
|
||||
await expect(page.locator('h2:has-text("Edit Table")')).toBeVisible();
|
||||
await expect(page.locator('div[data-testid="id"]')).toBeVisible();
|
||||
});
|
||||
|
||||
test('should create a table with an identity column', async ({
|
||||
@@ -146,13 +146,13 @@ test('should create a table with an identity column', async ({
|
||||
.locator(`li:has-text("${tableName}") #table-management-menu button`)
|
||||
.click();
|
||||
await page.getByText('Edit Table').click();
|
||||
expect(page.locator('h2:has-text("Edit Table")')).toBeVisible();
|
||||
expect(
|
||||
await expect(page.locator('h2:has-text("Edit Table")')).toBeVisible();
|
||||
await expect(
|
||||
page.locator('button#identityColumnIndex :has-text("identity_column")'),
|
||||
).toBeVisible();
|
||||
expect(page.locator('[id="columns.3.defaultValue"]')).toBeDisabled();
|
||||
expect(page.locator('[name="columns.3.isNullable"]')).toBeDisabled();
|
||||
expect(page.locator('[name="columns.3.isUnique"]')).toBeDisabled();
|
||||
await expect(page.locator('[id="columns.3.defaultValue"]')).toBeDisabled();
|
||||
await expect(page.locator('[name="columns.3.isNullable"]')).toBeDisabled();
|
||||
await expect(page.locator('[name="columns.3.isUnique"]')).toBeDisabled();
|
||||
});
|
||||
|
||||
test('should create table with foreign key constraint', async ({
|
||||
@@ -234,6 +234,46 @@ test('should create table with foreign key constraint', async ({
|
||||
).toBeVisible();
|
||||
});
|
||||
|
||||
test('should be able to create a table with a composite key', async ({
|
||||
authenticatedNhostPage: page,
|
||||
}) => {
|
||||
await page.getByRole('button', { name: /new table/i }).click();
|
||||
await expect(page.getByText(/create a new table/i)).toBeVisible();
|
||||
|
||||
const tableName = snakeCase(faker.lorem.words(3));
|
||||
|
||||
await prepareTable({
|
||||
page,
|
||||
name: tableName,
|
||||
primaryKeys: ['id', 'second_id'],
|
||||
columns: [
|
||||
{ name: 'id', type: 'uuid', defaultValue: 'gen_random_uuid()' },
|
||||
{ name: 'second_id', type: 'uuid', defaultValue: 'gen_random_uuid()' },
|
||||
{ name: 'name', type: 'text' },
|
||||
],
|
||||
});
|
||||
|
||||
await expect(page.locator('div[data-testid="id"]')).toBeVisible();
|
||||
await expect(page.locator('div[data-testid="second_id"]')).toBeVisible();
|
||||
|
||||
await page.getByRole('button', { name: /create/i }).click();
|
||||
|
||||
await page.waitForURL(
|
||||
`/orgs/${TEST_ORGANIZATION_SLUG}/projects/${TEST_PROJECT_SUBDOMAIN}/database/browser/default/public/${tableName}`,
|
||||
);
|
||||
|
||||
await expect(
|
||||
page.getByRole('link', { name: tableName, exact: true }),
|
||||
).toBeVisible();
|
||||
|
||||
await page
|
||||
.locator(`li:has-text("${tableName}") #table-management-menu button`)
|
||||
.click();
|
||||
await page.getByText('Edit Table').click();
|
||||
await expect(page.locator('div[data-testid="id"]')).toBeVisible();
|
||||
await expect(page.locator('div[data-testid="second_id"]')).toBeVisible();
|
||||
});
|
||||
|
||||
test('should not be able to create a table with a name that already exists', async ({
|
||||
authenticatedNhostPage: page,
|
||||
}) => {
|
||||
@@ -280,40 +320,3 @@ test('should not be able to create a table with a name that already exists', asy
|
||||
page.getByText(/error: a table with this name already exists/i),
|
||||
).toBeVisible();
|
||||
});
|
||||
|
||||
test('should be able to create a table with a composite key', async ({
|
||||
authenticatedNhostPage: page,
|
||||
}) => {
|
||||
await page.getByRole('button', { name: /new table/i }).click();
|
||||
await expect(page.getByText(/create a new table/i)).toBeVisible();
|
||||
|
||||
const tableName = snakeCase(faker.lorem.words(3));
|
||||
|
||||
await prepareTable({
|
||||
page,
|
||||
name: tableName,
|
||||
primaryKeys: ['id', 'second_id'],
|
||||
columns: [
|
||||
{ name: 'id', type: 'uuid', defaultValue: 'gen_random_uuid()' },
|
||||
{ name: 'second_id', type: 'uuid', defaultValue: 'gen_random_uuid()' },
|
||||
{ name: 'name', type: 'text' },
|
||||
],
|
||||
});
|
||||
|
||||
await page.getByRole('button', { name: /create/i }).click();
|
||||
|
||||
await page.waitForURL(
|
||||
`/orgs/${TEST_ORGANIZATION_SLUG}/projects/${TEST_PROJECT_SUBDOMAIN}/database/browser/default/public/${tableName}`,
|
||||
);
|
||||
|
||||
await expect(
|
||||
page.getByRole('link', { name: tableName, exact: true }),
|
||||
).toBeVisible();
|
||||
|
||||
await page
|
||||
.locator(`li:has-text("${tableName}") #table-management-menu button`)
|
||||
.click();
|
||||
await page.getByText('Edit Table').click();
|
||||
expect(page.locator('div[data-testid="id"]')).toBeVisible();
|
||||
expect(page.locator('div[data-testid="second_id"]')).toBeVisible();
|
||||
});
|
||||
|
||||
@@ -41,12 +41,13 @@ export const TEST_USER_PASSWORD = process.env.NHOST_TEST_USER_PASSWORD!;
|
||||
|
||||
export const TEST_PERSONAL_ORG_SLUG = process.env.NHOST_TEST_PERSONAL_ORG_SLUG!;
|
||||
|
||||
const freeUserEmails = process.env.NHOST_TEST_FREE_USER_EMAILS!;
|
||||
|
||||
export const TEST_FREE_USER_EMAILS: string[] = JSON.parse(freeUserEmails);
|
||||
export const TEST_ONBOARDING_USER = process.env.NHOST_TEST_ONBOARDING_USER!;
|
||||
|
||||
/**
|
||||
* Name of the remote schema serverless function to test against.
|
||||
*/
|
||||
export const TEST_PROJECT_REMOTE_SCHEMA_NAME =
|
||||
process.env.NHOST_TEST_PROJECT_REMOTE_SCHEMA_NAME!;
|
||||
|
||||
export const TEST_STAGING_SUBDOMAIN = process.env.NHOST_TEST_STAGING_SUBDOMAIN!;
|
||||
export const TEST_STAGING_REGION = process.env.NHOST_TEST_STAGING_REGION!;
|
||||
|
||||
@@ -1,13 +1,10 @@
|
||||
import { expect, test } from '@/e2e/fixtures/auth-hook';
|
||||
import {
|
||||
cleanupOnboardingTestIfNeeded,
|
||||
getCardExpiration,
|
||||
getOrgSlugFromUrl,
|
||||
getProjectSlugFromUrl,
|
||||
gotoUrl,
|
||||
loginWithFreeUser,
|
||||
setFreeUserStarterOrgSlug,
|
||||
setNewProjectName,
|
||||
setNewProjectSlug,
|
||||
} from '@/e2e/utils';
|
||||
import { faker } from '@faker-js/faker';
|
||||
import type { Page } from '@playwright/test';
|
||||
@@ -15,13 +12,15 @@ import type { Page } from '@playwright/test';
|
||||
let page: Page;
|
||||
|
||||
test.beforeAll(async ({ browser }) => {
|
||||
await cleanupOnboardingTestIfNeeded();
|
||||
|
||||
page = await browser.newPage();
|
||||
await loginWithFreeUser(page);
|
||||
});
|
||||
|
||||
test('user should be able to finish onboarding', async () => {
|
||||
await gotoUrl(page, `/onboarding`);
|
||||
expect(page.getByText('Welcome to Nhost!')).toBeVisible();
|
||||
await expect(page.getByText('Welcome to Nhost!')).toBeVisible();
|
||||
const organizationName = faker.lorem.words(3).slice(0, 32);
|
||||
|
||||
await page.getByLabel('Organization Name').fill(organizationName);
|
||||
@@ -68,34 +67,28 @@ test('user should be able to finish onboarding', async () => {
|
||||
.getByTestId('hosted-payment-submit-button')
|
||||
.click({ force: true });
|
||||
|
||||
expect(
|
||||
await expect(
|
||||
page.getByText('Processing new organization request').first(),
|
||||
).toBeVisible();
|
||||
await page.waitForSelector(
|
||||
'div:has-text("Organization created successfully. Redirecting...")',
|
||||
);
|
||||
|
||||
expect(page.getByText('Create Your First Project')).toBeVisible();
|
||||
await expect(page.getByText('Create Your First Project')).toBeVisible();
|
||||
|
||||
const projectName = faker.lorem.words(3).slice(0, 32);
|
||||
await page.getByLabel('Project Name').fill(projectName);
|
||||
|
||||
await page.getByText('Create Project', { exact: true }).click();
|
||||
|
||||
expect(page.getByText('Creating your project...')).toBeVisible();
|
||||
expect(page.getByText('Project created successfully!')).toBeVisible();
|
||||
await expect(page.getByText('Creating your project...')).toBeVisible();
|
||||
await expect(page.getByText('Project created successfully!')).toBeVisible();
|
||||
|
||||
expect(page.getByText('Internal info')).toBeVisible();
|
||||
await expect(page.getByText('Internal info')).toBeVisible();
|
||||
|
||||
await page.waitForSelector('h3:has-text("Project Health")', {
|
||||
timeout: 180000,
|
||||
});
|
||||
|
||||
const newProjectSlug = getProjectSlugFromUrl(page.url());
|
||||
setNewProjectSlug(newProjectSlug);
|
||||
setNewProjectName(organizationName);
|
||||
const newOrgSlug = getOrgSlugFromUrl(page.url());
|
||||
setFreeUserStarterOrgSlug(newOrgSlug);
|
||||
});
|
||||
|
||||
test('should delete the new organization', async () => {
|
||||
@@ -107,12 +100,12 @@ test('should delete the new organization', async () => {
|
||||
await page.getByRole('button', { name: 'Delete' }).click();
|
||||
|
||||
await page.waitForSelector('h2:has-text("Delete Organization")');
|
||||
expect(page.getByTestId('deleteOrgButton')).toBeDisabled();
|
||||
await expect(page.getByTestId('deleteOrgButton')).toBeDisabled();
|
||||
|
||||
await page.getByLabel("I'm sure I want to delete this Organization").click();
|
||||
expect(page.getByTestId('deleteOrgButton')).toBeDisabled();
|
||||
await expect(page.getByTestId('deleteOrgButton')).toBeDisabled();
|
||||
await page.getByLabel('I understand this action cannot be undone').click();
|
||||
expect(page.getByTestId('deleteOrgButton')).not.toBeDisabled();
|
||||
await expect(page.getByTestId('deleteOrgButton')).not.toBeDisabled();
|
||||
|
||||
await page.getByTestId('deleteOrgButton').click();
|
||||
|
||||
@@ -145,7 +138,7 @@ test('should be able to upgrade an organization', async () => {
|
||||
await page.getByRole('link', { name: 'Billing' }).click();
|
||||
|
||||
await page.waitForSelector('h4:has-text("Subscription plan")');
|
||||
expect(page.getByText('Upgrade')).toBeEnabled();
|
||||
await expect(page.getByText('Upgrade')).toBeEnabled();
|
||||
await page.getByText('Upgrade').click();
|
||||
await page.waitForSelector('h2:has-text("Upgrade Organization")');
|
||||
|
||||
@@ -205,12 +198,12 @@ test('should be able to upgrade an organization', async () => {
|
||||
await page.getByRole('button', { name: 'Delete' }).click();
|
||||
|
||||
await page.waitForSelector('h2:has-text("Delete Organization")');
|
||||
expect(page.getByTestId('deleteOrgButton')).toBeDisabled();
|
||||
await expect(page.getByTestId('deleteOrgButton')).toBeDisabled();
|
||||
|
||||
await page.getByLabel("I'm sure I want to delete this Organization").click();
|
||||
expect(page.getByTestId('deleteOrgButton')).toBeDisabled();
|
||||
await expect(page.getByTestId('deleteOrgButton')).toBeDisabled();
|
||||
await page.getByLabel('I understand this action cannot be undone').click();
|
||||
expect(page.getByTestId('deleteOrgButton')).not.toBeDisabled();
|
||||
await expect(page.getByTestId('deleteOrgButton')).not.toBeDisabled();
|
||||
|
||||
await page.getByTestId('deleteOrgButton').click();
|
||||
|
||||
|
||||
@@ -4,61 +4,64 @@ import {
|
||||
TEST_PROJECT_SUBDOMAIN,
|
||||
} from '@/e2e/env';
|
||||
import { expect, test } from '@/e2e/fixtures/auth-hook';
|
||||
import { cleanupRemoteSchemaTestIfNeeded } from '@/e2e/utils';
|
||||
import { faker } from '@faker-js/faker';
|
||||
import { snakeCase } from 'snake-case';
|
||||
|
||||
const REMOTE_SCHEMA_TEST_URL = `https://${TEST_PROJECT_SUBDOMAIN}.functions.eu-central-1.staging.nhost.run/v1/${TEST_PROJECT_REMOTE_SCHEMA_NAME}`;
|
||||
|
||||
test.describe('Remote Schemas', () => {
|
||||
test.beforeEach(async ({ authenticatedNhostPage: page }) => {
|
||||
const remoteSchemasRoute = `/orgs/${TEST_ORGANIZATION_SLUG}/projects/${TEST_PROJECT_SUBDOMAIN}/graphql/remote-schemas`;
|
||||
await page.goto(remoteSchemasRoute);
|
||||
await page.waitForURL(remoteSchemasRoute);
|
||||
});
|
||||
|
||||
test('should create and delete a remote schema from URL', async ({
|
||||
authenticatedNhostPage: page,
|
||||
}) => {
|
||||
await page.getByRole('button', { name: /add remote schema/i }).click();
|
||||
await expect(page.getByText(/create a new remote schema/i)).toBeVisible();
|
||||
|
||||
const schemaName = snakeCase(`e2e ${faker.lorem.words(2)}`);
|
||||
|
||||
await page.getByPlaceholder(/remote schema name/i).fill(schemaName);
|
||||
await page
|
||||
.getByPlaceholder(/graphql-service\.example\.com/i)
|
||||
.fill(REMOTE_SCHEMA_TEST_URL);
|
||||
|
||||
await page.getByRole('button', { name: /create/i }).click();
|
||||
|
||||
await page.waitForSelector(
|
||||
'div:has-text("The remote schema has been created successfully.")',
|
||||
);
|
||||
|
||||
const detailsUrl = `/orgs/${TEST_ORGANIZATION_SLUG}/projects/${TEST_PROJECT_SUBDOMAIN}/graphql/remote-schemas/${schemaName}`;
|
||||
await page.waitForURL(detailsUrl);
|
||||
|
||||
await expect(
|
||||
page.getByRole('link', { name: schemaName, exact: true }),
|
||||
).toBeVisible();
|
||||
|
||||
const schemaLink = page.getByRole('link', {
|
||||
name: schemaName,
|
||||
exact: true,
|
||||
});
|
||||
|
||||
await schemaLink.hover();
|
||||
await page
|
||||
.getByRole('listitem')
|
||||
.filter({ hasText: schemaName })
|
||||
.getByRole('button')
|
||||
.click();
|
||||
|
||||
await page.getByRole('menuitem', { name: /delete remote schema/i }).click();
|
||||
await page.getByRole('button', { name: /^delete$/i }).click();
|
||||
|
||||
await expect(
|
||||
page.getByRole('link', { name: schemaName, exact: true }),
|
||||
).toHaveCount(0);
|
||||
});
|
||||
test.beforeAll(async () => {
|
||||
await cleanupRemoteSchemaTestIfNeeded();
|
||||
});
|
||||
|
||||
test.beforeEach(async ({ authenticatedNhostPage: page }) => {
|
||||
const remoteSchemasRoute = `/orgs/${TEST_ORGANIZATION_SLUG}/projects/${TEST_PROJECT_SUBDOMAIN}/graphql/remote-schemas`;
|
||||
await page.goto(remoteSchemasRoute);
|
||||
await page.waitForURL(remoteSchemasRoute);
|
||||
});
|
||||
|
||||
test('should create and delete a remote schema from URL', async ({
|
||||
authenticatedNhostPage: page,
|
||||
}) => {
|
||||
await page.getByRole('button', { name: /add remote schema/i }).click();
|
||||
await expect(page.getByText(/create a new remote schema/i)).toBeVisible();
|
||||
|
||||
const schemaName = snakeCase(`e2e ${faker.lorem.words(2)}`);
|
||||
|
||||
await page.getByPlaceholder(/remote schema name/i).fill(schemaName);
|
||||
await page
|
||||
.getByPlaceholder(/graphql-service\.example\.com/i)
|
||||
.fill(REMOTE_SCHEMA_TEST_URL);
|
||||
|
||||
await page.getByRole('button', { name: /create/i }).click();
|
||||
|
||||
await page.waitForSelector(
|
||||
'div:has-text("The remote schema has been created successfully.")',
|
||||
);
|
||||
|
||||
const detailsUrl = `/orgs/${TEST_ORGANIZATION_SLUG}/projects/${TEST_PROJECT_SUBDOMAIN}/graphql/remote-schemas/${schemaName}`;
|
||||
await page.waitForURL(detailsUrl);
|
||||
|
||||
await expect(
|
||||
page.getByRole('link', { name: schemaName, exact: true }),
|
||||
).toBeVisible();
|
||||
|
||||
const schemaLink = page.getByRole('link', {
|
||||
name: schemaName,
|
||||
exact: true,
|
||||
});
|
||||
|
||||
await schemaLink.hover();
|
||||
await page
|
||||
.getByRole('listitem')
|
||||
.filter({ hasText: schemaName })
|
||||
.getByRole('button')
|
||||
.click();
|
||||
|
||||
await page.getByRole('menuitem', { name: /delete remote schema/i }).click();
|
||||
await page.getByRole('button', { name: /^delete$/i }).click();
|
||||
|
||||
await expect(
|
||||
page.getByRole('link', { name: schemaName, exact: true }),
|
||||
).toHaveCount(0);
|
||||
});
|
||||
|
||||
@@ -1,9 +1,16 @@
|
||||
/* eslint-disable no-await-in-loop */
|
||||
import {
|
||||
TEST_FREE_USER_EMAILS,
|
||||
TEST_ONBOARDING_USER,
|
||||
TEST_ORGANIZATION_SLUG,
|
||||
TEST_PROJECT_ADMIN_SECRET,
|
||||
TEST_PROJECT_SUBDOMAIN,
|
||||
TEST_STAGING_REGION,
|
||||
TEST_STAGING_SUBDOMAIN,
|
||||
TEST_USER_PASSWORD,
|
||||
} from '@/e2e/env';
|
||||
import { expect } from '@/e2e/fixtures/auth-hook';
|
||||
import { isEmptyValue } from '@/lib/utils';
|
||||
import type { ExportMetadataResponse } from '@/utils/hasura-api/generated/schemas';
|
||||
import { faker } from '@faker-js/faker';
|
||||
import { type Page } from '@playwright/test';
|
||||
import { add, format } from 'date-fns-v4';
|
||||
@@ -125,12 +132,26 @@ export async function prepareTable({
|
||||
),
|
||||
);
|
||||
await page.getByLabel('Primary Key').click();
|
||||
await Promise.all(
|
||||
primaryKeys.map(async (primaryKey) => {
|
||||
await page.getByRole('option', { name: primaryKey, exact: true }).click();
|
||||
}),
|
||||
);
|
||||
|
||||
await page
|
||||
.getByRole('option', { name: columns[0].name, exact: true })
|
||||
.waitFor({ timeout: 1000 });
|
||||
await expect(
|
||||
page.getByRole('option', { name: columns[0].name, exact: true }),
|
||||
).toBeVisible();
|
||||
// eslint-disable-next-line no-restricted-syntax
|
||||
for (const primaryKey of primaryKeys) {
|
||||
await page.waitForTimeout(1000);
|
||||
await page.getByRole('option', { name: primaryKey, exact: true }).click();
|
||||
await page
|
||||
.locator(`div[data-testid="${primaryKey}"]`)
|
||||
.waitFor({ timeout: 1000 });
|
||||
}
|
||||
await page.getByText('Create a New Table').click();
|
||||
await page.waitForTimeout(1000);
|
||||
await expect(
|
||||
page.getByRole('option', { name: columns[0].name, exact: true }),
|
||||
).not.toBeVisible();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -232,42 +253,6 @@ export async function gotoUrl(page: Page, url: string) {
|
||||
await page.waitForURL(url, { waitUntil: 'load' });
|
||||
}
|
||||
|
||||
let newOrgSlug: string;
|
||||
|
||||
export function getNewOrgSlug() {
|
||||
return newOrgSlug;
|
||||
}
|
||||
|
||||
export function setNewOrgSlug(slug: string) {
|
||||
newOrgSlug = slug;
|
||||
}
|
||||
|
||||
let freeUserStarterOrgSlug: string;
|
||||
|
||||
export function getFreeUserStarterOrgSlug() {
|
||||
return freeUserStarterOrgSlug;
|
||||
}
|
||||
|
||||
export function setFreeUserStarterOrgSlug(slug: string) {
|
||||
freeUserStarterOrgSlug = slug;
|
||||
}
|
||||
|
||||
let newProjectSlug: string;
|
||||
|
||||
export function getNewProjectSlug() {
|
||||
return newProjectSlug;
|
||||
}
|
||||
|
||||
export function setNewProjectSlug(slug: string) {
|
||||
newProjectSlug = slug;
|
||||
}
|
||||
|
||||
export function getProjectSlugFromUrl(url: string) {
|
||||
const [, projectSlug] = url.split('/projects/');
|
||||
|
||||
return projectSlug;
|
||||
}
|
||||
|
||||
export function getOrgSlugFromUrl(url: string) {
|
||||
const orgSlug = url.split('/orgs/')[1].split('/projects/')[0];
|
||||
return orgSlug;
|
||||
@@ -278,33 +263,13 @@ export function getCardExpiration() {
|
||||
return format(now, 'MMyy');
|
||||
}
|
||||
|
||||
let newProjectName: string;
|
||||
|
||||
export function getNewProjectName() {
|
||||
return newProjectName;
|
||||
}
|
||||
|
||||
export function setNewProjectName(name: string) {
|
||||
newProjectName = name;
|
||||
}
|
||||
|
||||
function getRandomUserIndex(): number {
|
||||
return Math.floor(Math.random() * TEST_FREE_USER_EMAILS.length);
|
||||
}
|
||||
|
||||
export async function loginWithFreeUser(page: Page) {
|
||||
const userIndex = getRandomUserIndex();
|
||||
|
||||
const freeUserEmail = TEST_FREE_USER_EMAILS[userIndex];
|
||||
|
||||
// eslint-disable-next-line no-console
|
||||
console.log(`Selected userIndex: ${userIndex}`);
|
||||
await page.goto('/');
|
||||
await page.waitForURL('/signin');
|
||||
await page.getByRole('link', { name: /continue with email/i }).click();
|
||||
|
||||
await page.waitForURL('/signin/email');
|
||||
await page.getByLabel('Email').fill(freeUserEmail);
|
||||
await page.getByLabel('Email').fill(TEST_ONBOARDING_USER);
|
||||
await page.getByLabel('Password').fill(TEST_USER_PASSWORD);
|
||||
await page.getByRole('button', { name: /sign in/i }).click();
|
||||
|
||||
@@ -319,3 +284,132 @@ export function toPascalCase(str: string, divider = ' ') {
|
||||
.map((word) => word.charAt(0).toUpperCase() + word.slice(1).toLowerCase())
|
||||
.join('');
|
||||
}
|
||||
|
||||
export async function cleanupOnboardingTestIfNeeded() {
|
||||
const signinUrl = `https://${TEST_STAGING_SUBDOMAIN}.auth.${TEST_STAGING_REGION}.nhost.run/v1/signin/email-password`;
|
||||
const graphqlUrl = `https://${TEST_STAGING_SUBDOMAIN}.graphql.${TEST_STAGING_REGION}.nhost.run/v1`;
|
||||
|
||||
try {
|
||||
const response = await fetch(signinUrl, {
|
||||
method: 'POST',
|
||||
headers: { 'Content-Type': 'application/json' },
|
||||
body: JSON.stringify({
|
||||
email: TEST_ONBOARDING_USER,
|
||||
password: TEST_USER_PASSWORD,
|
||||
}),
|
||||
});
|
||||
const data = await response.json();
|
||||
|
||||
const userId = data.session?.user?.id;
|
||||
const accessToken = data.session?.accessToken;
|
||||
const organizationPayload = {
|
||||
query: `
|
||||
query {
|
||||
organizations(where: { members: {userID: {_eq: "${userId}"}} }) {
|
||||
id
|
||||
}
|
||||
}`,
|
||||
};
|
||||
|
||||
const authHeader = `Bearer ${accessToken}`;
|
||||
|
||||
const orgResponse = await fetch(graphqlUrl, {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json',
|
||||
Authorization: authHeader,
|
||||
},
|
||||
body: JSON.stringify(organizationPayload),
|
||||
});
|
||||
|
||||
const orgData = await orgResponse.json();
|
||||
|
||||
const organizations = orgData.data?.organizations;
|
||||
|
||||
if (organizations && organizations.length > 0) {
|
||||
// eslint-disable-next-line no-console
|
||||
console.log('Cleaning up organization');
|
||||
await Promise.all(
|
||||
organizations.map(({ id }) =>
|
||||
fetch(graphqlUrl, {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json',
|
||||
Authorization: authHeader,
|
||||
},
|
||||
body: JSON.stringify({
|
||||
query: `
|
||||
mutation {
|
||||
billingDeleteOrganization(organizationID: "${id}")
|
||||
}
|
||||
`,
|
||||
}),
|
||||
}),
|
||||
),
|
||||
);
|
||||
}
|
||||
} catch (error) {
|
||||
// eslint-disable-next-line no-console
|
||||
console.log(error);
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
export async function cleanupRemoteSchemaTestIfNeeded() {
|
||||
try {
|
||||
const response = await fetch(
|
||||
`https://${TEST_PROJECT_SUBDOMAIN}.hasura.eu-central-1.staging.nhost.run/v1/metadata`,
|
||||
{
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'x-hasura-admin-secret': TEST_PROJECT_ADMIN_SECRET,
|
||||
},
|
||||
body: JSON.stringify({
|
||||
type: 'export_metadata',
|
||||
version: 2,
|
||||
args: {},
|
||||
}),
|
||||
},
|
||||
);
|
||||
const data = (await response.json()) as ExportMetadataResponse;
|
||||
|
||||
const remoteSchemas = data.metadata?.remote_schemas;
|
||||
|
||||
if (isEmptyValue(remoteSchemas)) {
|
||||
return;
|
||||
}
|
||||
|
||||
const schemasToDelete = remoteSchemas!.filter((remoteSchema) =>
|
||||
/^e2e_\w+_\w+$/.test(remoteSchema.name),
|
||||
);
|
||||
|
||||
await Promise.all(
|
||||
schemasToDelete.map((remoteSchema) =>
|
||||
fetch(
|
||||
`https://${TEST_PROJECT_SUBDOMAIN}.hasura.eu-central-1.staging.nhost.run/v1/metadata`,
|
||||
{
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'x-hasura-admin-secret': TEST_PROJECT_ADMIN_SECRET,
|
||||
},
|
||||
body: JSON.stringify({
|
||||
args: [
|
||||
{
|
||||
type: 'remove_remote_schema',
|
||||
args: {
|
||||
name: remoteSchema.name,
|
||||
},
|
||||
},
|
||||
],
|
||||
source: 'default',
|
||||
type: 'bulk',
|
||||
}),
|
||||
},
|
||||
),
|
||||
),
|
||||
);
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,6 +18,7 @@
|
||||
"format": "prettier --write \"src/**/*.{js,ts,tsx,jsx,json,md}\" --plugin-search-dir=.",
|
||||
"storybook": "start-storybook -p 6006 -s public",
|
||||
"build-storybook": "build-storybook",
|
||||
"install-browsers": "pnpm playwright install && pnpm playwright install-deps",
|
||||
"e2e:tests": "pnpm playwright test --config=playwright.config.ts -x",
|
||||
"e2e": "pnpm e2e:tests --project=main",
|
||||
"e2e:local": "pnpm e2e:tests --project=local",
|
||||
|
||||
@@ -6,14 +6,14 @@ dotenv.config({ path: path.resolve(__dirname, '.env.test') });
|
||||
|
||||
export default defineConfig({
|
||||
testDir: './e2e',
|
||||
maxFailures: 1,
|
||||
maxFailures: process.env.CI ? 3 : 1,
|
||||
timeout: 120 * 1000,
|
||||
expect: {
|
||||
timeout: 10000,
|
||||
},
|
||||
fullyParallel: false,
|
||||
forbidOnly: !!process.env.CI,
|
||||
retries: 2,
|
||||
retries: process.env.CI ? 2 : 0,
|
||||
workers: 1,
|
||||
reporter: 'html',
|
||||
use: {
|
||||
|
||||
@@ -0,0 +1,49 @@
|
||||
import { ApplicationPaused } from '@/features/orgs/projects/common/components/ApplicationPaused';
|
||||
import { ApplicationPausedBanner } from '@/features/orgs/projects/common/components/ApplicationPausedBanner';
|
||||
import { useRouter } from 'next/router';
|
||||
import { type PropsWithChildren } from 'react';
|
||||
|
||||
const baseProjectPageRoute = '/orgs/[orgSlug]/projects/[appSubdomain]/';
|
||||
const blockedPausedProjectPages = [
|
||||
'database',
|
||||
'database/browser/[dataSourceSlug]',
|
||||
'graphql',
|
||||
'graphql/remote-schemas',
|
||||
'graphql/remote-schemas/[remoteSchemaSlug]',
|
||||
'hasura',
|
||||
'users',
|
||||
'storage',
|
||||
'ai/auto-embeddings',
|
||||
'ai/assistants',
|
||||
'metrics',
|
||||
].map((page) => baseProjectPageRoute.concat(page));
|
||||
|
||||
function PausedProjectContent({ children }: PropsWithChildren) {
|
||||
const { route } = useRouter();
|
||||
|
||||
const isOnOverviewPage = route === '/orgs/[orgSlug]/projects/[appSubdomain]';
|
||||
|
||||
if (isOnOverviewPage) {
|
||||
return (
|
||||
<>
|
||||
<div className="mx-auto mt-5 flex max-w-7xl p-4 pb-0">
|
||||
<ApplicationPausedBanner
|
||||
alertClassName="flex-row"
|
||||
textContainerClassName="flex flex-col items-center justify-center text-left"
|
||||
wakeUpButtonClassName="w-fit self-center"
|
||||
/>
|
||||
</div>
|
||||
{children}
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
// block these pages when the project is paused
|
||||
if (blockedPausedProjectPages.includes(route)) {
|
||||
return <ApplicationPaused />;
|
||||
}
|
||||
|
||||
return children;
|
||||
}
|
||||
|
||||
export default PausedProjectContent;
|
||||
@@ -1,5 +1,8 @@
|
||||
import { mockApplication } from '@/tests/mocks';
|
||||
import { getProjectQuery } from '@/tests/msw/mocks/graphql/getProjectQuery';
|
||||
import {
|
||||
getProjectQuery,
|
||||
getProjectStateQuery,
|
||||
} from '@/tests/msw/mocks/graphql/getProjectQuery';
|
||||
import tokenQuery from '@/tests/msw/mocks/rest/tokenQuery';
|
||||
import {
|
||||
createGraphqlMockResolver,
|
||||
@@ -29,7 +32,7 @@ function TestComponent() {
|
||||
);
|
||||
}
|
||||
|
||||
const server = setupServer(tokenQuery);
|
||||
const server = setupServer(tokenQuery, getProjectStateQuery());
|
||||
|
||||
const getUseRouterObject = (
|
||||
route: string = '/orgs/[orgSlug]/projects/[appSubdomain]',
|
||||
|
||||
@@ -1,25 +1,17 @@
|
||||
import { type AuthenticatedLayoutProps } from '@/components/layout/AuthenticatedLayout';
|
||||
import { LoadingScreen } from '@/components/presentational/LoadingScreen';
|
||||
import { Alert } from '@/components/ui/v2/Alert';
|
||||
import type { BoxProps } from '@/components/ui/v2/Box';
|
||||
import { Box } from '@/components/ui/v2/Box';
|
||||
import { ApplicationPaused } from '@/features/orgs/projects/common/components/ApplicationPaused';
|
||||
import { ApplicationPausedBanner } from '@/features/orgs/projects/common/components/ApplicationPausedBanner';
|
||||
import { ApplicationProvisioning } from '@/features/orgs/projects/common/components/ApplicationProvisioning';
|
||||
import { ApplicationRestoring } from '@/features/orgs/projects/common/components/ApplicationRestoring';
|
||||
import { ApplicationUnknown } from '@/features/orgs/projects/common/components/ApplicationUnknown';
|
||||
import { ApplicationUnpausing } from '@/features/orgs/projects/common/components/ApplicationUnpausing';
|
||||
import { useAppState } from '@/features/orgs/projects/common/hooks/useAppState';
|
||||
import { useIsPlatform } from '@/features/orgs/projects/common/hooks/useIsPlatform';
|
||||
import { useProjectWithState } from '@/features/orgs/projects/hooks/useProjectWithState';
|
||||
import { isEmptyValue } from '@/lib/utils';
|
||||
import { useProject } from '@/features/orgs/projects/hooks/useProject';
|
||||
import { isEmptyValue, isNotEmptyValue } from '@/lib/utils';
|
||||
import { useAuth } from '@/providers/Auth';
|
||||
import { ApplicationStatus } from '@/types/application';
|
||||
import { getConfigServerUrl, isPlatform as isPlatformFn } from '@/utils/env';
|
||||
import { NextSeo } from 'next-seo';
|
||||
import { useRouter } from 'next/router';
|
||||
import { useCallback, useEffect, useMemo, type ReactNode } from 'react';
|
||||
import { useEffect } from 'react';
|
||||
import { twMerge } from 'tailwind-merge';
|
||||
import ProjectViewWithState from './ProjectViewWithState';
|
||||
|
||||
const platFormOnlyPages = [
|
||||
'/orgs/[orgSlug]/projects/[appSubdomain]/deployments',
|
||||
@@ -56,115 +48,15 @@ function ProjectLayoutContent({
|
||||
children,
|
||||
mainContainerProps = {},
|
||||
}: ProjectLayoutContentProps) {
|
||||
const {
|
||||
route,
|
||||
query: { appSubdomain },
|
||||
push,
|
||||
} = useRouter();
|
||||
const { route, push } = useRouter();
|
||||
|
||||
const { state } = useAppState();
|
||||
const isPlatform = useIsPlatform();
|
||||
|
||||
const { project, loading, error, projectNotFound } = useProjectWithState();
|
||||
const { project, loading, error, projectNotFound } = useProject();
|
||||
const { isAuthenticated, isLoading, isSigningOut } = useAuth();
|
||||
|
||||
const isUserLoggedIn = isAuthenticated && !isLoading && !isSigningOut;
|
||||
|
||||
const isOnOverviewPage = route === '/orgs/[orgSlug]/projects/[appSubdomain]';
|
||||
|
||||
const renderPausedProjectContent = useCallback(
|
||||
(_children: ReactNode) => {
|
||||
const baseProjectPageRoute = '/orgs/[orgSlug]/projects/[appSubdomain]/';
|
||||
const blockedPausedProjectPages = [
|
||||
'database',
|
||||
'database/browser/[dataSourceSlug]',
|
||||
'database/browser/[dataSourceSlug]/[schemaSlug]/[tableSlug]',
|
||||
'graphql',
|
||||
'graphql/remote-schemas',
|
||||
'graphql/remote-schemas/[remoteSchemaSlug]',
|
||||
'hasura',
|
||||
'users',
|
||||
'storage',
|
||||
'run',
|
||||
'ai/auto-embeddings',
|
||||
'ai/assistants',
|
||||
'metrics',
|
||||
].map((page) => baseProjectPageRoute.concat(page));
|
||||
|
||||
// show an alert box on top of the overview page with a wake up button
|
||||
if (isOnOverviewPage) {
|
||||
return (
|
||||
<>
|
||||
<div className="mx-auto mt-5 flex max-w-7xl p-4 pb-0">
|
||||
<ApplicationPausedBanner
|
||||
alertClassName="flex-row"
|
||||
textContainerClassName="flex flex-col items-center justify-center text-left"
|
||||
wakeUpButtonClassName="w-fit self-center"
|
||||
/>
|
||||
</div>
|
||||
{children}
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
// block these pages when the project is paused
|
||||
if (blockedPausedProjectPages.includes(route)) {
|
||||
return <ApplicationPaused />;
|
||||
}
|
||||
|
||||
return _children;
|
||||
},
|
||||
[route, isOnOverviewPage, children],
|
||||
);
|
||||
|
||||
// Render application state based on the current state
|
||||
const projectPageContent = useMemo(() => {
|
||||
if (!appSubdomain || state === undefined) {
|
||||
return children;
|
||||
}
|
||||
|
||||
switch (state) {
|
||||
case ApplicationStatus.Empty:
|
||||
case ApplicationStatus.Provisioning:
|
||||
return <ApplicationProvisioning />;
|
||||
case ApplicationStatus.Errored:
|
||||
if (isOnOverviewPage) {
|
||||
return (
|
||||
<>
|
||||
<div className="w-full p-4">
|
||||
<Alert severity="error" className="mx-auto max-w-7xl">
|
||||
Error deploying the project most likely due to invalid
|
||||
configuration. Please review your project's configuration
|
||||
and logs for more information.
|
||||
</Alert>
|
||||
</div>
|
||||
{children}
|
||||
</>
|
||||
);
|
||||
}
|
||||
return children;
|
||||
case ApplicationStatus.Pausing:
|
||||
case ApplicationStatus.Paused:
|
||||
return renderPausedProjectContent(children);
|
||||
case ApplicationStatus.Unpausing:
|
||||
return <ApplicationUnpausing />;
|
||||
case ApplicationStatus.Restoring:
|
||||
return <ApplicationRestoring />;
|
||||
case ApplicationStatus.Updating:
|
||||
case ApplicationStatus.Live:
|
||||
case ApplicationStatus.Migrating:
|
||||
return children;
|
||||
default:
|
||||
return <ApplicationUnknown />;
|
||||
}
|
||||
}, [
|
||||
state,
|
||||
children,
|
||||
appSubdomain,
|
||||
isOnOverviewPage,
|
||||
renderPausedProjectContent,
|
||||
]);
|
||||
|
||||
useEffect(() => {
|
||||
if (
|
||||
isPlatformOnlyPage(route) ||
|
||||
@@ -183,13 +75,11 @@ function ProjectLayoutContent({
|
||||
return null;
|
||||
}
|
||||
|
||||
// Handle loading state
|
||||
if (loading) {
|
||||
return <LoadingScreen data-testid="projectLoadingIndicator" />;
|
||||
}
|
||||
|
||||
// Handle error state
|
||||
if (error) {
|
||||
if (isNotEmptyValue(error)) {
|
||||
throw error;
|
||||
}
|
||||
|
||||
@@ -211,7 +101,7 @@ function ProjectLayoutContent({
|
||||
)}
|
||||
{...mainContainerProps}
|
||||
>
|
||||
{projectPageContent}
|
||||
<ProjectViewWithState>{children}</ProjectViewWithState>
|
||||
<NextSeo title={!isPlatform ? 'Local App' : project?.name} />
|
||||
</Box>
|
||||
);
|
||||
|
||||
@@ -0,0 +1,245 @@
|
||||
import {
|
||||
getProjectQuery,
|
||||
getProjectStateQuery,
|
||||
} from '@/tests/msw/mocks/graphql/getProjectQuery';
|
||||
import tokenQuery from '@/tests/msw/mocks/rest/tokenQuery';
|
||||
import { queryClient, render, screen } from '@/tests/testUtils';
|
||||
import { ApplicationStatus } from '@/types/application';
|
||||
import { setupServer } from 'msw/node';
|
||||
import { vi } from 'vitest';
|
||||
import ProjectViewWithState from './ProjectViewWithState';
|
||||
|
||||
const mocks = vi.hoisted(() => ({
|
||||
useRouter: vi.fn(),
|
||||
push: vi.fn(),
|
||||
}));
|
||||
|
||||
vi.mock('next/router', () => ({
|
||||
useRouter: mocks.useRouter,
|
||||
}));
|
||||
|
||||
vi.mock(
|
||||
'@/features/orgs/projects/common/components/ApplicationProvisioning',
|
||||
() => ({
|
||||
ApplicationProvisioning: () => <div>Application Provisioning</div>,
|
||||
}),
|
||||
);
|
||||
|
||||
vi.mock(
|
||||
'@/features/orgs/projects/common/components/ApplicationRestoring',
|
||||
() => ({
|
||||
ApplicationRestoring: () => (
|
||||
<div data-testid="appRestore">Application Restoring</div>
|
||||
),
|
||||
}),
|
||||
);
|
||||
|
||||
vi.mock(
|
||||
'@/features/orgs/projects/common/components/ApplicationUnknown',
|
||||
() => ({
|
||||
ApplicationUnknown: () => (
|
||||
<div data-testid="appUnknown">Application Unknown</div>
|
||||
),
|
||||
}),
|
||||
);
|
||||
|
||||
vi.mock(
|
||||
'@/features/orgs/projects/common/components/ApplicationUnpausing',
|
||||
() => ({
|
||||
ApplicationUnpausing: () => (
|
||||
<div data-testid="appUnpausing">Application Unpausing</div>
|
||||
),
|
||||
}),
|
||||
);
|
||||
|
||||
vi.mock(
|
||||
'@/features/orgs/projects/common/components/ApplicationPausedBanner',
|
||||
() => ({
|
||||
ApplicationPausedBanner: () => (
|
||||
<div data-testid="appBanner">Application Banner</div>
|
||||
),
|
||||
}),
|
||||
);
|
||||
|
||||
const getUseRouterObject = (
|
||||
route: string = '/orgs/[orgSlug]/projects/[appSubdomain]',
|
||||
) => ({
|
||||
basePath: '',
|
||||
pathname: '/orgs/xyz/projects/test-project',
|
||||
route,
|
||||
asPath: '/orgs/xyz/projects/test-project',
|
||||
isLocaleDomain: false,
|
||||
isReady: true,
|
||||
isPreview: false,
|
||||
query: {
|
||||
orgSlug: 'xyz',
|
||||
appSubdomain: 'test-project',
|
||||
},
|
||||
push: mocks.push,
|
||||
replace: vi.fn(),
|
||||
reload: vi.fn(),
|
||||
back: vi.fn(),
|
||||
prefetch: vi.fn(),
|
||||
beforePopState: vi.fn(),
|
||||
events: {
|
||||
on: vi.fn(),
|
||||
off: vi.fn(),
|
||||
emit: vi.fn(),
|
||||
},
|
||||
isFallback: false,
|
||||
});
|
||||
|
||||
function TestComponent() {
|
||||
return (
|
||||
<ProjectViewWithState>
|
||||
<h1>Application content</h1>
|
||||
</ProjectViewWithState>
|
||||
);
|
||||
}
|
||||
|
||||
const server = setupServer(tokenQuery);
|
||||
|
||||
describe('ProjectViewWithState', () => {
|
||||
beforeAll(() => {
|
||||
process.env.NEXT_PUBLIC_NHOST_PLATFORM = 'true';
|
||||
process.env.NEXT_PUBLIC_ENV = 'production';
|
||||
server.listen();
|
||||
});
|
||||
|
||||
beforeEach(() => {
|
||||
server.resetHandlers();
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
queryClient.clear();
|
||||
mocks.useRouter.mockRestore();
|
||||
mocks.push.mockRestore();
|
||||
vi.restoreAllMocks();
|
||||
});
|
||||
|
||||
it('should render the nothing when the state is empty', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(getProjectStateQuery([{ stateId: ApplicationStatus.Empty }]));
|
||||
render(<TestComponent />);
|
||||
expect(screen.queryByText('Application content')).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application in provisioning state', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(
|
||||
getProjectStateQuery([{ stateId: ApplicationStatus.Provisioning }]),
|
||||
);
|
||||
render(<TestComponent />);
|
||||
expect(
|
||||
await screen.findByText('Application Provisioning'),
|
||||
).toBeInTheDocument();
|
||||
expect(screen.queryByText('Application content')).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application in pausing state', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(getProjectStateQuery([{ stateId: ApplicationStatus.Pausing }]));
|
||||
render(<TestComponent />);
|
||||
expect(await screen.findByText('Application content')).toBeInTheDocument();
|
||||
expect(await screen.findByText('Application Banner')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application Unpausing application state', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(
|
||||
getProjectStateQuery([{ stateId: ApplicationStatus.Unpausing }]),
|
||||
);
|
||||
render(<TestComponent />);
|
||||
expect(screen.queryByText('Application content')).not.toBeInTheDocument();
|
||||
expect(
|
||||
await screen.findByText('Application Unpausing'),
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application paused application state', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(getProjectStateQuery([{ stateId: ApplicationStatus.Paused }]));
|
||||
render(<TestComponent />);
|
||||
expect(await screen.findByText('Application content')).toBeInTheDocument();
|
||||
expect(await screen.findByText('Application Banner')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application when the state is updating', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(getProjectStateQuery([{ stateId: ApplicationStatus.Updating }]));
|
||||
render(<TestComponent />);
|
||||
|
||||
expect(await screen.findByText('Application content')).toBeInTheDocument();
|
||||
|
||||
expect(screen.queryByText('Application Restoring')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Unknown')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Unpausing')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Banner')).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application when the state is live', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(getProjectStateQuery([{ stateId: ApplicationStatus.Live }]));
|
||||
render(<TestComponent />);
|
||||
|
||||
expect(await screen.findByText('Application content')).toBeInTheDocument();
|
||||
|
||||
expect(screen.queryByText('Application Restoring')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Unknown')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Unpausing')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Banner')).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application when the state is migrating', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(
|
||||
getProjectStateQuery([{ stateId: ApplicationStatus.Migrating }]),
|
||||
);
|
||||
render(<TestComponent />);
|
||||
|
||||
expect(await screen.findByText('Application content')).toBeInTheDocument();
|
||||
|
||||
expect(screen.queryByText('Application Restoring')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Unknown')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Unpausing')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Banner')).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application in an error state', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(getProjectStateQuery([{ stateId: ApplicationStatus.Errored }]));
|
||||
render(<TestComponent />);
|
||||
|
||||
expect(await screen.findByText('Application content')).toBeInTheDocument();
|
||||
|
||||
expect(await screen.findByText(/Error deploying/)).toBeInTheDocument();
|
||||
|
||||
expect(screen.queryByText('Application Restoring')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Unknown')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Unpausing')).not.toBeInTheDocument();
|
||||
expect(screen.queryByText('Application Banner')).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('should render the application in an error state', async () => {
|
||||
mocks.useRouter.mockImplementation(() => getUseRouterObject());
|
||||
server.use(getProjectQuery);
|
||||
server.use(
|
||||
getProjectStateQuery([{ stateId: ApplicationStatus.Restoring }]),
|
||||
);
|
||||
render(<TestComponent />);
|
||||
|
||||
expect(
|
||||
await screen.findByText('Application Restoring'),
|
||||
).toBeInTheDocument();
|
||||
expect(screen.queryByText('Application content')).not.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,68 @@
|
||||
import { Alert } from '@/components/ui/v2/Alert';
|
||||
import { ApplicationProvisioning } from '@/features/orgs/projects/common/components/ApplicationProvisioning';
|
||||
import { ApplicationRestoring } from '@/features/orgs/projects/common/components/ApplicationRestoring';
|
||||
import { ApplicationUnknown } from '@/features/orgs/projects/common/components/ApplicationUnknown';
|
||||
import { ApplicationUnpausing } from '@/features/orgs/projects/common/components/ApplicationUnpausing';
|
||||
import { useAppState } from '@/features/orgs/projects/common/hooks/useAppState';
|
||||
import { ApplicationStatus } from '@/types/application';
|
||||
import { useRouter } from 'next/router';
|
||||
import { type PropsWithChildren, useMemo } from 'react';
|
||||
|
||||
import PausedProjectContent from './PausedProjectContent';
|
||||
|
||||
function ProjectViewWithState({ children }: PropsWithChildren) {
|
||||
const {
|
||||
query: { appSubdomain },
|
||||
route,
|
||||
} = useRouter();
|
||||
|
||||
const { state } = useAppState();
|
||||
|
||||
const isOnOverviewPage = route === '/orgs/[orgSlug]/projects/[appSubdomain]';
|
||||
|
||||
const projectPageContent = useMemo(() => {
|
||||
if (!appSubdomain || state === undefined) {
|
||||
return children;
|
||||
}
|
||||
|
||||
switch (state) {
|
||||
case ApplicationStatus.Empty:
|
||||
return null;
|
||||
case ApplicationStatus.Provisioning:
|
||||
return <ApplicationProvisioning />;
|
||||
case ApplicationStatus.Errored:
|
||||
if (isOnOverviewPage) {
|
||||
return (
|
||||
<>
|
||||
<div className="w-full p-4">
|
||||
<Alert severity="error" className="mx-auto max-w-7xl">
|
||||
Error deploying the project most likely due to invalid
|
||||
configuration. Please review your project's configuration
|
||||
and logs for more information.
|
||||
</Alert>
|
||||
</div>
|
||||
{children}
|
||||
</>
|
||||
);
|
||||
}
|
||||
return children;
|
||||
case ApplicationStatus.Pausing:
|
||||
case ApplicationStatus.Paused:
|
||||
return <PausedProjectContent>{children}</PausedProjectContent>;
|
||||
case ApplicationStatus.Unpausing:
|
||||
return <ApplicationUnpausing />;
|
||||
case ApplicationStatus.Restoring:
|
||||
return <ApplicationRestoring />;
|
||||
case ApplicationStatus.Updating:
|
||||
case ApplicationStatus.Live:
|
||||
case ApplicationStatus.Migrating:
|
||||
return children;
|
||||
default:
|
||||
return <ApplicationUnknown />;
|
||||
}
|
||||
}, [state, children, appSubdomain, isOnOverviewPage]);
|
||||
|
||||
return projectPageContent;
|
||||
}
|
||||
|
||||
export default ProjectViewWithState;
|
||||
@@ -0,0 +1,87 @@
|
||||
import {
|
||||
getNotFoundProjectStateQuery,
|
||||
getProjectStateQuery,
|
||||
} from '@/tests/msw/mocks/graphql/getProjectQuery';
|
||||
import tokenQuery from '@/tests/msw/mocks/rest/tokenQuery';
|
||||
import { queryClient, render, screen, waitFor } from '@/tests/testUtils';
|
||||
import { ApplicationStatus } from '@/types/application';
|
||||
import { setupServer } from 'msw/node';
|
||||
import { vi } from 'vitest';
|
||||
import useAppState from './useAppState';
|
||||
|
||||
function TestComponent() {
|
||||
const { state } = useAppState();
|
||||
|
||||
return <h1>State: {state}</h1>;
|
||||
}
|
||||
|
||||
const mocks = vi.hoisted(() => ({
|
||||
refetch: vi.fn(),
|
||||
useProjectWithState: vi.fn(),
|
||||
}));
|
||||
|
||||
vi.mock('@/features/orgs/projects/hooks/useProject', async () => ({
|
||||
useProject: () => ({ refetch: mocks.refetch }),
|
||||
}));
|
||||
|
||||
const server = setupServer(tokenQuery);
|
||||
|
||||
describe('useAppState', () => {
|
||||
beforeAll(() => {
|
||||
process.env.NEXT_PUBLIC_NHOST_PLATFORM = 'true';
|
||||
process.env.NEXT_PUBLIC_ENV = 'production';
|
||||
server.listen();
|
||||
});
|
||||
|
||||
beforeEach(() => {
|
||||
server.resetHandlers();
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
queryClient.clear();
|
||||
mocks.refetch.mockRestore();
|
||||
mocks.useProjectWithState.mockRestore();
|
||||
vi.restoreAllMocks();
|
||||
});
|
||||
|
||||
it('should refetch the project, when the project is not found', async () => {
|
||||
server.use(getNotFoundProjectStateQuery);
|
||||
render(<TestComponent />);
|
||||
expect(await screen.findByText('State: 0')).toBeInTheDocument();
|
||||
await waitFor(() => {
|
||||
expect(mocks.refetch).toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
||||
it('Should not refetch the project if the state is empty', async () => {
|
||||
server.use(getProjectStateQuery([{ stateId: ApplicationStatus.Empty }]));
|
||||
render(<TestComponent />);
|
||||
expect(await screen.findByText('State: 0')).toBeInTheDocument();
|
||||
await waitFor(() => {
|
||||
expect(mocks.refetch).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
||||
it('Should return empty state if the application state has not been filled yet', async () => {
|
||||
server.use(getProjectStateQuery([]));
|
||||
render(<TestComponent />);
|
||||
expect(await screen.findByText('State: 0')).toBeInTheDocument();
|
||||
await waitFor(() => {
|
||||
expect(mocks.refetch).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
||||
it('Should return the first state from the response', async () => {
|
||||
server.use(
|
||||
getProjectStateQuery([
|
||||
{ stateId: ApplicationStatus.Live },
|
||||
{ stateId: ApplicationStatus.Empty },
|
||||
]),
|
||||
);
|
||||
render(<TestComponent />);
|
||||
expect(await screen.findByText('State: 5')).toBeInTheDocument();
|
||||
await waitFor(() => {
|
||||
expect(mocks.refetch).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -1,5 +1,8 @@
|
||||
import { useProject } from '@/features/orgs/projects/hooks/useProject';
|
||||
import { useProjectWithState } from '@/features/orgs/projects/hooks/useProjectWithState';
|
||||
import { isNotEmptyValue } from '@/lib/utils';
|
||||
import { ApplicationStatus } from '@/types/application';
|
||||
import { useEffect } from 'react';
|
||||
|
||||
/**
|
||||
* This hook returns the current application state. If the application state
|
||||
@@ -7,27 +10,19 @@ import { ApplicationStatus } from '@/types/application';
|
||||
*/
|
||||
export default function useAppState(): {
|
||||
state: ApplicationStatus;
|
||||
message?: string | null;
|
||||
} {
|
||||
const { project } = useProjectWithState();
|
||||
const noApplication = !project;
|
||||
const { project, projectNotFound } = useProjectWithState();
|
||||
const { refetch } = useProject();
|
||||
|
||||
if (noApplication) {
|
||||
return { state: ApplicationStatus.Empty };
|
||||
}
|
||||
|
||||
const emptyApplicationStates = !project.appStates;
|
||||
|
||||
if (noApplication || emptyApplicationStates) {
|
||||
return { state: ApplicationStatus.Empty };
|
||||
}
|
||||
|
||||
if (project.appStates?.length === 0) {
|
||||
return { state: ApplicationStatus.Empty };
|
||||
}
|
||||
useEffect(() => {
|
||||
if (projectNotFound) {
|
||||
refetch();
|
||||
}
|
||||
}, [projectNotFound, refetch]);
|
||||
|
||||
return {
|
||||
state: project.appStates[0].stateId,
|
||||
message: project.appStates[0].message,
|
||||
state: isNotEmptyValue(project?.appStates?.[0])
|
||||
? project.appStates[0].stateId
|
||||
: ApplicationStatus.Empty,
|
||||
};
|
||||
}
|
||||
|
||||
@@ -74,9 +74,6 @@ export default function useCheckProvisioning() {
|
||||
createdAt: data.app.appStates[0].createdAt,
|
||||
});
|
||||
stopPolling();
|
||||
// Will update the cache and update with the new application state
|
||||
// which will trigger the correct application component
|
||||
// under `src\components\applications\App.tsx`
|
||||
memoizedUpdateCache();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import { useIsPlatform } from '@/features/orgs/projects/common/hooks/useIsPlatform';
|
||||
import { localApplication } from '@/features/orgs/utils/local-dashboard';
|
||||
import { isEmptyValue } from '@/lib/utils';
|
||||
import { useAuth } from '@/providers/Auth';
|
||||
import { useNhostClient } from '@/providers/nhost';
|
||||
import {
|
||||
@@ -18,6 +19,7 @@ export interface UseProjectReturnType {
|
||||
loading?: boolean;
|
||||
error?: Error | null;
|
||||
refetch: (variables?: any) => Promise<any>;
|
||||
projectNotFound: boolean;
|
||||
}
|
||||
|
||||
export default function useProject(): UseProjectReturnType {
|
||||
@@ -39,13 +41,14 @@ export default function useProject(): UseProjectReturnType {
|
||||
[isPlatform, isAuthenticated, isAuthLoading, appSubdomain, isRouterReady],
|
||||
);
|
||||
|
||||
const { data, isLoading, refetch, error } = useQuery(
|
||||
const { data, isLoading, refetch, error, isFetched } = useQuery(
|
||||
['project', appSubdomain as string],
|
||||
async () => {
|
||||
const response = await nhost.graphql.request<{
|
||||
apps: ProjectFragment[];
|
||||
}>(GetProjectDocument, { subdomain: (appSubdomain as string) || '' });
|
||||
return response.body;
|
||||
|
||||
return response?.body.data;
|
||||
},
|
||||
{
|
||||
enabled: shouldFetchProject,
|
||||
@@ -54,10 +57,11 @@ export default function useProject(): UseProjectReturnType {
|
||||
|
||||
if (isPlatform) {
|
||||
return {
|
||||
project: data?.data?.apps?.[0] || null,
|
||||
project: data?.apps?.[0] || null,
|
||||
loading: isLoading && shouldFetchProject,
|
||||
error: Array.isArray(error || {}) ? error?.[0] : error,
|
||||
refetch,
|
||||
projectNotFound: isFetched && !isLoading && isEmptyValue(data?.apps),
|
||||
};
|
||||
}
|
||||
|
||||
@@ -66,5 +70,6 @@ export default function useProject(): UseProjectReturnType {
|
||||
loading: false,
|
||||
error: null,
|
||||
refetch: () => Promise.resolve(),
|
||||
projectNotFound: false,
|
||||
};
|
||||
}
|
||||
|
||||
@@ -10,3 +10,27 @@ export const getProjectQuery = nhostGraphQLLink.query(
|
||||
}),
|
||||
),
|
||||
);
|
||||
|
||||
export const getProjectStateQuery = (appStates?: any) =>
|
||||
nhostGraphQLLink.query('getProjectState', (_req, res, ctx) =>
|
||||
res(
|
||||
ctx.data({
|
||||
apps: [
|
||||
{
|
||||
...mockApplication,
|
||||
appStates: appStates || mockApplication.appStates,
|
||||
},
|
||||
],
|
||||
}),
|
||||
),
|
||||
);
|
||||
|
||||
export const getNotFoundProjectStateQuery = nhostGraphQLLink.query(
|
||||
'getProjectState',
|
||||
(_req, res, ctx) =>
|
||||
res(
|
||||
ctx.data({
|
||||
apps: [],
|
||||
}),
|
||||
),
|
||||
);
|
||||
|
||||
@@ -147,6 +147,22 @@
|
||||
"/products/auth/idtokens"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Workflows",
|
||||
"icon": "diagram-project",
|
||||
"pages": [
|
||||
"/products/auth/workflows/email-password",
|
||||
"/products/auth/workflows/oauth-providers",
|
||||
"/products/auth/workflows/passwordless-email",
|
||||
"/products/auth/workflows/passwordless-sms",
|
||||
"/products/auth/workflows/webauthn",
|
||||
"/products/auth/workflows/anonymous-users",
|
||||
"/products/auth/workflows/change-email",
|
||||
"/products/auth/workflows/change-password",
|
||||
"/products/auth/workflows/reset-password",
|
||||
"/products/auth/workflows/refresh-token"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Security",
|
||||
"icon": "shield",
|
||||
|
||||
@@ -4,8 +4,9 @@ set -euo pipefail
|
||||
|
||||
function build_openapi() {
|
||||
echo "⚒️⚒️⚒️ Building OpenAPI reference..."
|
||||
cp ../packages/nhost-js/api/auth.yaml reference/
|
||||
cp ../packages/nhost-js/api/storage.yaml reference/
|
||||
cp ../services/auth/docs/openapi.yaml reference/auth.yaml
|
||||
cp ../services/storage/controller/openapi.yaml reference/storage.yaml
|
||||
|
||||
|
||||
echo "⚒️⚒️⚒️ Generating documentation from OpenAPI specs for Auth service..."
|
||||
mintlify-openapi openapi \
|
||||
|
||||
@@ -20,7 +20,7 @@ Graphite, Nhost's AI service, extends the [Nhost stack](https://nhost.io) provid
|
||||
* Extend with custom data via webhooks
|
||||
* Automate workflows by exposing GraphQL queries or mutations or custom webhooks to the AI assistant
|
||||
* GraphQL API to interact with the assistants.
|
||||
* Permissions fully integrated with hasura and hasura-auth; control who and who can not use which assistant via permissions.
|
||||
* Permissions fully integrated with hasura and Auth; control who and who can not use which assistant via permissions.
|
||||
* Access to the underlying data for the assistant is limited to what the user can see.
|
||||
* Developer Assistant
|
||||
* Custom AI assistant with access to your project's information (i.e. database/graphql schema)
|
||||
|
||||
@@ -33,7 +33,7 @@ While the following permissions would require them first to elevate their access
|
||||
|
||||
# Protecting Auth data
|
||||
|
||||
Some user information needs to be changed via hasura-auth's API rather than via graphql mutations. These endpoints are:
|
||||
Some user information needs to be changed via Auth's API rather than via graphql mutations. These endpoints are:
|
||||
|
||||
- [/user/password](/reference/auth/post-user-password) for changing passwords
|
||||
- [/user/email/change](/reference/auth/post-user-email-change) for changing emails
|
||||
|
||||
30
docs/products/auth/workflows/anonymous-users.mdx
Normal file
30
docs/products/auth/workflows/anonymous-users.mdx
Normal file
@@ -0,0 +1,30 @@
|
||||
## Sign-in anonymously
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
U->>+A: HTTP POST /signin/anonymous
|
||||
A->>A: Create anonymous user
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
```
|
||||
|
||||
## Deanonymisation
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
U-->A: Sign in anonymously
|
||||
U->>+A: HTTP POST /user/deanonymize
|
||||
A->>A: Deanonymise user
|
||||
alt Sign-in method is email+password
|
||||
Note over U,A: Same pathway as email+password sign-up
|
||||
else Sign-in method is passwordless
|
||||
Note over U,A: Same pathway as passwordless email
|
||||
end
|
||||
deactivate A
|
||||
```
|
||||
23
docs/products/auth/workflows/change-email.mdx
Normal file
23
docs/products/auth/workflows/change-email.mdx
Normal file
@@ -0,0 +1,23 @@
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant E as SMTP server
|
||||
participant F as Frontend
|
||||
U-->A: Sign in
|
||||
U->>+A: HTTP POST /user/email/change
|
||||
Note right of U: new email
|
||||
A->>A: Generate ticket
|
||||
A->>A: Store new email
|
||||
A-)E: Send verification to new email
|
||||
A->>-U: HTTP POST OK (no data)
|
||||
E-)U: Receive email
|
||||
U->>+A: HTTP GET /verify
|
||||
Note right of U: Follow email link
|
||||
A->>A: Change email
|
||||
A->>+F: HTTP redirect
|
||||
deactivate A
|
||||
F->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
```
|
||||
17
docs/products/auth/workflows/change-password.mdx
Normal file
17
docs/products/auth/workflows/change-password.mdx
Normal file
@@ -0,0 +1,17 @@
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
opt Authenticated user
|
||||
U-->A: Sign in
|
||||
U->>+A: HTTP POST /user/password
|
||||
Note right of U: new password
|
||||
A->>-U: HTTP POST OK (no data)
|
||||
end
|
||||
opt Using ticket
|
||||
U->>+A: HTTP POST /user/password
|
||||
Note right of U: new password with ticket
|
||||
A->>-U: HTTP POST OK (no data)
|
||||
end
|
||||
```
|
||||
84
docs/products/auth/workflows/email-password.mdx
Normal file
84
docs/products/auth/workflows/email-password.mdx
Normal file
@@ -0,0 +1,84 @@
|
||||
## Sign up
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant E as SMTP server
|
||||
participant F as Frontend
|
||||
U->>+A: HTTP POST /signup/email-password
|
||||
A->>A: Create user
|
||||
alt No email verification
|
||||
A->>U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
else Email needs to be verified
|
||||
A->>A: Generate ticket
|
||||
A-)E: Send verification email
|
||||
A->>-U: HTTP OK response (no data)
|
||||
E-)U: Receive email
|
||||
U->>+A: HTTP GET /verify
|
||||
Note right of U: Follow email link
|
||||
A->>A: Flag user email as verified
|
||||
A->>-F: HTTP redirect with refresh token
|
||||
activate F
|
||||
F->>-U: HTTP OK response
|
||||
opt
|
||||
U->>+A: HTTP POST /token
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
end
|
||||
end
|
||||
```
|
||||
|
||||
## Sign in
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant G as Authenticator/Authy
|
||||
U->>+A: HTTP POST /signin/email-password
|
||||
alt No MFA
|
||||
A->>U: HTTP OK response
|
||||
Note left of A: Refresh + access tokens
|
||||
else User activated MFA
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: MFA code
|
||||
U->>+G: Ask for a TOTP code
|
||||
G->>-U:
|
||||
U->>+A: HTTP POST /signin/mfa/totp
|
||||
Note right of U: TOTP code
|
||||
A->>-U: HTTP OK reponse
|
||||
Note left of A: Refresh token + access token
|
||||
end
|
||||
```
|
||||
|
||||
## Activate Multi-Factor Authentication
|
||||
|
||||
It is possible to add a step to authentication with email and password authentication. Once users registered, they can activate MFA TOTP:
|
||||
|
||||
1. Users generate a QR Code, that is then scanned in an authentication app such as [Authy](https://authy.com/) or [Google Authenticator](https://en.wikipedia.org/wiki/Google_Authenticator).
|
||||
2. They then send the TOTP code to Hasura Auth. MFA is now activated
|
||||
3. Next time they authenticate, Hasura Auth will first expect their email and password, but then, instead of completing authentication, Hasura Auth will expect the TOTP in order to return the refresh and the access tokens.
|
||||
|
||||
In order for users to be able to activate MFA TOTP, the `AUTH_MFA_ENABLED` environment variable must be set to `true`.
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant G as Authenticator/Authy
|
||||
U-->A: Sign in
|
||||
U->>+A: HTTP GET /mfa/totp/generate
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: QR code as Data URL + TOTP secret
|
||||
U->>+G: Add account
|
||||
G->>-U: TOTP code
|
||||
U->>+A: HTTP POST /user/mfa
|
||||
Note right of U: TOTP code
|
||||
A->>A: Activate MFA
|
||||
A->>-U: HTTP OK response
|
||||
```
|
||||
25
docs/products/auth/workflows/oauth-providers.mdx
Normal file
25
docs/products/auth/workflows/oauth-providers.mdx
Normal file
@@ -0,0 +1,25 @@
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant P as Oauth Provider
|
||||
participant F as Frontend
|
||||
U->>+A: HTTP GET /signin/provider/{provider}
|
||||
A->>+P: Provider's authentication
|
||||
deactivate A
|
||||
P->>-A: HTTP GET /signin/provider/{provider}/callback
|
||||
activate A
|
||||
opt No user found
|
||||
A->>A: Create user
|
||||
end
|
||||
A->>A: Flag user email as verified
|
||||
A->>+F: HTTP redirect with refresh token
|
||||
deactivate A
|
||||
F->>-U: HTTP OK response
|
||||
opt
|
||||
U->>+A: HTTP POST /token
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
end
|
||||
```
|
||||
27
docs/products/auth/workflows/passwordless-email.mdx
Normal file
27
docs/products/auth/workflows/passwordless-email.mdx
Normal file
@@ -0,0 +1,27 @@
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant E as SMTP server
|
||||
participant F as Frontend
|
||||
U->>+A: HTTP POST /signin/passwordless/email
|
||||
opt No user found
|
||||
A->>A: Create user
|
||||
end
|
||||
A->>A: Generate ticket
|
||||
A-)E: Send verification email
|
||||
A->>-U: HTTP POST OK (no data)
|
||||
E-)U: Receive email
|
||||
U->>+A: HTTP GET /verify
|
||||
Note right of U: Follow email link
|
||||
A->>A: Flag user email as verified
|
||||
A->>+F: HTTP redirect with refresh token
|
||||
deactivate A
|
||||
F->>-U: HTTP OK response
|
||||
opt
|
||||
U->>+A: HTTP POST /token
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
end
|
||||
```
|
||||
24
docs/products/auth/workflows/passwordless-sms.mdx
Normal file
24
docs/products/auth/workflows/passwordless-sms.mdx
Normal file
@@ -0,0 +1,24 @@
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant S as SMS service
|
||||
U->>+A: HTTP POST /signin/passwordless/sms
|
||||
Note right of U: Phone number
|
||||
opt No user found
|
||||
A->>A: Create user
|
||||
end
|
||||
A-)+S: Send OTP code by SMS
|
||||
A->>-U: HTTP OK response (no data)
|
||||
S-)-U: Receive OTP code by SMS
|
||||
U->>+A: HTTP POST /signin/passwordless/sms/otp
|
||||
Note right of U: Phone number and OTP code
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
```
|
||||
|
||||
## Test phone numbers
|
||||
|
||||
Environmental variable `AUTH_SMS_TEST_PHONE_NUMBERS` can be set with a comma separated test phone numbers. When sign in
|
||||
is invoked the the SMS message with the verification code will be available in the logs. This way you can also test your SMS templates.
|
||||
10
docs/products/auth/workflows/refresh-token.mdx
Normal file
10
docs/products/auth/workflows/refresh-token.mdx
Normal file
@@ -0,0 +1,10 @@
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
U->>+A: HTTP POST /token
|
||||
A->>A: Update refresh token
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
```
|
||||
31
docs/products/auth/workflows/reset-password.mdx
Normal file
31
docs/products/auth/workflows/reset-password.mdx
Normal file
@@ -0,0 +1,31 @@
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant E as SMTP server
|
||||
participant F as Frontend
|
||||
U->>+A: HTTP POST /user/password/reset
|
||||
Note right of U: new email
|
||||
A->>A: Generate ticket
|
||||
A-)E: Send verification email
|
||||
A->>-U: HTTP POST OK (no data)
|
||||
E-)U: Receive email
|
||||
opt Use email redirect link
|
||||
U->>+A: HTTP GET /verify
|
||||
Note right of U: Follow email link
|
||||
A->>+F: HTTP redirect
|
||||
deactivate A
|
||||
F->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
end
|
||||
opt Use ticket to customize reset flow (e.g. mobile)
|
||||
U->>+F: Deeplink w/ ticket
|
||||
Note left of F: User enters new password
|
||||
F->>+A: HTTP POST /user/password
|
||||
Note right of A: Set new password with ticket
|
||||
A->>+F: HTTP POST OK (no data)
|
||||
F->>+U: User handling
|
||||
Note right of U: User notified or logged in
|
||||
end
|
||||
```
|
||||
116
docs/products/auth/workflows/webauthn.mdx
Normal file
116
docs/products/auth/workflows/webauthn.mdx
Normal file
@@ -0,0 +1,116 @@
|
||||
Auth implements the WebAuthn protocol to sign in with security keys, also referred as authenticators in the WebAuthn protocol.
|
||||
|
||||
A user needs first to sign up with another method, for instance email+password, passwordless email or Oauth, then to add their security key to their account.
|
||||
|
||||
Once the security key is added, it is then possible to sign in with it, using the email as a username.
|
||||
|
||||
## Sign up
|
||||
|
||||
The overall WebAuthn sign up workflow is similar to the email + password sign up workflow: after the user completed the registration of their email and security key, it will return the session, unless the email needs to be verified first. In this latter case, a verification email is sent, and the user is finally able to sign up once the email link is clicked and processed.
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant E as SMTP server
|
||||
participant G as Face ID/Fingerprint/Other
|
||||
participant F as Frontend
|
||||
U->>A: HTTP POST /signup/webauthn
|
||||
activate A
|
||||
A->>A: Create a tentative user
|
||||
A->>U: HTTP OK response
|
||||
deactivate A
|
||||
Note left of A: Challenge
|
||||
|
||||
U->>G: Sign Challenge
|
||||
activate G
|
||||
G->>G: Sign
|
||||
G->>U: Success
|
||||
deactivate G
|
||||
Note left of G: Signed Challenge
|
||||
U->>A: HTTP POST /user/webauthn/verify
|
||||
activate A
|
||||
Note left of A: Signed challenge
|
||||
A->>A: Verify Signed challenge
|
||||
A->>A: Add security key
|
||||
A->>A: Set user data
|
||||
|
||||
alt No email verification
|
||||
A->>U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
else Email needs to be verified
|
||||
A->>A: Generate ticket
|
||||
A-)E: Send verification email
|
||||
A->>-U: HTTP OK response (no data)
|
||||
E-)U: Receive email
|
||||
U->>+A: HTTP GET /verify
|
||||
Note right of U: Follow email link
|
||||
A->>A: Flag user email as verified
|
||||
A->>-F: HTTP redirect with refresh token
|
||||
activate F
|
||||
F->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
end
|
||||
```
|
||||
|
||||
## Sign in
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant G as Face ID/Fingerprint/Other
|
||||
U->>+A: HTTP POST /signin/webauthn
|
||||
alt Email not verified or user disabled
|
||||
A->>U: HTTP ERROR response
|
||||
else Email verified and user not disabled
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Challenge
|
||||
end
|
||||
U->>+G: Sign Challenge
|
||||
G->>G: Sign
|
||||
G->>-U: Success
|
||||
Note left of G: Signed Challenge
|
||||
U->>+A: HTTP POST /signin/webauthn/verify
|
||||
Note left of A: Signed challenge
|
||||
A->>A: Check if email is verified
|
||||
A->>A: Check if user is enabled
|
||||
alt Email not verified or user disabled
|
||||
A->>U: HTTP ERROR response
|
||||
else Email verified and user enabled
|
||||
A->>A: Verify Signed challenge
|
||||
opt
|
||||
A->>A: Update security key
|
||||
end
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
end
|
||||
```
|
||||
|
||||
## Add a security key
|
||||
|
||||
Users can add multiple security keys, for example when they need to login from multiple devices or browsers. Only authenticated users are allowed to add security keys.
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
actor U as User
|
||||
participant A as Hasura Auth
|
||||
participant G as Face ID/Fingerprint/Other
|
||||
U->>+A: HTTP POST /user/webauthn/add
|
||||
Note left of A: Passing Bearer token
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Challenge
|
||||
U->>+G: Sign Challenge
|
||||
G->>G: Sign
|
||||
G->>-U: Success
|
||||
Note left of G: Signed Challenge
|
||||
U->>+A: HTTP POST /user/webauthn/verify
|
||||
Note left of A: Signed challenge
|
||||
A->>A: Verify Signed challenge
|
||||
A->>A: Add security key
|
||||
A->>-U: HTTP OK response
|
||||
Note left of A: Refresh token + access token
|
||||
```
|
||||
@@ -12,8 +12,8 @@ To connect your service to the Nhost stack, use the following information:
|
||||
|
||||
- postgres: `postgres://postgres:<password>@postgres-service:5432/<subdomain>?sslmode=disable`
|
||||
- hasura: base URL is `http://hasura-service:8080`
|
||||
- hasura-auth: base URL is `http://hasura-auth-service:4000`
|
||||
- hasura-storage: base URL is `http://hasura-storage-service:5000`
|
||||
- auth: base URL is `http://hasura-auth-service:4000`
|
||||
- storage: base URL is `http://hasura-storage-service:5000`
|
||||
|
||||
## Connecting to your service internally
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ description: Learn how to integrate with ClamAV
|
||||
icon: shield-virus
|
||||
---
|
||||
|
||||
Integration with [clamav](https://www.clamav.net) antivirus relies on an external [clamd](https://docs.clamav.net/manual/Usage/Scanning.html#clamd) service. When a file is uploaded `hasura-storage` will create the file metadata first and then check if the file is clean with `clamd` via its TCP socket. If the file is clean the rest of the process will continue as usual. If a virus is found details about the virus will be added to the `virus` table and the rest of the process will be aborted.
|
||||
Integration with [clamav](https://www.clamav.net) antivirus relies on an external [clamd](https://docs.clamav.net/manual/Usage/Scanning.html#clamd) service. When a file is uploaded `storage` will create the file metadata first and then check if the file is clean with `clamd` via its TCP socket. If the file is clean the rest of the process will continue as usual. If a virus is found details about the virus will be added to the `virus` table and the rest of the process will be aborted.
|
||||
|
||||

|
||||
|
||||
|
||||
@@ -40,8 +40,8 @@ let
|
||||
(inDirectory "packages/nhost-js/src")
|
||||
(matchExt "ts")
|
||||
)
|
||||
../packages/nhost-js/api/auth.yaml
|
||||
../packages/nhost-js/api/storage.yaml
|
||||
../services/auth/docs/openapi.yaml
|
||||
../services/storage/controller/openapi.yaml
|
||||
../packages/nhost-js/tsconfig.json
|
||||
../build/configs/tsconfig/library.json
|
||||
../build/configs/tsconfig/base.json
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -254,7 +254,7 @@ Start local development environment
|
||||
|
||||
**--ca-certificates**="": Mounts and everrides path to CA certificates in the containers
|
||||
|
||||
**--dashboard-version**="": Dashboard version to use (default: nhost/dashboard:2.38.0)
|
||||
**--dashboard-version**="": Dashboard version to use (default: nhost/dashboard:2.38.4)
|
||||
|
||||
**--disable-tls**: Disable TLS
|
||||
|
||||
@@ -284,7 +284,7 @@ Start local development environment connected to an Nhost Cloud project (BETA)
|
||||
|
||||
**--ca-certificates**="": Mounts and everrides path to CA certificates in the containers
|
||||
|
||||
**--dashboard-version**="": Dashboard version to use (default: nhost/dashboard:2.38.0)
|
||||
**--dashboard-version**="": Dashboard version to use (default: nhost/dashboard:2.38.4)
|
||||
|
||||
**--disable-tls**: Disable TLS
|
||||
|
||||
|
||||
@@ -3142,6 +3142,7 @@ type SignInProvider =
|
||||
| 'bitbucket'
|
||||
| 'workos'
|
||||
| 'azuread'
|
||||
| 'entraid'
|
||||
| 'strava'
|
||||
| 'facebook'
|
||||
| 'windowslive'
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
6
envrc.sample
Normal file
6
envrc.sample
Normal file
@@ -0,0 +1,6 @@
|
||||
watch_file ../../flake.nix ../../nix/*.nix project.nix ./.envrc.custom
|
||||
use flake .\#$(basename $PWD)
|
||||
|
||||
if [[ -f .envrc.custom ]]; then
|
||||
. ./.envrc.custom
|
||||
fi
|
||||
@@ -54,7 +54,7 @@ services:
|
||||
AUTH_SMTP_PASS: password
|
||||
AUTH_SMTP_PORT: "1025"
|
||||
AUTH_SMTP_SECURE: "false"
|
||||
AUTH_SMTP_SENDER: hasura-auth@example.com
|
||||
AUTH_SMTP_SENDER: auth@example.com
|
||||
AUTH_SMTP_USER: user
|
||||
AUTH_TURNSTILE_SECRET: ""
|
||||
AUTH_USER_DEFAULT_ALLOWED_ROLES: user,me
|
||||
@@ -319,7 +319,7 @@ services:
|
||||
SMTP_PASS: password
|
||||
SMTP_PORT: "1025"
|
||||
SMTP_SECURE: "false"
|
||||
SMTP_SENDER: hasura-auth@example.com
|
||||
SMTP_SENDER: auth@example.com
|
||||
SMTP_USER: user
|
||||
extra_hosts:
|
||||
- host.docker.internal:host-gateway
|
||||
|
||||
11
flake.nix
11
flake.nix
@@ -24,6 +24,10 @@
|
||||
nix2containerPkgs = nix2container.packages.${system};
|
||||
nixops-lib = (import ./nixops/lib/lib.nix) { inherit pkgs nix2containerPkgs; };
|
||||
|
||||
authf = import ./services/auth/project.nix {
|
||||
inherit self pkgs nix-filter nixops-lib;
|
||||
};
|
||||
|
||||
clif = import ./cli/project.nix {
|
||||
inherit self pkgs nix-filter nixops-lib;
|
||||
};
|
||||
@@ -57,7 +61,7 @@
|
||||
};
|
||||
|
||||
nixopsf = import ./nixops/project.nix {
|
||||
inherit self pkgs nix-filter nixops-lib;
|
||||
inherit self pkgs nix2containerPkgs nix-filter nixops-lib;
|
||||
};
|
||||
|
||||
storagef = import ./services/storage/project.nix {
|
||||
@@ -71,6 +75,7 @@
|
||||
in
|
||||
{
|
||||
checks = {
|
||||
auth = authf.check;
|
||||
cli = clif.check;
|
||||
codegen = codegenf.check;
|
||||
dashboard = dashboardf.check;
|
||||
@@ -152,6 +157,7 @@
|
||||
];
|
||||
};
|
||||
|
||||
auth = authf.devShell;
|
||||
cli = clif.devShell;
|
||||
codegen = codegenf.devShell;
|
||||
dashboard = dashboardf.devShell;
|
||||
@@ -166,6 +172,8 @@
|
||||
};
|
||||
|
||||
packages = flake-utils.lib.flattenTree {
|
||||
auth = authf.package;
|
||||
auth-docker-image = authf.dockerImage;
|
||||
cli = clif.package;
|
||||
cli-multiplatform = clif.cli-multiplatform;
|
||||
cli-docker-image = clif.dockerImage;
|
||||
@@ -177,6 +185,7 @@
|
||||
mintlify-openapi = mintlify-openapif.package;
|
||||
nhost-js = nhost-jsf.package;
|
||||
nixops = nixopsf.package;
|
||||
nixops-docker-image = nixopsf.dockerImage;
|
||||
storage = storagef.package;
|
||||
storage-docker-image = storagef.dockerImage;
|
||||
clamav-docker-image = storagef.clamav-docker-image;
|
||||
|
||||
21
go.mod
21
go.mod
@@ -4,11 +4,13 @@ go 1.24.2
|
||||
|
||||
require (
|
||||
github.com/99designs/gqlgen v0.17.80
|
||||
github.com/MicahParks/keyfunc/v3 v3.7.0
|
||||
github.com/Yamashou/gqlgenc v0.33.0
|
||||
github.com/aws/aws-sdk-go-v2 v1.36.3
|
||||
github.com/aws/aws-sdk-go-v2/config v1.29.15
|
||||
github.com/aws/aws-sdk-go-v2/credentials v1.17.68
|
||||
github.com/aws/aws-sdk-go-v2/service/s3 v1.80.1
|
||||
github.com/bradfitz/gomemcache v0.0.0-20250403215159-8d39553ac7cf
|
||||
github.com/charmbracelet/lipgloss v1.1.0
|
||||
github.com/creack/pty v1.1.24
|
||||
github.com/davidbyttow/govips/v2 v2.16.0
|
||||
@@ -18,38 +20,48 @@ require (
|
||||
github.com/gin-gonic/gin v1.11.0
|
||||
github.com/go-git/go-git/v5 v5.16.2
|
||||
github.com/go-webauthn/webauthn v0.12.2
|
||||
github.com/gobwas/glob v0.2.3
|
||||
github.com/golang-jwt/jwt/v5 v5.2.2
|
||||
github.com/golang-migrate/migrate/v4 v4.19.0
|
||||
github.com/google/go-cmp v0.7.0
|
||||
github.com/google/uuid v1.6.0
|
||||
github.com/hashicorp/go-getter/v2 v2.2.3
|
||||
github.com/jackc/pgx/v5 v5.7.2
|
||||
github.com/lmittmann/tint v1.0.7
|
||||
github.com/mark3labs/mcp-go v0.41.1
|
||||
github.com/nhost/be v0.0.0-20250929153845-6db3e5249d33
|
||||
github.com/oapi-codegen/gin-middleware v1.0.2
|
||||
github.com/oapi-codegen/runtime v1.1.1
|
||||
github.com/pb33f/libopenapi v0.21.12
|
||||
github.com/pelletier/go-toml/v2 v2.2.4
|
||||
github.com/pquerna/otp v1.5.0
|
||||
github.com/rs/cors/wrapper/gin v0.0.0-20240830163046-1084d89a1692
|
||||
github.com/sirupsen/logrus v1.9.3
|
||||
github.com/spf13/cobra v1.8.1
|
||||
github.com/spf13/pflag v1.0.10
|
||||
github.com/spf13/viper v1.21.0
|
||||
github.com/stretchr/testify v1.11.1
|
||||
github.com/twilio/twilio-go v1.28.3
|
||||
github.com/urfave/cli-docs/v3 v3.0.0-alpha6
|
||||
github.com/urfave/cli/v3 v3.3.3
|
||||
github.com/valyala/fasttemplate v1.2.2
|
||||
github.com/vektah/gqlparser/v2 v2.5.30
|
||||
github.com/wI2L/jsondiff v0.7.0
|
||||
go.uber.org/mock v0.5.0
|
||||
golang.org/x/crypto v0.42.0
|
||||
golang.org/x/mod v0.28.0
|
||||
golang.org/x/oauth2 v0.30.0
|
||||
golang.org/x/term v0.35.0
|
||||
gopkg.in/evanphx/json-patch.v5 v5.9.11
|
||||
gopkg.in/yaml.v2 v2.4.0
|
||||
gopkg.in/yaml.v3 v3.0.1
|
||||
k8s.io/client-go v12.0.0+incompatible
|
||||
)
|
||||
|
||||
require (
|
||||
cuelang.org/go v0.11.2 // indirect
|
||||
dario.cat/mergo v1.0.0 // indirect
|
||||
github.com/MicahParks/jwkset v0.11.0 // indirect
|
||||
github.com/Microsoft/go-winio v0.6.2 // indirect
|
||||
github.com/ProtonMail/go-crypto v1.1.6 // indirect
|
||||
github.com/agnivade/levenshtein v1.2.1 // indirect
|
||||
@@ -72,6 +84,7 @@ require (
|
||||
github.com/bahlo/generic-list-go v0.2.0 // indirect
|
||||
github.com/beorn7/perks v1.0.1 // indirect
|
||||
github.com/bgentry/go-netrc v0.0.0-20140422174119-9fd32a8b3d3d // indirect
|
||||
github.com/boombuler/barcode v1.0.1-0.20190219062509-6c824513bacc // indirect
|
||||
github.com/buger/jsonparser v1.1.1 // indirect
|
||||
github.com/bytedance/sonic v1.14.0 // indirect
|
||||
github.com/bytedance/sonic/loader v0.3.0 // indirect
|
||||
@@ -102,6 +115,7 @@ require (
|
||||
github.com/goccy/go-json v0.10.5 // indirect
|
||||
github.com/goccy/go-yaml v1.18.0 // indirect
|
||||
github.com/golang/groupcache v0.0.0-20241129210726-2c02b8208cf8 // indirect
|
||||
github.com/golang/mock v1.6.0 // indirect
|
||||
github.com/google/go-tpm v0.9.3 // indirect
|
||||
github.com/gorilla/mux v1.8.1 // indirect
|
||||
github.com/gorilla/websocket v1.5.3 // indirect
|
||||
@@ -115,7 +129,7 @@ require (
|
||||
github.com/invopop/jsonschema v0.13.0 // indirect
|
||||
github.com/jackc/pgpassfile v1.0.0 // indirect
|
||||
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761 // indirect
|
||||
github.com/jackc/pgx/v5 v5.7.2 // indirect
|
||||
github.com/jackc/puddle/v2 v2.2.2 // indirect
|
||||
github.com/jbenet/go-context v0.0.0-20150711004518-d14ea06fba99 // indirect
|
||||
github.com/josharian/intern v1.0.0 // indirect
|
||||
github.com/json-iterator/go v1.1.12 // indirect
|
||||
@@ -140,6 +154,7 @@ require (
|
||||
github.com/oasdiff/yaml3 v0.0.0-20250309153720-d2182401db90 // indirect
|
||||
github.com/perimeterx/marshmallow v1.1.5 // indirect
|
||||
github.com/pjbgf/sha1cd v0.3.2 // indirect
|
||||
github.com/pkg/errors v0.9.1 // indirect
|
||||
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect
|
||||
github.com/prometheus/client_golang v1.22.0 // indirect
|
||||
github.com/prometheus/client_model v0.6.2 // indirect
|
||||
@@ -167,7 +182,6 @@ require (
|
||||
github.com/ugorji/go/codec v1.3.0 // indirect
|
||||
github.com/ulikunitz/xz v0.5.15 // indirect
|
||||
github.com/valyala/bytebufferpool v1.0.0 // indirect
|
||||
github.com/valyala/fasttemplate v1.2.2 // indirect
|
||||
github.com/wk8/go-ordered-map/v2 v2.1.9-0.20240815153524-6ea36470d1bd // indirect
|
||||
github.com/woodsbury/decimal128 v1.3.0 // indirect
|
||||
github.com/x448/float16 v0.8.4 // indirect
|
||||
@@ -177,13 +191,12 @@ require (
|
||||
go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.61.0 // indirect
|
||||
go.yaml.in/yaml/v3 v3.0.4 // indirect
|
||||
golang.org/x/arch v0.20.0 // indirect
|
||||
golang.org/x/crypto v0.42.0 // indirect
|
||||
golang.org/x/image v0.18.0 // indirect
|
||||
golang.org/x/net v0.44.0 // indirect
|
||||
golang.org/x/oauth2 v0.30.0 // indirect
|
||||
golang.org/x/sync v0.17.0 // indirect
|
||||
golang.org/x/sys v0.36.0 // indirect
|
||||
golang.org/x/text v0.29.0 // indirect
|
||||
golang.org/x/time v0.11.0 // indirect
|
||||
golang.org/x/tools v0.37.0 // indirect
|
||||
google.golang.org/protobuf v1.36.9 // indirect
|
||||
gopkg.in/warnings.v0 v0.1.2 // indirect
|
||||
|
||||
90
go.sum
90
go.sum
@@ -1,3 +1,4 @@
|
||||
cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
|
||||
cuelabs.dev/go/oci/ociregistry v0.0.0-20241125120445-2c00c104c6e1 h1:mRwydyTyhtRX2wXS3mqYWzR2qlv6KsmoKXmlz5vInjg=
|
||||
cuelabs.dev/go/oci/ociregistry v0.0.0-20241125120445-2c00c104c6e1/go.mod h1:5A4xfTzHTXfeVJBU6RAUf+QrlfTCW+017q/QiW+sMLg=
|
||||
cuelang.org/go v0.11.2 h1:9+mGCq20wzA7J+AETn0uSrkPk8RxmK/jaYAS5pAw5Wo=
|
||||
@@ -8,6 +9,11 @@ github.com/99designs/gqlgen v0.17.80 h1:S64VF9SK+q3JjQbilgdrM0o4iFQgB54mVQ3QvXEO
|
||||
github.com/99designs/gqlgen v0.17.80/go.mod h1:vgNcZlLwemsUhYim4dC1pvFP5FX0pr2Y+uYUoHFb1ig=
|
||||
github.com/Azure/go-ansiterm v0.0.0-20230124172434-306776ec8161 h1:L/gRVlceqvL25UVaW/CKtUDjefjrs0SPonmDGUVOYP0=
|
||||
github.com/Azure/go-ansiterm v0.0.0-20230124172434-306776ec8161/go.mod h1:xomTg63KZ2rFqZQzSB4Vz2SUXa1BpHTVz9L5PTmPC4E=
|
||||
github.com/Azure/go-autorest v11.1.2+incompatible/go.mod h1:r+4oMnoxhatjLLJ6zxSWATqVooLgysK6ZNox3g/xq24=
|
||||
github.com/MicahParks/jwkset v0.11.0 h1:yc0zG+jCvZpWgFDFmvs8/8jqqVBG9oyIbmBtmjOhoyQ=
|
||||
github.com/MicahParks/jwkset v0.11.0/go.mod h1:U2oRhRaLgDCLjtpGL2GseNKGmZtLs/3O7p+OZaL5vo0=
|
||||
github.com/MicahParks/keyfunc/v3 v3.7.0 h1:pdafUNyq+p3ZlvjJX1HWFP7MA3+cLpDtg69U3kITJGM=
|
||||
github.com/MicahParks/keyfunc/v3 v3.7.0/go.mod h1:z66bkCviwqfg2YUp+Jcc/xRE9IXLcMq6DrgV/+Htru0=
|
||||
github.com/Microsoft/go-winio v0.5.2/go.mod h1:WpS1mjBmmwHBEWmogvA2mj8546UReBk4v8QkMxJ6pZY=
|
||||
github.com/Microsoft/go-winio v0.6.2 h1:F2VQgta7ecxGYO8k3ZZz3RS8fVIXVxONVUPlNERoyfY=
|
||||
github.com/Microsoft/go-winio v0.6.2/go.mod h1:yd8OoFMLzJbo9gZq8j5qaps8bJ9aShtEA8Ipt1oGCvU=
|
||||
@@ -72,11 +78,16 @@ github.com/aymanbagabas/go-osc52/v2 v2.0.1 h1:HwpRHbFMcZLEVr42D4p7XBqjyuxQH5SMiE
|
||||
github.com/aymanbagabas/go-osc52/v2 v2.0.1/go.mod h1:uYgXzlJ7ZpABp8OJ+exZzJJhRNQ2ASbcXHWsFqH8hp8=
|
||||
github.com/bahlo/generic-list-go v0.2.0 h1:5sz/EEAK+ls5wF+NeqDpk5+iNdMDXrh3z3nPnH1Wvgk=
|
||||
github.com/bahlo/generic-list-go v0.2.0/go.mod h1:2KvAjgMlE5NNynlg/5iLrrCCZ2+5xWbdbCW3pNTGyYg=
|
||||
github.com/beevik/etree v1.1.0/go.mod h1:r8Aw8JqVegEf0w2fDnATrX9VpkMcyFeM0FhwO62wh+A=
|
||||
github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM=
|
||||
github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw=
|
||||
github.com/bgentry/go-netrc v0.0.0-20140422174119-9fd32a8b3d3d h1:xDfNPAt8lFiC1UJrqV3uuy861HCTo708pDMbjHHdCas=
|
||||
github.com/bgentry/go-netrc v0.0.0-20140422174119-9fd32a8b3d3d/go.mod h1:6QX/PXZ00z/TKoufEY6K/a0k6AhaJrQKdFe6OfVXsa4=
|
||||
github.com/bmatcuk/doublestar v1.1.1/go.mod h1:UD6OnuiIn0yFxxA2le/rnRU1G4RaI4UvFv1sNto9p6w=
|
||||
github.com/boombuler/barcode v1.0.1-0.20190219062509-6c824513bacc h1:biVzkmvwrH8WK8raXaxBx6fRVTlJILwEwQGL1I/ByEI=
|
||||
github.com/boombuler/barcode v1.0.1-0.20190219062509-6c824513bacc/go.mod h1:paBWMcWSl3LHKBqUq+rly7CNSldXjb2rDl3JlRe0mD8=
|
||||
github.com/bradfitz/gomemcache v0.0.0-20250403215159-8d39553ac7cf h1:TqhNAT4zKbTdLa62d2HDBFdvgSbIGB3eJE8HqhgiL9I=
|
||||
github.com/bradfitz/gomemcache v0.0.0-20250403215159-8d39553ac7cf/go.mod h1:r5xuitiExdLAJ09PR7vBVENGvp4ZuTBeWTGtxuX3K+c=
|
||||
github.com/buger/jsonparser v1.1.1 h1:2PnMjfWD7wBILjqQbt530v576A/cAbQvEW9gGIpYMUs=
|
||||
github.com/buger/jsonparser v1.1.1/go.mod h1:6RYKKt7H4d4+iWqouImQ9R2FZql3VbhNgx27UK13J/0=
|
||||
github.com/bytedance/sonic v1.14.0 h1:/OfKt8HFw0kh2rj8N0F6C/qPGRESq0BbaNZgcNXXzQQ=
|
||||
@@ -108,6 +119,7 @@ github.com/containerd/errdefs/pkg v0.3.0/go.mod h1:NJw6s9HwNuRhnjJhM7pylWwMyAkmC
|
||||
github.com/cpuguy83/go-md2man/v2 v2.0.4/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o=
|
||||
github.com/cpuguy83/go-md2man/v2 v2.0.7 h1:zbFlGlXEAKlwXpmvle3d8Oe3YnkKIK4xSRTd3sHPnBo=
|
||||
github.com/cpuguy83/go-md2man/v2 v2.0.7/go.mod h1:oOW0eioCTA6cOiMLiUPZOpcVxMig6NIQQ7OS05n1F4g=
|
||||
github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E=
|
||||
github.com/creack/pty v1.1.24 h1:bJrF4RRfyJnbTJqzRLHzcGaZK1NeM5kTC9jGgovnR1s=
|
||||
github.com/creack/pty v1.1.24/go.mod h1:08sCNb52WyoAwi2QDyzUCTgcvVFhUzewun7wtTfvcwE=
|
||||
github.com/cyphar/filepath-securejoin v0.4.1 h1:JyxxyPEaktOD+GAnqIqTf9A8tHyAG22rowi7HkoSU1s=
|
||||
@@ -118,6 +130,7 @@ github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc h1:U9qPSI2PIWSS1
|
||||
github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/davidbyttow/govips/v2 v2.16.0 h1:1nH/Rbx8qZP1hd+oYL9fYQjAnm1+KorX9s07ZGseQmo=
|
||||
github.com/davidbyttow/govips/v2 v2.16.0/go.mod h1:clH5/IDVmG5eVyc23qYpyi7kmOT0B/1QNTKtci4RkyM=
|
||||
github.com/dgrijalva/jwt-go v0.0.0-20160705203006-01aeca54ebda/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ=
|
||||
github.com/dgryski/trifles v0.0.0-20230903005119-f50d829f2e54 h1:SG7nF6SRlWhcT7cNTs5R6Hk4V2lcmLz2NsG2VnInyNo=
|
||||
github.com/dgryski/trifles v0.0.0-20230903005119-f50d829f2e54/go.mod h1:if7Fbed8SFyPtHLHbg49SI7NAdJiC5WIA09pe59rfAA=
|
||||
github.com/dhui/dktest v0.4.6 h1:+DPKyScKSEp3VLtbMDHcUq6V5Lm5zfZZVb0Sk7Ahom4=
|
||||
@@ -130,16 +143,20 @@ github.com/docker/go-connections v0.5.0 h1:USnMq7hx7gwdVZq1L49hLXaFtUdTADjXGp+uj
|
||||
github.com/docker/go-connections v0.5.0/go.mod h1:ov60Kzw0kKElRwhNs9UlUHAE/F9Fe6GLaXnqyDdmEXc=
|
||||
github.com/docker/go-units v0.5.0 h1:69rxXcBk27SvSaaxTtLh/8llcHD8vYHT7WSdRZ/jvr4=
|
||||
github.com/docker/go-units v0.5.0/go.mod h1:fgPhTUdO+D/Jk86RDLlptpiXQzgHJF7gydDDbaIK4Dk=
|
||||
github.com/docker/spdystream v0.0.0-20160310174837-449fdfce4d96/go.mod h1:Qh8CwZgvJUkLughtfhJv5dyTYa91l1fOUCrgjqmcifM=
|
||||
github.com/elazarl/goproxy v0.0.0-20170405201442-c4fc26588b6e/go.mod h1:/Zj4wYkgs4iZTTu3o/KG3Itv/qCCa8VVMlb3i9OVuzc=
|
||||
github.com/elazarl/goproxy v1.7.2 h1:Y2o6urb7Eule09PjlhQRGNsqRfPmYI3KKQLFpCAV3+o=
|
||||
github.com/elazarl/goproxy v1.7.2/go.mod h1:82vkLNir0ALaW14Rc399OTTjyNREgmdL2cVoIbS6XaE=
|
||||
github.com/emicklei/proto v1.14.0 h1:WYxC0OrBuuC+FUCTZvb8+fzEHdZMwLEF+OnVfZA3LXU=
|
||||
github.com/emicklei/proto v1.14.0/go.mod h1:rn1FgRS/FANiZdD2djyH7TMA9jdRDcYQ9IEN9yvjX0A=
|
||||
github.com/emirpasic/gods v1.18.1 h1:FXtiHYKDGKCW2KzwZKx0iC0PQmdlorYgdFG9jPXJ1Bc=
|
||||
github.com/emirpasic/gods v1.18.1/go.mod h1:8tpGGwCnJ5H4r6BWwaV6OrWmMoPhUl5jm/FMNAnJvWQ=
|
||||
github.com/evanphx/json-patch v0.0.0-20190203023257-5858425f7550/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk=
|
||||
github.com/felixge/httpsnoop v1.0.4 h1:NFTV2Zj1bL4mc9sqWACXbQFVBBg2W3GPvqp8/ESS2Wg=
|
||||
github.com/felixge/httpsnoop v1.0.4/go.mod h1:m8KPJKqk1gH5J9DgRY2ASl2lWCfGKXixSwevea8zH2U=
|
||||
github.com/frankban/quicktest v1.14.6 h1:7Xjx+VpznH+oBnejlPUj8oUpdxnVs4f8XU8WnHkI4W8=
|
||||
github.com/frankban/quicktest v1.14.6/go.mod h1:4ptaffx2x8+WTWXmUCuVU6aPUX1/Mz7zb5vbUoiM6w0=
|
||||
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
|
||||
github.com/fsnotify/fsnotify v1.9.0 h1:2Ml+OJNzbYCTzsxtv8vKSFD9PbJjmhYF14k/jKC7S9k=
|
||||
github.com/fsnotify/fsnotify v1.9.0/go.mod h1:8jBTzvmWwFyi3Pb8djgCCO5IBqzKJ/Jwo8TRcHyHii0=
|
||||
github.com/fxamacker/cbor/v2 v2.8.0 h1:fFtUGXUzXPHTIUdne5+zzMPTfffl3RD5qYnkY40vtxU=
|
||||
@@ -190,30 +207,44 @@ github.com/go-webauthn/webauthn v0.12.2 h1:yLaNPgBUEXDQtWnOjhsGhMMCEWbXwjg/aNkC8
|
||||
github.com/go-webauthn/webauthn v0.12.2/go.mod h1:Q8SZPPj4sZ469fNTcQXxRpzJOdb30jQrn/36FX8jilA=
|
||||
github.com/go-webauthn/x v0.1.19 h1:IUfdHiBRoTdujpBA/14qbrMXQ3LGzYe/PRGWdZcmudg=
|
||||
github.com/go-webauthn/x v0.1.19/go.mod h1:C5arLuTQ3pVHKPw89v7CDGnqAZSZJj+4Jnr40dsn7tk=
|
||||
github.com/gobwas/glob v0.2.3 h1:A4xDbljILXROh+kObIiy5kIaPYD8e96x1tgBhUI5J+Y=
|
||||
github.com/gobwas/glob v0.2.3/go.mod h1:d3Ez4x06l9bZtSvzIay5+Yzi0fmZzPgnTbPcKjJAkT8=
|
||||
github.com/goccy/go-json v0.10.5 h1:Fq85nIqj+gXn/S5ahsiTlK3TmC85qgirsdTP/+DeaC4=
|
||||
github.com/goccy/go-json v0.10.5/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M=
|
||||
github.com/goccy/go-yaml v1.18.0 h1:8W7wMFS12Pcas7KU+VVkaiCng+kG8QiFeFwzFb+rwuw=
|
||||
github.com/goccy/go-yaml v1.18.0/go.mod h1:XBurs7gK8ATbW4ZPGKgcbrY1Br56PdM69F7LkFRi1kA=
|
||||
github.com/gogo/protobuf v0.0.0-20171007142547-342cbe0a0415/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
|
||||
github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q=
|
||||
github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q=
|
||||
github.com/golang-jwt/jwt/v5 v5.2.2 h1:Rl4B7itRWVtYIHFrSNd7vhTiz9UpLdi6gZhZ3wEeDy8=
|
||||
github.com/golang-jwt/jwt/v5 v5.2.2/go.mod h1:pqrtFR0X4osieyHYxtmOUWsAWrfe1Q5UVIyoH402zdk=
|
||||
github.com/golang-migrate/migrate/v4 v4.19.0 h1:RcjOnCGz3Or6HQYEJ/EEVLfWnmw9KnoigPSjzhCuaSE=
|
||||
github.com/golang-migrate/migrate/v4 v4.19.0/go.mod h1:9dyEcu+hO+G9hPSw8AIg50yg622pXJsoHItQnDGZkI0=
|
||||
github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc=
|
||||
github.com/golang/groupcache v0.0.0-20241129210726-2c02b8208cf8 h1:f+oWsMOmNPc8JmEHVZIycC7hBoQxHH9pNKQORJNozsQ=
|
||||
github.com/golang/groupcache v0.0.0-20241129210726-2c02b8208cf8/go.mod h1:wcDNUvekVysuuOpQKo3191zZyTpiI6se1N1ULghS0sw=
|
||||
github.com/golang/mock v1.6.0 h1:ErTB+efbowRARo13NNdxyJji2egdxLGQhRaY+DUumQc=
|
||||
github.com/golang/mock v1.6.0/go.mod h1:p6yTPP+5HYm5mzsMV8JkE6ZKdX+/wYM6Hr+LicevLPs=
|
||||
github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
|
||||
github.com/google/btree v0.0.0-20160524151835-7d79101e329e/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ=
|
||||
github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
|
||||
github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
|
||||
github.com/google/go-cmp v0.7.0 h1:wk8382ETsv4JYUZwIsn6YpYiWiBsYLSJiTsyBybVuN8=
|
||||
github.com/google/go-cmp v0.7.0/go.mod h1:pXiqmnSA92OHEEa9HXL2W4E7lf9JzCmGVUdgjX3N/iU=
|
||||
github.com/google/go-tpm v0.9.3 h1:+yx0/anQuGzi+ssRqeD6WpXjW2L/V0dItUayO0i9sRc=
|
||||
github.com/google/go-tpm v0.9.3/go.mod h1:h9jEsEECg7gtLis0upRBQU+GhYVH6jMjrFxI8u6bVUY=
|
||||
github.com/google/gofuzz v0.0.0-20170612174753-24818f796faf/go.mod h1:HP5RmnzzSNb993RKQDq4+1A4ia9nllfqcQFTQJedwGI=
|
||||
github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg=
|
||||
github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
|
||||
github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0=
|
||||
github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
|
||||
github.com/googleapis/gnostic v0.0.0-20170729233727-0c5108395e2d/go.mod h1:sJBsCZ4ayReDTBIg8b9dl28c5xFWyhBTVRp3pOg5EKY=
|
||||
github.com/gophercloud/gophercloud v0.0.0-20190126172459-c818fa66e4c8/go.mod h1:3WdhXV3rUYy9p6AUW8d94kr+HS62Y4VL9mBnFxsD8q4=
|
||||
github.com/gorilla/mux v1.8.1 h1:TuBL49tXwgrFYWhqrNgrUNEY92u81SPhu7sTdzQEiWY=
|
||||
github.com/gorilla/mux v1.8.1/go.mod h1:AKf9I4AEqPTmMytcMc0KkNouC66V3BtZ4qD5fmWSiMQ=
|
||||
github.com/gorilla/websocket v1.5.3 h1:saDtZ6Pbx/0u+bgYQ3q96pZgCzfhKXGPqt7kZ72aNNg=
|
||||
github.com/gorilla/websocket v1.5.3/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE=
|
||||
github.com/gregjones/httpcache v0.0.0-20170728041850-787624de3eb7/go.mod h1:FecbI9+v66THATjSRHfNgh1IVFe/9kFxbXtjV0ctIMA=
|
||||
github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
|
||||
github.com/hashicorp/errwrap v1.1.0 h1:OxrOeh75EUXMY8TBjag2fzXGZ40LB6IKw45YeGUDY2I=
|
||||
github.com/hashicorp/errwrap v1.1.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
|
||||
@@ -227,8 +258,11 @@ github.com/hashicorp/go-safetemp v1.0.0 h1:2HR189eFNrjHQyENnQMMpCiBAsRxzbTMIgBhE
|
||||
github.com/hashicorp/go-safetemp v1.0.0/go.mod h1:oaerMy3BhqiTbVye6QuFhFtIceqFoDHxNAB65b+Rj1I=
|
||||
github.com/hashicorp/go-version v1.6.0 h1:feTTfFNnjP967rlCxM/I9g701jU+RN74YKx2mOkIeek=
|
||||
github.com/hashicorp/go-version v1.6.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA=
|
||||
github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
|
||||
github.com/hashicorp/golang-lru/v2 v2.0.7 h1:a+bsQ5rvGLjzHuww6tVxozPZFVghXaHOwFs4luLUK2k=
|
||||
github.com/hashicorp/golang-lru/v2 v2.0.7/go.mod h1:QeFd9opnmA6QUJc5vARoKUSoFhyfM2/ZepoAG6RGpeM=
|
||||
github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU=
|
||||
github.com/imdario/mergo v0.3.5/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA=
|
||||
github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8=
|
||||
github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw=
|
||||
github.com/invopop/jsonschema v0.13.0 h1:KvpoAJWEjR3uD9Kbm2HWJmqsEaHt8lBUpd0qHcIi21E=
|
||||
@@ -245,6 +279,7 @@ github.com/jbenet/go-context v0.0.0-20150711004518-d14ea06fba99 h1:BQSFePA1RWJOl
|
||||
github.com/jbenet/go-context v0.0.0-20150711004518-d14ea06fba99/go.mod h1:1lJo3i6rXxKeerYnT8Nvf0QmHCRC1n8sfWVwXF2Frvo=
|
||||
github.com/josharian/intern v1.0.0 h1:vlS4z54oSdjm0bgjRigI+G1HpF+tI+9rE5LLzOg8HmY=
|
||||
github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y=
|
||||
github.com/json-iterator/go v0.0.0-20180701071628-ab8a2e0c74be/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU=
|
||||
github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM=
|
||||
github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo=
|
||||
github.com/juju/gnuflag v0.0.0-20171113085948-2ce1bb71843d/go.mod h1:2PavIy+JPciBPrBUjwbNvtwB6RQlve+hkpll6QSNmOE=
|
||||
@@ -267,6 +302,10 @@ github.com/leodido/go-urn v1.4.0 h1:WT9HwE9SGECu3lg4d/dIA+jxlljEa1/ffXKmRjqdmIQ=
|
||||
github.com/leodido/go-urn v1.4.0/go.mod h1:bvxc+MVxLKB4z00jd1z+Dvzr47oO32F/QSNjSBOlFxI=
|
||||
github.com/lib/pq v1.10.9 h1:YXG7RB+JIjhP29X+OtkiDnYaXQwpS4JEWq7dtCCRUEw=
|
||||
github.com/lib/pq v1.10.9/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o=
|
||||
github.com/lmittmann/tint v1.0.7 h1:D/0OqWZ0YOGZ6AyC+5Y2kD8PBEzBk6rFHVSfOqCkF9Y=
|
||||
github.com/lmittmann/tint v1.0.7/go.mod h1:HIS3gSy7qNwGCj+5oRjAutErFBl4BzdQP6cJZ0NfMwE=
|
||||
github.com/localtunnel/go-localtunnel v0.0.0-20170326223115-8a804488f275 h1:IZycmTpoUtQK3PD60UYBwjaCUHUP7cML494ao9/O8+Q=
|
||||
github.com/localtunnel/go-localtunnel v0.0.0-20170326223115-8a804488f275/go.mod h1:zt6UU74K6Z6oMOYJbJzYpYucqdcQwSMPBEdSvGiaUMw=
|
||||
github.com/lucasb-eyer/go-colorful v1.2.0 h1:1nnpGOrhyZZuNyfu1QjKiUICQ74+3FNCN69Aj6K7nkY=
|
||||
github.com/lucasb-eyer/go-colorful v1.2.0/go.mod h1:R4dSotOR9KMtayYi1e77YzuveK+i7ruzyGqttikkLy0=
|
||||
github.com/mailru/easyjson v0.9.0 h1:PrnmzHw7262yW8sTBwxi1PdJA3Iw/EKBa8psRf7d9a4=
|
||||
@@ -292,6 +331,7 @@ github.com/moby/term v0.5.0/go.mod h1:8FzsFHVUBGZdbDsJw/ot+X+d5HLUbvklYLJ9uGfcI3
|
||||
github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
|
||||
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg=
|
||||
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q=
|
||||
github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0=
|
||||
github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M=
|
||||
github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk=
|
||||
github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826 h1:RWengNIwukTxcDr9M+97sNutRR1RKhG96O6jWumTTnw=
|
||||
@@ -302,6 +342,7 @@ github.com/muesli/termenv v0.16.0 h1:S5AlUN9dENB57rsbnkPyfdGuWIlkmzJjbFf0Tf5FWUc
|
||||
github.com/muesli/termenv v0.16.0/go.mod h1:ZRfOIKPFDYQoDFF4Olj7/QJbW60Ol/kL1pU3VfY/Cnk=
|
||||
github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 h1:C3w9PqII01/Oq1c1nUAm88MOHcQC9l5mIlSMApZMrHA=
|
||||
github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822/go.mod h1:+n7T8mK8HuQTcFwEeznm/DIxMOiR9yIdICNftLE1DvQ=
|
||||
github.com/mxk/go-flowrate v0.0.0-20140419014527-cca7078d478f/go.mod h1:ZdcZmHo+o7JKHSa8/e818NopupXU1YMK5fe1lsApnBw=
|
||||
github.com/nhost/be v0.0.0-20250929153845-6db3e5249d33 h1:BNFN3Mw4zY6LEmVc7RXkHSVvHtovDSm7Oesb7IUt27o=
|
||||
github.com/nhost/be v0.0.0-20250929153845-6db3e5249d33/go.mod h1:feVvqP3dft8hWbp9zNZExdGKbFEYv8aLYohfyAeINNQ=
|
||||
github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno=
|
||||
@@ -313,6 +354,8 @@ github.com/oasdiff/yaml v0.0.0-20250309154309-f31be36b4037 h1:G7ERwszslrBzRxj//J
|
||||
github.com/oasdiff/yaml v0.0.0-20250309154309-f31be36b4037/go.mod h1:2bpvgLBZEtENV5scfDFEtB/5+1M4hkQhDQrccEJ/qGw=
|
||||
github.com/oasdiff/yaml3 v0.0.0-20250309153720-d2182401db90 h1:bQx3WeLcUWy+RletIKwUIt4x3t8n2SxavmoclizMb8c=
|
||||
github.com/oasdiff/yaml3 v0.0.0-20250309153720-d2182401db90/go.mod h1:y5+oSEHCPT/DGrS++Wc/479ERge0zTFxaF8PbGKcg2o=
|
||||
github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE=
|
||||
github.com/onsi/gomega v0.0.0-20190113212917-5533ce8a0da3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY=
|
||||
github.com/onsi/gomega v1.34.1 h1:EUMJIKUjM8sKjYbtxQI9A4z2o+rruxnzNvpknOXie6k=
|
||||
github.com/onsi/gomega v1.34.1/go.mod h1:kU1QgUvBDLXBJq618Xvm2LUX6rSAfRaFRTcdOeDLwwY=
|
||||
github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8Oi/yOhh5U=
|
||||
@@ -325,6 +368,7 @@ github.com/pelletier/go-toml/v2 v2.2.4 h1:mye9XuhQ6gvn5h28+VilKrrPoQVanw5PMw/TB0
|
||||
github.com/pelletier/go-toml/v2 v2.2.4/go.mod h1:2gIqNv+qfxSVS7cM2xJQKtLSTLUE9V8t9Stt+h56mCY=
|
||||
github.com/perimeterx/marshmallow v1.1.5 h1:a2LALqQ1BlHM8PZblsDdidgv1mWi1DgC2UmX50IvK2s=
|
||||
github.com/perimeterx/marshmallow v1.1.5/go.mod h1:dsXbUu8CRzfYP5a87xpp0xq9S3u0Vchtcl8we9tYaXw=
|
||||
github.com/peterbourgon/diskv v2.0.1+incompatible/go.mod h1:uqqh8zWWbv1HBMNONnaR/tNboyR3/BZd58JJSHlUSCU=
|
||||
github.com/pjbgf/sha1cd v0.3.2 h1:a9wb0bp1oC2TGwStyn0Umc/IGKQnEgF0vVaZ8QF8eo4=
|
||||
github.com/pjbgf/sha1cd v0.3.2/go.mod h1:zQWigSxVmsHEZow5qaLtPYxpcKMMQpa09ixqBxuCS6A=
|
||||
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
|
||||
@@ -332,6 +376,8 @@ github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINE
|
||||
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
||||
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 h1:Jamvg5psRIccs7FGNTlIRMkT8wgtp5eCXdBlqhYGL6U=
|
||||
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
||||
github.com/pquerna/otp v1.5.0 h1:NMMR+WrmaqXU4EzdGJEE1aUUI0AMRzsp96fFFWNPwxs=
|
||||
github.com/pquerna/otp v1.5.0/go.mod h1:dkJfzwRKNiegxyNb54X/3fLwhCynbMspSyWKnvi1AEg=
|
||||
github.com/prometheus/client_golang v1.22.0 h1:rb93p9lokFEsctTys46VnV1kLCDpVZ0a/Y92Vm0Zc6Q=
|
||||
github.com/prometheus/client_golang v1.22.0/go.mod h1:R7ljNsLXhuQXYZYtw6GAE9AZg8Y7vEW5scdCXrWRXC0=
|
||||
github.com/prometheus/client_model v0.6.2 h1:oBsgwpGs7iVziMvrGhE53c/GrLUsZdHnqNwqPLxwZyk=
|
||||
@@ -378,6 +424,7 @@ github.com/spf13/cast v1.10.0 h1:h2x0u2shc1QuLHfxi+cTJvs30+ZAHOGRic8uyGTDWxY=
|
||||
github.com/spf13/cast v1.10.0/go.mod h1:jNfB8QC9IA6ZuY2ZjDp0KtFO2LZZlg4S/7bzP6qqeHo=
|
||||
github.com/spf13/cobra v1.8.1 h1:e5/vxKd/rZsfSJMUX1agtjeTDf+qv1/JdBF8gg5k9ZM=
|
||||
github.com/spf13/cobra v1.8.1/go.mod h1:wHxEcudfqmLYa8iTfL+OuZPbBZkmvliBWKIezN3kD9Y=
|
||||
github.com/spf13/pflag v1.0.1/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
|
||||
github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg=
|
||||
github.com/spf13/pflag v1.0.10 h1:4EBh2KAYBwaONj6b2Ye1GiHfwjqyROoF4RwYO+vPwFk=
|
||||
github.com/spf13/pflag v1.0.10/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg=
|
||||
@@ -409,6 +456,8 @@ github.com/tidwall/pretty v1.2.1 h1:qjsOFOWWQl+N3RsoF5/ssm1pHmJJwhjlSbZ51I6wMl4=
|
||||
github.com/tidwall/pretty v1.2.1/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU=
|
||||
github.com/tidwall/sjson v1.2.5 h1:kLy8mja+1c9jlljvWTlSazM7cKDRfJuR/bOJhcY5NcY=
|
||||
github.com/tidwall/sjson v1.2.5/go.mod h1:Fvgq9kS/6ociJEDnK0Fk1cpYF4FIW6ZF7LAe+6jwd28=
|
||||
github.com/twilio/twilio-go v1.28.3 h1:zaDex4kAAxY2lvrMyFscvw8ga6CIrQ/bIx+ycvcDcvc=
|
||||
github.com/twilio/twilio-go v1.28.3/go.mod h1:FpgNWMoD8CFnmukpKq9RNpUSGXC0BwnbeKZj2YHlIkw=
|
||||
github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI=
|
||||
github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08=
|
||||
github.com/ugorji/go/codec v1.3.0 h1:Qd2W2sQawAfG8XSvzwhBeoGq71zXOC/Q1E9y/wUcsUA=
|
||||
@@ -439,6 +488,7 @@ github.com/xo/terminfo v0.0.0-20220910002029-abceb7e1c41e h1:JVG44RsyaB9T2KIHavM
|
||||
github.com/xo/terminfo v0.0.0-20220910002029-abceb7e1c41e/go.mod h1:RbqR21r5mrJuqunuUZ/Dhy/avygyECGrLceyNeo4LiM=
|
||||
github.com/yosida95/uritemplate/v3 v3.0.2 h1:Ed3Oyj9yrmi9087+NczuL5BwkIc4wvTb5zIM+UJPGz4=
|
||||
github.com/yosida95/uritemplate/v3 v3.0.2/go.mod h1:ILOh0sOhIJR3+L/8afwt/kE++YT040gmv5BQTMR2HP4=
|
||||
github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
|
||||
github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY=
|
||||
go.opentelemetry.io/auto/sdk v1.1.0 h1:cH53jehLUN6UFLY71z+NDOiNJqDdPRaXzTel0sJySYA=
|
||||
go.opentelemetry.io/auto/sdk v1.1.0/go.mod h1:3wSPjt5PWp2RhlCcmmOial7AvC4DQqZb7a7wCow3W8A=
|
||||
@@ -456,7 +506,9 @@ go.yaml.in/yaml/v3 v3.0.4 h1:tfq32ie2Jv2UxXFdLJdh3jXuOzWiL1fo0bu/FbuKpbc=
|
||||
go.yaml.in/yaml/v3 v3.0.4/go.mod h1:DhzuOOF2ATzADvBadXxruRBLzYTpT36CKvDb3+aBEFg=
|
||||
golang.org/x/arch v0.20.0 h1:dx1zTU0MAE98U+TQ8BLl7XsJbgze2WnNKF/8tGp/Q6c=
|
||||
golang.org/x/arch v0.20.0/go.mod h1:bdwinDaKcfZUGpH09BB7ZmOfhalA8lQdzl62l8gGWsk=
|
||||
golang.org/x/crypto v0.0.0-20181025213731-e84da0312774/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
||||
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||
golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
|
||||
golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
|
||||
golang.org/x/crypto v0.13.0/go.mod h1:y6Z2r+Rw4iayiXXAIxJIDAJ1zMW4yaTpebo8fPOliYc=
|
||||
@@ -468,6 +520,7 @@ golang.org/x/exp v0.0.0-20240719175910-8a7402abbf56 h1:2dVuKD2vS7b0QIHQbpyTISPd0
|
||||
golang.org/x/exp v0.0.0-20240719175910-8a7402abbf56/go.mod h1:M4RDyNAINzryxdtnbRXRL/OHtkFuWGRjvuhBJpk2IlY=
|
||||
golang.org/x/image v0.18.0 h1:jGzIakQa/ZXI1I0Fxvaa9W7yP25TqT6cHIHn+6CqvSQ=
|
||||
golang.org/x/image v0.18.0/go.mod h1:4yyo5vMFQjVjUcVk4jEQcU9MGy/rulF5WvUILseCM2E=
|
||||
golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||
golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4=
|
||||
golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs=
|
||||
golang.org/x/mod v0.12.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs=
|
||||
@@ -475,8 +528,14 @@ golang.org/x/mod v0.15.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c=
|
||||
golang.org/x/mod v0.17.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c=
|
||||
golang.org/x/mod v0.28.0 h1:gQBtGhjxykdjY9YhZpSlZIsbnaE2+PgjfLWUQTnoZ1U=
|
||||
golang.org/x/mod v0.28.0/go.mod h1:yfB/L0NOf/kmEbXjzCPOx1iK1fRutOydrCMsqRhEBxI=
|
||||
golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20190206173232-65e2d4e15006/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
|
||||
golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
|
||||
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||
golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
|
||||
golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||
golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
|
||||
golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
|
||||
@@ -486,9 +545,13 @@ golang.org/x/net v0.21.0/go.mod h1:bIjVDfnllIU7BJ2DNgfnXvpSvtn8VRwhlsaeUTyUS44=
|
||||
golang.org/x/net v0.25.0/go.mod h1:JkAGAh7GEvH74S6FOH42FLoXpXbE/aqXSrIQjXgsiwM=
|
||||
golang.org/x/net v0.44.0 h1:evd8IRDyfNBMBTTY5XRF1vaZlD+EmWx6x8PkhR04H/I=
|
||||
golang.org/x/net v0.44.0/go.mod h1:ECOoLqd5U3Lhyeyo/QDCEVQ4sNgYsqvCZ722XogGieY=
|
||||
golang.org/x/oauth2 v0.0.0-20190402181905-9f3314589c9a/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
|
||||
golang.org/x/oauth2 v0.30.0 h1:dnDm7JmhM45NNpd8FDDeLhK6FwqbOf4MLCM9zb1BOHI=
|
||||
golang.org/x/oauth2 v0.30.0/go.mod h1:B++QgG3ZKulg6sRPGD/mqlHQs5rB3Ml9erfeDY7xKlU=
|
||||
golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y=
|
||||
@@ -496,11 +559,16 @@ golang.org/x/sync v0.6.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
|
||||
golang.org/x/sync v0.7.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
|
||||
golang.org/x/sync v0.17.0 h1:l60nONMj9l5drqw6jlhIELNv9I0A4OFgRsG9k2oT9Ug=
|
||||
golang.org/x/sync v0.17.0/go.mod h1:9KTHXmSnoGruLpwFjVSX0lNNA75CykiMECbovNTZqGI=
|
||||
golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||
@@ -524,6 +592,7 @@ golang.org/x/term v0.20.0/go.mod h1:8UkIAJTvZgivsXaD6/pH6U9ecQzZ45awqEOzuCvwpFY=
|
||||
golang.org/x/term v0.35.0 h1:bZBVKBudEyhRcajGcNc3jIfWPqV4y/Kt2XcoigOWtDQ=
|
||||
golang.org/x/term v0.35.0/go.mod h1:TPGtkTLesOwf2DE8CgVYiZinHAOuy5AYUYT1lENIZnA=
|
||||
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||
golang.org/x/text v0.3.1-0.20181227161524-e6919f6577db/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
|
||||
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||
golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
|
||||
@@ -535,8 +604,12 @@ golang.org/x/text v0.15.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU=
|
||||
golang.org/x/text v0.16.0/go.mod h1:GhwF1Be+LQoKShO3cGOHzqOgRrGaYc9AvblQOmPVHnI=
|
||||
golang.org/x/text v0.29.0 h1:1neNs90w9YzJ9BocxfsQNHKuAT4pkghyXc4nhZ6sJvk=
|
||||
golang.org/x/text v0.29.0/go.mod h1:7MhJOA9CD2qZyOKYazxdYMF85OwPdEr9jTtBpO7ydH4=
|
||||
golang.org/x/time v0.0.0-20161028155119-f51c12702a4d/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||
golang.org/x/time v0.11.0 h1:/bpjEDfN9tkoN/ryeYHnv5hcMlc8ncjMcM4XBk5NWV0=
|
||||
golang.org/x/time v0.11.0/go.mod h1:CDIdPxbZBQxdj6cxyCIdrNogrJKMJ7pr37NYpMcMDSg=
|
||||
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
|
||||
golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
|
||||
golang.org/x/tools v0.1.1/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
|
||||
golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc=
|
||||
golang.org/x/tools v0.6.0/go.mod h1:Xwgl3UAJ/d3gWutnCtw505GrjyAbvKui8lOU390QaIU=
|
||||
golang.org/x/tools v0.13.0/go.mod h1:HvlwmtVNQAhOuCjW7xxvovg8wbNq7LwfXh/k7wXUl58=
|
||||
@@ -544,22 +617,39 @@ golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d/go.mod h1:aiJjzUbINMkxb
|
||||
golang.org/x/tools v0.37.0 h1:DVSRzp7FwePZW356yEAChSdNcQo6Nsp+fex1SUW09lE=
|
||||
golang.org/x/tools v0.37.0/go.mod h1:MBN5QPQtLMHVdvsbtarmTNukZDdgwdwlO5qGacAzF0w=
|
||||
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||
google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
|
||||
google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
|
||||
google.golang.org/protobuf v1.36.9 h1:w2gp2mA27hUeUzj9Ex9FBjsBm40zfaDtEWow293U7Iw=
|
||||
google.golang.org/protobuf v1.36.9/go.mod h1:fuxRtAxBytpl4zzqUh6/eyUujkJdNiuEkXntxiD/uRU=
|
||||
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20200902074654-038fdea0a05b/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk=
|
||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q=
|
||||
gopkg.in/evanphx/json-patch.v5 v5.9.11 h1:OMPeiLomOQwe8+Ku4nwXsdOmrRw2vGUpP3XgLj3ojNw=
|
||||
gopkg.in/evanphx/json-patch.v5 v5.9.11/go.mod h1:/kvTRh1TVm5wuM6OkHxqXtE/1nUZZpihg29RtuIyfvk=
|
||||
gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys=
|
||||
gopkg.in/inf.v0 v0.9.0/go.mod h1:cWUDdTG/fYaXco+Dcufb5Vnc6Gp2YChqWtbxRZE0mXw=
|
||||
gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw=
|
||||
gopkg.in/warnings.v0 v0.1.2 h1:wFXVbFY8DY5/xOe1ECiWdKCzZlxgshcYVNkBHstARME=
|
||||
gopkg.in/warnings.v0 v0.1.2/go.mod h1:jksf8JmL6Qr/oQM2OXTHunEvvTAsrWBLb6OOjuVWRNI=
|
||||
gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
|
||||
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
|
||||
gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
|
||||
gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
|
||||
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
|
||||
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
|
||||
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
|
||||
k8s.io/api v0.0.0-20190620084959-7cf5895f2711/go.mod h1:TBhBqb1AWbBQbW3XRusr7n7E4v2+5ZY8r8sAMnyFC5A=
|
||||
k8s.io/apimachinery v0.0.0-20190612205821-1799e75a0719/go.mod h1:I4A+glKBHiTgiEjQiCCQfCAIcIMFGt291SmsvcrFzJA=
|
||||
k8s.io/client-go v12.0.0+incompatible h1:YlJxncpeVUC98/WMZKC3JZGk/OXQWCZjAB4Xr3B17RY=
|
||||
k8s.io/client-go v12.0.0+incompatible/go.mod h1:E95RaSlHr79aHaX0aGSwcPNfygDiPKOVXdmivCIZT0k=
|
||||
k8s.io/klog v0.3.1/go.mod h1:Gq+BEi5rUBO/HRz0bTSXDUcqjScdoY3a9IHpCEIOOfk=
|
||||
k8s.io/kube-openapi v0.0.0-20190228160746-b3a7cee44a30/go.mod h1:BXM9ceUBTj2QnfH2MK1odQs778ajze1RxcmP6S8RVVc=
|
||||
k8s.io/utils v0.0.0-20190221042446-c2654d5206da/go.mod h1:8k8uAuAQ0rXslZKaEWd0c3oVhZz7sSzSiPnVZayjIX0=
|
||||
sigs.k8s.io/yaml v1.1.0/go.mod h1:UJmg0vDUVViEyp3mgSv9WPwZCDxu4rQW1olrI1uml+o=
|
||||
sigs.k8s.io/yaml v1.4.0 h1:Mk1wCc2gy/F0THH0TAp1QYyJNzRm2KCLy3o5ASXVI5E=
|
||||
sigs.k8s.io/yaml v1.4.0/go.mod h1:Ejl7/uTz7PSA4eKMyQCUTnhZYNmLIl+5c2lQPGR2BPY=
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
{ self, pkgs, nix-filter, nixops-lib }:
|
||||
{ self, pkgs, nix2containerPkgs, nix-filter, nixops-lib }:
|
||||
let
|
||||
name = "nixops";
|
||||
version = "0.0.0-dev";
|
||||
created = "1970-01-01T00:00:00Z";
|
||||
submodule = "${name}";
|
||||
|
||||
src = nix-filter.lib.filter {
|
||||
@@ -34,18 +35,65 @@ let
|
||||
gqlgenc
|
||||
oapi-codegen
|
||||
nhost-cli
|
||||
gofumpt
|
||||
golines
|
||||
skopeo
|
||||
postgresql_14_18-client
|
||||
postgresql_15_13-client
|
||||
postgresql_16_9-client
|
||||
postgresql_17_5-client
|
||||
postgresql_14_18
|
||||
postgresql_15_13
|
||||
postgresql_16_9
|
||||
postgresql_17_5
|
||||
sqlc
|
||||
vacuum-go
|
||||
bun
|
||||
clang
|
||||
pkg-config
|
||||
];
|
||||
|
||||
nativeBuildInputs = [ ];
|
||||
|
||||
user = "user";
|
||||
group = "user";
|
||||
uid = "1000";
|
||||
gid = "1000";
|
||||
|
||||
|
||||
l = pkgs.lib // builtins;
|
||||
|
||||
mkUser = pkgs.runCommand "mkUser" { } ''
|
||||
mkdir -p $out/etc/pam.d
|
||||
|
||||
echo "${user}:x:${uid}:${gid}::" > $out/etc/passwd
|
||||
echo "${user}:!x:::::::" > $out/etc/shadow
|
||||
|
||||
echo "${group}:x:${gid}:" > $out/etc/group
|
||||
echo "${group}:x::" > $out/etc/gshadow
|
||||
|
||||
cat > $out/etc/pam.d/other <<EOF
|
||||
account sufficient pam_unix.so
|
||||
auth sufficient pam_rootok.so
|
||||
password requisite pam_unix.so nullok sha512
|
||||
session required pam_unix.so
|
||||
EOF
|
||||
|
||||
touch $out/etc/login.defs
|
||||
mkdir -p $out/home/${user}
|
||||
'';
|
||||
|
||||
tmpFolder = (pkgs.writeTextFile {
|
||||
name = "tmp-file";
|
||||
text = ''
|
||||
dummy file to generate tmpdir
|
||||
'';
|
||||
destination = "/tmp/tmp-file";
|
||||
});
|
||||
|
||||
nixConfig = pkgs.writeTextFile {
|
||||
name = "nix-config";
|
||||
text = ''
|
||||
sandbox = false
|
||||
sandbox-fallback = false
|
||||
experimental-features = nix-command flakes
|
||||
trusted-users = root ${user}
|
||||
'';
|
||||
destination = "/etc/nix/nix.conf";
|
||||
};
|
||||
in
|
||||
{
|
||||
check = nixops-lib.nix.check { inherit src; };
|
||||
@@ -66,5 +114,78 @@ in
|
||||
cp -r ${src} $out/
|
||||
'';
|
||||
};
|
||||
}
|
||||
|
||||
dockerImage = pkgs.runCommand "image-as-dir" { } ''
|
||||
${(nix2containerPkgs.nix2container.buildImage {
|
||||
inherit name created;
|
||||
tag = version;
|
||||
maxLayers = 100;
|
||||
|
||||
initializeNixDatabase = true;
|
||||
nixUid = l.toInt uid;
|
||||
nixGid = l.toInt gid;
|
||||
|
||||
copyToRoot = [
|
||||
(pkgs.buildEnv {
|
||||
name = "image";
|
||||
paths = [
|
||||
(pkgs.buildEnv {
|
||||
name = "root";
|
||||
paths = with pkgs; [
|
||||
coreutils
|
||||
nix
|
||||
bash
|
||||
gnugrep
|
||||
gnumake
|
||||
];
|
||||
pathsToLink = "/bin";
|
||||
})
|
||||
];
|
||||
})
|
||||
nixConfig
|
||||
tmpFolder
|
||||
mkUser
|
||||
];
|
||||
|
||||
perms = [
|
||||
{
|
||||
path = mkUser;
|
||||
regex = "/home/${user}";
|
||||
mode = "0744";
|
||||
uid = l.toInt uid;
|
||||
gid = l.toInt gid;
|
||||
uname = user;
|
||||
gname = group;
|
||||
}
|
||||
{
|
||||
path = tmpFolder;
|
||||
regex = "/tmp";
|
||||
mode = "0777";
|
||||
uid = l.toInt uid;
|
||||
gid = l.toInt gid;
|
||||
uname = user;
|
||||
gname = group;
|
||||
}
|
||||
];
|
||||
|
||||
config = {
|
||||
User = "user";
|
||||
WorkingDir = "/home/user";
|
||||
Env = [
|
||||
"NIX_PAGER=cat"
|
||||
"USER=nobody"
|
||||
"HOME=/home/user"
|
||||
"TMPDIR=/tmp"
|
||||
"SSL_CERT_FILE=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt"
|
||||
];
|
||||
};
|
||||
|
||||
layers = [
|
||||
(nix2containerPkgs.nix2container.buildLayer {
|
||||
deps = buildInputs;
|
||||
})
|
||||
];
|
||||
|
||||
}).copyTo}/bin/copy-to dir:$out
|
||||
'';
|
||||
}
|
||||
|
||||
77
packages/nhost-js/CONTRIBUTING.md
Normal file
77
packages/nhost-js/CONTRIBUTING.md
Normal file
@@ -0,0 +1,77 @@
|
||||
# Developer Guide
|
||||
|
||||
## Requirements
|
||||
|
||||
We use nix to manage the development environment, the build process and for running tests.
|
||||
|
||||
### With Nix (Recommended)
|
||||
|
||||
Run `nix develop \#nhost-js` to get a complete development environment.
|
||||
|
||||
### Without Nix
|
||||
|
||||
Check `project.nix` (checkDeps, buildInputs, buildNativeInputs) for manual dependency installation. Alternatively, you can run `make nixops-container-env` in the root of the repository to enter a Docker container with nix and all dependencies pre-installed (note it is a large image).
|
||||
|
||||
## Development Workflow
|
||||
|
||||
### Running Tests
|
||||
|
||||
**With Nix:**
|
||||
```bash
|
||||
make dev-env-up
|
||||
make check
|
||||
```
|
||||
|
||||
**Without Nix:**
|
||||
```bash
|
||||
make dev-env-up
|
||||
|
||||
pnpm install
|
||||
|
||||
pnpm test
|
||||
```
|
||||
|
||||
### Formatting
|
||||
|
||||
Format code before committing:
|
||||
```bash
|
||||
pnpm format
|
||||
```
|
||||
|
||||
### Code Generation
|
||||
|
||||
Generate TypeScript clients from OpenAPI specs:
|
||||
|
||||
```bash
|
||||
pnpm generate
|
||||
```
|
||||
|
||||
This runs `./gen.sh` which generates code from:
|
||||
- `services/auth/docs/openapi.yaml` - Auth service API
|
||||
- `services/storage/controller/openapi.yaml` - Storage service API
|
||||
|
||||
## Building
|
||||
|
||||
### Build for Distribution
|
||||
|
||||
```bash
|
||||
pnpm build
|
||||
```
|
||||
|
||||
This produces:
|
||||
- TypeScript type definitions
|
||||
- ESM bundles (`.es.js`)
|
||||
- CommonJS bundles (`.cjs.js`)
|
||||
- UMD bundles for browser usage
|
||||
|
||||
Output is placed in the `dist/` directory.
|
||||
|
||||
## Development Notes
|
||||
|
||||
### Code Generation
|
||||
|
||||
The code generation script (`gen.sh`) reads OpenAPI specifications from the auth and storage services and generates TypeScript clients. Always regenerate after API changes.
|
||||
|
||||
### Dependencies
|
||||
|
||||
This package has minimal runtime dependencies to keep bundle size small. Only `tslib` is included as a production dependency.
|
||||
File diff suppressed because it is too large
Load Diff
@@ -3,14 +3,14 @@
|
||||
set -e
|
||||
|
||||
codegen gen \
|
||||
--openapi-file ./api/auth.yaml \
|
||||
--openapi-file ../../services/auth/docs/openapi.yaml \
|
||||
--output-file ./src/auth/client.ts \
|
||||
--plugin typescript
|
||||
|
||||
pnpm prettier -w ./src/auth/client.ts
|
||||
|
||||
codegen gen \
|
||||
--openapi-file ./api/storage.yaml \
|
||||
--openapi-file ../../services/storage/controller/openapi.yaml \
|
||||
--output-file ./src/storage/client.ts \
|
||||
--plugin typescript
|
||||
|
||||
|
||||
@@ -43,8 +43,9 @@ let
|
||||
"${submodule}/tsconfig.json"
|
||||
"${submodule}/vite.config.ts"
|
||||
"${submodule}/vite.umd.config.ts"
|
||||
(inDirectory "${submodule}/api")
|
||||
(inDirectory "${submodule}/src")
|
||||
../../services/auth/docs/openapi.yaml
|
||||
../../services/storage/controller/openapi.yaml
|
||||
];
|
||||
};
|
||||
|
||||
|
||||
@@ -1490,6 +1490,7 @@ export type SignInProvider =
|
||||
| "bitbucket"
|
||||
| "workos"
|
||||
| "azuread"
|
||||
| "entraid"
|
||||
| "strava"
|
||||
| "facebook"
|
||||
| "windowslive"
|
||||
|
||||
29
services/auth/.env.example
Normal file
29
services/auth/.env.example
Normal file
@@ -0,0 +1,29 @@
|
||||
NODE_ENV=development
|
||||
AUTH_API_PREFIX=""
|
||||
HASURA_GRAPHQL_DATABASE_URL="postgres://postgres:postgres@127.0.0.1:5432/local"
|
||||
HASURA_GRAPHQL_JWT_SECRET='{"type":"HS256", "key":"5152fa850c02dc222631cca898ed1485821a70912a6e3649c49076912daa3b62182ba013315915d64f40cddfbb8b58eb5bd11ba225336a6af45bbae07ca873f3","issuer":"hasura-auth"}'
|
||||
# HASURA_GRAPHQL_JWT_SECRET='{"type":"RS256", "key":"-----BEGIN PUBLIC KEY-----\nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA0M9zJVMJV8TgNPT9p737\nKR1XyWL9PSePXdcyk9aWcusG/m2OGsvuAgbMuDQx+Pns9PH9hd1kl53yfpTXOp3T\n13Uqox3IuHMlx8JyS+raqURSAew8/RkQ8nq+68XBBr9atDvVcSknS+jtZGH6Du1V\ntUy7Sz8VTVQuXDURF1Aa2wwNkRkC/wg5X0BXfN4Felh+mpK05PZbqJcRA5dbDlWk\n5nkdKbCG3urmtfF8brh6SlV7xBODJbqQws6E9WTclDQXWjmjcVNVSJE7OblZj1JB\nNGMN9rjUSS1kiRozhMtSlRv9MHAsz3e05MnvbyMWtoRpH8iLs0jmf8uucEBkMS/6\nBQIDAQAB\n-----END PUBLIC KEY-----","signing_key":"-----BEGIN PRIVATE KEY-----\nMIIEvwIBADANBgkqhkiG9w0BAQEFAASCBKkwggSlAgEAAoIBAQDQz3MlUwlXxOA0\n9P2nvfspHVfJYv09J49d1zKT1pZy6wb+bY4ay+4CBsy4NDH4+ez08f2F3WSXnfJ+\nlNc6ndPXdSqjHci4cyXHwnJL6tqpRFIB7Dz9GRDyer7rxcEGv1q0O9VxKSdL6O1k\nYfoO7VW1TLtLPxVNVC5cNREXUBrbDA2RGQL/CDlfQFd83gV6WH6akrTk9luolxED\nl1sOVaTmeR0psIbe6ua18XxuuHpKVXvEE4MlupDCzoT1ZNyUNBdaOaNxU1VIkTs5\nuVmPUkE0Yw32uNRJLWSJGjOEy1KVG/0wcCzPd7Tkye9vIxa2hGkfyIuzSOZ/y65w\nQGQxL/oFAgMBAAECggEBAKO3g1hoWpLuUbwzug2i7yG1V/cWHees9MNmzskLHrrL\ne5hQ3XI1Ik+EdU6X3faQPjFu6o/indQiitakbHwQ8t+jheKOn6m+3ohY9LSBVyAP\n6RyI1Oi8loUHqFnDmyxnK/7USu2GjsD9x+NEzoKVovWbS94bf+A5eH/jO5tDu0qy\nJMoe2jLx5IQQwLuvmQ+5ccZOUSQLG4/9Bw7g4xdroSvyVH27g9hqmEuY2orhcMm3\nlvlAx3PIH/kjKtpnP6MIBDhznlJ/VqAHhT/zC9xIwohyVGymoyDhdNSpn5N2QmWK\nKsneTdYdWz/oMB+HtcmvSoI4saEv1tlGEOTTINyBpwECgYEA+vrMFKhIoS3EbNiS\n5mSw/ejHl+60hsORGahPaYoXDfbDr2lyG58OfGu+l0qIe5SX4ueHo+ydhN70GR4l\nrtX9R+8uV9hb4B9e/hTZZnnAyFZrZSPfx4ZtPeyAlL+zhIGwxTy4BrbuxgynGict\nu+7XgbOYesDGRCvc4/1HKOgnf9kCgYEA1Py22UkY1iQQ4JNkfI1U6XqrydlMy1BG\nYSglI37UkVGUWG1hry+HCdhxHupBeUspZ/4vzKCLO1A1RlkCi9+TcOpY8UBqo1uq\nBaBPSlWD7T4oTOEPvANqT43SJ+RFkjtfVvDDtXBImO0+Nu57FmD6pMZJtvsxFkQB\nZKP6Mx3Q3A0CgYEAmGQJ4I0htIQmnXSPFceT1EgwUOdGxAEhLHQO6+VGBFuODAc5\nmt3kHNYLHq/J2UerRcIRkQ4NwuzhSBMPDG6wYKow+HPNrXM+6YXdTySkUsBuazXy\nHaNY112v4SHZLZ7Vp50rnCAdMTHjkLSzR0ZJol5bOkWs3R3I/MIAIC1+NlkCgYEA\n0kevP1er7cAt6Yub6lyfOOSkNuUTrKfU1JeOEz1lIRQqIiPcDdoeuNm41Yzyl45d\nkw6ioqTe0fCeqJW4reBO8Wxt48J1hlM5ydQ8dGd5mQGFSGHr5vR4QZMDqd710SpN\nNsj+cGQrSNDyW8mYPMACtiwPG1llXVZHCdXbcBw/2QECgYABLllfHVarmMwKTLWo\n8rRdEsIwcD/VxOxG4BxL6rZNQ4ADd8pL+9TohZeWp8wvlDGU7yB9wgyaD62Mhyog\nAGJt5Y/twAPTiVEi+0jVCXraLwPZpQFafw7p/x33eHkhwOTqlwlkRNlvrVk6A29I\nU0PVQZdMwEj/CPZVeCJ4DX63qQ==\n-----END PRIVATE KEY-----","issuer":"hasura-auth"}'
|
||||
HASURA_GRAPHQL_ADMIN_SECRET=nhost-admin-secret
|
||||
HASURA_GRAPHQL_GRAPHQL_URL=http://127.0.0.1:8080/v1/graphql
|
||||
AUTH_PORT=4000
|
||||
AUTH_SERVER_URL=http://127.0.0.2:4000
|
||||
AUTH_USER_DEFAULT_ALLOWED_ROLES='me,user,editor'
|
||||
AUTH_SMTP_AUTH_METHOD=PLAIN
|
||||
AUTH_SMTP_HOST=127.0.0.1
|
||||
AUTH_SMTP_PASS=password
|
||||
AUTH_SMTP_PORT="1025"
|
||||
AUTH_SMTP_SECURE="false"
|
||||
AUTH_SMTP_SENDER=hasura-auth@example.com
|
||||
AUTH_SMTP_USER=user
|
||||
AUTH_LOG_LEVEL=debug
|
||||
AUTH_CLIENT_URL='http://127.0.0.1:3000'
|
||||
# SMS configuration
|
||||
# AUTH_SMS_PASSWORDLESS_ENABLED=false
|
||||
# AUTH_SMS_PROVIDER=twilio
|
||||
# Twilio SMS settings
|
||||
# AUTH_SMS_TWILIO_ACCOUNT_SID=
|
||||
# AUTH_SMS_TWILIO_AUTH_TOKEN=
|
||||
# AUTH_SMS_TWILIO_MESSAGING_SERVICE_ID=
|
||||
# Modica Group SMS settings
|
||||
# AUTH_SMS_MODICA_USERNAME=
|
||||
# AUTH_SMS_MODICA_PASSWORD=
|
||||
13
services/auth/CHANGELOG.md
Normal file
13
services/auth/CHANGELOG.md
Normal file
@@ -0,0 +1,13 @@
|
||||
# Changelog
|
||||
|
||||
All notable changes to this project will be documented in this file.
|
||||
|
||||
## [auth@0.42.2] - 2025-10-13
|
||||
|
||||
### ⚙️ Miscellaneous Tasks
|
||||
|
||||
- *(docs)* Udpated README.md and CONTRIBUTING.md (#3587)
|
||||
- *(auth)* Add wget to docker image (#3601)
|
||||
|
||||
|
||||
For previous versions, please see the [old releases page](https://github.com/nhost/hasura-auth/releases).
|
||||
424
services/auth/CLAUDE.md
Normal file
424
services/auth/CLAUDE.md
Normal file
@@ -0,0 +1,424 @@
|
||||
# Nhost Hasura Auth - Go Development Guide
|
||||
|
||||
This document contains patterns, conventions, and workflows for implementing new endpoints and features in the Nhost Hasura Auth Go codebase.
|
||||
|
||||
## Core Principles
|
||||
|
||||
- **Always write tests** for endpoints and new use cases in existing endpoints
|
||||
- **Follow existing patterns** - use other implementations as examples
|
||||
- **Security first** - never expose secrets, always validate inputs, follow auth patterns
|
||||
- **Database safety** - use transactions where appropriate, handle errors gracefully
|
||||
|
||||
## Directory Structure
|
||||
|
||||
```
|
||||
go/
|
||||
├── api/ # OpenAPI specs and generated types
|
||||
│ ├── server.cfg.yaml # oapi-codegen server generation config
|
||||
│ ├── types.cfg.yaml # oapi-codegen types generation config
|
||||
│ ├── server.gen.go # Generated server code
|
||||
│ └── types.gen.go # Generated types
|
||||
├── controller/ # HTTP handlers and business logic
|
||||
│ ├── sign_in_*.go # Endpoint handlers (following naming pattern)
|
||||
│ ├── *_test.go # Tests
|
||||
│ ├── workflows.go # Business logic workflows
|
||||
│ ├── errors.go # Error definitions and handling
|
||||
│ ├── controller.go # Main controller and interfaces
|
||||
│ └── mock/ # Generated mocks
|
||||
├── sql/ # Database layer
|
||||
│ ├── query.sql # SQL queries
|
||||
│ ├── query.sql.go # Generated Go code
|
||||
│ ├── sqlc.yaml # sqlc configuration
|
||||
│ └── models.go # Database models
|
||||
└── middleware/ # HTTP middleware
|
||||
```
|
||||
|
||||
## Implementing New Endpoints
|
||||
|
||||
### 1. API Specification (OpenAPI)
|
||||
|
||||
Add endpoint definition to `docs/openapi.yaml`:
|
||||
|
||||
```yaml
|
||||
paths:
|
||||
/your-endpoint:
|
||||
post:
|
||||
summary: Description of what this does
|
||||
tags:
|
||||
- authentication # Use existing tags: authentication, security, session, user, system, verification
|
||||
security:
|
||||
- BearerAuth: [] # For authenticated endpoints
|
||||
- {} # For optional auth
|
||||
requestBody:
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/YourRequest'
|
||||
required: true
|
||||
responses:
|
||||
'200':
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/YourResponse'
|
||||
description: Success description
|
||||
'401':
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/ErrorResponse'
|
||||
description: Error description
|
||||
|
||||
components:
|
||||
schemas:
|
||||
YourRequest:
|
||||
type: object
|
||||
additionalProperties: false
|
||||
properties:
|
||||
field:
|
||||
type: string
|
||||
description: Field description
|
||||
required:
|
||||
- field
|
||||
```
|
||||
|
||||
**Important**:
|
||||
- Use `additionalProperties: false` for strict validation
|
||||
- Add proper descriptions and examples
|
||||
- Define all possible response codes
|
||||
- Use existing error response schemas
|
||||
|
||||
### 2. SQL Queries
|
||||
|
||||
Add database queries to `go/sql/query.sql`:
|
||||
|
||||
```sql
|
||||
-- name: YourQueryName :one/:many/:exec
|
||||
SELECT/UPDATE/DELETE/INSERT ...
|
||||
WHERE condition = $1;
|
||||
```
|
||||
|
||||
**Query naming conventions**:
|
||||
- `:one` - returns single row
|
||||
- `:many` - returns multiple rows
|
||||
- `:exec` - no return value (INSERT/UPDATE/DELETE)
|
||||
- Use descriptive names like `GetUserByRefreshTokenHash`
|
||||
|
||||
### 3. Controller Implementation
|
||||
|
||||
Create `go/controller/your_endpoint.go`:
|
||||
|
||||
```go
|
||||
package controller
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"github.com/nhost/nhost/services/auth/go/api"
|
||||
"github.com/nhost/nhost/services/auth/go/middleware"
|
||||
)
|
||||
|
||||
func (ctrl *Controller) YourEndpoint( //nolint:ireturn
|
||||
ctx context.Context, request api.YourEndpointRequestObject,
|
||||
) (api.YourEndpointResponseObject, error) {
|
||||
logger := middleware.LoggerFromContext(ctx)
|
||||
|
||||
// Validate inputs
|
||||
if apiErr := ctrl.wf.ValidateInput(request.Body.Field, logger); apiErr != nil {
|
||||
return ctrl.respondWithError(apiErr), nil
|
||||
}
|
||||
|
||||
// Get authenticated user if needed
|
||||
user, apiErr := ctrl.wf.GetUserFromJWTInContext(ctx, logger)
|
||||
if apiErr != nil {
|
||||
return ctrl.sendError(ErrUnauthenticatedUser), nil
|
||||
}
|
||||
|
||||
// Business logic
|
||||
result, apiErr := ctrl.wf.DoSomething(ctx, user.ID, request.Body.Field, logger)
|
||||
if apiErr != nil {
|
||||
return ctrl.respondWithError(apiErr), nil
|
||||
}
|
||||
|
||||
return api.YourEndpoint200JSONResponse(*result), nil
|
||||
}
|
||||
```
|
||||
|
||||
**Controller patterns**:
|
||||
- Always get logger from context: `middleware.LoggerFromContext(ctx)`
|
||||
- Use workflows for business logic, not direct DB calls
|
||||
- Handle errors with `ctrl.respondWithError(apiErr)` or `ctrl.sendError(ErrType)`
|
||||
- Return appropriate HTTP status codes via generated response types
|
||||
|
||||
### 4. Workflow Methods
|
||||
|
||||
Add business logic to `go/controller/workflows.go`:
|
||||
|
||||
```go
|
||||
func (wf *Workflows) DoSomething(
|
||||
ctx context.Context,
|
||||
userID uuid.UUID,
|
||||
input string,
|
||||
logger *slog.Logger,
|
||||
) (*Result, *APIError) {
|
||||
// Validate business rules
|
||||
if !wf.ValidateBusinessRule(input) {
|
||||
logger.WarnContext(ctx, "business rule validation failed")
|
||||
return nil, ErrInvalidRequest
|
||||
}
|
||||
|
||||
// Database operations
|
||||
result, err := wf.db.YourQuery(ctx, sql.YourQueryParams{
|
||||
UserID: userID,
|
||||
Input: pgtype.Text{String: input, Valid: true},
|
||||
})
|
||||
if errors.Is(err, pgx.ErrNoRows) {
|
||||
logger.WarnContext(ctx, "resource not found")
|
||||
return nil, ErrNotFound
|
||||
}
|
||||
if err != nil {
|
||||
logger.ErrorContext(ctx, "database error", logError(err))
|
||||
return nil, ErrInternalServerError
|
||||
}
|
||||
|
||||
return &result, nil
|
||||
}
|
||||
```
|
||||
|
||||
**Workflow patterns**:
|
||||
- Take context, relevant IDs, inputs, and logger as parameters
|
||||
- Return result and `*APIError` (not Go error)
|
||||
- Log warnings for user errors, errors for system errors
|
||||
- Use `pgtype.Text{String: value, Valid: true}` for nullable text fields or `sql.Text(value)` helper
|
||||
- Handle `pgx.ErrNoRows` specifically for not found cases
|
||||
|
||||
### 5. Error Handling
|
||||
|
||||
Add errors to `go/controller/errors.go` if needed:
|
||||
|
||||
```go
|
||||
var (
|
||||
ErrYourSpecificError = &APIError{api.YourErrorType}
|
||||
)
|
||||
```
|
||||
|
||||
**Error patterns**:
|
||||
- Use existing error types when possible (`ErrInvalidRequest`, `ErrInternalServerError`, etc.)
|
||||
- Map to appropriate HTTP status codes
|
||||
- Provide meaningful error messages
|
||||
- Never expose internal system details
|
||||
|
||||
### 6. Database Interface
|
||||
|
||||
If adding new database methods, update `go/controller/controller.go`:
|
||||
|
||||
```go
|
||||
type DBClient interface {
|
||||
// ... existing composed interfaces
|
||||
YourNewMethod(ctx context.Context, params YourParams) (YourResult, error)
|
||||
}
|
||||
```
|
||||
|
||||
### 7. Testing
|
||||
|
||||
Create `go/controller/your_endpoint_test.go`:
|
||||
|
||||
```go
|
||||
package controller_test
|
||||
|
||||
import (
|
||||
"context"
|
||||
"testing"
|
||||
|
||||
"github.com/google/go-cmp/cmp"
|
||||
"github.com/google/uuid"
|
||||
"github.com/nhost/nhost/services/auth/go/api"
|
||||
"github.com/nhost/nhost/services/auth/go/controller"
|
||||
"github.com/nhost/nhost/services/auth/go/controller/mock"
|
||||
"go.uber.org/mock/gomock"
|
||||
)
|
||||
|
||||
func TestYourEndpoint(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
userID := uuid.MustParse("db477732-48fa-4289-b694-2886a646b6eb")
|
||||
|
||||
cases := []testRequest[api.YourEndpointRequestObject, api.YourEndpointResponseObject]{
|
||||
{
|
||||
name: "success case",
|
||||
config: getConfig,
|
||||
db: func(ctrl *gomock.Controller) controller.DBClient {
|
||||
mock := mock.NewMockDBClient(ctrl)
|
||||
|
||||
mock.EXPECT().YourQuery(
|
||||
gomock.Any(),
|
||||
gomock.Any(),
|
||||
).Return(expectedResult, nil)
|
||||
|
||||
return mock
|
||||
},
|
||||
request: api.YourEndpointRequestObject{
|
||||
Body: &api.YourRequest{
|
||||
Field: "test-value",
|
||||
},
|
||||
},
|
||||
expectedResponse: api.YourEndpoint200JSONResponse(expectedResponse),
|
||||
expectedJWT: nil,
|
||||
jwtTokenFn: nil,
|
||||
getControllerOpts: []getControllerOptsFunc{},
|
||||
},
|
||||
// Add error cases, edge cases, etc.
|
||||
}
|
||||
|
||||
for _, tc := range cases {
|
||||
t.Run(tc.name, func(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
ctrl := gomock.NewController(t)
|
||||
defer ctrl.Finish()
|
||||
|
||||
c, _ := getController(t, ctrl, tc.config, tc.db, tc.getControllerOpts...)
|
||||
|
||||
resp, err := c.YourEndpoint(context.Background(), tc.request)
|
||||
if err != nil {
|
||||
t.Fatalf("unexpected error: %v", err)
|
||||
}
|
||||
|
||||
if diff := cmp.Diff(tc.expectedResponse, resp); diff != "" {
|
||||
t.Errorf("unexpected response (-want +got):\n%s", diff)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Testing patterns**:
|
||||
- Use `testRequest` struct for consistent test structure
|
||||
- Test success cases, error cases, edge cases, and validation
|
||||
- Use `gomock.NewController(t)` and `defer ctrl.Finish()`
|
||||
- Use `cmp.Diff` for response comparison
|
||||
- Use `getSigninUser(userID)` helper for authenticated user scenarios
|
||||
|
||||
## Code Generation
|
||||
|
||||
After making changes, always run:
|
||||
|
||||
```bash
|
||||
go generate ./...
|
||||
```
|
||||
|
||||
This generates:
|
||||
- API server code from OpenAPI spec (`api/server.gen.go`, `api/types.gen.go`)
|
||||
- SQL client code from queries (`sql/query.sql.go`)
|
||||
- Mocks from interfaces (`controller/mock/`)
|
||||
|
||||
**Generation directives**:
|
||||
- OpenAPI: `//go:generate oapi-codegen -config go/api/server.cfg.yaml docs/openapi.yaml`
|
||||
- Mocks: `//go:generate mockgen -package mock -destination mock/controller.go --source=controller.go`
|
||||
|
||||
## Authentication Patterns
|
||||
|
||||
### JWT Authentication
|
||||
|
||||
```go
|
||||
// Get authenticated user
|
||||
user, apiErr := ctrl.wf.GetUserFromJWTInContext(ctx, logger)
|
||||
if apiErr != nil {
|
||||
return ctrl.sendError(ErrUnauthenticatedUser), nil
|
||||
}
|
||||
```
|
||||
|
||||
### Optional Authentication
|
||||
|
||||
```go
|
||||
// Optional auth - proceed with or without user
|
||||
user, _ := ctrl.wf.GetUserFromJWTInContext(ctx, logger)
|
||||
// user will be empty if not authenticated
|
||||
```
|
||||
|
||||
### Refresh Token Operations
|
||||
|
||||
```go
|
||||
// Hash refresh tokens before database operations
|
||||
hashedToken := hashRefreshToken([]byte(refreshToken))
|
||||
|
||||
// Use proper pgtype for database parameters
|
||||
pgtype.Text{String: hashedToken, Valid: true}
|
||||
// Or use helper
|
||||
sql.Text(hashedToken)
|
||||
```
|
||||
|
||||
## Security Best Practices
|
||||
|
||||
1. **Input Validation**: Always validate inputs at the workflow level
|
||||
2. **Authorization**: Check user permissions before operations
|
||||
3. **Token Handling**: Always hash tokens before storage/comparison
|
||||
4. **Error Messages**: Don't expose sensitive information in errors
|
||||
5. **Logging**: Log security events appropriately (warn for user errors, error for system issues)
|
||||
|
||||
## Database Best Practices
|
||||
|
||||
1. **Use Transactions**: For multi-step operations
|
||||
2. **Handle NULL**: Use `pgtype.Text` for nullable fields or `sql.Text()` helper
|
||||
3. **Error Handling**: Always check for `pgx.ErrNoRows`
|
||||
4. **Parameterized Queries**: Never build SQL strings dynamically
|
||||
5. **Naming**: Use descriptive query names following existing patterns
|
||||
|
||||
## Common Patterns
|
||||
|
||||
### Refresh Token Deletion
|
||||
|
||||
```go
|
||||
// Single token
|
||||
wf.db.DeleteRefreshToken(ctx, pgtype.Text{String: hashedToken, Valid: true})
|
||||
|
||||
// All user tokens
|
||||
wf.db.DeleteRefreshTokens(ctx, userID)
|
||||
```
|
||||
|
||||
### User Validation
|
||||
|
||||
```go
|
||||
if apiErr := wf.ValidateUser(user, logger); apiErr != nil {
|
||||
return user, apiErr
|
||||
}
|
||||
```
|
||||
|
||||
### Error Response
|
||||
|
||||
```go
|
||||
// For client errors (400-level)
|
||||
return ctrl.sendError(ErrInvalidRequest), nil
|
||||
|
||||
// For server errors (500-level)
|
||||
return ctrl.respondWithError(apiErr), nil
|
||||
```
|
||||
|
||||
## Development Workflow
|
||||
|
||||
1. **Design**: Plan the endpoint, request/response, and database changes
|
||||
2. **OpenAPI**: Define the API specification
|
||||
3. **SQL**: Add required database queries
|
||||
4. **Generate**: Run `go generate ./...`
|
||||
5. **Implement**: Write controller and workflow code
|
||||
6. **Test**: Write comprehensive tests
|
||||
7. **Format**: Run `golines -w --base-formatter=gofumpt .`
|
||||
8. **Lint**: Run `golangci-lint run --fix`
|
||||
9. **Test**: Run `go test -v ./...`
|
||||
|
||||
## Lint and Tests
|
||||
|
||||
- **Formatter**: `golines -w --base-formatter=gofumpt .`
|
||||
- **Linter**: `golangci-lint run --fix`
|
||||
- **Tests**: `go test -v ./...`
|
||||
- **Coverage**: `go test -v -cover ./...`
|
||||
|
||||
## Additional Notes
|
||||
|
||||
When implementing new features:
|
||||
1. Review existing similar implementations for business logic patterns
|
||||
2. Identify required database operations and add appropriate queries
|
||||
3. Follow established validation patterns in workflows
|
||||
4. Ensure error codes match existing API conventions
|
||||
5. Test authentication flows thoroughly
|
||||
6. Verify response formats match API specifications
|
||||
84
services/auth/CONTRIBUTING.md
Normal file
84
services/auth/CONTRIBUTING.md
Normal file
@@ -0,0 +1,84 @@
|
||||
# Developer Guide
|
||||
|
||||
## Requirements
|
||||
|
||||
We use nix to manage the development environment, the build process and for running tests.
|
||||
|
||||
### With Nix (Recommended)
|
||||
|
||||
Run `nix develop \#auth` to get a complete development environment.
|
||||
|
||||
### Without Nix
|
||||
|
||||
Check `project.nix` (checkDeps, buildInputs, buildNativeInputs) for manual dependency installation. Alternatively, you can run `make nixops-container-env` in the root of the repository to enter a Docker container with nix and all dependencies pre-installed (note it is a large image).
|
||||
|
||||
## Development Workflow
|
||||
|
||||
### Running Tests
|
||||
|
||||
**With Nix:**
|
||||
```bash
|
||||
make dev-env-up
|
||||
make check
|
||||
```
|
||||
|
||||
**Without Nix:**
|
||||
```bash
|
||||
# Start development environment
|
||||
make dev-env-up
|
||||
|
||||
# Lint OpenAPI spec
|
||||
vacuum lint \
|
||||
-dqb -n info \
|
||||
--ruleset vacuum.yaml \
|
||||
docs/openapi.yaml
|
||||
|
||||
# Generate code
|
||||
go generate ./...
|
||||
|
||||
# Lint Go code
|
||||
golangci-lint run ./...
|
||||
|
||||
# Run tests
|
||||
go test -v ./...
|
||||
|
||||
# Run e2e tests
|
||||
bun install
|
||||
bun test
|
||||
```
|
||||
|
||||
### Formatting
|
||||
|
||||
Format code before committing:
|
||||
```bash
|
||||
golines -w --base-formatter=gofumpt .
|
||||
```
|
||||
|
||||
## Building
|
||||
|
||||
### Local Build
|
||||
|
||||
Build the project (output in `./result`):
|
||||
```bash
|
||||
make build
|
||||
```
|
||||
|
||||
### Docker Image
|
||||
|
||||
Build and import Docker image with skopeo:
|
||||
```bash
|
||||
make build-docker-image
|
||||
```
|
||||
|
||||
If you run the command above inside the dockerized nixops-container-env and you get an error like:
|
||||
|
||||
```
|
||||
FATA[0000] writing blob: io: read/write on closed pipe
|
||||
```
|
||||
|
||||
then you need to run the following command outside of the container (needs skopeo installed on the host):
|
||||
|
||||
```bash
|
||||
cd cli
|
||||
make build-docker-image-import-bare
|
||||
```
|
||||
24
services/auth/Makefile
Normal file
24
services/auth/Makefile
Normal file
@@ -0,0 +1,24 @@
|
||||
ROOT_DIR?=$(abspath ../..)
|
||||
include $(ROOT_DIR)/build/makefiles/general.makefile
|
||||
|
||||
DOCKER_DEV_ENV_PATH=build/dev/docker
|
||||
|
||||
|
||||
.PHONY: _dev-env-up
|
||||
_dev-env-up:
|
||||
docker compose -f ${DOCKER_DEV_ENV_PATH}/docker-compose.yaml up -d
|
||||
|
||||
|
||||
.PHONY: _dev-env-down
|
||||
_dev-env-down:
|
||||
docker compose -f ${DOCKER_DEV_ENV_PATH}/docker-compose.yaml down --volumes
|
||||
|
||||
|
||||
.PHONY: _dev-env-build
|
||||
_dev-env-build: build-docker-image
|
||||
docker compose -f ${DOCKER_DEV_ENV_PATH}/docker-compose.yaml build
|
||||
|
||||
|
||||
.PHONY: dev-env-up-short
|
||||
dev-env-up-short: ## Starts development environment without auth
|
||||
docker compose -f ${DOCKER_DEV_ENV_PATH}/docker-compose.yaml up -d postgres graphql mailhog memcached
|
||||
26
services/auth/README.md
Normal file
26
services/auth/README.md
Normal file
@@ -0,0 +1,26 @@
|
||||
# Auth
|
||||
|
||||
## Core Features
|
||||
|
||||
- 🧑🤝🧑 Users are stored in Postgres and accessed via GraphQL
|
||||
- 🔑 Multiple sign-in methods.
|
||||
- ✨ Integrates with GraphQL and Hasura Permissions
|
||||
- 🔐 JWT tokens and Refresh Tokens.
|
||||
- ✉️ Emails sent on various operations
|
||||
- ✅ Optional checking for Pwned Passwords.
|
||||
|
||||
## Sign in methods
|
||||
|
||||
- **Email and Password** - simple email and password method.
|
||||
- **Email** - also called **passwordless email** or **magic link**.
|
||||
- **SMS** - also called **passwordless sms**.
|
||||
- **Anonymous** - sign in users without any method. Anonymous users can be
|
||||
converted to _regular_ users.
|
||||
- **OAuth providers**: Facebook, Google, GitHub, Twitter, Apple, Azure AD, LinkedIn, Windows Live, Spotify, Strava, GitLab, BitBucket, Discord, WorkOS.
|
||||
- **Security keys with WebAuthn**
|
||||
- Others...
|
||||
|
||||
## Documentation
|
||||
|
||||
- [Official Documentation](https://docs.nhost.io/products/auth/overview).
|
||||
- [OpenAPI schema](https://docs.nhost.io/reference/auth/get--well-known-jwks-json)
|
||||
174
services/auth/build/dev/docker/docker-compose.yaml
Normal file
174
services/auth/build/dev/docker/docker-compose.yaml
Normal file
@@ -0,0 +1,174 @@
|
||||
services:
|
||||
auth:
|
||||
image: auth:0.0.0-dev
|
||||
# image: nhost/auth:0.44.0
|
||||
command: serve
|
||||
depends_on:
|
||||
graphql:
|
||||
condition: service_healthy
|
||||
postgres:
|
||||
condition: service_healthy
|
||||
ports:
|
||||
- mode: ingress
|
||||
target: 4000
|
||||
published: "4000"
|
||||
protocol: tcp
|
||||
environment:
|
||||
AUTH_ENABLE_CHANGE_ENV: "true"
|
||||
AUTH_API_PREFIX: ""
|
||||
HASURA_GRAPHQL_DATABASE_URL: "postgres://postgres:postgres@postgres:5432/local?sslmode=disable"
|
||||
HASURA_GRAPHQL_JWT_SECRET: '{"type":"HS256", "key":"5152fa850c02dc222631cca898ed1485821a70912a6e3649c49076912daa3b62182ba013315915d64f40cddfbb8b58eb5bd11ba225336a6af45bbae07ca873f3","issuer":"hasura-auth"}'
|
||||
HASURA_GRAPHQL_ADMIN_SECRET: nhost-admin-secret
|
||||
HASURA_GRAPHQL_GRAPHQL_URL: http://graphql:8080/v1/graphql
|
||||
AUTH_PORT: 4000
|
||||
AUTH_SERVER_URL: http://127.0.0.2:4000
|
||||
AUTH_USER_DEFAULT_ALLOWED_ROLES: 'me,user,editor'
|
||||
AUTH_SMTP_AUTH_METHOD: PLAIN
|
||||
AUTH_SMTP_HOST: mailhog
|
||||
AUTH_SMTP_PASS: password
|
||||
AUTH_SMTP_PORT: "1025"
|
||||
AUTH_SMTP_SECURE: "false"
|
||||
AUTH_SMTP_SENDER: auth@example.com
|
||||
AUTH_SMTP_USER: user
|
||||
AUTH_LOG_LEVEL: debug
|
||||
AUTH_CLIENT_URL: 'http://localhost:3000'
|
||||
AUTH_LOG_FORMAT_TEXT: 'true'
|
||||
AUTH_EMAIL_SIGNIN_EMAIL_VERIFIED_REQUIRED: 'false'
|
||||
healthcheck:
|
||||
test:
|
||||
- CMD
|
||||
- wget
|
||||
- --spider
|
||||
- -S
|
||||
- http://localhost:4000/healthz
|
||||
timeout: 60s
|
||||
interval: 10s
|
||||
start_period: 10s
|
||||
restart: always
|
||||
|
||||
graphql:
|
||||
image: nhost/graphql-engine:v2.33.4-ce
|
||||
depends_on:
|
||||
postgres:
|
||||
condition: service_healthy
|
||||
environment:
|
||||
HASURA_GRAPHQL_ADMIN_INTERNAL_ERRORS: "true"
|
||||
HASURA_GRAPHQL_ADMIN_SECRET: nhost-admin-secret
|
||||
HASURA_GRAPHQL_CONSOLE_ASSETS_DIR: /srv/console-assets
|
||||
HASURA_GRAPHQL_CORS_DOMAIN: '*'
|
||||
HASURA_GRAPHQL_DATABASE_URL: postgres://nhost_hasura@postgres:5432/local
|
||||
HASURA_GRAPHQL_DEV_MODE: "true"
|
||||
HASURA_GRAPHQL_DISABLE_CORS: "false"
|
||||
HASURA_GRAPHQL_ENABLE_ALLOWLIST: "false"
|
||||
HASURA_GRAPHQL_ENABLE_CONSOLE: "true"
|
||||
HASURA_GRAPHQL_ENABLE_REMOTE_SCHEMA_PERMISSIONS: "false"
|
||||
HASURA_GRAPHQL_ENABLE_TELEMETRY: "false"
|
||||
HASURA_GRAPHQL_ENABLED_APIS: metadata,graphql,pgdump,config
|
||||
HASURA_GRAPHQL_ENABLED_LOG_TYPES: startup,http-log,webhook-log,websocket-log
|
||||
HASURA_GRAPHQL_EVENTS_HTTP_POOL_SIZE: "100"
|
||||
# HASURA_GRAPHQL_JWT_SECRET: '{"jwk_url":"http://auth:4000/.well-known/jwks.json"}'
|
||||
HASURA_GRAPHQL_JWT_SECRET: '{"type":"RS256", "key":"-----BEGIN PUBLIC KEY-----\nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA0M9zJVMJV8TgNPT9p737\nKR1XyWL9PSePXdcyk9aWcusG/m2OGsvuAgbMuDQx+Pns9PH9hd1kl53yfpTXOp3T\n13Uqox3IuHMlx8JyS+raqURSAew8/RkQ8nq+68XBBr9atDvVcSknS+jtZGH6Du1V\ntUy7Sz8VTVQuXDURF1Aa2wwNkRkC/wg5X0BXfN4Felh+mpK05PZbqJcRA5dbDlWk\n5nkdKbCG3urmtfF8brh6SlV7xBODJbqQws6E9WTclDQXWjmjcVNVSJE7OblZj1JB\nNGMN9rjUSS1kiRozhMtSlRv9MHAsz3e05MnvbyMWtoRpH8iLs0jmf8uucEBkMS/6\nBQIDAQAB\n-----END PUBLIC KEY-----","signing_key":"-----BEGIN PRIVATE KEY-----\nMIIEvwIBADANBgkqhkiG9w0BAQEFAASCBKkwggSlAgEAAoIBAQDQz3MlUwlXxOA0\n9P2nvfspHVfJYv09J49d1zKT1pZy6wb+bY4ay+4CBsy4NDH4+ez08f2F3WSXnfJ+\nlNc6ndPXdSqjHci4cyXHwnJL6tqpRFIB7Dz9GRDyer7rxcEGv1q0O9VxKSdL6O1k\nYfoO7VW1TLtLPxVNVC5cNREXUBrbDA2RGQL/CDlfQFd83gV6WH6akrTk9luolxED\nl1sOVaTmeR0psIbe6ua18XxuuHpKVXvEE4MlupDCzoT1ZNyUNBdaOaNxU1VIkTs5\nuVmPUkE0Yw32uNRJLWSJGjOEy1KVG/0wcCzPd7Tkye9vIxa2hGkfyIuzSOZ/y65w\nQGQxL/oFAgMBAAECggEBAKO3g1hoWpLuUbwzug2i7yG1V/cWHees9MNmzskLHrrL\ne5hQ3XI1Ik+EdU6X3faQPjFu6o/indQiitakbHwQ8t+jheKOn6m+3ohY9LSBVyAP\n6RyI1Oi8loUHqFnDmyxnK/7USu2GjsD9x+NEzoKVovWbS94bf+A5eH/jO5tDu0qy\nJMoe2jLx5IQQwLuvmQ+5ccZOUSQLG4/9Bw7g4xdroSvyVH27g9hqmEuY2orhcMm3\nlvlAx3PIH/kjKtpnP6MIBDhznlJ/VqAHhT/zC9xIwohyVGymoyDhdNSpn5N2QmWK\nKsneTdYdWz/oMB+HtcmvSoI4saEv1tlGEOTTINyBpwECgYEA+vrMFKhIoS3EbNiS\n5mSw/ejHl+60hsORGahPaYoXDfbDr2lyG58OfGu+l0qIe5SX4ueHo+ydhN70GR4l\nrtX9R+8uV9hb4B9e/hTZZnnAyFZrZSPfx4ZtPeyAlL+zhIGwxTy4BrbuxgynGict\nu+7XgbOYesDGRCvc4/1HKOgnf9kCgYEA1Py22UkY1iQQ4JNkfI1U6XqrydlMy1BG\nYSglI37UkVGUWG1hry+HCdhxHupBeUspZ/4vzKCLO1A1RlkCi9+TcOpY8UBqo1uq\nBaBPSlWD7T4oTOEPvANqT43SJ+RFkjtfVvDDtXBImO0+Nu57FmD6pMZJtvsxFkQB\nZKP6Mx3Q3A0CgYEAmGQJ4I0htIQmnXSPFceT1EgwUOdGxAEhLHQO6+VGBFuODAc5\nmt3kHNYLHq/J2UerRcIRkQ4NwuzhSBMPDG6wYKow+HPNrXM+6YXdTySkUsBuazXy\nHaNY112v4SHZLZ7Vp50rnCAdMTHjkLSzR0ZJol5bOkWs3R3I/MIAIC1+NlkCgYEA\n0kevP1er7cAt6Yub6lyfOOSkNuUTrKfU1JeOEz1lIRQqIiPcDdoeuNm41Yzyl45d\nkw6ioqTe0fCeqJW4reBO8Wxt48J1hlM5ydQ8dGd5mQGFSGHr5vR4QZMDqd710SpN\nNsj+cGQrSNDyW8mYPMACtiwPG1llXVZHCdXbcBw/2QECgYABLllfHVarmMwKTLWo\n8rRdEsIwcD/VxOxG4BxL6rZNQ4ADd8pL+9TohZeWp8wvlDGU7yB9wgyaD62Mhyog\nAGJt5Y/twAPTiVEi+0jVCXraLwPZpQFafw7p/x33eHkhwOTqlwlkRNlvrVk6A29I\nU0PVQZdMwEj/CPZVeCJ4DX63qQ==\n-----END PRIVATE KEY-----","issuer":"hasura-auth"}'
|
||||
HASURA_GRAPHQL_LIVE_QUERIES_MULTIPLEXED_BATCH_SIZE: "100"
|
||||
HASURA_GRAPHQL_LIVE_QUERIES_MULTIPLEXED_REFETCH_INTERVAL: "1000"
|
||||
HASURA_GRAPHQL_LOG_LEVEL: warn
|
||||
HASURA_GRAPHQL_PG_CONNECTIONS: "50"
|
||||
HASURA_GRAPHQL_PG_TIMEOUT: "180"
|
||||
HASURA_GRAPHQL_STRINGIFY_NUMERIC_TYPES: "false"
|
||||
HASURA_GRAPHQL_TX_ISOLATION: read-committed
|
||||
HASURA_GRAPHQL_UNAUTHORIZED_ROLE: public
|
||||
HASURA_GRAPHQL_USE_PREPARED_STATEMENTS: "true"
|
||||
HASURA_GRAPHQL_WS_READ_COOKIE: "false"
|
||||
GRAPHITE_WEBHOOK_SECRET: graphite-secret
|
||||
ports:
|
||||
- mode: ingress
|
||||
target: 8080
|
||||
published: "8080"
|
||||
protocol: tcp
|
||||
healthcheck:
|
||||
test:
|
||||
- CMD-SHELL
|
||||
- curl http://localhost:8080/healthz > /dev/null 2>&1
|
||||
timeout: 60s
|
||||
interval: 10s
|
||||
start_period: 10s
|
||||
restart: always
|
||||
|
||||
postgres:
|
||||
image: nhost/postgres:14.6-20231018-1
|
||||
command:
|
||||
- postgres
|
||||
- -c
|
||||
- config_file=/etc/postgresql.conf
|
||||
- -c
|
||||
- hba_file=/etc/pg_hba_local.conf
|
||||
environment:
|
||||
PGDATA: /var/lib/postgresql/data/pgdata
|
||||
POSTGRES_DB: local
|
||||
POSTGRES_PASSWORD: postgres
|
||||
POSTGRES_USER: postgres
|
||||
healthcheck:
|
||||
test:
|
||||
- CMD-SHELL
|
||||
- pg_isready -U postgres
|
||||
- -d
|
||||
- postgres
|
||||
- -q
|
||||
timeout: 60s
|
||||
interval: 10s
|
||||
start_period: 10s
|
||||
ports:
|
||||
- mode: ingress
|
||||
target: 5432
|
||||
published: "5432"
|
||||
protocol: tcp
|
||||
restart: always
|
||||
volumes:
|
||||
- type: volume
|
||||
source: pgdata
|
||||
target: /var/lib/postgresql/data/pgdata
|
||||
- type: bind
|
||||
source: ./pg_hba_local.conf
|
||||
target: /etc/pg_hba_local.conf
|
||||
read_only: true
|
||||
|
||||
memcached:
|
||||
image: memcached:1.6
|
||||
ports:
|
||||
- mode: ingress
|
||||
target: 11211
|
||||
published: "11211"
|
||||
protocol: tcp
|
||||
restart: always
|
||||
|
||||
mailhog:
|
||||
image: jcalonso/mailhog:v1.0.1
|
||||
ports:
|
||||
- mode: ingress
|
||||
target: 1025
|
||||
published: "1025"
|
||||
protocol: tcp
|
||||
- mode: ingress
|
||||
target: 8025
|
||||
published: "8025"
|
||||
protocol: tcp
|
||||
environment:
|
||||
SMTP_HOST: mailhog
|
||||
SMTP_PASS: password
|
||||
SMTP_PORT: "1025"
|
||||
SMTP_SECURE: "false"
|
||||
SMTP_SENDER: auth@example.com
|
||||
SMTP_USER: user
|
||||
restart: always
|
||||
|
||||
nginx:
|
||||
image: nginx:alpine
|
||||
ports:
|
||||
- "443:443"
|
||||
volumes:
|
||||
- ./nginx/html:/usr/share/nginx/html
|
||||
- ./nginx/nginx.conf:/etc/nginx/nginx.conf:ro
|
||||
- ./nginx//ssl:/etc/nginx/ssl
|
||||
restart: unless-stopped
|
||||
|
||||
volumes:
|
||||
pgdata: {}
|
||||
95
services/auth/build/dev/docker/nginx/html/index.html
Normal file
95
services/auth/build/dev/docker/nginx/html/index.html
Normal file
@@ -0,0 +1,95 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Sign Up Form</title>
|
||||
<script src="https://challenges.cloudflare.com/turnstile/v0/api.js" async defer></script>
|
||||
<style>
|
||||
body {
|
||||
font-family: Arial, sans-serif;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
height: 100vh;
|
||||
margin: 0;
|
||||
background-color: #f0f0f0;
|
||||
}
|
||||
form {
|
||||
background-color: white;
|
||||
padding: 20px;
|
||||
border-radius: 8px;
|
||||
box-shadow: 0 0 10px rgba(0,0,0,0.1);
|
||||
}
|
||||
input {
|
||||
display: block;
|
||||
width: 100%;
|
||||
margin-bottom: 10px;
|
||||
padding: 8px;
|
||||
border: 1px solid #ddd;
|
||||
border-radius: 4px;
|
||||
}
|
||||
button {
|
||||
width: 100%;
|
||||
padding: 10px;
|
||||
background-color: #007bff;
|
||||
color: white;
|
||||
border: none;
|
||||
border-radius: 4px;
|
||||
cursor: pointer;
|
||||
}
|
||||
button:hover {
|
||||
background-color: #0056b3;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<form id="signupForm">
|
||||
<h2>Sign Up</h2>
|
||||
<input type="email" id="email" placeholder="Email" required>
|
||||
<input type="password" id="password" placeholder="Password" required>
|
||||
<div class="cf-turnstile" data-sitekey="FIXME"></div>
|
||||
<button type="submit">Sign Up</button>
|
||||
</form>
|
||||
|
||||
<script>
|
||||
document.getElementById('signupForm').addEventListener('submit', async function(e) {
|
||||
e.preventDefault();
|
||||
|
||||
const email = document.getElementById('email').value;
|
||||
const password = document.getElementById('password').value;
|
||||
const turnstileResponse = turnstile.getResponse();
|
||||
|
||||
if (!turnstileResponse) {
|
||||
alert('Please complete the Turnstile challenge.');
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
const response = await fetch('http://localhost:4000/signup/email-password', {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json',
|
||||
'x-cf-turnstile-response': turnstileResponse,
|
||||
},
|
||||
body: JSON.stringify({
|
||||
email,
|
||||
password,
|
||||
}),
|
||||
});
|
||||
|
||||
if (response.ok) {
|
||||
alert('Sign up successful!');
|
||||
// Optionally, redirect the user or clear the form
|
||||
} else {
|
||||
const errorData = await response.json();
|
||||
alert(`Sign up failed: ${errorData.message || 'Unknown error'}`);
|
||||
}
|
||||
} catch (error) {
|
||||
console.error('Error:', error);
|
||||
alert('An error occurred. Please try again.');
|
||||
}
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
41
services/auth/build/dev/docker/nginx/nginx.conf
Normal file
41
services/auth/build/dev/docker/nginx/nginx.conf
Normal file
@@ -0,0 +1,41 @@
|
||||
events {
|
||||
worker_connections 1024;
|
||||
}
|
||||
|
||||
http {
|
||||
server {
|
||||
listen 443 ssl;
|
||||
server_name localhost;
|
||||
|
||||
ssl_certificate /etc/nginx/ssl/nginx-selfsigned.crt;
|
||||
ssl_certificate_key /etc/nginx/ssl/nginx-selfsigned.key;
|
||||
|
||||
ssl_protocols TLSv1.2 TLSv1.3;
|
||||
ssl_prefer_server_ciphers on;
|
||||
ssl_ciphers ECDHE-RSA-AES256-GCM-SHA512:DHE-RSA-AES256-GCM-SHA512:ECDHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-SHA384;
|
||||
|
||||
location / {
|
||||
root /usr/share/nginx/html;
|
||||
index index.html;
|
||||
|
||||
add_header 'Access-Control-Allow-Origin' 'https://challenges.cloudflare.com';
|
||||
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
|
||||
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
|
||||
add_header 'Access-Control-Expose-Headers' 'Content-Length,Content-Range';
|
||||
|
||||
|
||||
add_header Content-Security-Policy "default-src 'self'; frame-src 'self' https://challenges.cloudflare.com; frame-ancestors 'self' https://challenges.cloudflare.com; script-src 'self' 'unsafe-inline' 'unsafe-eval' https://challenges.cloudflare.com; style-src 'self' 'unsafe-inline' https://challenges.cloudflare.com; img-src 'self' data: https:; font-src 'self' https:; connect-src 'self' http://localhost:4000 https://challenges.cloudflare.com;";
|
||||
|
||||
if ($request_method = 'OPTIONS') {
|
||||
add_header 'Access-Control-Allow-Origin' 'https://challenges.cloudflare.com';
|
||||
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
|
||||
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
|
||||
add_header 'Access-Control-Max-Age' 1728000;
|
||||
add_header 'Content-Type' 'text/plain; charset=utf-8';
|
||||
add_header 'Content-Length' 0;
|
||||
return 204;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
-----BEGIN CERTIFICATE-----
|
||||
MIIDSDCCAjACCQDGV/un6TjVazANBgkqhkiG9w0BAQsFADBmMQswCQYDVQQGEwJV
|
||||
UzEOMAwGA1UECAwFU3RhdGUxDTALBgNVBAcMBENpdHkxFTATBgNVBAoMDE9yZ2Fu
|
||||
aXphdGlvbjENMAsGA1UECwwEVW5pdDESMBAGA1UEAwwJbG9jYWxob3N0MB4XDTI0
|
||||
MDkyNTA4MTA0NVoXDTI1MDkyNTA4MTA0NVowZjELMAkGA1UEBhMCVVMxDjAMBgNV
|
||||
BAgMBVN0YXRlMQ0wCwYDVQQHDARDaXR5MRUwEwYDVQQKDAxPcmdhbml6YXRpb24x
|
||||
DTALBgNVBAsMBFVuaXQxEjAQBgNVBAMMCWxvY2FsaG9zdDCCASIwDQYJKoZIhvcN
|
||||
AQEBBQADggEPADCCAQoCggEBAMLzWZAlYj7FMsBHFbiRPNebUTYiVmDiyH/Yk/eG
|
||||
JhS4Rpw2UjI9LpBgGOJKrPRAD14KBjNHJSSTVrPV6l2kdsugDJDwDUhWlRxng1+Z
|
||||
zP6MNB9WME6wOFxiUARHumHaABqd/8zY4Ws1DJbPgyXgARmv+2PaeFMOrTsBn70N
|
||||
Og5s7JZC0V9u7vRxsbrmmWiq9Ew3GOO3RnPg+6gmrxQEo2K85h0npOeCRtP3zfd+
|
||||
pAUnujstk+75gqAEPlkf+DrUmg8opd4CquoRg2dVai2YwIdvtMqE0SWgZs/wbaOg
|
||||
gATdOtp8T8YKuyTZ7cTnQRHZJFVMkzfZ6/WCLcysHgtItTMCAwEAATANBgkqhkiG
|
||||
9w0BAQsFAAOCAQEAXIDN3YBDj+QF+L1F1PlV54/hUv3vXoU35hTfKLu09k76n7wD
|
||||
pYLHj7/pdZtuqt+0PCllfGBXnCMMtFeH+ZSUZciSinoDg4fpUUT9BnhUVr9MvESu
|
||||
1fa64aYsOY9KYi8I9LpdIYs3DfpVuAKxFOOW2vH54+HaZMKfGH3ZZKQ8QL+KZzk4
|
||||
zxaCkl2jCFwD2cCuvc/wu5EBGcjkv429eapFp/8lXqv9YbiW2833t0r4rkEUroP1
|
||||
Dbm+kf6AUt7tm5AkxvRmbtKjQ8l5kB+GnHVMo+eltmesb8HHMYJqOBbIOTOUz6b8
|
||||
uPJWrTgLvYT2El87a3pFL2XP4PkV9igakf94gg==
|
||||
-----END CERTIFICATE-----
|
||||
@@ -0,0 +1,28 @@
|
||||
-----BEGIN PRIVATE KEY-----
|
||||
MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDC81mQJWI+xTLA
|
||||
RxW4kTzXm1E2IlZg4sh/2JP3hiYUuEacNlIyPS6QYBjiSqz0QA9eCgYzRyUkk1az
|
||||
1epdpHbLoAyQ8A1IVpUcZ4Nfmcz+jDQfVjBOsDhcYlAER7ph2gAanf/M2OFrNQyW
|
||||
z4Ml4AEZr/tj2nhTDq07AZ+9DToObOyWQtFfbu70cbG65ploqvRMNxjjt0Zz4Puo
|
||||
Jq8UBKNivOYdJ6TngkbT9833fqQFJ7o7LZPu+YKgBD5ZH/g61JoPKKXeAqrqEYNn
|
||||
VWotmMCHb7TKhNEloGbP8G2joIAE3TrafE/GCrsk2e3E50ER2SRVTJM32ev1gi3M
|
||||
rB4LSLUzAgMBAAECggEAHnzCD+nYwGpEco9rVS7ZbfprK+UYzxQIOP4cvcPr5qee
|
||||
20Ufe53Xz1pH6fO1sojmHlXA/Hnu1BZ6o6sbeMOElHmWHYB9A0gPD58ci3HY/iHc
|
||||
8N2gtl2WotP5IYI6Ip1eEMuOunFcZ1CnhFo1b1HluiesT8RVtt9/tc+eNImB/8lA
|
||||
/FFGn6/Q78xeS9MbwFEpEXgEaBX3DKEcmfwcvu5fDpc12koYWenLGTor16fepJ5a
|
||||
rFI64yCxDAg3A0mRdiY6RlgmFvqlm9J3BdO+np/GrE4QkrmE78LuX8mToMwnE8Q9
|
||||
vZeh731WNv2EzJsewy+ayyh/RIEH5PUAgVt+qLP+AQKBgQDujnQzgoBEgA7XTTiz
|
||||
w6I90lvFxw3DR7ptc4ai79gz/cTzoJoIGpcjI2cyDpcGL5RuBh06L8Y64NVQxp29
|
||||
jnGFt9Hil/2ZomYlCnc3OUiaTQZnn98k4jPsLNwB8Ng+AZYHMVuJ2qut2x0KDUz2
|
||||
e6F/N7h5VGjLFZnM1w80T3TIMwKBgQDRNKLbSPOLxCiNV2OF5KfDbIQt6sWPMnDo
|
||||
zGyGQgT4WZjLdVX4a3NYKwaHVQq6bASqbr2X1Vdk5zEMzqqTM+AvFA/9OCne1mrH
|
||||
fPISBimZzLB3iNyu2qTmrJKZcuTV/Bn6lwjbH2sy2Ms1CugQVJDd+LQjJ7/ZaaoM
|
||||
BmxUj1NfAQKBgQCLjSYI4/SpHciQxom/D1iflak9/33bmOBEGurN8kSl1XQbmP3C
|
||||
c9uqIJHDxKkwYzEPU+BRI5Vw6AmhoS6xrtxV/vx287bU4x2h2Yd39Li2Gwz+HZXp
|
||||
+7GoHW3ubLfzPfZH6uXDtPntUFqigLlfD1+gDjaKM4jCFLbOD5jDXx/P5QKBgQCM
|
||||
BylCkY/Ca2ehQ27v/d50pbvLaCsX7/E3QS0aqDHfcUkeVclXX8RyrUnPZ5KouQhe
|
||||
c4UfjcLTXROtuN7fbIePu2QAX4lXCDmskOsOOWW69hDf0ZG0z9A0PipZ31dgCz/w
|
||||
RQu+b0c3X3iUZlpyI8hbas5YAZEeGuWg6uOzrcNmAQKBgAf15LHx7IVEeIfn8ta/
|
||||
YnZnODsvN5+4ybMIIuX8yAPmXOy3klYvp1+8BH6jZMVHXAqQugooGirfik02RzQv
|
||||
tCbCXDoTSMzMQU5iSlvnxtcug93rWa4VFvmU9nSqp7lpJQmiOBwWFf2/mmSwyLc9
|
||||
MvOVZTA46IefrGuG64T83RRf
|
||||
-----END PRIVATE KEY-----
|
||||
2
services/auth/build/dev/docker/pg_hba_local.conf
Normal file
2
services/auth/build/dev/docker/pg_hba_local.conf
Normal file
@@ -0,0 +1,2 @@
|
||||
local all all trust
|
||||
host all all all trust
|
||||
36
services/auth/build/nix-docker-image.sh
Executable file
36
services/auth/build/nix-docker-image.sh
Executable file
@@ -0,0 +1,36 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
which nix > /dev/null
|
||||
|
||||
IMAGE=${1:-"docker-image"}
|
||||
SYSTEM=${2:-""}
|
||||
|
||||
if [[ $NIX_BUILD_NATIVE -eq 1 ]]; then
|
||||
if [[ -z $SYSTEM ]]; then
|
||||
case $(uname -m) in
|
||||
"arm64")
|
||||
SYSTEM="aarch64-linux"
|
||||
;;
|
||||
*)
|
||||
SYSTEM="x86_64-linux"
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
|
||||
nix build .\#packages.${SYSTEM}.$IMAGE --print-build-logs
|
||||
exit $?
|
||||
fi
|
||||
|
||||
if [[ ( $? -eq 0 ) && ( `uname` == "Linux" ) ]]; then
|
||||
nix build .\#$IMAGE --print-build-logs
|
||||
exit $?
|
||||
fi
|
||||
|
||||
|
||||
docker run --rm -it \
|
||||
-v /var/run/docker.sock:/var/run/docker.sock \
|
||||
-v $PWD:/build \
|
||||
-w /build \
|
||||
--entrypoint sh \
|
||||
dbarroso/nix:2.6.0 \
|
||||
-c "nix build .\\#$IMAGE --print-build-logs && docker load < result"
|
||||
16
services/auth/build/nix.sh
Executable file
16
services/auth/build/nix.sh
Executable file
@@ -0,0 +1,16 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
which nix > /dev/null
|
||||
|
||||
if [ $? -eq 0 ]; then
|
||||
nix $@
|
||||
exit $?
|
||||
fi
|
||||
|
||||
docker run --rm -it \
|
||||
-v /var/run/docker.sock:/var/run/docker.sock \
|
||||
-v $PWD:/build \
|
||||
-w /build \
|
||||
--entrypoint nix \
|
||||
dbarroso/nix:2.6.0 \
|
||||
"$@"
|
||||
850
services/auth/bun.lock
Normal file
850
services/auth/bun.lock
Normal file
@@ -0,0 +1,850 @@
|
||||
{
|
||||
"lockfileVersion": 1,
|
||||
"workspaces": {
|
||||
"": {
|
||||
"name": "auth",
|
||||
"devDependencies": {
|
||||
"@types/bcryptjs": "^2.4.6",
|
||||
"@types/faker": "^5.5.9",
|
||||
"@types/jest": "^27.5.2",
|
||||
"@types/node-fetch": "^2.6.11",
|
||||
"@types/pg": "^7.14.11",
|
||||
"@types/rfc2047": "^2.0.3",
|
||||
"@types/supertest": "^2.0.16",
|
||||
"@types/uuid": "7.0.2",
|
||||
"axios": "^1.6.8",
|
||||
"bcryptjs": "^2.4.3",
|
||||
"faker": "^5.5.3",
|
||||
"http-status-codes": "^2.3.0",
|
||||
"jose": "^5.2.3",
|
||||
"node-fetch": "^2.7.0",
|
||||
"otplib": "12.0.1",
|
||||
"pg": "^8.11.4",
|
||||
"rfc2047": "^3.0.1",
|
||||
"supertest": "^6.3.4",
|
||||
"ts-jest": "^27.1.5",
|
||||
"typescript": "4.5.4",
|
||||
"uuid": "7.0.3",
|
||||
},
|
||||
},
|
||||
},
|
||||
"packages": {
|
||||
"@ampproject/remapping": ["@ampproject/remapping@2.3.0", "", { "dependencies": { "@jridgewell/gen-mapping": "^0.3.5", "@jridgewell/trace-mapping": "^0.3.24" } }, "sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw=="],
|
||||
|
||||
"@babel/code-frame": ["@babel/code-frame@7.27.1", "", { "dependencies": { "@babel/helper-validator-identifier": "^7.27.1", "js-tokens": "^4.0.0", "picocolors": "^1.1.1" } }, "sha512-cjQ7ZlQ0Mv3b47hABuTevyTuYN4i+loJKGeV9flcCgIK37cCXRh+L1bd3iBHlynerhQ7BhCkn2BPbQUL+rGqFg=="],
|
||||
|
||||
"@babel/compat-data": ["@babel/compat-data@7.27.5", "", {}, "sha512-KiRAp/VoJaWkkte84TvUd9qjdbZAdiqyvMxrGl1N6vzFogKmaLgoM3L1kgtLicp2HP5fBJS8JrZKLVIZGVJAVg=="],
|
||||
|
||||
"@babel/core": ["@babel/core@7.27.4", "", { "dependencies": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.27.1", "@babel/generator": "^7.27.3", "@babel/helper-compilation-targets": "^7.27.2", "@babel/helper-module-transforms": "^7.27.3", "@babel/helpers": "^7.27.4", "@babel/parser": "^7.27.4", "@babel/template": "^7.27.2", "@babel/traverse": "^7.27.4", "@babel/types": "^7.27.3", "convert-source-map": "^2.0.0", "debug": "^4.1.0", "gensync": "^1.0.0-beta.2", "json5": "^2.2.3", "semver": "^6.3.1" } }, "sha512-bXYxrXFubeYdvB0NhD/NBB3Qi6aZeV20GOWVI47t2dkecCEoneR4NPVcb7abpXDEvejgrUfFtG6vG/zxAKmg+g=="],
|
||||
|
||||
"@babel/generator": ["@babel/generator@7.27.5", "", { "dependencies": { "@babel/parser": "^7.27.5", "@babel/types": "^7.27.3", "@jridgewell/gen-mapping": "^0.3.5", "@jridgewell/trace-mapping": "^0.3.25", "jsesc": "^3.0.2" } }, "sha512-ZGhA37l0e/g2s1Cnzdix0O3aLYm66eF8aufiVteOgnwxgnRP8GoyMj7VWsgWnQbVKXyge7hqrFh2K2TQM6t1Hw=="],
|
||||
|
||||
"@babel/helper-compilation-targets": ["@babel/helper-compilation-targets@7.27.2", "", { "dependencies": { "@babel/compat-data": "^7.27.2", "@babel/helper-validator-option": "^7.27.1", "browserslist": "^4.24.0", "lru-cache": "^5.1.1", "semver": "^6.3.1" } }, "sha512-2+1thGUUWWjLTYTHZWK1n8Yga0ijBz1XAhUXcKy81rd5g6yh7hGqMp45v7cadSbEHc9G3OTv45SyneRN3ps4DQ=="],
|
||||
|
||||
"@babel/helper-module-imports": ["@babel/helper-module-imports@7.27.1", "", { "dependencies": { "@babel/traverse": "^7.27.1", "@babel/types": "^7.27.1" } }, "sha512-0gSFWUPNXNopqtIPQvlD5WgXYI5GY2kP2cCvoT8kczjbfcfuIljTbcWrulD1CIPIX2gt1wghbDy08yE1p+/r3w=="],
|
||||
|
||||
"@babel/helper-module-transforms": ["@babel/helper-module-transforms@7.27.3", "", { "dependencies": { "@babel/helper-module-imports": "^7.27.1", "@babel/helper-validator-identifier": "^7.27.1", "@babel/traverse": "^7.27.3" }, "peerDependencies": { "@babel/core": "^7.0.0" } }, "sha512-dSOvYwvyLsWBeIRyOeHXp5vPj5l1I011r52FM1+r1jCERv+aFXYk4whgQccYEGYxK2H3ZAIA8nuPkQ0HaUo3qg=="],
|
||||
|
||||
"@babel/helper-plugin-utils": ["@babel/helper-plugin-utils@7.27.1", "", {}, "sha512-1gn1Up5YXka3YYAHGKpbideQ5Yjf1tDa9qYcgysz+cNCXukyLl6DjPXhD3VRwSb8c0J9tA4b2+rHEZtc6R0tlw=="],
|
||||
|
||||
"@babel/helper-string-parser": ["@babel/helper-string-parser@7.27.1", "", {}, "sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA=="],
|
||||
|
||||
"@babel/helper-validator-identifier": ["@babel/helper-validator-identifier@7.27.1", "", {}, "sha512-D2hP9eA+Sqx1kBZgzxZh0y1trbuU+JoDkiEwqhQ36nodYqJwyEIhPSdMNd7lOm/4io72luTPWH20Yda0xOuUow=="],
|
||||
|
||||
"@babel/helper-validator-option": ["@babel/helper-validator-option@7.27.1", "", {}, "sha512-YvjJow9FxbhFFKDSuFnVCe2WxXk1zWc22fFePVNEaWJEu8IrZVlda6N0uHwzZrUM1il7NC9Mlp4MaJYbYd9JSg=="],
|
||||
|
||||
"@babel/helpers": ["@babel/helpers@7.27.6", "", { "dependencies": { "@babel/template": "^7.27.2", "@babel/types": "^7.27.6" } }, "sha512-muE8Tt8M22638HU31A3CgfSUciwz1fhATfoVai05aPXGor//CdWDCbnlY1yvBPo07njuVOCNGCSp/GTt12lIug=="],
|
||||
|
||||
"@babel/parser": ["@babel/parser@7.27.5", "", { "dependencies": { "@babel/types": "^7.27.3" }, "bin": "./bin/babel-parser.js" }, "sha512-OsQd175SxWkGlzbny8J3K8TnnDD0N3lrIUtB92xwyRpzaenGZhxDvxN/JgU00U3CDZNj9tPuDJ5H0WS4Nt3vKg=="],
|
||||
|
||||
"@babel/plugin-syntax-async-generators": ["@babel/plugin-syntax-async-generators@7.8.4", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.8.0" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw=="],
|
||||
|
||||
"@babel/plugin-syntax-bigint": ["@babel/plugin-syntax-bigint@7.8.3", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.8.0" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-wnTnFlG+YxQm3vDxpGE57Pj0srRU4sHE/mDkt1qv2YJJSeUAec2ma4WLUnUPeKjyrfntVwe/N6dCXpU+zL3Npg=="],
|
||||
|
||||
"@babel/plugin-syntax-class-properties": ["@babel/plugin-syntax-class-properties@7.12.13", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.12.13" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA=="],
|
||||
|
||||
"@babel/plugin-syntax-class-static-block": ["@babel/plugin-syntax-class-static-block@7.14.5", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.14.5" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-b+YyPmr6ldyNnM6sqYeMWE+bgJcJpO6yS4QD7ymxgH34GBPNDM/THBh8iunyvKIZztiwLH4CJZ0RxTk9emgpjw=="],
|
||||
|
||||
"@babel/plugin-syntax-import-attributes": ["@babel/plugin-syntax-import-attributes@7.27.1", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.27.1" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-oFT0FrKHgF53f4vOsZGi2Hh3I35PfSmVs4IBFLFj4dnafP+hIWDLg3VyKmUHfLoLHlyxY4C7DGtmHuJgn+IGww=="],
|
||||
|
||||
"@babel/plugin-syntax-import-meta": ["@babel/plugin-syntax-import-meta@7.10.4", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.10.4" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-Yqfm+XDx0+Prh3VSeEQCPU81yC+JWZ2pDPFSS4ZdpfZhp4MkFMaDC1UqseovEKwSUpnIL7+vK+Clp7bfh0iD7g=="],
|
||||
|
||||
"@babel/plugin-syntax-json-strings": ["@babel/plugin-syntax-json-strings@7.8.3", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.8.0" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA=="],
|
||||
|
||||
"@babel/plugin-syntax-logical-assignment-operators": ["@babel/plugin-syntax-logical-assignment-operators@7.10.4", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.10.4" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig=="],
|
||||
|
||||
"@babel/plugin-syntax-nullish-coalescing-operator": ["@babel/plugin-syntax-nullish-coalescing-operator@7.8.3", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.8.0" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ=="],
|
||||
|
||||
"@babel/plugin-syntax-numeric-separator": ["@babel/plugin-syntax-numeric-separator@7.10.4", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.10.4" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug=="],
|
||||
|
||||
"@babel/plugin-syntax-object-rest-spread": ["@babel/plugin-syntax-object-rest-spread@7.8.3", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.8.0" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA=="],
|
||||
|
||||
"@babel/plugin-syntax-optional-catch-binding": ["@babel/plugin-syntax-optional-catch-binding@7.8.3", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.8.0" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q=="],
|
||||
|
||||
"@babel/plugin-syntax-optional-chaining": ["@babel/plugin-syntax-optional-chaining@7.8.3", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.8.0" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg=="],
|
||||
|
||||
"@babel/plugin-syntax-private-property-in-object": ["@babel/plugin-syntax-private-property-in-object@7.14.5", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.14.5" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-0wVnp9dxJ72ZUJDV27ZfbSj6iHLoytYZmh3rFcxNnvsJF3ktkzLDZPy/mA17HGsaQT3/DQsWYX1f1QGWkCoVUg=="],
|
||||
|
||||
"@babel/plugin-syntax-top-level-await": ["@babel/plugin-syntax-top-level-await@7.14.5", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.14.5" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw=="],
|
||||
|
||||
"@babel/plugin-syntax-typescript": ["@babel/plugin-syntax-typescript@7.27.1", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.27.1" }, "peerDependencies": { "@babel/core": "^7.0.0-0" } }, "sha512-xfYCBMxveHrRMnAWl1ZlPXOZjzkN82THFvLhQhFXFt81Z5HnN+EtUkZhv/zcKpmT3fzmWZB0ywiBrbC3vogbwQ=="],
|
||||
|
||||
"@babel/template": ["@babel/template@7.27.2", "", { "dependencies": { "@babel/code-frame": "^7.27.1", "@babel/parser": "^7.27.2", "@babel/types": "^7.27.1" } }, "sha512-LPDZ85aEJyYSd18/DkjNh4/y1ntkE5KwUHWTiqgRxruuZL2F1yuHligVHLvcHY2vMHXttKFpJn6LwfI7cw7ODw=="],
|
||||
|
||||
"@babel/traverse": ["@babel/traverse@7.27.4", "", { "dependencies": { "@babel/code-frame": "^7.27.1", "@babel/generator": "^7.27.3", "@babel/parser": "^7.27.4", "@babel/template": "^7.27.2", "@babel/types": "^7.27.3", "debug": "^4.3.1", "globals": "^11.1.0" } }, "sha512-oNcu2QbHqts9BtOWJosOVJapWjBDSxGCpFvikNR5TGDYDQf3JwpIoMzIKrvfoti93cLfPJEG4tH9SPVeyCGgdA=="],
|
||||
|
||||
"@babel/types": ["@babel/types@7.27.6", "", { "dependencies": { "@babel/helper-string-parser": "^7.27.1", "@babel/helper-validator-identifier": "^7.27.1" } }, "sha512-ETyHEk2VHHvl9b9jZP5IHPavHYk57EhanlRRuae9XCpb/j5bDCbPPMOBfCWhnl/7EDJz0jEMCi/RhccCE8r1+Q=="],
|
||||
|
||||
"@bcoe/v8-coverage": ["@bcoe/v8-coverage@0.2.3", "", {}, "sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw=="],
|
||||
|
||||
"@istanbuljs/load-nyc-config": ["@istanbuljs/load-nyc-config@1.1.0", "", { "dependencies": { "camelcase": "^5.3.1", "find-up": "^4.1.0", "get-package-type": "^0.1.0", "js-yaml": "^3.13.1", "resolve-from": "^5.0.0" } }, "sha512-VjeHSlIzpv/NyD3N0YuHfXOPDIixcA1q2ZV98wsMqcYlPmv2n3Yb2lYP9XMElnaFVXg5A7YLTeLu6V84uQDjmQ=="],
|
||||
|
||||
"@istanbuljs/schema": ["@istanbuljs/schema@0.1.3", "", {}, "sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA=="],
|
||||
|
||||
"@jest/console": ["@jest/console@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "@types/node": "*", "chalk": "^4.0.0", "jest-message-util": "^27.5.1", "jest-util": "^27.5.1", "slash": "^3.0.0" } }, "sha512-kZ/tNpS3NXn0mlXXXPNuDZnb4c0oZ20r4K5eemM2k30ZC3G0T02nXUvyhf5YdbXWHPEJLc9qGLxEZ216MdL+Zg=="],
|
||||
|
||||
"@jest/core": ["@jest/core@27.5.1", "", { "dependencies": { "@jest/console": "^27.5.1", "@jest/reporters": "^27.5.1", "@jest/test-result": "^27.5.1", "@jest/transform": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "ansi-escapes": "^4.2.1", "chalk": "^4.0.0", "emittery": "^0.8.1", "exit": "^0.1.2", "graceful-fs": "^4.2.9", "jest-changed-files": "^27.5.1", "jest-config": "^27.5.1", "jest-haste-map": "^27.5.1", "jest-message-util": "^27.5.1", "jest-regex-util": "^27.5.1", "jest-resolve": "^27.5.1", "jest-resolve-dependencies": "^27.5.1", "jest-runner": "^27.5.1", "jest-runtime": "^27.5.1", "jest-snapshot": "^27.5.1", "jest-util": "^27.5.1", "jest-validate": "^27.5.1", "jest-watcher": "^27.5.1", "micromatch": "^4.0.4", "rimraf": "^3.0.0", "slash": "^3.0.0", "strip-ansi": "^6.0.0" }, "peerDependencies": { "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" }, "optionalPeers": ["node-notifier"] }, "sha512-AK6/UTrvQD0Cd24NSqmIA6rKsu0tKIxfiCducZvqxYdmMisOYAsdItspT+fQDQYARPf8XgjAFZi0ogW2agH5nQ=="],
|
||||
|
||||
"@jest/environment": ["@jest/environment@27.5.1", "", { "dependencies": { "@jest/fake-timers": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "jest-mock": "^27.5.1" } }, "sha512-/WQjhPJe3/ghaol/4Bq480JKXV/Rfw8nQdN7f41fM8VDHLcxKXou6QyXAh3EFr9/bVG3x74z1NWDkP87EiY8gA=="],
|
||||
|
||||
"@jest/fake-timers": ["@jest/fake-timers@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "@sinonjs/fake-timers": "^8.0.1", "@types/node": "*", "jest-message-util": "^27.5.1", "jest-mock": "^27.5.1", "jest-util": "^27.5.1" } }, "sha512-/aPowoolwa07k7/oM3aASneNeBGCmGQsc3ugN4u6s4C/+s5M64MFo/+djTdiwcbQlRfFElGuDXWzaWj6QgKObQ=="],
|
||||
|
||||
"@jest/globals": ["@jest/globals@27.5.1", "", { "dependencies": { "@jest/environment": "^27.5.1", "@jest/types": "^27.5.1", "expect": "^27.5.1" } }, "sha512-ZEJNB41OBQQgGzgyInAv0UUfDDj3upmHydjieSxFvTRuZElrx7tXg/uVQ5hYVEwiXs3+aMsAeEc9X7xiSKCm4Q=="],
|
||||
|
||||
"@jest/reporters": ["@jest/reporters@27.5.1", "", { "dependencies": { "@bcoe/v8-coverage": "^0.2.3", "@jest/console": "^27.5.1", "@jest/test-result": "^27.5.1", "@jest/transform": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "chalk": "^4.0.0", "collect-v8-coverage": "^1.0.0", "exit": "^0.1.2", "glob": "^7.1.2", "graceful-fs": "^4.2.9", "istanbul-lib-coverage": "^3.0.0", "istanbul-lib-instrument": "^5.1.0", "istanbul-lib-report": "^3.0.0", "istanbul-lib-source-maps": "^4.0.0", "istanbul-reports": "^3.1.3", "jest-haste-map": "^27.5.1", "jest-resolve": "^27.5.1", "jest-util": "^27.5.1", "jest-worker": "^27.5.1", "slash": "^3.0.0", "source-map": "^0.6.0", "string-length": "^4.0.1", "terminal-link": "^2.0.0", "v8-to-istanbul": "^8.1.0" }, "peerDependencies": { "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" }, "optionalPeers": ["node-notifier"] }, "sha512-cPXh9hWIlVJMQkVk84aIvXuBB4uQQmFqZiacloFuGiP3ah1sbCxCosidXFDfqG8+6fO1oR2dTJTlsOy4VFmUfw=="],
|
||||
|
||||
"@jest/source-map": ["@jest/source-map@27.5.1", "", { "dependencies": { "callsites": "^3.0.0", "graceful-fs": "^4.2.9", "source-map": "^0.6.0" } }, "sha512-y9NIHUYF3PJRlHk98NdC/N1gl88BL08aQQgu4k4ZopQkCw9t9cV8mtl3TV8b/YCB8XaVTFrmUTAJvjsntDireg=="],
|
||||
|
||||
"@jest/test-result": ["@jest/test-result@27.5.1", "", { "dependencies": { "@jest/console": "^27.5.1", "@jest/types": "^27.5.1", "@types/istanbul-lib-coverage": "^2.0.0", "collect-v8-coverage": "^1.0.0" } }, "sha512-EW35l2RYFUcUQxFJz5Cv5MTOxlJIQs4I7gxzi2zVU7PJhOwfYq1MdC5nhSmYjX1gmMmLPvB3sIaC+BkcHRBfag=="],
|
||||
|
||||
"@jest/test-sequencer": ["@jest/test-sequencer@27.5.1", "", { "dependencies": { "@jest/test-result": "^27.5.1", "graceful-fs": "^4.2.9", "jest-haste-map": "^27.5.1", "jest-runtime": "^27.5.1" } }, "sha512-LCheJF7WB2+9JuCS7VB/EmGIdQuhtqjRNI9A43idHv3E4KltCTsPsLxvdaubFHSYwY/fNjMWjl6vNRhDiN7vpQ=="],
|
||||
|
||||
"@jest/transform": ["@jest/transform@27.5.1", "", { "dependencies": { "@babel/core": "^7.1.0", "@jest/types": "^27.5.1", "babel-plugin-istanbul": "^6.1.1", "chalk": "^4.0.0", "convert-source-map": "^1.4.0", "fast-json-stable-stringify": "^2.0.0", "graceful-fs": "^4.2.9", "jest-haste-map": "^27.5.1", "jest-regex-util": "^27.5.1", "jest-util": "^27.5.1", "micromatch": "^4.0.4", "pirates": "^4.0.4", "slash": "^3.0.0", "source-map": "^0.6.1", "write-file-atomic": "^3.0.0" } }, "sha512-ipON6WtYgl/1329g5AIJVbUuEh0wZVbdpGwC99Jw4LwuoBNS95MVphU6zOeD9pDkon+LLbFL7lOQRapbB8SCHw=="],
|
||||
|
||||
"@jest/types": ["@jest/types@27.5.1", "", { "dependencies": { "@types/istanbul-lib-coverage": "^2.0.0", "@types/istanbul-reports": "^3.0.0", "@types/node": "*", "@types/yargs": "^16.0.0", "chalk": "^4.0.0" } }, "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw=="],
|
||||
|
||||
"@jridgewell/gen-mapping": ["@jridgewell/gen-mapping@0.3.8", "", { "dependencies": { "@jridgewell/set-array": "^1.2.1", "@jridgewell/sourcemap-codec": "^1.4.10", "@jridgewell/trace-mapping": "^0.3.24" } }, "sha512-imAbBGkb+ebQyxKgzv5Hu2nmROxoDOXHh80evxdoXNOrvAnVx7zimzc1Oo5h9RlfV4vPXaE2iM5pOFbvOCClWA=="],
|
||||
|
||||
"@jridgewell/resolve-uri": ["@jridgewell/resolve-uri@3.1.2", "", {}, "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw=="],
|
||||
|
||||
"@jridgewell/set-array": ["@jridgewell/set-array@1.2.1", "", {}, "sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A=="],
|
||||
|
||||
"@jridgewell/sourcemap-codec": ["@jridgewell/sourcemap-codec@1.5.0", "", {}, "sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ=="],
|
||||
|
||||
"@jridgewell/trace-mapping": ["@jridgewell/trace-mapping@0.3.25", "", { "dependencies": { "@jridgewell/resolve-uri": "^3.1.0", "@jridgewell/sourcemap-codec": "^1.4.14" } }, "sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ=="],
|
||||
|
||||
"@noble/hashes": ["@noble/hashes@1.8.0", "", {}, "sha512-jCs9ldd7NwzpgXDIf6P3+NrHh9/sD6CQdxHyjQI+h/6rDNo88ypBxxz45UDuZHz9r3tNz7N/VInSVoVdtXEI4A=="],
|
||||
|
||||
"@otplib/core": ["@otplib/core@12.0.1", "", {}, "sha512-4sGntwbA/AC+SbPhbsziRiD+jNDdIzsZ3JUyfZwjtKyc/wufl1pnSIaG4Uqx8ymPagujub0o92kgBnB89cuAMA=="],
|
||||
|
||||
"@otplib/plugin-crypto": ["@otplib/plugin-crypto@12.0.1", "", { "dependencies": { "@otplib/core": "^12.0.1" } }, "sha512-qPuhN3QrT7ZZLcLCyKOSNhuijUi9G5guMRVrxq63r9YNOxxQjPm59gVxLM+7xGnHnM6cimY57tuKsjK7y9LM1g=="],
|
||||
|
||||
"@otplib/plugin-thirty-two": ["@otplib/plugin-thirty-two@12.0.1", "", { "dependencies": { "@otplib/core": "^12.0.1", "thirty-two": "^1.0.2" } }, "sha512-MtT+uqRso909UkbrrYpJ6XFjj9D+x2Py7KjTO9JDPhL0bJUYVu5kFP4TFZW4NFAywrAtFRxOVY261u0qwb93gA=="],
|
||||
|
||||
"@otplib/preset-default": ["@otplib/preset-default@12.0.1", "", { "dependencies": { "@otplib/core": "^12.0.1", "@otplib/plugin-crypto": "^12.0.1", "@otplib/plugin-thirty-two": "^12.0.1" } }, "sha512-xf1v9oOJRyXfluBhMdpOkr+bsE+Irt+0D5uHtvg6x1eosfmHCsCC6ej/m7FXiWqdo0+ZUI6xSKDhJwc8yfiOPQ=="],
|
||||
|
||||
"@otplib/preset-v11": ["@otplib/preset-v11@12.0.1", "", { "dependencies": { "@otplib/core": "^12.0.1", "@otplib/plugin-crypto": "^12.0.1", "@otplib/plugin-thirty-two": "^12.0.1" } }, "sha512-9hSetMI7ECqbFiKICrNa4w70deTUfArtwXykPUvSHWOdzOlfa9ajglu7mNCntlvxycTiOAXkQGwjQCzzDEMRMg=="],
|
||||
|
||||
"@paralleldrive/cuid2": ["@paralleldrive/cuid2@2.2.2", "", { "dependencies": { "@noble/hashes": "^1.1.5" } }, "sha512-ZOBkgDwEdoYVlSeRbYYXs0S9MejQofiVYoTbKzy/6GQa39/q5tQU2IX46+shYnUkpEl3wc+J6wRlar7r2EK2xA=="],
|
||||
|
||||
"@sinonjs/commons": ["@sinonjs/commons@1.8.6", "", { "dependencies": { "type-detect": "4.0.8" } }, "sha512-Ky+XkAkqPZSm3NLBeUng77EBQl3cmeJhITaGHdYH8kjVB+aun3S4XBRti2zt17mtt0mIUDiNxYeoJm6drVvBJQ=="],
|
||||
|
||||
"@sinonjs/fake-timers": ["@sinonjs/fake-timers@8.1.0", "", { "dependencies": { "@sinonjs/commons": "^1.7.0" } }, "sha512-OAPJUAtgeINhh/TAlUID4QTs53Njm7xzddaVlEs/SXwgtiD1tW22zAB/W1wdqfrpmikgaWQ9Fw6Ws+hsiRm5Vg=="],
|
||||
|
||||
"@tootallnate/once": ["@tootallnate/once@1.1.2", "", {}, "sha512-RbzJvlNzmRq5c3O09UipeuXno4tA1FE6ikOjxZK0tuxVv3412l64l5t1W5pj4+rJq9vpkm/kwiR07aZXnsKPxw=="],
|
||||
|
||||
"@types/babel__core": ["@types/babel__core@7.20.5", "", { "dependencies": { "@babel/parser": "^7.20.7", "@babel/types": "^7.20.7", "@types/babel__generator": "*", "@types/babel__template": "*", "@types/babel__traverse": "*" } }, "sha512-qoQprZvz5wQFJwMDqeseRXWv3rqMvhgpbXFfVyWhbx9X47POIA6i/+dXefEmZKoAgOaTdaIgNSMqMIU61yRyzA=="],
|
||||
|
||||
"@types/babel__generator": ["@types/babel__generator@7.27.0", "", { "dependencies": { "@babel/types": "^7.0.0" } }, "sha512-ufFd2Xi92OAVPYsy+P4n7/U7e68fex0+Ee8gSG9KX7eo084CWiQ4sdxktvdl0bOPupXtVJPY19zk6EwWqUQ8lg=="],
|
||||
|
||||
"@types/babel__template": ["@types/babel__template@7.4.4", "", { "dependencies": { "@babel/parser": "^7.1.0", "@babel/types": "^7.0.0" } }, "sha512-h/NUaSyG5EyxBIp8YRxo4RMe2/qQgvyowRwVMzhYhBCONbW8PUsg4lkFMrhgZhUe5z3L3MiLDuvyJ/CaPa2A8A=="],
|
||||
|
||||
"@types/babel__traverse": ["@types/babel__traverse@7.20.7", "", { "dependencies": { "@babel/types": "^7.20.7" } }, "sha512-dkO5fhS7+/oos4ciWxyEyjWe48zmG6wbCheo/G2ZnHx4fs3EU6YC6UM8rk56gAjNJ9P3MTH2jo5jb92/K6wbng=="],
|
||||
|
||||
"@types/bcryptjs": ["@types/bcryptjs@2.4.6", "", {}, "sha512-9xlo6R2qDs5uixm0bcIqCeMCE6HiQsIyel9KQySStiyqNl2tnj2mP3DX1Nf56MD6KMenNNlBBsy3LJ7gUEQPXQ=="],
|
||||
|
||||
"@types/cookiejar": ["@types/cookiejar@2.1.5", "", {}, "sha512-he+DHOWReW0nghN24E1WUqM0efK4kI9oTqDm6XmK8ZPe2djZ90BSNdGnIyCLzCPw7/pogPlGbzI2wHGGmi4O/Q=="],
|
||||
|
||||
"@types/faker": ["@types/faker@5.5.9", "", {}, "sha512-uCx6mP3UY5SIO14XlspxsGjgaemrxpssJI0Ol+GfhxtcKpv9pgRZYsS4eeKeHVLje6Qtc8lGszuBI461+gVZBA=="],
|
||||
|
||||
"@types/graceful-fs": ["@types/graceful-fs@4.1.9", "", { "dependencies": { "@types/node": "*" } }, "sha512-olP3sd1qOEe5dXTSaFvQG+02VdRXcdytWLAZsAq1PecU8uqQAhkrnbli7DagjtXKW/Bl7YJbUsa8MPcuc8LHEQ=="],
|
||||
|
||||
"@types/istanbul-lib-coverage": ["@types/istanbul-lib-coverage@2.0.6", "", {}, "sha512-2QF/t/auWm0lsy8XtKVPG19v3sSOQlJe/YHZgfjb/KBBHOGSV+J2q/S671rcq9uTBrLAXmZpqJiaQbMT+zNU1w=="],
|
||||
|
||||
"@types/istanbul-lib-report": ["@types/istanbul-lib-report@3.0.3", "", { "dependencies": { "@types/istanbul-lib-coverage": "*" } }, "sha512-NQn7AHQnk/RSLOxrBbGyJM/aVQ+pjj5HCgasFxc0K/KhoATfQ/47AyUl15I2yBUpihjmas+a+VJBOqecrFH+uA=="],
|
||||
|
||||
"@types/istanbul-reports": ["@types/istanbul-reports@3.0.4", "", { "dependencies": { "@types/istanbul-lib-report": "*" } }, "sha512-pk2B1NWalF9toCRu6gjBzR69syFjP4Od8WRAX+0mmf9lAjCRicLOWc+ZrxZHx/0XRjotgkF9t6iaMJ+aXcOdZQ=="],
|
||||
|
||||
"@types/jest": ["@types/jest@27.5.2", "", { "dependencies": { "jest-matcher-utils": "^27.0.0", "pretty-format": "^27.0.0" } }, "sha512-mpT8LJJ4CMeeahobofYWIjFo0xonRS/HfxnVEPMPFSQdGUt1uHCnoPT7Zhb+sjDU2wz0oKV0OLUR0WzrHNgfeA=="],
|
||||
|
||||
"@types/methods": ["@types/methods@1.1.4", "", {}, "sha512-ymXWVrDiCxTBE3+RIrrP533E70eA+9qu7zdWoHuOmGujkYtzf4HQF96b8nwHLqhuf4ykX61IGRIB38CC6/sImQ=="],
|
||||
|
||||
"@types/node": ["@types/node@17.0.45", "", {}, "sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw=="],
|
||||
|
||||
"@types/node-fetch": ["@types/node-fetch@2.6.12", "", { "dependencies": { "@types/node": "*", "form-data": "^4.0.0" } }, "sha512-8nneRWKCg3rMtF69nLQJnOYUcbafYeFSjqkw3jCRLsqkWFlHaoQrr5mXmofFGOx3DKn7UfmBMyov8ySvLRVldA=="],
|
||||
|
||||
"@types/pg": ["@types/pg@7.14.11", "", { "dependencies": { "@types/node": "*", "pg-protocol": "^1.2.0", "pg-types": "^2.2.0" } }, "sha512-EnZkZ1OMw9DvNfQkn2MTJrwKmhJYDEs5ujWrPfvseWNoI95N8B4HzU/Ltrq5ZfYxDX/Zg8mTzwr6UAyTjjFvXA=="],
|
||||
|
||||
"@types/prettier": ["@types/prettier@2.7.3", "", {}, "sha512-+68kP9yzs4LMp7VNh8gdzMSPZFL44MLGqiHWvttYJe+6qnuVr4Ek9wSBQoveqY/r+LwjCcU29kNVkidwim+kYA=="],
|
||||
|
||||
"@types/rfc2047": ["@types/rfc2047@2.0.3", "", {}, "sha512-ALrav8usNLr6OmfHPPmx6om2rgwCQaZaLw2nW+VoH43ZzU6nPbUhejE5+kyEtqr5F54aLuK9Mv6sRwYCgBYc0w=="],
|
||||
|
||||
"@types/stack-utils": ["@types/stack-utils@2.0.3", "", {}, "sha512-9aEbYZ3TbYMznPdcdr3SmIrLXwC/AKZXQeCf9Pgao5CKb8CyHuEX5jzWPTkvregvhRJHcpRO6BFoGW9ycaOkYw=="],
|
||||
|
||||
"@types/superagent": ["@types/superagent@8.1.9", "", { "dependencies": { "@types/cookiejar": "^2.1.5", "@types/methods": "^1.1.4", "@types/node": "*", "form-data": "^4.0.0" } }, "sha512-pTVjI73witn+9ILmoJdajHGW2jkSaOzhiFYF1Rd3EQ94kymLqB9PjD9ISg7WaALC7+dCHT0FGe9T2LktLq/3GQ=="],
|
||||
|
||||
"@types/supertest": ["@types/supertest@2.0.16", "", { "dependencies": { "@types/superagent": "*" } }, "sha512-6c2ogktZ06tr2ENoZivgm7YnprnhYE4ZoXGMY+oA7IuAf17M8FWvujXZGmxLv8y0PTyts4x5A+erSwVUFA8XSg=="],
|
||||
|
||||
"@types/uuid": ["@types/uuid@7.0.2", "", {}, "sha512-8Ly3zIPTnT0/8RCU6Kg/G3uTICf9sRwYOpUzSIM3503tLIKcnJPRuinHhXngJUy2MntrEf6dlpOHXJju90Qh5w=="],
|
||||
|
||||
"@types/yargs": ["@types/yargs@16.0.9", "", { "dependencies": { "@types/yargs-parser": "*" } }, "sha512-tHhzvkFXZQeTECenFoRljLBYPZJ7jAVxqqtEI0qTLOmuultnFp4I9yKE17vTuhf7BkhCu7I4XuemPgikDVuYqA=="],
|
||||
|
||||
"@types/yargs-parser": ["@types/yargs-parser@21.0.3", "", {}, "sha512-I4q9QU9MQv4oEOz4tAHJtNz1cwuLxn2F3xcc2iV5WdqLPpUnj30aUuxt1mAxYTG+oe8CZMV/+6rU4S4gRDzqtQ=="],
|
||||
|
||||
"abab": ["abab@2.0.6", "", {}, "sha512-j2afSsaIENvHZN2B8GOpF566vZ5WVk5opAiMTvWgaQT8DkbOqsTfvNAvHoRGU2zzP8cPoqys+xHTRDWW8L+/BA=="],
|
||||
|
||||
"acorn": ["acorn@8.15.0", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg=="],
|
||||
|
||||
"acorn-globals": ["acorn-globals@6.0.0", "", { "dependencies": { "acorn": "^7.1.1", "acorn-walk": "^7.1.1" } }, "sha512-ZQl7LOWaF5ePqqcX4hLuv/bLXYQNfNWw2c0/yX/TsPRKamzHcTGQnlCjHT3TsmkOUVEPS3crCxiPfdzE/Trlhg=="],
|
||||
|
||||
"acorn-walk": ["acorn-walk@7.2.0", "", {}, "sha512-OPdCF6GsMIP+Az+aWfAAOEt2/+iVDKE7oy6lJ098aoe59oAmK76qV6Gw60SbZ8jHuG2wH058GF4pLFbYamYrVA=="],
|
||||
|
||||
"agent-base": ["agent-base@6.0.2", "", { "dependencies": { "debug": "4" } }, "sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ=="],
|
||||
|
||||
"ansi-escapes": ["ansi-escapes@4.3.2", "", { "dependencies": { "type-fest": "^0.21.3" } }, "sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ=="],
|
||||
|
||||
"ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="],
|
||||
|
||||
"ansi-styles": ["ansi-styles@5.2.0", "", {}, "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA=="],
|
||||
|
||||
"anymatch": ["anymatch@3.1.3", "", { "dependencies": { "normalize-path": "^3.0.0", "picomatch": "^2.0.4" } }, "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw=="],
|
||||
|
||||
"argparse": ["argparse@1.0.10", "", { "dependencies": { "sprintf-js": "~1.0.2" } }, "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg=="],
|
||||
|
||||
"asap": ["asap@2.0.6", "", {}, "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA=="],
|
||||
|
||||
"asynckit": ["asynckit@0.4.0", "", {}, "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q=="],
|
||||
|
||||
"axios": ["axios@1.10.0", "", { "dependencies": { "follow-redirects": "^1.15.6", "form-data": "^4.0.0", "proxy-from-env": "^1.1.0" } }, "sha512-/1xYAC4MP/HEG+3duIhFr4ZQXR4sQXOIe+o6sdqzeykGLx6Upp/1p8MHqhINOvGeP7xyNHe7tsiJByc4SSVUxw=="],
|
||||
|
||||
"babel-jest": ["babel-jest@27.5.1", "", { "dependencies": { "@jest/transform": "^27.5.1", "@jest/types": "^27.5.1", "@types/babel__core": "^7.1.14", "babel-plugin-istanbul": "^6.1.1", "babel-preset-jest": "^27.5.1", "chalk": "^4.0.0", "graceful-fs": "^4.2.9", "slash": "^3.0.0" }, "peerDependencies": { "@babel/core": "^7.8.0" } }, "sha512-cdQ5dXjGRd0IBRATiQ4mZGlGlRE8kJpjPOixdNRdT+m3UcNqmYWN6rK6nvtXYfY3D76cb8s/O1Ss8ea24PIwcg=="],
|
||||
|
||||
"babel-plugin-istanbul": ["babel-plugin-istanbul@6.1.1", "", { "dependencies": { "@babel/helper-plugin-utils": "^7.0.0", "@istanbuljs/load-nyc-config": "^1.0.0", "@istanbuljs/schema": "^0.1.2", "istanbul-lib-instrument": "^5.0.4", "test-exclude": "^6.0.0" } }, "sha512-Y1IQok9821cC9onCx5otgFfRm7Lm+I+wwxOx738M/WLPZ9Q42m4IG5W0FNX8WLL2gYMZo3JkuXIH2DOpWM+qwA=="],
|
||||
|
||||
"babel-plugin-jest-hoist": ["babel-plugin-jest-hoist@27.5.1", "", { "dependencies": { "@babel/template": "^7.3.3", "@babel/types": "^7.3.3", "@types/babel__core": "^7.0.0", "@types/babel__traverse": "^7.0.6" } }, "sha512-50wCwD5EMNW4aRpOwtqzyZHIewTYNxLA4nhB+09d8BIssfNfzBRhkBIHiaPv1Si226TQSvp8gxAJm2iY2qs2hQ=="],
|
||||
|
||||
"babel-preset-current-node-syntax": ["babel-preset-current-node-syntax@1.1.0", "", { "dependencies": { "@babel/plugin-syntax-async-generators": "^7.8.4", "@babel/plugin-syntax-bigint": "^7.8.3", "@babel/plugin-syntax-class-properties": "^7.12.13", "@babel/plugin-syntax-class-static-block": "^7.14.5", "@babel/plugin-syntax-import-attributes": "^7.24.7", "@babel/plugin-syntax-import-meta": "^7.10.4", "@babel/plugin-syntax-json-strings": "^7.8.3", "@babel/plugin-syntax-logical-assignment-operators": "^7.10.4", "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.3", "@babel/plugin-syntax-numeric-separator": "^7.10.4", "@babel/plugin-syntax-object-rest-spread": "^7.8.3", "@babel/plugin-syntax-optional-catch-binding": "^7.8.3", "@babel/plugin-syntax-optional-chaining": "^7.8.3", "@babel/plugin-syntax-private-property-in-object": "^7.14.5", "@babel/plugin-syntax-top-level-await": "^7.14.5" }, "peerDependencies": { "@babel/core": "^7.0.0" } }, "sha512-ldYss8SbBlWva1bs28q78Ju5Zq1F+8BrqBZZ0VFhLBvhh6lCpC2o3gDJi/5DRLs9FgYZCnmPYIVFU4lRXCkyUw=="],
|
||||
|
||||
"babel-preset-jest": ["babel-preset-jest@27.5.1", "", { "dependencies": { "babel-plugin-jest-hoist": "^27.5.1", "babel-preset-current-node-syntax": "^1.0.0" }, "peerDependencies": { "@babel/core": "^7.0.0" } }, "sha512-Nptf2FzlPCWYuJg41HBqXVT8ym6bXOevuCTbhxlUpjwtysGaIWFvDEjp4y+G7fl13FgOdjs7P/DmErqH7da0Ag=="],
|
||||
|
||||
"balanced-match": ["balanced-match@1.0.2", "", {}, "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="],
|
||||
|
||||
"bcryptjs": ["bcryptjs@2.4.3", "", {}, "sha512-V/Hy/X9Vt7f3BbPJEi8BdVFMByHi+jNXrYkW3huaybV/kQ0KJg0Y6PkEMbn+zeT+i+SiKZ/HMqJGIIt4LZDqNQ=="],
|
||||
|
||||
"brace-expansion": ["brace-expansion@1.1.12", "", { "dependencies": { "balanced-match": "^1.0.0", "concat-map": "0.0.1" } }, "sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg=="],
|
||||
|
||||
"braces": ["braces@3.0.3", "", { "dependencies": { "fill-range": "^7.1.1" } }, "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA=="],
|
||||
|
||||
"browser-process-hrtime": ["browser-process-hrtime@1.0.0", "", {}, "sha512-9o5UecI3GhkpM6DrXr69PblIuWxPKk9Y0jHBRhdocZ2y7YECBFCsHm79Pr3OyR2AvjhDkabFJaDJMYRazHgsow=="],
|
||||
|
||||
"browserslist": ["browserslist@4.25.0", "", { "dependencies": { "caniuse-lite": "^1.0.30001718", "electron-to-chromium": "^1.5.160", "node-releases": "^2.0.19", "update-browserslist-db": "^1.1.3" }, "bin": { "browserslist": "cli.js" } }, "sha512-PJ8gYKeS5e/whHBh8xrwYK+dAvEj7JXtz6uTucnMRB8OiGTsKccFekoRrjajPBHV8oOY+2tI4uxeceSimKwMFA=="],
|
||||
|
||||
"bs-logger": ["bs-logger@0.2.6", "", { "dependencies": { "fast-json-stable-stringify": "2.x" } }, "sha512-pd8DCoxmbgc7hyPKOvxtqNcjYoOsABPQdcCUjGp3d42VR2CX1ORhk2A87oqqu5R1kk+76nsxZupkmyd+MVtCog=="],
|
||||
|
||||
"bser": ["bser@2.1.1", "", { "dependencies": { "node-int64": "^0.4.0" } }, "sha512-gQxTNE/GAfIIrmHLUE3oJyp5FO6HRBfhjnw4/wMmA63ZGDJnWBmgY/lyQBpnDUkGmAhbSe39tx2d/iTOAfglwQ=="],
|
||||
|
||||
"buffer-from": ["buffer-from@1.1.2", "", {}, "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ=="],
|
||||
|
||||
"call-bind-apply-helpers": ["call-bind-apply-helpers@1.0.2", "", { "dependencies": { "es-errors": "^1.3.0", "function-bind": "^1.1.2" } }, "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ=="],
|
||||
|
||||
"call-bound": ["call-bound@1.0.4", "", { "dependencies": { "call-bind-apply-helpers": "^1.0.2", "get-intrinsic": "^1.3.0" } }, "sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg=="],
|
||||
|
||||
"callsites": ["callsites@3.1.0", "", {}, "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ=="],
|
||||
|
||||
"camelcase": ["camelcase@5.3.1", "", {}, "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg=="],
|
||||
|
||||
"caniuse-lite": ["caniuse-lite@1.0.30001724", "", {}, "sha512-WqJo7p0TbHDOythNTqYujmaJTvtYRZrjpP8TCvH6Vb9CYJerJNKamKzIWOM4BkQatWj9H2lYulpdAQNBe7QhNA=="],
|
||||
|
||||
"chalk": ["chalk@4.1.2", "", { "dependencies": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" } }, "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA=="],
|
||||
|
||||
"char-regex": ["char-regex@1.0.2", "", {}, "sha512-kWWXztvZ5SBQV+eRgKFeh8q5sLuZY2+8WUIzlxWVTg+oGwY14qylx1KbKzHd8P6ZYkAg0xyIDU9JMHhyJMZ1jw=="],
|
||||
|
||||
"ci-info": ["ci-info@3.9.0", "", {}, "sha512-NIxF55hv4nSqQswkAeiOi1r83xy8JldOFDTWiug55KBu9Jnblncd2U6ViHmYgHf01TPZS77NJBhBMKdWj9HQMQ=="],
|
||||
|
||||
"cjs-module-lexer": ["cjs-module-lexer@1.4.3", "", {}, "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q=="],
|
||||
|
||||
"cliui": ["cliui@7.0.4", "", { "dependencies": { "string-width": "^4.2.0", "strip-ansi": "^6.0.0", "wrap-ansi": "^7.0.0" } }, "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ=="],
|
||||
|
||||
"co": ["co@4.6.0", "", {}, "sha512-QVb0dM5HvG+uaxitm8wONl7jltx8dqhfU33DcqtOZcLSVIKSDDLDi7+0LbAKiyI8hD9u42m2YxXSkMGWThaecQ=="],
|
||||
|
||||
"collect-v8-coverage": ["collect-v8-coverage@1.0.2", "", {}, "sha512-lHl4d5/ONEbLlJvaJNtsF/Lz+WvB07u2ycqTYbdrq7UypDXailES4valYb2eWiJFxZlVmpGekfqoxQhzyFdT4Q=="],
|
||||
|
||||
"color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="],
|
||||
|
||||
"color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="],
|
||||
|
||||
"combined-stream": ["combined-stream@1.0.8", "", { "dependencies": { "delayed-stream": "~1.0.0" } }, "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg=="],
|
||||
|
||||
"component-emitter": ["component-emitter@1.3.1", "", {}, "sha512-T0+barUSQRTUQASh8bx02dl+DhF54GtIDY13Y3m9oWTklKbb3Wv974meRpeZ3lp1JpLVECWWNHC4vaG2XHXouQ=="],
|
||||
|
||||
"concat-map": ["concat-map@0.0.1", "", {}, "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg=="],
|
||||
|
||||
"convert-source-map": ["convert-source-map@2.0.0", "", {}, "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg=="],
|
||||
|
||||
"cookiejar": ["cookiejar@2.1.4", "", {}, "sha512-LDx6oHrK+PhzLKJU9j5S7/Y3jM/mUHvD/DeI1WQmJn652iPC5Y4TBzC9l+5OMOXlyTTA+SmVUPm0HQUwpD5Jqw=="],
|
||||
|
||||
"cross-spawn": ["cross-spawn@7.0.6", "", { "dependencies": { "path-key": "^3.1.0", "shebang-command": "^2.0.0", "which": "^2.0.1" } }, "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA=="],
|
||||
|
||||
"cssom": ["cssom@0.4.4", "", {}, "sha512-p3pvU7r1MyyqbTk+WbNJIgJjG2VmTIaB10rI93LzVPrmDJKkzKYMtxxyAvQXR/NS6otuzveI7+7BBq3SjBS2mw=="],
|
||||
|
||||
"cssstyle": ["cssstyle@2.3.0", "", { "dependencies": { "cssom": "~0.3.6" } }, "sha512-AZL67abkUzIuvcHqk7c09cezpGNcxUxU4Ioi/05xHk4DQeTkWmGYftIE6ctU6AEt+Gn4n1lDStOtj7FKycP71A=="],
|
||||
|
||||
"data-urls": ["data-urls@2.0.0", "", { "dependencies": { "abab": "^2.0.3", "whatwg-mimetype": "^2.3.0", "whatwg-url": "^8.0.0" } }, "sha512-X5eWTSXO/BJmpdIKCRuKUgSCgAN0OwliVK3yPKbwIWU1Tdw5BRajxlzMidvh+gwko9AfQ9zIj52pzF91Q3YAvQ=="],
|
||||
|
||||
"debug": ["debug@4.4.1", "", { "dependencies": { "ms": "^2.1.3" } }, "sha512-KcKCqiftBJcZr++7ykoDIEwSa3XWowTfNPo92BYxjXiyYEVrUQh2aLyhxBCwww+heortUFxEJYcRzosstTEBYQ=="],
|
||||
|
||||
"decimal.js": ["decimal.js@10.5.0", "", {}, "sha512-8vDa8Qxvr/+d94hSh5P3IJwI5t8/c0KsMp+g8bNw9cY2icONa5aPfvKeieW1WlG0WQYwwhJ7mjui2xtiePQSXw=="],
|
||||
|
||||
"dedent": ["dedent@0.7.0", "", {}, "sha512-Q6fKUPqnAHAyhiUgFU7BUzLiv0kd8saH9al7tnu5Q/okj6dnupxyTgFIBjVzJATdfIAm9NAsvXNzjaKa+bxVyA=="],
|
||||
|
||||
"deepmerge": ["deepmerge@4.3.1", "", {}, "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A=="],
|
||||
|
||||
"delayed-stream": ["delayed-stream@1.0.0", "", {}, "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ=="],
|
||||
|
||||
"detect-newline": ["detect-newline@3.1.0", "", {}, "sha512-TLz+x/vEXm/Y7P7wn1EJFNLxYpUD4TgMosxY6fAVJUnJMbupHBOncxyWUG9OpTaH9EBD7uFI5LfEgmMOc54DsA=="],
|
||||
|
||||
"dezalgo": ["dezalgo@1.0.4", "", { "dependencies": { "asap": "^2.0.0", "wrappy": "1" } }, "sha512-rXSP0bf+5n0Qonsb+SVVfNfIsimO4HEtmnIpPHY8Q1UCzKlQrDMfdobr8nJOOsRgWCyMRqeSBQzmWUMq7zvVig=="],
|
||||
|
||||
"diff-sequences": ["diff-sequences@27.5.1", "", {}, "sha512-k1gCAXAsNgLwEL+Y8Wvl+M6oEFj5bgazfZULpS5CneoPPXRaCCW7dm+q21Ky2VEE5X+VeRDBVg1Pcvvsr4TtNQ=="],
|
||||
|
||||
"domexception": ["domexception@2.0.1", "", { "dependencies": { "webidl-conversions": "^5.0.0" } }, "sha512-yxJ2mFy/sibVQlu5qHjOkf9J3K6zgmCxgJ94u2EdvDOV09H+32LtRswEcUsmUWN72pVLOEnTSRaIVVzVQgS0dg=="],
|
||||
|
||||
"dunder-proto": ["dunder-proto@1.0.1", "", { "dependencies": { "call-bind-apply-helpers": "^1.0.1", "es-errors": "^1.3.0", "gopd": "^1.2.0" } }, "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A=="],
|
||||
|
||||
"electron-to-chromium": ["electron-to-chromium@1.5.171", "", {}, "sha512-scWpzXEJEMrGJa4Y6m/tVotb0WuvNmasv3wWVzUAeCgKU0ToFOhUW6Z+xWnRQANMYGxN4ngJXIThgBJOqzVPCQ=="],
|
||||
|
||||
"emittery": ["emittery@0.8.1", "", {}, "sha512-uDfvUjVrfGJJhymx/kz6prltenw1u7WrCg1oa94zYY8xxVpLLUu045LAT0dhDZdXG58/EpPL/5kA180fQ/qudg=="],
|
||||
|
||||
"emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="],
|
||||
|
||||
"error-ex": ["error-ex@1.3.2", "", { "dependencies": { "is-arrayish": "^0.2.1" } }, "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g=="],
|
||||
|
||||
"es-define-property": ["es-define-property@1.0.1", "", {}, "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g=="],
|
||||
|
||||
"es-errors": ["es-errors@1.3.0", "", {}, "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw=="],
|
||||
|
||||
"es-object-atoms": ["es-object-atoms@1.1.1", "", { "dependencies": { "es-errors": "^1.3.0" } }, "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA=="],
|
||||
|
||||
"es-set-tostringtag": ["es-set-tostringtag@2.1.0", "", { "dependencies": { "es-errors": "^1.3.0", "get-intrinsic": "^1.2.6", "has-tostringtag": "^1.0.2", "hasown": "^2.0.2" } }, "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA=="],
|
||||
|
||||
"escalade": ["escalade@3.2.0", "", {}, "sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA=="],
|
||||
|
||||
"escape-string-regexp": ["escape-string-regexp@2.0.0", "", {}, "sha512-UpzcLCXolUWcNu5HtVMHYdXJjArjsF9C0aNnquZYY4uW/Vu0miy5YoWvbV345HauVvcAUnpRuhMMcqTcGOY2+w=="],
|
||||
|
||||
"escodegen": ["escodegen@2.1.0", "", { "dependencies": { "esprima": "^4.0.1", "estraverse": "^5.2.0", "esutils": "^2.0.2" }, "optionalDependencies": { "source-map": "~0.6.1" }, "bin": { "esgenerate": "bin/esgenerate.js", "escodegen": "bin/escodegen.js" } }, "sha512-2NlIDTwUWJN0mRPQOdtQBzbUHvdGY2P1VXSyU83Q3xKxM7WHX2Ql8dKq782Q9TgQUNOLEzEYu9bzLNj1q88I5w=="],
|
||||
|
||||
"esprima": ["esprima@4.0.1", "", { "bin": { "esparse": "./bin/esparse.js", "esvalidate": "./bin/esvalidate.js" } }, "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A=="],
|
||||
|
||||
"estraverse": ["estraverse@5.3.0", "", {}, "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA=="],
|
||||
|
||||
"esutils": ["esutils@2.0.3", "", {}, "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g=="],
|
||||
|
||||
"execa": ["execa@5.1.1", "", { "dependencies": { "cross-spawn": "^7.0.3", "get-stream": "^6.0.0", "human-signals": "^2.1.0", "is-stream": "^2.0.0", "merge-stream": "^2.0.0", "npm-run-path": "^4.0.1", "onetime": "^5.1.2", "signal-exit": "^3.0.3", "strip-final-newline": "^2.0.0" } }, "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg=="],
|
||||
|
||||
"exit": ["exit@0.1.2", "", {}, "sha512-Zk/eNKV2zbjpKzrsQ+n1G6poVbErQxJ0LBOJXaKZ1EViLzH+hrLu9cdXI4zw9dBQJslwBEpbQ2P1oS7nDxs6jQ=="],
|
||||
|
||||
"expect": ["expect@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "jest-get-type": "^27.5.1", "jest-matcher-utils": "^27.5.1", "jest-message-util": "^27.5.1" } }, "sha512-E1q5hSUG2AmYQwQJ041nvgpkODHQvB+RKlB4IYdru6uJsyFTRyZAP463M+1lINorwbqAmUggi6+WwkD8lCS/Dw=="],
|
||||
|
||||
"faker": ["faker@5.5.3", "", {}, "sha512-wLTv2a28wjUyWkbnX7u/ABZBkUkIF2fCd73V6P2oFqEGEktDfzWx4UxrSqtPRw0xPRAcjeAOIiJWqZm3pP4u3g=="],
|
||||
|
||||
"fast-json-stable-stringify": ["fast-json-stable-stringify@2.1.0", "", {}, "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw=="],
|
||||
|
||||
"fast-safe-stringify": ["fast-safe-stringify@2.1.1", "", {}, "sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA=="],
|
||||
|
||||
"fb-watchman": ["fb-watchman@2.0.2", "", { "dependencies": { "bser": "2.1.1" } }, "sha512-p5161BqbuCaSnB8jIbzQHOlpgsPmK5rJVDfDKO91Axs5NC1uu3HRQm6wt9cd9/+GtQQIO53JdGXXoyDpTAsgYA=="],
|
||||
|
||||
"fill-range": ["fill-range@7.1.1", "", { "dependencies": { "to-regex-range": "^5.0.1" } }, "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg=="],
|
||||
|
||||
"find-up": ["find-up@4.1.0", "", { "dependencies": { "locate-path": "^5.0.0", "path-exists": "^4.0.0" } }, "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw=="],
|
||||
|
||||
"follow-redirects": ["follow-redirects@1.15.9", "", {}, "sha512-gew4GsXizNgdoRyqmyfMHyAmXsZDk6mHkSxZFCzW9gwlbtOW44CDtYavM+y+72qD/Vq2l550kMF52DT8fOLJqQ=="],
|
||||
|
||||
"form-data": ["form-data@4.0.3", "", { "dependencies": { "asynckit": "^0.4.0", "combined-stream": "^1.0.8", "es-set-tostringtag": "^2.1.0", "hasown": "^2.0.2", "mime-types": "^2.1.12" } }, "sha512-qsITQPfmvMOSAdeyZ+12I1c+CKSstAFAwu+97zrnWAbIr5u8wfsExUzCesVLC8NgHuRUqNN4Zy6UPWUTRGslcA=="],
|
||||
|
||||
"formidable": ["formidable@2.1.5", "", { "dependencies": { "@paralleldrive/cuid2": "^2.2.2", "dezalgo": "^1.0.4", "once": "^1.4.0", "qs": "^6.11.0" } }, "sha512-Oz5Hwvwak/DCaXVVUtPn4oLMLLy1CdclLKO1LFgU7XzDpVMUU5UjlSLpGMocyQNNk8F6IJW9M/YdooSn2MRI+Q=="],
|
||||
|
||||
"fs.realpath": ["fs.realpath@1.0.0", "", {}, "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw=="],
|
||||
|
||||
"fsevents": ["fsevents@2.3.3", "", { "os": "darwin" }, "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw=="],
|
||||
|
||||
"function-bind": ["function-bind@1.1.2", "", {}, "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA=="],
|
||||
|
||||
"gensync": ["gensync@1.0.0-beta.2", "", {}, "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg=="],
|
||||
|
||||
"get-caller-file": ["get-caller-file@2.0.5", "", {}, "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg=="],
|
||||
|
||||
"get-intrinsic": ["get-intrinsic@1.3.0", "", { "dependencies": { "call-bind-apply-helpers": "^1.0.2", "es-define-property": "^1.0.1", "es-errors": "^1.3.0", "es-object-atoms": "^1.1.1", "function-bind": "^1.1.2", "get-proto": "^1.0.1", "gopd": "^1.2.0", "has-symbols": "^1.1.0", "hasown": "^2.0.2", "math-intrinsics": "^1.1.0" } }, "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ=="],
|
||||
|
||||
"get-package-type": ["get-package-type@0.1.0", "", {}, "sha512-pjzuKtY64GYfWizNAJ0fr9VqttZkNiK2iS430LtIHzjBEr6bX8Am2zm4sW4Ro5wjWW5cAlRL1qAMTcXbjNAO2Q=="],
|
||||
|
||||
"get-proto": ["get-proto@1.0.1", "", { "dependencies": { "dunder-proto": "^1.0.1", "es-object-atoms": "^1.0.0" } }, "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g=="],
|
||||
|
||||
"get-stream": ["get-stream@6.0.1", "", {}, "sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg=="],
|
||||
|
||||
"glob": ["glob@7.2.3", "", { "dependencies": { "fs.realpath": "^1.0.0", "inflight": "^1.0.4", "inherits": "2", "minimatch": "^3.1.1", "once": "^1.3.0", "path-is-absolute": "^1.0.0" } }, "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q=="],
|
||||
|
||||
"globals": ["globals@11.12.0", "", {}, "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA=="],
|
||||
|
||||
"gopd": ["gopd@1.2.0", "", {}, "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg=="],
|
||||
|
||||
"graceful-fs": ["graceful-fs@4.2.11", "", {}, "sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ=="],
|
||||
|
||||
"has-flag": ["has-flag@4.0.0", "", {}, "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ=="],
|
||||
|
||||
"has-symbols": ["has-symbols@1.1.0", "", {}, "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ=="],
|
||||
|
||||
"has-tostringtag": ["has-tostringtag@1.0.2", "", { "dependencies": { "has-symbols": "^1.0.3" } }, "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw=="],
|
||||
|
||||
"hasown": ["hasown@2.0.2", "", { "dependencies": { "function-bind": "^1.1.2" } }, "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ=="],
|
||||
|
||||
"html-encoding-sniffer": ["html-encoding-sniffer@2.0.1", "", { "dependencies": { "whatwg-encoding": "^1.0.5" } }, "sha512-D5JbOMBIR/TVZkubHT+OyT2705QvogUW4IBn6nHd756OwieSF9aDYFj4dv6HHEVGYbHaLETa3WggZYWWMyy3ZQ=="],
|
||||
|
||||
"html-escaper": ["html-escaper@2.0.2", "", {}, "sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg=="],
|
||||
|
||||
"http-proxy-agent": ["http-proxy-agent@4.0.1", "", { "dependencies": { "@tootallnate/once": "1", "agent-base": "6", "debug": "4" } }, "sha512-k0zdNgqWTGA6aeIRVpvfVob4fL52dTfaehylg0Y4UvSySvOq/Y+BOyPrgpUrA7HylqvU8vIZGsRuXmspskV0Tg=="],
|
||||
|
||||
"http-status-codes": ["http-status-codes@2.3.0", "", {}, "sha512-RJ8XvFvpPM/Dmc5SV+dC4y5PCeOhT3x1Hq0NU3rjGeg5a/CqlhZ7uudknPwZFz4aeAXDcbAyaeP7GAo9lvngtA=="],
|
||||
|
||||
"https-proxy-agent": ["https-proxy-agent@5.0.1", "", { "dependencies": { "agent-base": "6", "debug": "4" } }, "sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA=="],
|
||||
|
||||
"human-signals": ["human-signals@2.1.0", "", {}, "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw=="],
|
||||
|
||||
"iconv-lite": ["iconv-lite@0.4.5", "", {}, "sha512-LQ4GtDkFagYaac8u4rE73zWu7h0OUUmR0qVBOgzLyFSoJhoDG2xV9PZJWWyVVcYha/9/RZzQHUinFMbNKiOoAA=="],
|
||||
|
||||
"import-local": ["import-local@3.2.0", "", { "dependencies": { "pkg-dir": "^4.2.0", "resolve-cwd": "^3.0.0" }, "bin": { "import-local-fixture": "fixtures/cli.js" } }, "sha512-2SPlun1JUPWoM6t3F0dw0FkCF/jWY8kttcY4f599GLTSjh2OCuuhdTkJQsEcZzBqbXZGKMK2OqW1oZsjtf/gQA=="],
|
||||
|
||||
"imurmurhash": ["imurmurhash@0.1.4", "", {}, "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA=="],
|
||||
|
||||
"inflight": ["inflight@1.0.6", "", { "dependencies": { "once": "^1.3.0", "wrappy": "1" } }, "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA=="],
|
||||
|
||||
"inherits": ["inherits@2.0.4", "", {}, "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ=="],
|
||||
|
||||
"is-arrayish": ["is-arrayish@0.2.1", "", {}, "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg=="],
|
||||
|
||||
"is-core-module": ["is-core-module@2.16.1", "", { "dependencies": { "hasown": "^2.0.2" } }, "sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w=="],
|
||||
|
||||
"is-fullwidth-code-point": ["is-fullwidth-code-point@3.0.0", "", {}, "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg=="],
|
||||
|
||||
"is-generator-fn": ["is-generator-fn@2.1.0", "", {}, "sha512-cTIB4yPYL/Grw0EaSzASzg6bBy9gqCofvWN8okThAYIxKJZC+udlRAmGbM0XLeniEJSs8uEgHPGuHSe1XsOLSQ=="],
|
||||
|
||||
"is-number": ["is-number@7.0.0", "", {}, "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng=="],
|
||||
|
||||
"is-potential-custom-element-name": ["is-potential-custom-element-name@1.0.1", "", {}, "sha512-bCYeRA2rVibKZd+s2625gGnGF/t7DSqDs4dP7CrLA1m7jKWz6pps0LpYLJN8Q64HtmPKJ1hrN3nzPNKFEKOUiQ=="],
|
||||
|
||||
"is-stream": ["is-stream@2.0.1", "", {}, "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg=="],
|
||||
|
||||
"is-typedarray": ["is-typedarray@1.0.0", "", {}, "sha512-cyA56iCMHAh5CdzjJIa4aohJyeO1YbwLi3Jc35MmRU6poroFjIGZzUzupGiRPOjgHg9TLu43xbpwXk523fMxKA=="],
|
||||
|
||||
"isexe": ["isexe@2.0.0", "", {}, "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="],
|
||||
|
||||
"istanbul-lib-coverage": ["istanbul-lib-coverage@3.2.2", "", {}, "sha512-O8dpsF+r0WV/8MNRKfnmrtCWhuKjxrq2w+jpzBL5UZKTi2LeVWnWOmWRxFlesJONmc+wLAGvKQZEOanko0LFTg=="],
|
||||
|
||||
"istanbul-lib-instrument": ["istanbul-lib-instrument@5.2.1", "", { "dependencies": { "@babel/core": "^7.12.3", "@babel/parser": "^7.14.7", "@istanbuljs/schema": "^0.1.2", "istanbul-lib-coverage": "^3.2.0", "semver": "^6.3.0" } }, "sha512-pzqtp31nLv/XFOzXGuvhCb8qhjmTVo5vjVk19XE4CRlSWz0KoeJ3bw9XsA7nOp9YBf4qHjwBxkDzKcME/J29Yg=="],
|
||||
|
||||
"istanbul-lib-report": ["istanbul-lib-report@3.0.1", "", { "dependencies": { "istanbul-lib-coverage": "^3.0.0", "make-dir": "^4.0.0", "supports-color": "^7.1.0" } }, "sha512-GCfE1mtsHGOELCU8e/Z7YWzpmybrx/+dSTfLrvY8qRmaY6zXTKWn6WQIjaAFw069icm6GVMNkgu0NzI4iPZUNw=="],
|
||||
|
||||
"istanbul-lib-source-maps": ["istanbul-lib-source-maps@4.0.1", "", { "dependencies": { "debug": "^4.1.1", "istanbul-lib-coverage": "^3.0.0", "source-map": "^0.6.1" } }, "sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw=="],
|
||||
|
||||
"istanbul-reports": ["istanbul-reports@3.1.7", "", { "dependencies": { "html-escaper": "^2.0.0", "istanbul-lib-report": "^3.0.0" } }, "sha512-BewmUXImeuRk2YY0PVbxgKAysvhRPUQE0h5QRM++nVWyubKGV0l8qQ5op8+B2DOmwSe63Jivj0BjkPQVf8fP5g=="],
|
||||
|
||||
"jest": ["jest@27.5.1", "", { "dependencies": { "@jest/core": "^27.5.1", "import-local": "^3.0.2", "jest-cli": "^27.5.1" }, "peerDependencies": { "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" }, "optionalPeers": ["node-notifier"], "bin": { "jest": "bin/jest.js" } }, "sha512-Yn0mADZB89zTtjkPJEXwrac3LHudkQMR+Paqa8uxJHCBr9agxztUifWCyiYrjhMPBoUVBjyny0I7XH6ozDr7QQ=="],
|
||||
|
||||
"jest-changed-files": ["jest-changed-files@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "execa": "^5.0.0", "throat": "^6.0.1" } }, "sha512-buBLMiByfWGCoMsLLzGUUSpAmIAGnbR2KJoMN10ziLhOLvP4e0SlypHnAel8iqQXTrcbmfEY9sSqae5sgUsTvw=="],
|
||||
|
||||
"jest-circus": ["jest-circus@27.5.1", "", { "dependencies": { "@jest/environment": "^27.5.1", "@jest/test-result": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "chalk": "^4.0.0", "co": "^4.6.0", "dedent": "^0.7.0", "expect": "^27.5.1", "is-generator-fn": "^2.0.0", "jest-each": "^27.5.1", "jest-matcher-utils": "^27.5.1", "jest-message-util": "^27.5.1", "jest-runtime": "^27.5.1", "jest-snapshot": "^27.5.1", "jest-util": "^27.5.1", "pretty-format": "^27.5.1", "slash": "^3.0.0", "stack-utils": "^2.0.3", "throat": "^6.0.1" } }, "sha512-D95R7x5UtlMA5iBYsOHFFbMD/GVA4R/Kdq15f7xYWUfWHBto9NYRsOvnSauTgdF+ogCpJ4tyKOXhUifxS65gdw=="],
|
||||
|
||||
"jest-cli": ["jest-cli@27.5.1", "", { "dependencies": { "@jest/core": "^27.5.1", "@jest/test-result": "^27.5.1", "@jest/types": "^27.5.1", "chalk": "^4.0.0", "exit": "^0.1.2", "graceful-fs": "^4.2.9", "import-local": "^3.0.2", "jest-config": "^27.5.1", "jest-util": "^27.5.1", "jest-validate": "^27.5.1", "prompts": "^2.0.1", "yargs": "^16.2.0" }, "peerDependencies": { "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" }, "optionalPeers": ["node-notifier"], "bin": { "jest": "bin/jest.js" } }, "sha512-Hc6HOOwYq4/74/c62dEE3r5elx8wjYqxY0r0G/nFrLDPMFRu6RA/u8qINOIkvhxG7mMQ5EJsOGfRpI8L6eFUVw=="],
|
||||
|
||||
"jest-config": ["jest-config@27.5.1", "", { "dependencies": { "@babel/core": "^7.8.0", "@jest/test-sequencer": "^27.5.1", "@jest/types": "^27.5.1", "babel-jest": "^27.5.1", "chalk": "^4.0.0", "ci-info": "^3.2.0", "deepmerge": "^4.2.2", "glob": "^7.1.1", "graceful-fs": "^4.2.9", "jest-circus": "^27.5.1", "jest-environment-jsdom": "^27.5.1", "jest-environment-node": "^27.5.1", "jest-get-type": "^27.5.1", "jest-jasmine2": "^27.5.1", "jest-regex-util": "^27.5.1", "jest-resolve": "^27.5.1", "jest-runner": "^27.5.1", "jest-util": "^27.5.1", "jest-validate": "^27.5.1", "micromatch": "^4.0.4", "parse-json": "^5.2.0", "pretty-format": "^27.5.1", "slash": "^3.0.0", "strip-json-comments": "^3.1.1" }, "peerDependencies": { "ts-node": ">=9.0.0" }, "optionalPeers": ["ts-node"] }, "sha512-5sAsjm6tGdsVbW9ahcChPAFCk4IlkQUknH5AvKjuLTSlcO/wCZKyFdn7Rg0EkC+OGgWODEy2hDpWB1PgzH0JNA=="],
|
||||
|
||||
"jest-diff": ["jest-diff@27.5.1", "", { "dependencies": { "chalk": "^4.0.0", "diff-sequences": "^27.5.1", "jest-get-type": "^27.5.1", "pretty-format": "^27.5.1" } }, "sha512-m0NvkX55LDt9T4mctTEgnZk3fmEg3NRYutvMPWM/0iPnkFj2wIeF45O1718cMSOFO1vINkqmxqD8vE37uTEbqw=="],
|
||||
|
||||
"jest-docblock": ["jest-docblock@27.5.1", "", { "dependencies": { "detect-newline": "^3.0.0" } }, "sha512-rl7hlABeTsRYxKiUfpHrQrG4e2obOiTQWfMEH3PxPjOtdsfLQO4ReWSZaQ7DETm4xu07rl4q/h4zcKXyU0/OzQ=="],
|
||||
|
||||
"jest-each": ["jest-each@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "chalk": "^4.0.0", "jest-get-type": "^27.5.1", "jest-util": "^27.5.1", "pretty-format": "^27.5.1" } }, "sha512-1Ff6p+FbhT/bXQnEouYy00bkNSY7OUpfIcmdl8vZ31A1UUaurOLPA8a8BbJOF2RDUElwJhmeaV7LnagI+5UwNQ=="],
|
||||
|
||||
"jest-environment-jsdom": ["jest-environment-jsdom@27.5.1", "", { "dependencies": { "@jest/environment": "^27.5.1", "@jest/fake-timers": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "jest-mock": "^27.5.1", "jest-util": "^27.5.1", "jsdom": "^16.6.0" } }, "sha512-TFBvkTC1Hnnnrka/fUb56atfDtJ9VMZ94JkjTbggl1PEpwrYtUBKMezB3inLmWqQsXYLcMwNoDQwoBTAvFfsfw=="],
|
||||
|
||||
"jest-environment-node": ["jest-environment-node@27.5.1", "", { "dependencies": { "@jest/environment": "^27.5.1", "@jest/fake-timers": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "jest-mock": "^27.5.1", "jest-util": "^27.5.1" } }, "sha512-Jt4ZUnxdOsTGwSRAfKEnE6BcwsSPNOijjwifq5sDFSA2kesnXTvNqKHYgM0hDq3549Uf/KzdXNYn4wMZJPlFLw=="],
|
||||
|
||||
"jest-get-type": ["jest-get-type@27.5.1", "", {}, "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw=="],
|
||||
|
||||
"jest-haste-map": ["jest-haste-map@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "@types/graceful-fs": "^4.1.2", "@types/node": "*", "anymatch": "^3.0.3", "fb-watchman": "^2.0.0", "graceful-fs": "^4.2.9", "jest-regex-util": "^27.5.1", "jest-serializer": "^27.5.1", "jest-util": "^27.5.1", "jest-worker": "^27.5.1", "micromatch": "^4.0.4", "walker": "^1.0.7" }, "optionalDependencies": { "fsevents": "^2.3.2" } }, "sha512-7GgkZ4Fw4NFbMSDSpZwXeBiIbx+t/46nJ2QitkOjvwPYyZmqttu2TDSimMHP1EkPOi4xUZAN1doE5Vd25H4Jng=="],
|
||||
|
||||
"jest-jasmine2": ["jest-jasmine2@27.5.1", "", { "dependencies": { "@jest/environment": "^27.5.1", "@jest/source-map": "^27.5.1", "@jest/test-result": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "chalk": "^4.0.0", "co": "^4.6.0", "expect": "^27.5.1", "is-generator-fn": "^2.0.0", "jest-each": "^27.5.1", "jest-matcher-utils": "^27.5.1", "jest-message-util": "^27.5.1", "jest-runtime": "^27.5.1", "jest-snapshot": "^27.5.1", "jest-util": "^27.5.1", "pretty-format": "^27.5.1", "throat": "^6.0.1" } }, "sha512-jtq7VVyG8SqAorDpApwiJJImd0V2wv1xzdheGHRGyuT7gZm6gG47QEskOlzsN1PG/6WNaCo5pmwMHDf3AkG2pQ=="],
|
||||
|
||||
"jest-leak-detector": ["jest-leak-detector@27.5.1", "", { "dependencies": { "jest-get-type": "^27.5.1", "pretty-format": "^27.5.1" } }, "sha512-POXfWAMvfU6WMUXftV4HolnJfnPOGEu10fscNCA76KBpRRhcMN2c8d3iT2pxQS3HLbA+5X4sOUPzYO2NUyIlHQ=="],
|
||||
|
||||
"jest-matcher-utils": ["jest-matcher-utils@27.5.1", "", { "dependencies": { "chalk": "^4.0.0", "jest-diff": "^27.5.1", "jest-get-type": "^27.5.1", "pretty-format": "^27.5.1" } }, "sha512-z2uTx/T6LBaCoNWNFWwChLBKYxTMcGBRjAt+2SbP929/Fflb9aa5LGma654Rz8z9HLxsrUaYzxE9T/EFIL/PAw=="],
|
||||
|
||||
"jest-message-util": ["jest-message-util@27.5.1", "", { "dependencies": { "@babel/code-frame": "^7.12.13", "@jest/types": "^27.5.1", "@types/stack-utils": "^2.0.0", "chalk": "^4.0.0", "graceful-fs": "^4.2.9", "micromatch": "^4.0.4", "pretty-format": "^27.5.1", "slash": "^3.0.0", "stack-utils": "^2.0.3" } }, "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g=="],
|
||||
|
||||
"jest-mock": ["jest-mock@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "@types/node": "*" } }, "sha512-K4jKbY1d4ENhbrG2zuPWaQBvDly+iZ2yAW+T1fATN78hc0sInwn7wZB8XtlNnvHug5RMwV897Xm4LqmPM4e2Og=="],
|
||||
|
||||
"jest-pnp-resolver": ["jest-pnp-resolver@1.2.3", "", { "peerDependencies": { "jest-resolve": "*" }, "optionalPeers": ["jest-resolve"] }, "sha512-+3NpwQEnRoIBtx4fyhblQDPgJI0H1IEIkX7ShLUjPGA7TtUTvI1oiKi3SR4oBR0hQhQR80l4WAe5RrXBwWMA8w=="],
|
||||
|
||||
"jest-regex-util": ["jest-regex-util@27.5.1", "", {}, "sha512-4bfKq2zie+x16okqDXjXn9ql2B0dScQu+vcwe4TvFVhkVyuWLqpZrZtXxLLWoXYgn0E87I6r6GRYHF7wFZBUvg=="],
|
||||
|
||||
"jest-resolve": ["jest-resolve@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "chalk": "^4.0.0", "graceful-fs": "^4.2.9", "jest-haste-map": "^27.5.1", "jest-pnp-resolver": "^1.2.2", "jest-util": "^27.5.1", "jest-validate": "^27.5.1", "resolve": "^1.20.0", "resolve.exports": "^1.1.0", "slash": "^3.0.0" } }, "sha512-FFDy8/9E6CV83IMbDpcjOhumAQPDyETnU2KZ1O98DwTnz8AOBsW/Xv3GySr1mOZdItLR+zDZ7I/UdTFbgSOVCw=="],
|
||||
|
||||
"jest-resolve-dependencies": ["jest-resolve-dependencies@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "jest-regex-util": "^27.5.1", "jest-snapshot": "^27.5.1" } }, "sha512-QQOOdY4PE39iawDn5rzbIePNigfe5B9Z91GDD1ae/xNDlu9kaat8QQ5EKnNmVWPV54hUdxCVwwj6YMgR2O7IOg=="],
|
||||
|
||||
"jest-runner": ["jest-runner@27.5.1", "", { "dependencies": { "@jest/console": "^27.5.1", "@jest/environment": "^27.5.1", "@jest/test-result": "^27.5.1", "@jest/transform": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "chalk": "^4.0.0", "emittery": "^0.8.1", "graceful-fs": "^4.2.9", "jest-docblock": "^27.5.1", "jest-environment-jsdom": "^27.5.1", "jest-environment-node": "^27.5.1", "jest-haste-map": "^27.5.1", "jest-leak-detector": "^27.5.1", "jest-message-util": "^27.5.1", "jest-resolve": "^27.5.1", "jest-runtime": "^27.5.1", "jest-util": "^27.5.1", "jest-worker": "^27.5.1", "source-map-support": "^0.5.6", "throat": "^6.0.1" } }, "sha512-g4NPsM4mFCOwFKXO4p/H/kWGdJp9V8kURY2lX8Me2drgXqG7rrZAx5kv+5H7wtt/cdFIjhqYx1HrlqWHaOvDaQ=="],
|
||||
|
||||
"jest-runtime": ["jest-runtime@27.5.1", "", { "dependencies": { "@jest/environment": "^27.5.1", "@jest/fake-timers": "^27.5.1", "@jest/globals": "^27.5.1", "@jest/source-map": "^27.5.1", "@jest/test-result": "^27.5.1", "@jest/transform": "^27.5.1", "@jest/types": "^27.5.1", "chalk": "^4.0.0", "cjs-module-lexer": "^1.0.0", "collect-v8-coverage": "^1.0.0", "execa": "^5.0.0", "glob": "^7.1.3", "graceful-fs": "^4.2.9", "jest-haste-map": "^27.5.1", "jest-message-util": "^27.5.1", "jest-mock": "^27.5.1", "jest-regex-util": "^27.5.1", "jest-resolve": "^27.5.1", "jest-snapshot": "^27.5.1", "jest-util": "^27.5.1", "slash": "^3.0.0", "strip-bom": "^4.0.0" } }, "sha512-o7gxw3Gf+H2IGt8fv0RiyE1+r83FJBRruoA+FXrlHw6xEyBsU8ugA6IPfTdVyA0w8HClpbK+DGJxH59UrNMx8A=="],
|
||||
|
||||
"jest-serializer": ["jest-serializer@27.5.1", "", { "dependencies": { "@types/node": "*", "graceful-fs": "^4.2.9" } }, "sha512-jZCyo6iIxO1aqUxpuBlwTDMkzOAJS4a3eYz3YzgxxVQFwLeSA7Jfq5cbqCY+JLvTDrWirgusI/0KwxKMgrdf7w=="],
|
||||
|
||||
"jest-snapshot": ["jest-snapshot@27.5.1", "", { "dependencies": { "@babel/core": "^7.7.2", "@babel/generator": "^7.7.2", "@babel/plugin-syntax-typescript": "^7.7.2", "@babel/traverse": "^7.7.2", "@babel/types": "^7.0.0", "@jest/transform": "^27.5.1", "@jest/types": "^27.5.1", "@types/babel__traverse": "^7.0.4", "@types/prettier": "^2.1.5", "babel-preset-current-node-syntax": "^1.0.0", "chalk": "^4.0.0", "expect": "^27.5.1", "graceful-fs": "^4.2.9", "jest-diff": "^27.5.1", "jest-get-type": "^27.5.1", "jest-haste-map": "^27.5.1", "jest-matcher-utils": "^27.5.1", "jest-message-util": "^27.5.1", "jest-util": "^27.5.1", "natural-compare": "^1.4.0", "pretty-format": "^27.5.1", "semver": "^7.3.2" } }, "sha512-yYykXI5a0I31xX67mgeLw1DZ0bJB+gpq5IpSuCAoyDi0+BhgU/RIrL+RTzDmkNTchvDFWKP8lp+w/42Z3us5sA=="],
|
||||
|
||||
"jest-util": ["jest-util@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "@types/node": "*", "chalk": "^4.0.0", "ci-info": "^3.2.0", "graceful-fs": "^4.2.9", "picomatch": "^2.2.3" } }, "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw=="],
|
||||
|
||||
"jest-validate": ["jest-validate@27.5.1", "", { "dependencies": { "@jest/types": "^27.5.1", "camelcase": "^6.2.0", "chalk": "^4.0.0", "jest-get-type": "^27.5.1", "leven": "^3.1.0", "pretty-format": "^27.5.1" } }, "sha512-thkNli0LYTmOI1tDB3FI1S1RTp/Bqyd9pTarJwL87OIBFuqEb5Apv5EaApEudYg4g86e3CT6kM0RowkhtEnCBQ=="],
|
||||
|
||||
"jest-watcher": ["jest-watcher@27.5.1", "", { "dependencies": { "@jest/test-result": "^27.5.1", "@jest/types": "^27.5.1", "@types/node": "*", "ansi-escapes": "^4.2.1", "chalk": "^4.0.0", "jest-util": "^27.5.1", "string-length": "^4.0.1" } }, "sha512-z676SuD6Z8o8qbmEGhoEUFOM1+jfEiL3DXHK/xgEiG2EyNYfFG60jluWcupY6dATjfEsKQuibReS1djInQnoVw=="],
|
||||
|
||||
"jest-worker": ["jest-worker@27.5.1", "", { "dependencies": { "@types/node": "*", "merge-stream": "^2.0.0", "supports-color": "^8.0.0" } }, "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg=="],
|
||||
|
||||
"jose": ["jose@5.10.0", "", {}, "sha512-s+3Al/p9g32Iq+oqXxkW//7jk2Vig6FF1CFqzVXoTUXt2qz89YWbL+OwS17NFYEvxC35n0FKeGO2LGYSxeM2Gg=="],
|
||||
|
||||
"js-tokens": ["js-tokens@4.0.0", "", {}, "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ=="],
|
||||
|
||||
"js-yaml": ["js-yaml@3.14.1", "", { "dependencies": { "argparse": "^1.0.7", "esprima": "^4.0.0" }, "bin": { "js-yaml": "bin/js-yaml.js" } }, "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g=="],
|
||||
|
||||
"jsdom": ["jsdom@16.7.0", "", { "dependencies": { "abab": "^2.0.5", "acorn": "^8.2.4", "acorn-globals": "^6.0.0", "cssom": "^0.4.4", "cssstyle": "^2.3.0", "data-urls": "^2.0.0", "decimal.js": "^10.2.1", "domexception": "^2.0.1", "escodegen": "^2.0.0", "form-data": "^3.0.0", "html-encoding-sniffer": "^2.0.1", "http-proxy-agent": "^4.0.1", "https-proxy-agent": "^5.0.0", "is-potential-custom-element-name": "^1.0.1", "nwsapi": "^2.2.0", "parse5": "6.0.1", "saxes": "^5.0.1", "symbol-tree": "^3.2.4", "tough-cookie": "^4.0.0", "w3c-hr-time": "^1.0.2", "w3c-xmlserializer": "^2.0.0", "webidl-conversions": "^6.1.0", "whatwg-encoding": "^1.0.5", "whatwg-mimetype": "^2.3.0", "whatwg-url": "^8.5.0", "ws": "^7.4.6", "xml-name-validator": "^3.0.0" }, "peerDependencies": { "canvas": "^2.5.0" }, "optionalPeers": ["canvas"] }, "sha512-u9Smc2G1USStM+s/x1ru5Sxrl6mPYCbByG1U/hUmqaVsm4tbNyS7CicOSRyuGQYZhTu0h84qkZZQ/I+dzizSVw=="],
|
||||
|
||||
"jsesc": ["jsesc@3.1.0", "", { "bin": { "jsesc": "bin/jsesc" } }, "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA=="],
|
||||
|
||||
"json-parse-even-better-errors": ["json-parse-even-better-errors@2.3.1", "", {}, "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w=="],
|
||||
|
||||
"json5": ["json5@2.2.3", "", { "bin": { "json5": "lib/cli.js" } }, "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg=="],
|
||||
|
||||
"kleur": ["kleur@3.0.3", "", {}, "sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w=="],
|
||||
|
||||
"leven": ["leven@3.1.0", "", {}, "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A=="],
|
||||
|
||||
"lines-and-columns": ["lines-and-columns@1.2.4", "", {}, "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg=="],
|
||||
|
||||
"locate-path": ["locate-path@5.0.0", "", { "dependencies": { "p-locate": "^4.1.0" } }, "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g=="],
|
||||
|
||||
"lodash": ["lodash@4.17.21", "", {}, "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg=="],
|
||||
|
||||
"lodash.memoize": ["lodash.memoize@4.1.2", "", {}, "sha512-t7j+NzmgnQzTAYXcsHYLgimltOV1MXHtlOWf6GjL9Kj8GK5FInw5JotxvbOs+IvV1/Dzo04/fCGfLVs7aXb4Ag=="],
|
||||
|
||||
"lru-cache": ["lru-cache@5.1.1", "", { "dependencies": { "yallist": "^3.0.2" } }, "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w=="],
|
||||
|
||||
"make-dir": ["make-dir@4.0.0", "", { "dependencies": { "semver": "^7.5.3" } }, "sha512-hXdUTZYIVOt1Ex//jAQi+wTZZpUpwBj/0QsOzqegb3rGMMeJiSEu5xLHnYfBrRV4RH2+OCSOO95Is/7x1WJ4bw=="],
|
||||
|
||||
"make-error": ["make-error@1.3.6", "", {}, "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw=="],
|
||||
|
||||
"makeerror": ["makeerror@1.0.12", "", { "dependencies": { "tmpl": "1.0.5" } }, "sha512-JmqCvUhmt43madlpFzG4BQzG2Z3m6tvQDNKdClZnO3VbIudJYmxsT0FNJMeiB2+JTSlTQTSbU8QdesVmwJcmLg=="],
|
||||
|
||||
"math-intrinsics": ["math-intrinsics@1.1.0", "", {}, "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g=="],
|
||||
|
||||
"merge-stream": ["merge-stream@2.0.0", "", {}, "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w=="],
|
||||
|
||||
"methods": ["methods@1.1.2", "", {}, "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w=="],
|
||||
|
||||
"micromatch": ["micromatch@4.0.8", "", { "dependencies": { "braces": "^3.0.3", "picomatch": "^2.3.1" } }, "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA=="],
|
||||
|
||||
"mime": ["mime@2.6.0", "", { "bin": { "mime": "cli.js" } }, "sha512-USPkMeET31rOMiarsBNIHZKLGgvKc/LrjofAnBlOttf5ajRvqiRA8QsenbcooctK6d6Ts6aqZXBA+XbkKthiQg=="],
|
||||
|
||||
"mime-db": ["mime-db@1.52.0", "", {}, "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg=="],
|
||||
|
||||
"mime-types": ["mime-types@2.1.35", "", { "dependencies": { "mime-db": "1.52.0" } }, "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw=="],
|
||||
|
||||
"mimic-fn": ["mimic-fn@2.1.0", "", {}, "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg=="],
|
||||
|
||||
"minimatch": ["minimatch@3.1.2", "", { "dependencies": { "brace-expansion": "^1.1.7" } }, "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw=="],
|
||||
|
||||
"ms": ["ms@2.1.3", "", {}, "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA=="],
|
||||
|
||||
"natural-compare": ["natural-compare@1.4.0", "", {}, "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw=="],
|
||||
|
||||
"node-fetch": ["node-fetch@2.7.0", "", { "dependencies": { "whatwg-url": "^5.0.0" }, "peerDependencies": { "encoding": "^0.1.0" }, "optionalPeers": ["encoding"] }, "sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A=="],
|
||||
|
||||
"node-int64": ["node-int64@0.4.0", "", {}, "sha512-O5lz91xSOeoXP6DulyHfllpq+Eg00MWitZIbtPfoSEvqIHdl5gfcY6hYzDWnj0qD5tz52PI08u9qUvSVeUBeHw=="],
|
||||
|
||||
"node-releases": ["node-releases@2.0.19", "", {}, "sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw=="],
|
||||
|
||||
"normalize-path": ["normalize-path@3.0.0", "", {}, "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA=="],
|
||||
|
||||
"npm-run-path": ["npm-run-path@4.0.1", "", { "dependencies": { "path-key": "^3.0.0" } }, "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw=="],
|
||||
|
||||
"nwsapi": ["nwsapi@2.2.20", "", {}, "sha512-/ieB+mDe4MrrKMT8z+mQL8klXydZWGR5Dowt4RAGKbJ3kIGEx3X4ljUo+6V73IXtUPWgfOlU5B9MlGxFO5T+cA=="],
|
||||
|
||||
"object-inspect": ["object-inspect@1.13.4", "", {}, "sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew=="],
|
||||
|
||||
"once": ["once@1.4.0", "", { "dependencies": { "wrappy": "1" } }, "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w=="],
|
||||
|
||||
"onetime": ["onetime@5.1.2", "", { "dependencies": { "mimic-fn": "^2.1.0" } }, "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg=="],
|
||||
|
||||
"otplib": ["otplib@12.0.1", "", { "dependencies": { "@otplib/core": "^12.0.1", "@otplib/preset-default": "^12.0.1", "@otplib/preset-v11": "^12.0.1" } }, "sha512-xDGvUOQjop7RDgxTQ+o4pOol0/3xSZzawTiPKRrHnQWAy0WjhNs/5HdIDJCrqC4MBynmjXgULc6YfioaxZeFgg=="],
|
||||
|
||||
"p-limit": ["p-limit@2.3.0", "", { "dependencies": { "p-try": "^2.0.0" } }, "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w=="],
|
||||
|
||||
"p-locate": ["p-locate@4.1.0", "", { "dependencies": { "p-limit": "^2.2.0" } }, "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A=="],
|
||||
|
||||
"p-try": ["p-try@2.2.0", "", {}, "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ=="],
|
||||
|
||||
"parse-json": ["parse-json@5.2.0", "", { "dependencies": { "@babel/code-frame": "^7.0.0", "error-ex": "^1.3.1", "json-parse-even-better-errors": "^2.3.0", "lines-and-columns": "^1.1.6" } }, "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg=="],
|
||||
|
||||
"parse5": ["parse5@6.0.1", "", {}, "sha512-Ofn/CTFzRGTTxwpNEs9PP93gXShHcTq255nzRYSKe8AkVpZY7e1fpmTfOyoIvjP5HG7Z2ZM7VS9PPhQGW2pOpw=="],
|
||||
|
||||
"path-exists": ["path-exists@4.0.0", "", {}, "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w=="],
|
||||
|
||||
"path-is-absolute": ["path-is-absolute@1.0.1", "", {}, "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg=="],
|
||||
|
||||
"path-key": ["path-key@3.1.1", "", {}, "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q=="],
|
||||
|
||||
"path-parse": ["path-parse@1.0.7", "", {}, "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw=="],
|
||||
|
||||
"pg": ["pg@8.16.2", "", { "dependencies": { "pg-connection-string": "^2.9.1", "pg-pool": "^3.10.1", "pg-protocol": "^1.10.2", "pg-types": "2.2.0", "pgpass": "1.0.5" }, "optionalDependencies": { "pg-cloudflare": "^1.2.6" }, "peerDependencies": { "pg-native": ">=3.0.1" }, "optionalPeers": ["pg-native"] }, "sha512-OtLWF0mKLmpxelOt9BqVq83QV6bTfsS0XLegIeAKqKjurRnRKie1Dc1iL89MugmSLhftxw6NNCyZhm1yQFLMEQ=="],
|
||||
|
||||
"pg-cloudflare": ["pg-cloudflare@1.2.6", "", {}, "sha512-uxmJAnmIgmYgnSFzgOf2cqGQBzwnRYcrEgXuFjJNEkpedEIPBSEzxY7ph4uA9k1mI+l/GR0HjPNS6FKNZe8SBQ=="],
|
||||
|
||||
"pg-connection-string": ["pg-connection-string@2.9.1", "", {}, "sha512-nkc6NpDcvPVpZXxrreI/FOtX3XemeLl8E0qFr6F2Lrm/I8WOnaWNhIPK2Z7OHpw7gh5XJThi6j6ppgNoaT1w4w=="],
|
||||
|
||||
"pg-int8": ["pg-int8@1.0.1", "", {}, "sha512-WCtabS6t3c8SkpDBUlb1kjOs7l66xsGdKpIPZsg4wR+B3+u9UAum2odSsF9tnvxg80h4ZxLWMy4pRjOsFIqQpw=="],
|
||||
|
||||
"pg-pool": ["pg-pool@3.10.1", "", { "peerDependencies": { "pg": ">=8.0" } }, "sha512-Tu8jMlcX+9d8+QVzKIvM/uJtp07PKr82IUOYEphaWcoBhIYkoHpLXN3qO59nAI11ripznDsEzEv8nUxBVWajGg=="],
|
||||
|
||||
"pg-protocol": ["pg-protocol@1.10.2", "", {}, "sha512-Ci7jy8PbaWxfsck2dwZdERcDG2A0MG8JoQILs+uZNjABFuBuItAZCWUNz8sXRDMoui24rJw7WlXqgpMdBSN/vQ=="],
|
||||
|
||||
"pg-types": ["pg-types@2.2.0", "", { "dependencies": { "pg-int8": "1.0.1", "postgres-array": "~2.0.0", "postgres-bytea": "~1.0.0", "postgres-date": "~1.0.4", "postgres-interval": "^1.1.0" } }, "sha512-qTAAlrEsl8s4OiEQY69wDvcMIdQN6wdz5ojQiOy6YRMuynxenON0O5oCpJI6lshc6scgAY8qvJ2On/p+CXY0GA=="],
|
||||
|
||||
"pgpass": ["pgpass@1.0.5", "", { "dependencies": { "split2": "^4.1.0" } }, "sha512-FdW9r/jQZhSeohs1Z3sI1yxFQNFvMcnmfuj4WBMUTxOrAyLMaTcE1aAMBiTlbMNaXvBCQuVi0R7hd8udDSP7ug=="],
|
||||
|
||||
"picocolors": ["picocolors@1.1.1", "", {}, "sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA=="],
|
||||
|
||||
"picomatch": ["picomatch@2.3.1", "", {}, "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA=="],
|
||||
|
||||
"pirates": ["pirates@4.0.7", "", {}, "sha512-TfySrs/5nm8fQJDcBDuUng3VOUKsd7S+zqvbOTiGXHfxX4wK31ard+hoNuvkicM/2YFzlpDgABOevKSsB4G/FA=="],
|
||||
|
||||
"pkg-dir": ["pkg-dir@4.2.0", "", { "dependencies": { "find-up": "^4.0.0" } }, "sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ=="],
|
||||
|
||||
"postgres-array": ["postgres-array@2.0.0", "", {}, "sha512-VpZrUqU5A69eQyW2c5CA1jtLecCsN2U/bD6VilrFDWq5+5UIEVO7nazS3TEcHf1zuPYO/sqGvUvW62g86RXZuA=="],
|
||||
|
||||
"postgres-bytea": ["postgres-bytea@1.0.0", "", {}, "sha512-xy3pmLuQqRBZBXDULy7KbaitYqLcmxigw14Q5sj8QBVLqEwXfeybIKVWiqAXTlcvdvb0+xkOtDbfQMOf4lST1w=="],
|
||||
|
||||
"postgres-date": ["postgres-date@1.0.7", "", {}, "sha512-suDmjLVQg78nMK2UZ454hAG+OAW+HQPZ6n++TNDUX+L0+uUlLywnoxJKDou51Zm+zTCjrCl0Nq6J9C5hP9vK/Q=="],
|
||||
|
||||
"postgres-interval": ["postgres-interval@1.2.0", "", { "dependencies": { "xtend": "^4.0.0" } }, "sha512-9ZhXKM/rw350N1ovuWHbGxnGh/SNJ4cnxHiM0rxE4VN41wsg8P8zWn9hv/buK00RP4WvlOyr/RBDiptyxVbkZQ=="],
|
||||
|
||||
"pretty-format": ["pretty-format@27.5.1", "", { "dependencies": { "ansi-regex": "^5.0.1", "ansi-styles": "^5.0.0", "react-is": "^17.0.1" } }, "sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ=="],
|
||||
|
||||
"prompts": ["prompts@2.4.2", "", { "dependencies": { "kleur": "^3.0.3", "sisteransi": "^1.0.5" } }, "sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q=="],
|
||||
|
||||
"proxy-from-env": ["proxy-from-env@1.1.0", "", {}, "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg=="],
|
||||
|
||||
"psl": ["psl@1.15.0", "", { "dependencies": { "punycode": "^2.3.1" } }, "sha512-JZd3gMVBAVQkSs6HdNZo9Sdo0LNcQeMNP3CozBJb3JYC/QUYZTnKxP+f8oWRX4rHP5EurWxqAHTSwUCjlNKa1w=="],
|
||||
|
||||
"punycode": ["punycode@2.3.1", "", {}, "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg=="],
|
||||
|
||||
"qs": ["qs@6.14.0", "", { "dependencies": { "side-channel": "^1.1.0" } }, "sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w=="],
|
||||
|
||||
"querystringify": ["querystringify@2.2.0", "", {}, "sha512-FIqgj2EUvTa7R50u0rGsyTftzjYmv/a3hO345bZNrqabNqjtgiDMgmo4mkUjd+nzU5oF3dClKqFIPUKybUyqoQ=="],
|
||||
|
||||
"react-is": ["react-is@17.0.2", "", {}, "sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w=="],
|
||||
|
||||
"require-directory": ["require-directory@2.1.1", "", {}, "sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q=="],
|
||||
|
||||
"requires-port": ["requires-port@1.0.0", "", {}, "sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ=="],
|
||||
|
||||
"resolve": ["resolve@1.22.10", "", { "dependencies": { "is-core-module": "^2.16.0", "path-parse": "^1.0.7", "supports-preserve-symlinks-flag": "^1.0.0" }, "bin": { "resolve": "bin/resolve" } }, "sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w=="],
|
||||
|
||||
"resolve-cwd": ["resolve-cwd@3.0.0", "", { "dependencies": { "resolve-from": "^5.0.0" } }, "sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg=="],
|
||||
|
||||
"resolve-from": ["resolve-from@5.0.0", "", {}, "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw=="],
|
||||
|
||||
"resolve.exports": ["resolve.exports@1.1.1", "", {}, "sha512-/NtpHNDN7jWhAaQ9BvBUYZ6YTXsRBgfqWFWP7BZBaoMJO/I3G5OFzvTuWNlZC3aPjins1F+TNrLKsGbH4rfsRQ=="],
|
||||
|
||||
"rfc2047": ["rfc2047@3.0.1", "", { "dependencies": { "iconv-lite": "0.4.5" } }, "sha512-XlPpflkoON+4884qmLzSBx7QKjw3XTncID8bPsFLv6Y7eXkrGweYRnWPz1i2UXwAxnnB1H40pqePoAp2bytC/w=="],
|
||||
|
||||
"rimraf": ["rimraf@3.0.2", "", { "dependencies": { "glob": "^7.1.3" }, "bin": { "rimraf": "bin.js" } }, "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA=="],
|
||||
|
||||
"safer-buffer": ["safer-buffer@2.1.2", "", {}, "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg=="],
|
||||
|
||||
"saxes": ["saxes@5.0.1", "", { "dependencies": { "xmlchars": "^2.2.0" } }, "sha512-5LBh1Tls8c9xgGjw3QrMwETmTMVk0oFgvrFSvWx62llR2hcEInrKNZ2GZCCuuy2lvWrdl5jhbpeqc5hRYKFOcw=="],
|
||||
|
||||
"semver": ["semver@7.7.2", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA=="],
|
||||
|
||||
"shebang-command": ["shebang-command@2.0.0", "", { "dependencies": { "shebang-regex": "^3.0.0" } }, "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA=="],
|
||||
|
||||
"shebang-regex": ["shebang-regex@3.0.0", "", {}, "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A=="],
|
||||
|
||||
"side-channel": ["side-channel@1.1.0", "", { "dependencies": { "es-errors": "^1.3.0", "object-inspect": "^1.13.3", "side-channel-list": "^1.0.0", "side-channel-map": "^1.0.1", "side-channel-weakmap": "^1.0.2" } }, "sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw=="],
|
||||
|
||||
"side-channel-list": ["side-channel-list@1.0.0", "", { "dependencies": { "es-errors": "^1.3.0", "object-inspect": "^1.13.3" } }, "sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA=="],
|
||||
|
||||
"side-channel-map": ["side-channel-map@1.0.1", "", { "dependencies": { "call-bound": "^1.0.2", "es-errors": "^1.3.0", "get-intrinsic": "^1.2.5", "object-inspect": "^1.13.3" } }, "sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA=="],
|
||||
|
||||
"side-channel-weakmap": ["side-channel-weakmap@1.0.2", "", { "dependencies": { "call-bound": "^1.0.2", "es-errors": "^1.3.0", "get-intrinsic": "^1.2.5", "object-inspect": "^1.13.3", "side-channel-map": "^1.0.1" } }, "sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A=="],
|
||||
|
||||
"signal-exit": ["signal-exit@3.0.7", "", {}, "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ=="],
|
||||
|
||||
"sisteransi": ["sisteransi@1.0.5", "", {}, "sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg=="],
|
||||
|
||||
"slash": ["slash@3.0.0", "", {}, "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q=="],
|
||||
|
||||
"source-map": ["source-map@0.6.1", "", {}, "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g=="],
|
||||
|
||||
"source-map-support": ["source-map-support@0.5.21", "", { "dependencies": { "buffer-from": "^1.0.0", "source-map": "^0.6.0" } }, "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w=="],
|
||||
|
||||
"split2": ["split2@4.2.0", "", {}, "sha512-UcjcJOWknrNkF6PLX83qcHM6KHgVKNkV62Y8a5uYDVv9ydGQVwAHMKqHdJje1VTWpljG0WYpCDhrCdAOYH4TWg=="],
|
||||
|
||||
"sprintf-js": ["sprintf-js@1.0.3", "", {}, "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g=="],
|
||||
|
||||
"stack-utils": ["stack-utils@2.0.6", "", { "dependencies": { "escape-string-regexp": "^2.0.0" } }, "sha512-XlkWvfIm6RmsWtNJx+uqtKLS8eqFbxUg0ZzLXqY0caEy9l7hruX8IpiDnjsLavoBgqCCR71TqWO8MaXYheJ3RQ=="],
|
||||
|
||||
"string-length": ["string-length@4.0.2", "", { "dependencies": { "char-regex": "^1.0.2", "strip-ansi": "^6.0.0" } }, "sha512-+l6rNN5fYHNhZZy41RXsYptCjA2Igmq4EG7kZAYFQI1E1VTXarr6ZPXBg6eq7Y6eK4FEhY6AJlyuFIb/v/S0VQ=="],
|
||||
|
||||
"string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="],
|
||||
|
||||
"strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
|
||||
|
||||
"strip-bom": ["strip-bom@4.0.0", "", {}, "sha512-3xurFv5tEgii33Zi8Jtp55wEIILR9eh34FAW00PZf+JnSsTmV/ioewSgQl97JHvgjoRGwPShsWm+IdrxB35d0w=="],
|
||||
|
||||
"strip-final-newline": ["strip-final-newline@2.0.0", "", {}, "sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA=="],
|
||||
|
||||
"strip-json-comments": ["strip-json-comments@3.1.1", "", {}, "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig=="],
|
||||
|
||||
"superagent": ["superagent@8.1.2", "", { "dependencies": { "component-emitter": "^1.3.0", "cookiejar": "^2.1.4", "debug": "^4.3.4", "fast-safe-stringify": "^2.1.1", "form-data": "^4.0.0", "formidable": "^2.1.2", "methods": "^1.1.2", "mime": "2.6.0", "qs": "^6.11.0", "semver": "^7.3.8" } }, "sha512-6WTxW1EB6yCxV5VFOIPQruWGHqc3yI7hEmZK6h+pyk69Lk/Ut7rLUY6W/ONF2MjBuGjvmMiIpsrVJ2vjrHlslA=="],
|
||||
|
||||
"supertest": ["supertest@6.3.4", "", { "dependencies": { "methods": "^1.1.2", "superagent": "^8.1.2" } }, "sha512-erY3HFDG0dPnhw4U+udPfrzXa4xhSG+n4rxfRuZWCUvjFWwKl+OxWf/7zk50s84/fAAs7vf5QAb9uRa0cCykxw=="],
|
||||
|
||||
"supports-color": ["supports-color@7.2.0", "", { "dependencies": { "has-flag": "^4.0.0" } }, "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw=="],
|
||||
|
||||
"supports-hyperlinks": ["supports-hyperlinks@2.3.0", "", { "dependencies": { "has-flag": "^4.0.0", "supports-color": "^7.0.0" } }, "sha512-RpsAZlpWcDwOPQA22aCH4J0t7L8JmAvsCxfOSEwm7cQs3LshN36QaTkwd70DnBOXDWGssw2eUoc8CaRWT0XunA=="],
|
||||
|
||||
"supports-preserve-symlinks-flag": ["supports-preserve-symlinks-flag@1.0.0", "", {}, "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w=="],
|
||||
|
||||
"symbol-tree": ["symbol-tree@3.2.4", "", {}, "sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw=="],
|
||||
|
||||
"terminal-link": ["terminal-link@2.1.1", "", { "dependencies": { "ansi-escapes": "^4.2.1", "supports-hyperlinks": "^2.0.0" } }, "sha512-un0FmiRUQNr5PJqy9kP7c40F5BOfpGlYTrxonDChEZB7pzZxRNp/bt+ymiy9/npwXya9KH99nJ/GXFIiUkYGFQ=="],
|
||||
|
||||
"test-exclude": ["test-exclude@6.0.0", "", { "dependencies": { "@istanbuljs/schema": "^0.1.2", "glob": "^7.1.4", "minimatch": "^3.0.4" } }, "sha512-cAGWPIyOHU6zlmg88jwm7VRyXnMN7iV68OGAbYDk/Mh/xC/pzVPlQtY6ngoIH/5/tciuhGfvESU8GrHrcxD56w=="],
|
||||
|
||||
"thirty-two": ["thirty-two@1.0.2", "", {}, "sha512-OEI0IWCe+Dw46019YLl6V10Us5bi574EvlJEOcAkB29IzQ/mYD1A6RyNHLjZPiHCmuodxvgF6U+vZO1L15lxVA=="],
|
||||
|
||||
"throat": ["throat@6.0.2", "", {}, "sha512-WKexMoJj3vEuK0yFEapj8y64V0A6xcuPuK9Gt1d0R+dzCSJc0lHqQytAbSB4cDAK0dWh4T0E2ETkoLE2WZ41OQ=="],
|
||||
|
||||
"tmpl": ["tmpl@1.0.5", "", {}, "sha512-3f0uOEAQwIqGuWW2MVzYg8fV/QNnc/IpuJNG837rLuczAaLVHslWHZQj4IGiEl5Hs3kkbhwL9Ab7Hrsmuj+Smw=="],
|
||||
|
||||
"to-regex-range": ["to-regex-range@5.0.1", "", { "dependencies": { "is-number": "^7.0.0" } }, "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ=="],
|
||||
|
||||
"tough-cookie": ["tough-cookie@4.1.4", "", { "dependencies": { "psl": "^1.1.33", "punycode": "^2.1.1", "universalify": "^0.2.0", "url-parse": "^1.5.3" } }, "sha512-Loo5UUvLD9ScZ6jh8beX1T6sO1w2/MpCRpEP7V280GKMVUQ0Jzar2U3UJPsrdbziLEMMhu3Ujnq//rhiFuIeag=="],
|
||||
|
||||
"tr46": ["tr46@0.0.3", "", {}, "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw=="],
|
||||
|
||||
"ts-jest": ["ts-jest@27.1.5", "", { "dependencies": { "bs-logger": "0.x", "fast-json-stable-stringify": "2.x", "jest-util": "^27.0.0", "json5": "2.x", "lodash.memoize": "4.x", "make-error": "1.x", "semver": "7.x", "yargs-parser": "20.x" }, "peerDependencies": { "@babel/core": ">=7.0.0-beta.0 <8", "@types/jest": "^27.0.0", "babel-jest": ">=27.0.0 <28", "jest": "^27.0.0", "typescript": ">=3.8 <5.0" }, "optionalPeers": ["@babel/core", "@types/jest", "babel-jest"], "bin": { "ts-jest": "cli.js" } }, "sha512-Xv6jBQPoBEvBq/5i2TeSG9tt/nqkbpcurrEG1b+2yfBrcJelOZF9Ml6dmyMh7bcW9JyFbRYpR5rxROSlBLTZHA=="],
|
||||
|
||||
"type-detect": ["type-detect@4.0.8", "", {}, "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g=="],
|
||||
|
||||
"type-fest": ["type-fest@0.21.3", "", {}, "sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w=="],
|
||||
|
||||
"typedarray-to-buffer": ["typedarray-to-buffer@3.1.5", "", { "dependencies": { "is-typedarray": "^1.0.0" } }, "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q=="],
|
||||
|
||||
"typescript": ["typescript@4.5.4", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-VgYs2A2QIRuGphtzFV7aQJduJ2gyfTljngLzjpfW9FoYZF6xuw1W0vW9ghCKLfcWrCFxK81CSGRAvS1pn4fIUg=="],
|
||||
|
||||
"universalify": ["universalify@0.2.0", "", {}, "sha512-CJ1QgKmNg3CwvAv/kOFmtnEN05f0D/cn9QntgNOQlQF9dgvVTHj3t+8JPdjqawCHk7V/KA+fbUqzZ9XWhcqPUg=="],
|
||||
|
||||
"update-browserslist-db": ["update-browserslist-db@1.1.3", "", { "dependencies": { "escalade": "^3.2.0", "picocolors": "^1.1.1" }, "peerDependencies": { "browserslist": ">= 4.21.0" }, "bin": { "update-browserslist-db": "cli.js" } }, "sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw=="],
|
||||
|
||||
"url-parse": ["url-parse@1.5.10", "", { "dependencies": { "querystringify": "^2.1.1", "requires-port": "^1.0.0" } }, "sha512-WypcfiRhfeUP9vvF0j6rw0J3hrWrw6iZv3+22h6iRMJ/8z1Tj6XfLP4DsUix5MhMPnXpiHDoKyoZ/bdCkwBCiQ=="],
|
||||
|
||||
"uuid": ["uuid@7.0.3", "", { "bin": { "uuid": "dist/bin/uuid" } }, "sha512-DPSke0pXhTZgoF/d+WSt2QaKMCFSfx7QegxEWT+JOuHF5aWrKEn0G+ztjuJg/gG8/ItK+rbPCD/yNv8yyih6Cg=="],
|
||||
|
||||
"v8-to-istanbul": ["v8-to-istanbul@8.1.1", "", { "dependencies": { "@types/istanbul-lib-coverage": "^2.0.1", "convert-source-map": "^1.6.0", "source-map": "^0.7.3" } }, "sha512-FGtKtv3xIpR6BYhvgH8MI/y78oT7d8Au3ww4QIxymrCtZEh5b8gCw2siywE+puhEmuWKDtmfrvF5UlB298ut3w=="],
|
||||
|
||||
"w3c-hr-time": ["w3c-hr-time@1.0.2", "", { "dependencies": { "browser-process-hrtime": "^1.0.0" } }, "sha512-z8P5DvDNjKDoFIHK7q8r8lackT6l+jo/Ye3HOle7l9nICP9lf1Ci25fy9vHd0JOWewkIFzXIEig3TdKT7JQ5fQ=="],
|
||||
|
||||
"w3c-xmlserializer": ["w3c-xmlserializer@2.0.0", "", { "dependencies": { "xml-name-validator": "^3.0.0" } }, "sha512-4tzD0mF8iSiMiNs30BiLO3EpfGLZUT2MSX/G+o7ZywDzliWQ3OPtTZ0PTC3B3ca1UAf4cJMHB+2Bf56EriJuRA=="],
|
||||
|
||||
"walker": ["walker@1.0.8", "", { "dependencies": { "makeerror": "1.0.12" } }, "sha512-ts/8E8l5b7kY0vlWLewOkDXMmPdLcVV4GmOQLyxuSswIJsweeFZtAsMF7k1Nszz+TYBQrlYRmzOnr398y1JemQ=="],
|
||||
|
||||
"webidl-conversions": ["webidl-conversions@3.0.1", "", {}, "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ=="],
|
||||
|
||||
"whatwg-encoding": ["whatwg-encoding@1.0.5", "", { "dependencies": { "iconv-lite": "0.4.24" } }, "sha512-b5lim54JOPN9HtzvK9HFXvBma/rnfFeqsic0hSpjtDbVxR3dJKLc+KB4V6GgiGOvl7CY/KNh8rxSo9DKQrnUEw=="],
|
||||
|
||||
"whatwg-mimetype": ["whatwg-mimetype@2.3.0", "", {}, "sha512-M4yMwr6mAnQz76TbJm914+gPpB/nCwvZbJU28cUD6dR004SAxDLOOSUaB1JDRqLtaOV/vi0IC5lEAGFgrjGv/g=="],
|
||||
|
||||
"whatwg-url": ["whatwg-url@5.0.0", "", { "dependencies": { "tr46": "~0.0.3", "webidl-conversions": "^3.0.0" } }, "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw=="],
|
||||
|
||||
"which": ["which@2.0.2", "", { "dependencies": { "isexe": "^2.0.0" }, "bin": { "node-which": "./bin/node-which" } }, "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA=="],
|
||||
|
||||
"wrap-ansi": ["wrap-ansi@7.0.0", "", { "dependencies": { "ansi-styles": "^4.0.0", "string-width": "^4.1.0", "strip-ansi": "^6.0.0" } }, "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q=="],
|
||||
|
||||
"wrappy": ["wrappy@1.0.2", "", {}, "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ=="],
|
||||
|
||||
"write-file-atomic": ["write-file-atomic@3.0.3", "", { "dependencies": { "imurmurhash": "^0.1.4", "is-typedarray": "^1.0.0", "signal-exit": "^3.0.2", "typedarray-to-buffer": "^3.1.5" } }, "sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q=="],
|
||||
|
||||
"ws": ["ws@7.5.10", "", { "peerDependencies": { "bufferutil": "^4.0.1", "utf-8-validate": "^5.0.2" }, "optionalPeers": ["bufferutil", "utf-8-validate"] }, "sha512-+dbF1tHwZpXcbOJdVOkzLDxZP1ailvSxM6ZweXTegylPny803bFhA+vqBYw4s31NSAk4S2Qz+AKXK9a4wkdjcQ=="],
|
||||
|
||||
"xml-name-validator": ["xml-name-validator@3.0.0", "", {}, "sha512-A5CUptxDsvxKJEU3yO6DuWBSJz/qizqzJKOMIfUJHETbBw/sFaDxgd6fxm1ewUaM0jZ444Fc5vC5ROYurg/4Pw=="],
|
||||
|
||||
"xmlchars": ["xmlchars@2.2.0", "", {}, "sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw=="],
|
||||
|
||||
"xtend": ["xtend@4.0.2", "", {}, "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ=="],
|
||||
|
||||
"y18n": ["y18n@5.0.8", "", {}, "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA=="],
|
||||
|
||||
"yallist": ["yallist@3.1.1", "", {}, "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g=="],
|
||||
|
||||
"yargs": ["yargs@16.2.0", "", { "dependencies": { "cliui": "^7.0.2", "escalade": "^3.1.1", "get-caller-file": "^2.0.5", "require-directory": "^2.1.1", "string-width": "^4.2.0", "y18n": "^5.0.5", "yargs-parser": "^20.2.2" } }, "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw=="],
|
||||
|
||||
"yargs-parser": ["yargs-parser@20.2.9", "", {}, "sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w=="],
|
||||
|
||||
"@babel/core/semver": ["semver@6.3.1", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA=="],
|
||||
|
||||
"@babel/helper-compilation-targets/semver": ["semver@6.3.1", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA=="],
|
||||
|
||||
"@jest/transform/convert-source-map": ["convert-source-map@1.9.0", "", {}, "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A=="],
|
||||
|
||||
"acorn-globals/acorn": ["acorn@7.4.1", "", { "bin": { "acorn": "bin/acorn" } }, "sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A=="],
|
||||
|
||||
"chalk/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="],
|
||||
|
||||
"cssstyle/cssom": ["cssom@0.3.8", "", {}, "sha512-b0tGHbfegbhPJpxpiBPU2sCkigAqtM9O121le6bbOlgyV+NyGyCmVfJ6QW9eRjz8CpNfWEOYBIMIGRYkLwsIYg=="],
|
||||
|
||||
"data-urls/whatwg-url": ["whatwg-url@8.7.0", "", { "dependencies": { "lodash": "^4.7.0", "tr46": "^2.1.0", "webidl-conversions": "^6.1.0" } }, "sha512-gAojqb/m9Q8a5IV96E3fHJM70AzCkgt4uXYX2O7EmuyOnLrViCQlsEBmF9UQIu3/aeAIp2U17rtbpZWNntQqdg=="],
|
||||
|
||||
"domexception/webidl-conversions": ["webidl-conversions@5.0.0", "", {}, "sha512-VlZwKPCkYKxQgeSbH5EyngOmRp7Ww7I9rQLERETtf5ofd9pGeswWiOtogpEO850jziPRarreGxn5QIiTqpb2wA=="],
|
||||
|
||||
"istanbul-lib-instrument/semver": ["semver@6.3.1", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA=="],
|
||||
|
||||
"jest-validate/camelcase": ["camelcase@6.3.0", "", {}, "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA=="],
|
||||
|
||||
"jest-worker/supports-color": ["supports-color@8.1.1", "", { "dependencies": { "has-flag": "^4.0.0" } }, "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q=="],
|
||||
|
||||
"jsdom/form-data": ["form-data@3.0.3", "", { "dependencies": { "asynckit": "^0.4.0", "combined-stream": "^1.0.8", "es-set-tostringtag": "^2.1.0", "mime-types": "^2.1.35" } }, "sha512-q5YBMeWy6E2Un0nMGWMgI65MAKtaylxfNJGJxpGh45YDciZB4epbWpaAfImil6CPAPTYB4sh0URQNDRIZG5F2w=="],
|
||||
|
||||
"jsdom/webidl-conversions": ["webidl-conversions@6.1.0", "", {}, "sha512-qBIvFLGiBpLjfwmYAaHPXsn+ho5xZnGvyGvsarywGNc8VyQJUMHJ8OBKGGrPER0okBeMDaan4mNBlgBROxuI8w=="],
|
||||
|
||||
"jsdom/whatwg-url": ["whatwg-url@8.7.0", "", { "dependencies": { "lodash": "^4.7.0", "tr46": "^2.1.0", "webidl-conversions": "^6.1.0" } }, "sha512-gAojqb/m9Q8a5IV96E3fHJM70AzCkgt4uXYX2O7EmuyOnLrViCQlsEBmF9UQIu3/aeAIp2U17rtbpZWNntQqdg=="],
|
||||
|
||||
"v8-to-istanbul/convert-source-map": ["convert-source-map@1.9.0", "", {}, "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A=="],
|
||||
|
||||
"v8-to-istanbul/source-map": ["source-map@0.7.4", "", {}, "sha512-l3BikUxvPOcn5E74dZiq5BGsTb5yEwhaTSzccU6t4sDOH8NWJCstKO5QT2CvtFoK6F0saL7p9xHAqHOlCPJygA=="],
|
||||
|
||||
"whatwg-encoding/iconv-lite": ["iconv-lite@0.4.24", "", { "dependencies": { "safer-buffer": ">= 2.1.2 < 3" } }, "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA=="],
|
||||
|
||||
"wrap-ansi/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="],
|
||||
|
||||
"data-urls/whatwg-url/tr46": ["tr46@2.1.0", "", { "dependencies": { "punycode": "^2.1.1" } }, "sha512-15Ih7phfcdP5YxqiB+iDtLoaTz4Nd35+IiAv0kQ5FNKHzXgdWqPoTIqEDDJmXceQt4JZk6lVPT8lnDlPpGDppw=="],
|
||||
|
||||
"data-urls/whatwg-url/webidl-conversions": ["webidl-conversions@6.1.0", "", {}, "sha512-qBIvFLGiBpLjfwmYAaHPXsn+ho5xZnGvyGvsarywGNc8VyQJUMHJ8OBKGGrPER0okBeMDaan4mNBlgBROxuI8w=="],
|
||||
|
||||
"jsdom/whatwg-url/tr46": ["tr46@2.1.0", "", { "dependencies": { "punycode": "^2.1.1" } }, "sha512-15Ih7phfcdP5YxqiB+iDtLoaTz4Nd35+IiAv0kQ5FNKHzXgdWqPoTIqEDDJmXceQt4JZk6lVPT8lnDlPpGDppw=="],
|
||||
}
|
||||
}
|
||||
2
services/auth/bunfig.toml
Normal file
2
services/auth/bunfig.toml
Normal file
@@ -0,0 +1,2 @@
|
||||
[test]
|
||||
preload = ["./test/setup.ts"]
|
||||
12
services/auth/docker/initdb.d/0001-create-schema.sql
Normal file
12
services/auth/docker/initdb.d/0001-create-schema.sql
Normal file
@@ -0,0 +1,12 @@
|
||||
-- auth schema
|
||||
CREATE SCHEMA IF NOT EXISTS auth;
|
||||
-- https://github.com/hasura/graphql-engine/issues/3657
|
||||
CREATE EXTENSION IF NOT EXISTS pgcrypto WITH SCHEMA public;
|
||||
CREATE EXTENSION IF NOT EXISTS citext WITH SCHEMA public;
|
||||
CREATE OR REPLACE FUNCTION public.set_current_timestamp_updated_at() RETURNS trigger LANGUAGE plpgsql AS $$
|
||||
declare _new record;
|
||||
begin _new := new;
|
||||
_new."updated_at" = now();
|
||||
return _new;
|
||||
end;
|
||||
$$;
|
||||
8
services/auth/docs/openapi.go
Normal file
8
services/auth/docs/openapi.go
Normal file
@@ -0,0 +1,8 @@
|
||||
package docs
|
||||
|
||||
import (
|
||||
_ "embed"
|
||||
)
|
||||
|
||||
//go:embed openapi.yaml
|
||||
var OpenAPISchema []byte
|
||||
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user