update
Browse files- app/scripts/notion-importer/.cursorignore +1 -0
- app/scripts/notion-importer/.notion-to-md/media/27877f1c-9c9d-804d-9c82-f7b3905578ff_media.json +198 -0
- app/scripts/notion-importer/README.md +291 -0
- app/scripts/notion-importer/custom-code-renderer.mjs +33 -0
- app/scripts/notion-importer/debug-properties.mjs +87 -0
- app/scripts/notion-importer/env.example +2 -0
- app/scripts/notion-importer/index.mjs +324 -0
- app/scripts/notion-importer/input/pages.json +9 -0
- app/scripts/notion-importer/mdx-converter.mjs +551 -0
- app/scripts/notion-importer/notion-converter.mjs +259 -0
- app/scripts/notion-importer/notion-metadata-extractor.mjs +303 -0
- app/scripts/notion-importer/output/.temp-pages.json +9 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8013-b668-f14bd1ac0ec0.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8014-834f-d700b623256b.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-801d-841a-e35011491566.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8031-ac8d-c5678af1bdd5.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8048-9b7e-db4fa7485915.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-804d-bd0a-e0b1c15e504f.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8075-ae2e-dc24fe9296ca.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8078-b6da-c7a4c67c8f35.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-808d-9c6d-fae817ac8868.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-808f-b712-c7c608da3fc6.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80a9-b4d0-f2129716632d.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80aa-b968-c54c9fe7e5d7.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80b6-be07-e8646502f82a.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80b9-8cfb-f0a6aaaa8760.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80e7-a500-fb79cebde7e3.png +3 -0
- app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80e9-b729-dbd328930bed.png +3 -0
- app/scripts/notion-importer/output/smol-training-guide.md +0 -0
- app/scripts/notion-importer/output/smol-training-guide.mdx +0 -0
- app/scripts/notion-importer/output/smol.md +0 -0
- app/scripts/notion-importer/output/smol.mdx +0 -0
- app/scripts/notion-importer/package-lock.json +0 -0
- app/scripts/notion-importer/package.json +0 -0
- app/scripts/notion-importer/post-processor.mjs +369 -0
- app/scripts/notion-importer/test-access.mjs +39 -0
- app/scripts/notion-importer/yarn.lock +1118 -0
app/scripts/notion-importer/.cursorignore
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
.env
|
app/scripts/notion-importer/.notion-to-md/media/27877f1c-9c9d-804d-9c82-f7b3905578ff_media.json
ADDED
|
@@ -0,0 +1,198 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"pageId": "27877f1c-9c9d-804d-9c82-f7b3905578ff",
|
| 3 |
+
"lastUpdated": "2025-10-08T13:00:26.065Z",
|
| 4 |
+
"mediaEntries": {
|
| 5 |
+
"27877f1c-9c9d-8078-b6da-c7a4c67c8f35": {
|
| 6 |
+
"mediaInfo": {
|
| 7 |
+
"type": "DOWNLOAD",
|
| 8 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/69940e63-ba02-4d6b-bc79-81dcab16590b/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466RQAHHWD2%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQCja3KUJzl59DJB4he%2BZc4EIAdSKZH6PHGkvSc5iTCA5gIhAK1O3OugR1Ap%2Fhuos6U7RbD2KxvfMHmfQXSU6K7IuEKgKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igw0pXUjiFqmEZtM2z8q3AMIdeJHjnKFMXfrzdsbRQMk5j3lsQc7tLMnmEPmHH%2FmX7sZrT4UjUkaKoeSyH%2Bg7wFpYmgvN77x8nGQ0nEQtZAPw2%2F3EH4nPTYF53xRmvyn7%2FMwloMmw7eBz7SIZ3Xk0aPYpbtVRoPUesefx7Jvddzmxu0Q%2FQpw0%2FrRCkLPJAnMdsR8fY3n8s8TBv7cVHHWkjpqgeaNKOD7O7Ej%2FNkVahgG%2BVi%2B8DlcuBG8FNk2EzDNroum71dNW6RzTO3ju65V5xHwLgmRkZRTKS%2FHeolCb01h51d%2BhJY03OORmJCMcOEYzPWg48LVGlFl%2FOA6OAhR%2FQ0eWs%2B1ZzKAz7HOSK6gHOhmcCj%2Bbve0%2FVaH2P708k33m5SQqjZQmfmO0JUCNn2WRPK9uYfSy64QFqpzeEXgAGiaNMQCrWjrLpO1TNcK457IQ4ofuJ9bt3be947z17Fa2pKdcescLFE7GdVtV5L4Nps5%2FoHCl0X1BxCPjpxN8zLRIQZtHFRloU8K6ebOrPFIb4bkjxfC9VidpyS0vnZ1DhFt8ssI1sOwrzRn5Kf%2FRltkKxvJPAp829yFUsrA35VhLZLllGpsdLzGVZS1GWkNqf0UxA5BZhdb9t4qPmp1WbBIufTnxcFuHKdUMxsdfTCxpZnHBjqkASugrWSTfsJxQU%2BvD6fKuut0yaNhG1Zscr6q%2FLX6mZAcKzCrMYWhsql27FMH5lEFZTsvBfNoX2h1ie3MPQw%2B67C4yNLYGIvBL%2BFPBfaw6qimvk48x5JDZBNsxN4fEMufvUM1%2FbemWiZZJSl8V5Q5h0NMxBmZFJkachxllAPWTTVPbSArY%2FYyX3vpKDGMi1fYZYT4IjNycyQDb6nSEKlqbnOjUosj&X-Amz-Signature=0e7a6d2cf89a76128b1e4ecd8e12053deb0a5e802a15e3e8c3d7979e2131fa09&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 9 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8078-b6da-c7a4c67c8f35.png",
|
| 10 |
+
"sourceType": "block",
|
| 11 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8078-b6da-c7a4c67c8f35.png"
|
| 12 |
+
},
|
| 13 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 14 |
+
"createdAt": "2025-09-24T09:36:35.892Z",
|
| 15 |
+
"updatedAt": "2025-10-08T13:00:25.689Z"
|
| 16 |
+
},
|
| 17 |
+
"27877f1c-9c9d-8014-834f-d700b623256b": {
|
| 18 |
+
"mediaInfo": {
|
| 19 |
+
"type": "DOWNLOAD",
|
| 20 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/a11fbd23-10f8-4485-ad35-f3de9d480449/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466RQAHHWD2%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQCja3KUJzl59DJB4he%2BZc4EIAdSKZH6PHGkvSc5iTCA5gIhAK1O3OugR1Ap%2Fhuos6U7RbD2KxvfMHmfQXSU6K7IuEKgKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igw0pXUjiFqmEZtM2z8q3AMIdeJHjnKFMXfrzdsbRQMk5j3lsQc7tLMnmEPmHH%2FmX7sZrT4UjUkaKoeSyH%2Bg7wFpYmgvN77x8nGQ0nEQtZAPw2%2F3EH4nPTYF53xRmvyn7%2FMwloMmw7eBz7SIZ3Xk0aPYpbtVRoPUesefx7Jvddzmxu0Q%2FQpw0%2FrRCkLPJAnMdsR8fY3n8s8TBv7cVHHWkjpqgeaNKOD7O7Ej%2FNkVahgG%2BVi%2B8DlcuBG8FNk2EzDNroum71dNW6RzTO3ju65V5xHwLgmRkZRTKS%2FHeolCb01h51d%2BhJY03OORmJCMcOEYzPWg48LVGlFl%2FOA6OAhR%2FQ0eWs%2B1ZzKAz7HOSK6gHOhmcCj%2Bbve0%2FVaH2P708k33m5SQqjZQmfmO0JUCNn2WRPK9uYfSy64QFqpzeEXgAGiaNMQCrWjrLpO1TNcK457IQ4ofuJ9bt3be947z17Fa2pKdcescLFE7GdVtV5L4Nps5%2FoHCl0X1BxCPjpxN8zLRIQZtHFRloU8K6ebOrPFIb4bkjxfC9VidpyS0vnZ1DhFt8ssI1sOwrzRn5Kf%2FRltkKxvJPAp829yFUsrA35VhLZLllGpsdLzGVZS1GWkNqf0UxA5BZhdb9t4qPmp1WbBIufTnxcFuHKdUMxsdfTCxpZnHBjqkASugrWSTfsJxQU%2BvD6fKuut0yaNhG1Zscr6q%2FLX6mZAcKzCrMYWhsql27FMH5lEFZTsvBfNoX2h1ie3MPQw%2B67C4yNLYGIvBL%2BFPBfaw6qimvk48x5JDZBNsxN4fEMufvUM1%2FbemWiZZJSl8V5Q5h0NMxBmZFJkachxllAPWTTVPbSArY%2FYyX3vpKDGMi1fYZYT4IjNycyQDb6nSEKlqbnOjUosj&X-Amz-Signature=9145e81d85d35d531ffb6bbabad25d5846aa559613d371bc2880f6d02529b799&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 21 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8014-834f-d700b623256b.png",
|
| 22 |
+
"sourceType": "block",
|
| 23 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8014-834f-d700b623256b.png"
|
| 24 |
+
},
|
| 25 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 26 |
+
"createdAt": "2025-09-24T09:36:35.899Z",
|
| 27 |
+
"updatedAt": "2025-10-08T13:00:25.703Z"
|
| 28 |
+
},
|
| 29 |
+
"27877f1c-9c9d-808d-9c6d-fae817ac8868": {
|
| 30 |
+
"mediaInfo": {
|
| 31 |
+
"type": "DOWNLOAD",
|
| 32 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/9b549e26-b527-4ad5-b1ad-3ed049747090/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466X3VEST5Q%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130020Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQC4Th0nobtVjj0GnPkA6aNua8I5iyMPP5wm3FPgOcNrpQIhAM6Cd1AyvJOWLCdgyh%2F9xxRIzhQ8ZEYJPtDoTzf9dVzsKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igwbq%2Fmpsk4PhTeoeU8q3ANUdDY8Un1V3sp1KnXAZQmxQggeyUGmjkp%2BsBgML%2Bh3jLesSMzdlQPFwlTBbqh74KOfU7NmNfHFLiHqWLrpeLClymtDa9BGRQAnfNGuT%2BUXXxp5dSoeOsbUJInqYhW4FsjUBRNw%2FSAslpIJKfTrmcN81%2FIUQNc0TRtVmiiXKPFUCNfWErOAQlec%2B6mNZCJYY1EbzUg1tPFNYYLpoiNb45%2F0t1VlsyeG6WlkA2KFXybguL2BmlWms%2BC%2BDeANHe2r%2Bq0h9JVtz%2BYBB3CzzQdeerNfGtyml%2BTz5DiBvv0h9F5FNcqJ4Uf1CbLGaRVIlCXLHam3xV3Fk%2FpYYQerVcK6t6YWWeRO0x92Uj1TyF1H4aCPO%2BuAjxDdY0WJfdLROdRvwH69zTdBYb26Lo7h2T2MnY%2FjJ4UNGPf0CWoGMVU9BJCO6%2Bm7RySlYPw1Axogb7clhfZAUYsM%2FhBI01n5OLo2mIl1dMcIxnZNc%2FFxp3njz6Jpth%2Fu0KOe8X%2FPTgM9S58jNUVTWHYd3bEm54SfyUlEIwmSVHkdHAvZw8QfhIC8DAJULbBkKHe6nRKxvGqo1UZW2OY0%2BKpOu7kPBwFl13lcqjMeSy%2F%2BvpZDgwHonNSKYiYRrlffBfL%2BUFWdiijebzDHpJnHBjqkAfpE6DXG5ducvq1TeQISVLspLOKXhLJ0Jn1auWbgWOv02xnmSsxVrzmbEGcfsyZArqlrtxdg9N9yH30onEToRB0OnUGFrpiazcXfmdl7JS0Cn3mL4FiEHdFC%2B2lUkrwFbKVX0NhXsjQRmkeUUtT7dXPTDyzpPIxoyghxvJsm6OswiSouBbg4NB6EQaFjgxRw9KEg79jjKbCgyYvpKNs56YVN9kvk&X-Amz-Signature=b9e650906f6978d3d01caebf5329c1571bfa97d53d88a3c571eaaa7b618970d2&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 33 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-808d-9c6d-fae817ac8868.png",
|
| 34 |
+
"sourceType": "block",
|
| 35 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-808d-9c6d-fae817ac8868.png"
|
| 36 |
+
},
|
| 37 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 38 |
+
"createdAt": "2025-09-24T09:36:35.943Z",
|
| 39 |
+
"updatedAt": "2025-10-08T13:00:25.727Z"
|
| 40 |
+
},
|
| 41 |
+
"27877f1c-9c9d-8075-ae2e-dc24fe9296ca": {
|
| 42 |
+
"mediaInfo": {
|
| 43 |
+
"type": "DOWNLOAD",
|
| 44 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/943ada15-c18b-4434-ac96-cca2440119db/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466X3VEST5Q%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130020Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQC4Th0nobtVjj0GnPkA6aNua8I5iyMPP5wm3FPgOcNrpQIhAM6Cd1AyvJOWLCdgyh%2F9xxRIzhQ8ZEYJPtDoTzf9dVzsKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igwbq%2Fmpsk4PhTeoeU8q3ANUdDY8Un1V3sp1KnXAZQmxQggeyUGmjkp%2BsBgML%2Bh3jLesSMzdlQPFwlTBbqh74KOfU7NmNfHFLiHqWLrpeLClymtDa9BGRQAnfNGuT%2BUXXxp5dSoeOsbUJInqYhW4FsjUBRNw%2FSAslpIJKfTrmcN81%2FIUQNc0TRtVmiiXKPFUCNfWErOAQlec%2B6mNZCJYY1EbzUg1tPFNYYLpoiNb45%2F0t1VlsyeG6WlkA2KFXybguL2BmlWms%2BC%2BDeANHe2r%2Bq0h9JVtz%2BYBB3CzzQdeerNfGtyml%2BTz5DiBvv0h9F5FNcqJ4Uf1CbLGaRVIlCXLHam3xV3Fk%2FpYYQerVcK6t6YWWeRO0x92Uj1TyF1H4aCPO%2BuAjxDdY0WJfdLROdRvwH69zTdBYb26Lo7h2T2MnY%2FjJ4UNGPf0CWoGMVU9BJCO6%2Bm7RySlYPw1Axogb7clhfZAUYsM%2FhBI01n5OLo2mIl1dMcIxnZNc%2FFxp3njz6Jpth%2Fu0KOe8X%2FPTgM9S58jNUVTWHYd3bEm54SfyUlEIwmSVHkdHAvZw8QfhIC8DAJULbBkKHe6nRKxvGqo1UZW2OY0%2BKpOu7kPBwFl13lcqjMeSy%2F%2BvpZDgwHonNSKYiYRrlffBfL%2BUFWdiijebzDHpJnHBjqkAfpE6DXG5ducvq1TeQISVLspLOKXhLJ0Jn1auWbgWOv02xnmSsxVrzmbEGcfsyZArqlrtxdg9N9yH30onEToRB0OnUGFrpiazcXfmdl7JS0Cn3mL4FiEHdFC%2B2lUkrwFbKVX0NhXsjQRmkeUUtT7dXPTDyzpPIxoyghxvJsm6OswiSouBbg4NB6EQaFjgxRw9KEg79jjKbCgyYvpKNs56YVN9kvk&X-Amz-Signature=f6c6aeafa758351188cf92575d7adbac6d4438d61891b377861cceebe4699c16&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 45 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8075-ae2e-dc24fe9296ca.png",
|
| 46 |
+
"sourceType": "block",
|
| 47 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8075-ae2e-dc24fe9296ca.png"
|
| 48 |
+
},
|
| 49 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 50 |
+
"createdAt": "2025-09-24T09:36:36.095Z",
|
| 51 |
+
"updatedAt": "2025-10-08T13:00:25.926Z"
|
| 52 |
+
},
|
| 53 |
+
"27877f1c-9c9d-801d-841a-e35011491566": {
|
| 54 |
+
"mediaInfo": {
|
| 55 |
+
"type": "DOWNLOAD",
|
| 56 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/3a912fb2-01eb-46d2-9687-41ffbb5b0446/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466Y2XCJFFW%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQDGr1WaO6mypVW00YGoLx4XK5HeMm7tg4Wxi4tRLT0sBQIhAJZB9sfEWXoL6QQ8WnamF77mePTGmWqiZjYqIQ1Ba5kMKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1IgyvfgauHIg52DwLqjMq3AOxwogx8uxNPXYdZuG3Giz0pcRPcVYGSzx%2FsCHi3wTJAjMOnK7oq5bOcT%2Fl2UzIP2n1RWhZZWYAbDJFjDsGnnxxjP1dA4W%2BG2JxtQjoyKDV24YvvyoKp%2B8c%2BVuzeJYc%2FAp0wja9UZjjmB6We9vy73l%2F0lzOEnuDWGvA3Wz7HN72nCAxRWfFw3VXoLc12NJA7jMXJpMTJ0kQhR54IefMuCgXQRkP9ThY944aJBcJDVVW2oPCliR0sNKWOwxmzYLfqTaCfVYnYWij0W2PFYWTl8O8Fz%2F6tJQeBzIzYZkQH%2B%2FID9QHo2H91PyVglygKK5nFfSUGmu5%2BlBHNZhF0tQ%2BkkSiJBO%2Fzpzh1l3tJ5%2FSDTS3OkCq9CgQS1LlOZ%2FWVGRa0dO%2BPKuLt2kSE3g%2BdENrh0uHMXL16JnD8tihVBQjDVDteb9ty3wYric3oz7UIdTbcFFhBvLNK2iaTTxgVVe8Iwec1Yh5%2Br70PVEtQ2RGpeJRNF%2FTCdNajTXZecTA4gfj3Dep1uEbLH6wJzKpoYff5ewJZaQ5NqIKjBbwZlP0ZsdmirA3vCFTiBuA%2FtxyQutgfCfqtxDzRYtRLdYtuXHnOJX19k0dW1qKTx%2FvJHjGhd%2BF7DDuSjbWdZfyMNBtvTCCpZnHBjqkAXWtzxhDxy981YikbANxxcBAJxQM7hXL4Lmn9JZH3hI2Z46Dd1xpYDzpq%2Bv0TjPTSsilTsyySr4C8rXZuw4BTrdyjlduhH34%2FNp16EC1u7PlP2iNue5eMeLdERldacspGGFk9eApo%2FSCPEUJdHN%2B514Zr0nBCSnGWEy9najlnY9KFSWwfrPpbEz0Z2MLkADQVvGJ4N1Aa7S4MU9m9WAxOA%2BBxMyX&X-Amz-Signature=fdbb11308e72b72824529e50a6386bf06785d0576e5c27d6cf6f609380614733&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 57 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-801d-841a-e35011491566.png",
|
| 58 |
+
"sourceType": "block",
|
| 59 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-801d-841a-e35011491566.png"
|
| 60 |
+
},
|
| 61 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 62 |
+
"createdAt": "2025-09-24T09:36:36.121Z",
|
| 63 |
+
"updatedAt": "2025-10-08T13:00:25.898Z"
|
| 64 |
+
},
|
| 65 |
+
"27877f1c-9c9d-8048-9b7e-db4fa7485915": {
|
| 66 |
+
"mediaInfo": {
|
| 67 |
+
"type": "DOWNLOAD",
|
| 68 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/58651851-13c8-4e99-92e3-857c8e3d305b/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466X3VEST5Q%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130020Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQC4Th0nobtVjj0GnPkA6aNua8I5iyMPP5wm3FPgOcNrpQIhAM6Cd1AyvJOWLCdgyh%2F9xxRIzhQ8ZEYJPtDoTzf9dVzsKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igwbq%2Fmpsk4PhTeoeU8q3ANUdDY8Un1V3sp1KnXAZQmxQggeyUGmjkp%2BsBgML%2Bh3jLesSMzdlQPFwlTBbqh74KOfU7NmNfHFLiHqWLrpeLClymtDa9BGRQAnfNGuT%2BUXXxp5dSoeOsbUJInqYhW4FsjUBRNw%2FSAslpIJKfTrmcN81%2FIUQNc0TRtVmiiXKPFUCNfWErOAQlec%2B6mNZCJYY1EbzUg1tPFNYYLpoiNb45%2F0t1VlsyeG6WlkA2KFXybguL2BmlWms%2BC%2BDeANHe2r%2Bq0h9JVtz%2BYBB3CzzQdeerNfGtyml%2BTz5DiBvv0h9F5FNcqJ4Uf1CbLGaRVIlCXLHam3xV3Fk%2FpYYQerVcK6t6YWWeRO0x92Uj1TyF1H4aCPO%2BuAjxDdY0WJfdLROdRvwH69zTdBYb26Lo7h2T2MnY%2FjJ4UNGPf0CWoGMVU9BJCO6%2Bm7RySlYPw1Axogb7clhfZAUYsM%2FhBI01n5OLo2mIl1dMcIxnZNc%2FFxp3njz6Jpth%2Fu0KOe8X%2FPTgM9S58jNUVTWHYd3bEm54SfyUlEIwmSVHkdHAvZw8QfhIC8DAJULbBkKHe6nRKxvGqo1UZW2OY0%2BKpOu7kPBwFl13lcqjMeSy%2F%2BvpZDgwHonNSKYiYRrlffBfL%2BUFWdiijebzDHpJnHBjqkAfpE6DXG5ducvq1TeQISVLspLOKXhLJ0Jn1auWbgWOv02xnmSsxVrzmbEGcfsyZArqlrtxdg9N9yH30onEToRB0OnUGFrpiazcXfmdl7JS0Cn3mL4FiEHdFC%2B2lUkrwFbKVX0NhXsjQRmkeUUtT7dXPTDyzpPIxoyghxvJsm6OswiSouBbg4NB6EQaFjgxRw9KEg79jjKbCgyYvpKNs56YVN9kvk&X-Amz-Signature=f13847b038a80822deb40d3e0873722dc40cb227be4a6edfdb70d27be0794729&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 69 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8048-9b7e-db4fa7485915.png",
|
| 70 |
+
"sourceType": "block",
|
| 71 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8048-9b7e-db4fa7485915.png"
|
| 72 |
+
},
|
| 73 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 74 |
+
"createdAt": "2025-09-24T09:36:36.136Z",
|
| 75 |
+
"updatedAt": "2025-10-08T13:00:25.917Z"
|
| 76 |
+
},
|
| 77 |
+
"27877f1c-9c9d-804d-bd0a-e0b1c15e504f": {
|
| 78 |
+
"mediaInfo": {
|
| 79 |
+
"type": "DOWNLOAD",
|
| 80 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/3fbc7e6c-8ec0-4ef5-9161-7aef75930323/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466RQAHHWD2%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130014Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQCja3KUJzl59DJB4he%2BZc4EIAdSKZH6PHGkvSc5iTCA5gIhAK1O3OugR1Ap%2Fhuos6U7RbD2KxvfMHmfQXSU6K7IuEKgKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igw0pXUjiFqmEZtM2z8q3AMIdeJHjnKFMXfrzdsbRQMk5j3lsQc7tLMnmEPmHH%2FmX7sZrT4UjUkaKoeSyH%2Bg7wFpYmgvN77x8nGQ0nEQtZAPw2%2F3EH4nPTYF53xRmvyn7%2FMwloMmw7eBz7SIZ3Xk0aPYpbtVRoPUesefx7Jvddzmxu0Q%2FQpw0%2FrRCkLPJAnMdsR8fY3n8s8TBv7cVHHWkjpqgeaNKOD7O7Ej%2FNkVahgG%2BVi%2B8DlcuBG8FNk2EzDNroum71dNW6RzTO3ju65V5xHwLgmRkZRTKS%2FHeolCb01h51d%2BhJY03OORmJCMcOEYzPWg48LVGlFl%2FOA6OAhR%2FQ0eWs%2B1ZzKAz7HOSK6gHOhmcCj%2Bbve0%2FVaH2P708k33m5SQqjZQmfmO0JUCNn2WRPK9uYfSy64QFqpzeEXgAGiaNMQCrWjrLpO1TNcK457IQ4ofuJ9bt3be947z17Fa2pKdcescLFE7GdVtV5L4Nps5%2FoHCl0X1BxCPjpxN8zLRIQZtHFRloU8K6ebOrPFIb4bkjxfC9VidpyS0vnZ1DhFt8ssI1sOwrzRn5Kf%2FRltkKxvJPAp829yFUsrA35VhLZLllGpsdLzGVZS1GWkNqf0UxA5BZhdb9t4qPmp1WbBIufTnxcFuHKdUMxsdfTCxpZnHBjqkASugrWSTfsJxQU%2BvD6fKuut0yaNhG1Zscr6q%2FLX6mZAcKzCrMYWhsql27FMH5lEFZTsvBfNoX2h1ie3MPQw%2B67C4yNLYGIvBL%2BFPBfaw6qimvk48x5JDZBNsxN4fEMufvUM1%2FbemWiZZJSl8V5Q5h0NMxBmZFJkachxllAPWTTVPbSArY%2FYyX3vpKDGMi1fYZYT4IjNycyQDb6nSEKlqbnOjUosj&X-Amz-Signature=fd7ef992dc4f3a290a5f04a0a640fe2828b5a33487682c4956913fe674c9c017&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 81 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-804d-bd0a-e0b1c15e504f.png",
|
| 82 |
+
"sourceType": "block",
|
| 83 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-804d-bd0a-e0b1c15e504f.png"
|
| 84 |
+
},
|
| 85 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 86 |
+
"createdAt": "2025-09-24T09:36:36.244Z",
|
| 87 |
+
"updatedAt": "2025-10-08T13:00:26.009Z"
|
| 88 |
+
},
|
| 89 |
+
"27877f1c-9c9d-80b9-8cfb-f0a6aaaa8760": {
|
| 90 |
+
"mediaInfo": {
|
| 91 |
+
"type": "DOWNLOAD",
|
| 92 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/d3899f55-47ba-45b0-be0f-9abc5bb4f247/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466RQAHHWD2%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQCja3KUJzl59DJB4he%2BZc4EIAdSKZH6PHGkvSc5iTCA5gIhAK1O3OugR1Ap%2Fhuos6U7RbD2KxvfMHmfQXSU6K7IuEKgKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igw0pXUjiFqmEZtM2z8q3AMIdeJHjnKFMXfrzdsbRQMk5j3lsQc7tLMnmEPmHH%2FmX7sZrT4UjUkaKoeSyH%2Bg7wFpYmgvN77x8nGQ0nEQtZAPw2%2F3EH4nPTYF53xRmvyn7%2FMwloMmw7eBz7SIZ3Xk0aPYpbtVRoPUesefx7Jvddzmxu0Q%2FQpw0%2FrRCkLPJAnMdsR8fY3n8s8TBv7cVHHWkjpqgeaNKOD7O7Ej%2FNkVahgG%2BVi%2B8DlcuBG8FNk2EzDNroum71dNW6RzTO3ju65V5xHwLgmRkZRTKS%2FHeolCb01h51d%2BhJY03OORmJCMcOEYzPWg48LVGlFl%2FOA6OAhR%2FQ0eWs%2B1ZzKAz7HOSK6gHOhmcCj%2Bbve0%2FVaH2P708k33m5SQqjZQmfmO0JUCNn2WRPK9uYfSy64QFqpzeEXgAGiaNMQCrWjrLpO1TNcK457IQ4ofuJ9bt3be947z17Fa2pKdcescLFE7GdVtV5L4Nps5%2FoHCl0X1BxCPjpxN8zLRIQZtHFRloU8K6ebOrPFIb4bkjxfC9VidpyS0vnZ1DhFt8ssI1sOwrzRn5Kf%2FRltkKxvJPAp829yFUsrA35VhLZLllGpsdLzGVZS1GWkNqf0UxA5BZhdb9t4qPmp1WbBIufTnxcFuHKdUMxsdfTCxpZnHBjqkASugrWSTfsJxQU%2BvD6fKuut0yaNhG1Zscr6q%2FLX6mZAcKzCrMYWhsql27FMH5lEFZTsvBfNoX2h1ie3MPQw%2B67C4yNLYGIvBL%2BFPBfaw6qimvk48x5JDZBNsxN4fEMufvUM1%2FbemWiZZJSl8V5Q5h0NMxBmZFJkachxllAPWTTVPbSArY%2FYyX3vpKDGMi1fYZYT4IjNycyQDb6nSEKlqbnOjUosj&X-Amz-Signature=0e702a4db1c4dabdd69b83b59535958cd39a3e2906332aa607e61864797bca59&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 93 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80b9-8cfb-f0a6aaaa8760.png",
|
| 94 |
+
"sourceType": "block",
|
| 95 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80b9-8cfb-f0a6aaaa8760.png"
|
| 96 |
+
},
|
| 97 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 98 |
+
"createdAt": "2025-09-24T09:36:36.247Z",
|
| 99 |
+
"updatedAt": "2025-10-08T13:00:26.000Z"
|
| 100 |
+
},
|
| 101 |
+
"27877f1c-9c9d-80aa-b968-c54c9fe7e5d7": {
|
| 102 |
+
"mediaInfo": {
|
| 103 |
+
"type": "DOWNLOAD",
|
| 104 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/1f240ffd-b4d7-422a-9a81-0aabda1f6c16/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466Y2XCJFFW%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQDGr1WaO6mypVW00YGoLx4XK5HeMm7tg4Wxi4tRLT0sBQIhAJZB9sfEWXoL6QQ8WnamF77mePTGmWqiZjYqIQ1Ba5kMKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1IgyvfgauHIg52DwLqjMq3AOxwogx8uxNPXYdZuG3Giz0pcRPcVYGSzx%2FsCHi3wTJAjMOnK7oq5bOcT%2Fl2UzIP2n1RWhZZWYAbDJFjDsGnnxxjP1dA4W%2BG2JxtQjoyKDV24YvvyoKp%2B8c%2BVuzeJYc%2FAp0wja9UZjjmB6We9vy73l%2F0lzOEnuDWGvA3Wz7HN72nCAxRWfFw3VXoLc12NJA7jMXJpMTJ0kQhR54IefMuCgXQRkP9ThY944aJBcJDVVW2oPCliR0sNKWOwxmzYLfqTaCfVYnYWij0W2PFYWTl8O8Fz%2F6tJQeBzIzYZkQH%2B%2FID9QHo2H91PyVglygKK5nFfSUGmu5%2BlBHNZhF0tQ%2BkkSiJBO%2Fzpzh1l3tJ5%2FSDTS3OkCq9CgQS1LlOZ%2FWVGRa0dO%2BPKuLt2kSE3g%2BdENrh0uHMXL16JnD8tihVBQjDVDteb9ty3wYric3oz7UIdTbcFFhBvLNK2iaTTxgVVe8Iwec1Yh5%2Br70PVEtQ2RGpeJRNF%2FTCdNajTXZecTA4gfj3Dep1uEbLH6wJzKpoYff5ewJZaQ5NqIKjBbwZlP0ZsdmirA3vCFTiBuA%2FtxyQutgfCfqtxDzRYtRLdYtuXHnOJX19k0dW1qKTx%2FvJHjGhd%2BF7DDuSjbWdZfyMNBtvTCCpZnHBjqkAXWtzxhDxy981YikbANxxcBAJxQM7hXL4Lmn9JZH3hI2Z46Dd1xpYDzpq%2Bv0TjPTSsilTsyySr4C8rXZuw4BTrdyjlduhH34%2FNp16EC1u7PlP2iNue5eMeLdERldacspGGFk9eApo%2FSCPEUJdHN%2B514Zr0nBCSnGWEy9najlnY9KFSWwfrPpbEz0Z2MLkADQVvGJ4N1Aa7S4MU9m9WAxOA%2BBxMyX&X-Amz-Signature=c353bf2bf0d4ef95c66531df5c779035a90add76e2c286e9e26d41c1a6526eb9&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 105 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80aa-b968-c54c9fe7e5d7.png",
|
| 106 |
+
"sourceType": "block",
|
| 107 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80aa-b968-c54c9fe7e5d7.png"
|
| 108 |
+
},
|
| 109 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 110 |
+
"createdAt": "2025-09-24T09:36:36.247Z",
|
| 111 |
+
"updatedAt": "2025-10-08T13:00:26.061Z"
|
| 112 |
+
},
|
| 113 |
+
"27877f1c-9c9d-8013-b668-f14bd1ac0ec0": {
|
| 114 |
+
"mediaInfo": {
|
| 115 |
+
"type": "DOWNLOAD",
|
| 116 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/cb01b334-89a5-436f-a141-b7c310d25b57/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466Y2XCJFFW%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQDGr1WaO6mypVW00YGoLx4XK5HeMm7tg4Wxi4tRLT0sBQIhAJZB9sfEWXoL6QQ8WnamF77mePTGmWqiZjYqIQ1Ba5kMKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1IgyvfgauHIg52DwLqjMq3AOxwogx8uxNPXYdZuG3Giz0pcRPcVYGSzx%2FsCHi3wTJAjMOnK7oq5bOcT%2Fl2UzIP2n1RWhZZWYAbDJFjDsGnnxxjP1dA4W%2BG2JxtQjoyKDV24YvvyoKp%2B8c%2BVuzeJYc%2FAp0wja9UZjjmB6We9vy73l%2F0lzOEnuDWGvA3Wz7HN72nCAxRWfFw3VXoLc12NJA7jMXJpMTJ0kQhR54IefMuCgXQRkP9ThY944aJBcJDVVW2oPCliR0sNKWOwxmzYLfqTaCfVYnYWij0W2PFYWTl8O8Fz%2F6tJQeBzIzYZkQH%2B%2FID9QHo2H91PyVglygKK5nFfSUGmu5%2BlBHNZhF0tQ%2BkkSiJBO%2Fzpzh1l3tJ5%2FSDTS3OkCq9CgQS1LlOZ%2FWVGRa0dO%2BPKuLt2kSE3g%2BdENrh0uHMXL16JnD8tihVBQjDVDteb9ty3wYric3oz7UIdTbcFFhBvLNK2iaTTxgVVe8Iwec1Yh5%2Br70PVEtQ2RGpeJRNF%2FTCdNajTXZecTA4gfj3Dep1uEbLH6wJzKpoYff5ewJZaQ5NqIKjBbwZlP0ZsdmirA3vCFTiBuA%2FtxyQutgfCfqtxDzRYtRLdYtuXHnOJX19k0dW1qKTx%2FvJHjGhd%2BF7DDuSjbWdZfyMNBtvTCCpZnHBjqkAXWtzxhDxy981YikbANxxcBAJxQM7hXL4Lmn9JZH3hI2Z46Dd1xpYDzpq%2Bv0TjPTSsilTsyySr4C8rXZuw4BTrdyjlduhH34%2FNp16EC1u7PlP2iNue5eMeLdERldacspGGFk9eApo%2FSCPEUJdHN%2B514Zr0nBCSnGWEy9najlnY9KFSWwfrPpbEz0Z2MLkADQVvGJ4N1Aa7S4MU9m9WAxOA%2BBxMyX&X-Amz-Signature=ff0a0599c70fd9f202d55e4a7e887de8d8727724550d0e9faf6df28e0e9b7696&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 117 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8013-b668-f14bd1ac0ec0.png",
|
| 118 |
+
"sourceType": "block",
|
| 119 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8013-b668-f14bd1ac0ec0.png"
|
| 120 |
+
},
|
| 121 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 122 |
+
"createdAt": "2025-09-24T09:36:36.250Z",
|
| 123 |
+
"updatedAt": "2025-10-08T13:00:26.056Z"
|
| 124 |
+
},
|
| 125 |
+
"27877f1c-9c9d-80e9-b729-dbd328930bed": {
|
| 126 |
+
"mediaInfo": {
|
| 127 |
+
"type": "DOWNLOAD",
|
| 128 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/9d723e06-252f-44e3-844e-1410fa92667a/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466RQAHHWD2%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQCja3KUJzl59DJB4he%2BZc4EIAdSKZH6PHGkvSc5iTCA5gIhAK1O3OugR1Ap%2Fhuos6U7RbD2KxvfMHmfQXSU6K7IuEKgKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igw0pXUjiFqmEZtM2z8q3AMIdeJHjnKFMXfrzdsbRQMk5j3lsQc7tLMnmEPmHH%2FmX7sZrT4UjUkaKoeSyH%2Bg7wFpYmgvN77x8nGQ0nEQtZAPw2%2F3EH4nPTYF53xRmvyn7%2FMwloMmw7eBz7SIZ3Xk0aPYpbtVRoPUesefx7Jvddzmxu0Q%2FQpw0%2FrRCkLPJAnMdsR8fY3n8s8TBv7cVHHWkjpqgeaNKOD7O7Ej%2FNkVahgG%2BVi%2B8DlcuBG8FNk2EzDNroum71dNW6RzTO3ju65V5xHwLgmRkZRTKS%2FHeolCb01h51d%2BhJY03OORmJCMcOEYzPWg48LVGlFl%2FOA6OAhR%2FQ0eWs%2B1ZzKAz7HOSK6gHOhmcCj%2Bbve0%2FVaH2P708k33m5SQqjZQmfmO0JUCNn2WRPK9uYfSy64QFqpzeEXgAGiaNMQCrWjrLpO1TNcK457IQ4ofuJ9bt3be947z17Fa2pKdcescLFE7GdVtV5L4Nps5%2FoHCl0X1BxCPjpxN8zLRIQZtHFRloU8K6ebOrPFIb4bkjxfC9VidpyS0vnZ1DhFt8ssI1sOwrzRn5Kf%2FRltkKxvJPAp829yFUsrA35VhLZLllGpsdLzGVZS1GWkNqf0UxA5BZhdb9t4qPmp1WbBIufTnxcFuHKdUMxsdfTCxpZnHBjqkASugrWSTfsJxQU%2BvD6fKuut0yaNhG1Zscr6q%2FLX6mZAcKzCrMYWhsql27FMH5lEFZTsvBfNoX2h1ie3MPQw%2B67C4yNLYGIvBL%2BFPBfaw6qimvk48x5JDZBNsxN4fEMufvUM1%2FbemWiZZJSl8V5Q5h0NMxBmZFJkachxllAPWTTVPbSArY%2FYyX3vpKDGMi1fYZYT4IjNycyQDb6nSEKlqbnOjUosj&X-Amz-Signature=4faf0d241e315ba80e5f56bb4cb410229c15e429fcab990fd1ebc2b17e2e4388&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 129 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80e9-b729-dbd328930bed.png",
|
| 130 |
+
"sourceType": "block",
|
| 131 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80e9-b729-dbd328930bed.png"
|
| 132 |
+
},
|
| 133 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 134 |
+
"createdAt": "2025-09-24T09:36:36.251Z",
|
| 135 |
+
"updatedAt": "2025-10-08T13:00:26.048Z"
|
| 136 |
+
},
|
| 137 |
+
"27877f1c-9c9d-80a9-b4d0-f2129716632d": {
|
| 138 |
+
"mediaInfo": {
|
| 139 |
+
"type": "DOWNLOAD",
|
| 140 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/137c2c51-6f89-437f-ba45-3a844c747b7a/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466W5FHSQK6%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130018Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJGMEQCIAhuEUuJdQLuRcUIqWrlF%2FxJVRmDyl6u61kVLhtjlfZUAiBV%2Fg6BRYZGv8gjl2KUiGhGUm6oydw9R%2BGbL4YBC8orxyqIBAi9%2F%2F%2F%2F%2F%2F%2F%2F%2F%2F8BEAAaDDYzNzQyMzE4MzgwNSIM3uBXzGO9Ig0qNGY4KtwD8SFvKEBtLvytudTAIznpwZ0LlbKJs50UtNCuHXZMaMCWVzh3bh5s1YUDv9F8QzpxpmwoEHNA0zdieOQ0RTayznMP%2FQonTMVpq110QUSpjw0oiOQAObBO%2FZhOW3eVIvyERdtG8hJ%2FFdtOx68HiwShjXQNIx%2FTLP%2FyKsamFu97bNFKLLbXaKEQL%2FPeYBMfUh1FOikwzUsWtnX6xkIyDZlzyvR5XfiR93IkhPKAe3tRogdfHErVfaMhWD4CLC3CotugLqYLChLu2FEgjljFpEHc5u5od5FnVy9AUpcA9X21VVFEM5ZdQ2e3RAB6wIMQvIaYTHHCnFFfouA8nRqcEVzWysN3qwh2ilXM%2FkIfZN7fRIxbBSPLyUIVcJpZNwbzs8d5bs3qvzM9G8FkzDvtYML3JOdEzF4LuxAAJJLAqhTTQ1PhnB4lalWW%2BzGBluxdvxfidxr7w8b74x1A6sr2RRg204TCYmbv8epUSs%2BRfkjbpQb25T59MrJnDDkvR3vwM0uRiYOcx7BIJoJQ9NABbDhUdQivPKSx%2FWfUI4qzy2Qu3ylcwrudYUrkObXxW8EpCrpCr3q7hWCPkKfvLhioYojN04XKEoAr9eJNJKYu8%2BGtS2%2FHsFqf94Soxz4NYa8wsaWZxwY6pgEneyRps7aPn1nFrZvbD3DUmmNVnG7Ot90eZ9AeaSCgE0a8LPo2EBJqYduCTOFx0ZS31WSpymmuKKyjsI94sx8u%2F5Mmvyc%2F6g6F%2FSGga8Z7F5NIPVciGCTsa2iZFLblK4LGKDfvx5RgoyuAatccTNlNYca%2F5w9iQ1JXOu83l39OW1O54Xr5rX96kIiak60h5LxJgIHU3zeBdD4UeGH39LaRoJyMksdX&X-Amz-Signature=3e45baae308e0004d8e62bc03d6e459d6310e19ae4935db52491727bc24231cb&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 141 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80a9-b4d0-f2129716632d.png",
|
| 142 |
+
"sourceType": "block",
|
| 143 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80a9-b4d0-f2129716632d.png"
|
| 144 |
+
},
|
| 145 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 146 |
+
"createdAt": "2025-09-24T09:36:36.257Z",
|
| 147 |
+
"updatedAt": "2025-10-08T13:00:26.048Z"
|
| 148 |
+
},
|
| 149 |
+
"27877f1c-9c9d-80b6-be07-e8646502f82a": {
|
| 150 |
+
"mediaInfo": {
|
| 151 |
+
"type": "DOWNLOAD",
|
| 152 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/843a4edd-435d-45ca-8212-1af31305fb3a/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466RQAHHWD2%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQCja3KUJzl59DJB4he%2BZc4EIAdSKZH6PHGkvSc5iTCA5gIhAK1O3OugR1Ap%2Fhuos6U7RbD2KxvfMHmfQXSU6K7IuEKgKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igw0pXUjiFqmEZtM2z8q3AMIdeJHjnKFMXfrzdsbRQMk5j3lsQc7tLMnmEPmHH%2FmX7sZrT4UjUkaKoeSyH%2Bg7wFpYmgvN77x8nGQ0nEQtZAPw2%2F3EH4nPTYF53xRmvyn7%2FMwloMmw7eBz7SIZ3Xk0aPYpbtVRoPUesefx7Jvddzmxu0Q%2FQpw0%2FrRCkLPJAnMdsR8fY3n8s8TBv7cVHHWkjpqgeaNKOD7O7Ej%2FNkVahgG%2BVi%2B8DlcuBG8FNk2EzDNroum71dNW6RzTO3ju65V5xHwLgmRkZRTKS%2FHeolCb01h51d%2BhJY03OORmJCMcOEYzPWg48LVGlFl%2FOA6OAhR%2FQ0eWs%2B1ZzKAz7HOSK6gHOhmcCj%2Bbve0%2FVaH2P708k33m5SQqjZQmfmO0JUCNn2WRPK9uYfSy64QFqpzeEXgAGiaNMQCrWjrLpO1TNcK457IQ4ofuJ9bt3be947z17Fa2pKdcescLFE7GdVtV5L4Nps5%2FoHCl0X1BxCPjpxN8zLRIQZtHFRloU8K6ebOrPFIb4bkjxfC9VidpyS0vnZ1DhFt8ssI1sOwrzRn5Kf%2FRltkKxvJPAp829yFUsrA35VhLZLllGpsdLzGVZS1GWkNqf0UxA5BZhdb9t4qPmp1WbBIufTnxcFuHKdUMxsdfTCxpZnHBjqkASugrWSTfsJxQU%2BvD6fKuut0yaNhG1Zscr6q%2FLX6mZAcKzCrMYWhsql27FMH5lEFZTsvBfNoX2h1ie3MPQw%2B67C4yNLYGIvBL%2BFPBfaw6qimvk48x5JDZBNsxN4fEMufvUM1%2FbemWiZZJSl8V5Q5h0NMxBmZFJkachxllAPWTTVPbSArY%2FYyX3vpKDGMi1fYZYT4IjNycyQDb6nSEKlqbnOjUosj&X-Amz-Signature=6b41be5cc09cf3fae5304c63a3291650e24c6ad9285ba21202c90a186c8be390&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 153 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80b6-be07-e8646502f82a.png",
|
| 154 |
+
"sourceType": "block",
|
| 155 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80b6-be07-e8646502f82a.png"
|
| 156 |
+
},
|
| 157 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 158 |
+
"createdAt": "2025-09-24T09:36:36.274Z",
|
| 159 |
+
"updatedAt": "2025-10-08T13:00:25.995Z"
|
| 160 |
+
},
|
| 161 |
+
"27877f1c-9c9d-808f-b712-c7c608da3fc6": {
|
| 162 |
+
"mediaInfo": {
|
| 163 |
+
"type": "DOWNLOAD",
|
| 164 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/33327526-41c3-4e9c-b4ee-c7cc3c23c7ca/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466Y2XCJFFW%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130015Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQDGr1WaO6mypVW00YGoLx4XK5HeMm7tg4Wxi4tRLT0sBQIhAJZB9sfEWXoL6QQ8WnamF77mePTGmWqiZjYqIQ1Ba5kMKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1IgyvfgauHIg52DwLqjMq3AOxwogx8uxNPXYdZuG3Giz0pcRPcVYGSzx%2FsCHi3wTJAjMOnK7oq5bOcT%2Fl2UzIP2n1RWhZZWYAbDJFjDsGnnxxjP1dA4W%2BG2JxtQjoyKDV24YvvyoKp%2B8c%2BVuzeJYc%2FAp0wja9UZjjmB6We9vy73l%2F0lzOEnuDWGvA3Wz7HN72nCAxRWfFw3VXoLc12NJA7jMXJpMTJ0kQhR54IefMuCgXQRkP9ThY944aJBcJDVVW2oPCliR0sNKWOwxmzYLfqTaCfVYnYWij0W2PFYWTl8O8Fz%2F6tJQeBzIzYZkQH%2B%2FID9QHo2H91PyVglygKK5nFfSUGmu5%2BlBHNZhF0tQ%2BkkSiJBO%2Fzpzh1l3tJ5%2FSDTS3OkCq9CgQS1LlOZ%2FWVGRa0dO%2BPKuLt2kSE3g%2BdENrh0uHMXL16JnD8tihVBQjDVDteb9ty3wYric3oz7UIdTbcFFhBvLNK2iaTTxgVVe8Iwec1Yh5%2Br70PVEtQ2RGpeJRNF%2FTCdNajTXZecTA4gfj3Dep1uEbLH6wJzKpoYff5ewJZaQ5NqIKjBbwZlP0ZsdmirA3vCFTiBuA%2FtxyQutgfCfqtxDzRYtRLdYtuXHnOJX19k0dW1qKTx%2FvJHjGhd%2BF7DDuSjbWdZfyMNBtvTCCpZnHBjqkAXWtzxhDxy981YikbANxxcBAJxQM7hXL4Lmn9JZH3hI2Z46Dd1xpYDzpq%2Bv0TjPTSsilTsyySr4C8rXZuw4BTrdyjlduhH34%2FNp16EC1u7PlP2iNue5eMeLdERldacspGGFk9eApo%2FSCPEUJdHN%2B514Zr0nBCSnGWEy9najlnY9KFSWwfrPpbEz0Z2MLkADQVvGJ4N1Aa7S4MU9m9WAxOA%2BBxMyX&X-Amz-Signature=68518895319bebfef33cc5c5786ea73b408d55f058fe1b07a6e057f3167389dc&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 165 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-808f-b712-c7c608da3fc6.png",
|
| 166 |
+
"sourceType": "block",
|
| 167 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-808f-b712-c7c608da3fc6.png"
|
| 168 |
+
},
|
| 169 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 170 |
+
"createdAt": "2025-09-24T09:36:36.274Z",
|
| 171 |
+
"updatedAt": "2025-10-08T13:00:25.863Z"
|
| 172 |
+
},
|
| 173 |
+
"27877f1c-9c9d-8031-ac8d-c5678af1bdd5": {
|
| 174 |
+
"mediaInfo": {
|
| 175 |
+
"type": "DOWNLOAD",
|
| 176 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/16831579-d887-4894-b36a-d4df8a134653/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466X3VEST5Q%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130020Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQC4Th0nobtVjj0GnPkA6aNua8I5iyMPP5wm3FPgOcNrpQIhAM6Cd1AyvJOWLCdgyh%2F9xxRIzhQ8ZEYJPtDoTzf9dVzsKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igwbq%2Fmpsk4PhTeoeU8q3ANUdDY8Un1V3sp1KnXAZQmxQggeyUGmjkp%2BsBgML%2Bh3jLesSMzdlQPFwlTBbqh74KOfU7NmNfHFLiHqWLrpeLClymtDa9BGRQAnfNGuT%2BUXXxp5dSoeOsbUJInqYhW4FsjUBRNw%2FSAslpIJKfTrmcN81%2FIUQNc0TRtVmiiXKPFUCNfWErOAQlec%2B6mNZCJYY1EbzUg1tPFNYYLpoiNb45%2F0t1VlsyeG6WlkA2KFXybguL2BmlWms%2BC%2BDeANHe2r%2Bq0h9JVtz%2BYBB3CzzQdeerNfGtyml%2BTz5DiBvv0h9F5FNcqJ4Uf1CbLGaRVIlCXLHam3xV3Fk%2FpYYQerVcK6t6YWWeRO0x92Uj1TyF1H4aCPO%2BuAjxDdY0WJfdLROdRvwH69zTdBYb26Lo7h2T2MnY%2FjJ4UNGPf0CWoGMVU9BJCO6%2Bm7RySlYPw1Axogb7clhfZAUYsM%2FhBI01n5OLo2mIl1dMcIxnZNc%2FFxp3njz6Jpth%2Fu0KOe8X%2FPTgM9S58jNUVTWHYd3bEm54SfyUlEIwmSVHkdHAvZw8QfhIC8DAJULbBkKHe6nRKxvGqo1UZW2OY0%2BKpOu7kPBwFl13lcqjMeSy%2F%2BvpZDgwHonNSKYiYRrlffBfL%2BUFWdiijebzDHpJnHBjqkAfpE6DXG5ducvq1TeQISVLspLOKXhLJ0Jn1auWbgWOv02xnmSsxVrzmbEGcfsyZArqlrtxdg9N9yH30onEToRB0OnUGFrpiazcXfmdl7JS0Cn3mL4FiEHdFC%2B2lUkrwFbKVX0NhXsjQRmkeUUtT7dXPTDyzpPIxoyghxvJsm6OswiSouBbg4NB6EQaFjgxRw9KEg79jjKbCgyYvpKNs56YVN9kvk&X-Amz-Signature=0e07c27075a366f43cf237c80660a72ba43bdbad3486e7f1f9e3a12afdfcc7f0&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 177 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8031-ac8d-c5678af1bdd5.png",
|
| 178 |
+
"sourceType": "block",
|
| 179 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8031-ac8d-c5678af1bdd5.png"
|
| 180 |
+
},
|
| 181 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 182 |
+
"createdAt": "2025-09-24T09:36:36.276Z",
|
| 183 |
+
"updatedAt": "2025-10-08T13:00:25.920Z"
|
| 184 |
+
},
|
| 185 |
+
"27877f1c-9c9d-80e7-a500-fb79cebde7e3": {
|
| 186 |
+
"mediaInfo": {
|
| 187 |
+
"type": "DOWNLOAD",
|
| 188 |
+
"originalUrl": "https://prod-files-secure.s3.us-west-2.amazonaws.com/6fe77f1c-9c9d-81b1-b174-00031f2bc702/0458ed42-9805-4c8f-9d7e-c675474a626e/image.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Content-Sha256=UNSIGNED-PAYLOAD&X-Amz-Credential=ASIAZI2LB466X3VEST5Q%2F20251008%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-Date=20251008T130020Z&X-Amz-Expires=3600&X-Amz-Security-Token=IQoJb3JpZ2luX2VjECQaCXVzLXdlc3QtMiJIMEYCIQC4Th0nobtVjj0GnPkA6aNua8I5iyMPP5wm3FPgOcNrpQIhAM6Cd1AyvJOWLCdgyh%2F9xxRIzhQ8ZEYJPtDoTzf9dVzsKogECL3%2F%2F%2F%2F%2F%2F%2F%2F%2F%2FwEQABoMNjM3NDIzMTgzODA1Igwbq%2Fmpsk4PhTeoeU8q3ANUdDY8Un1V3sp1KnXAZQmxQggeyUGmjkp%2BsBgML%2Bh3jLesSMzdlQPFwlTBbqh74KOfU7NmNfHFLiHqWLrpeLClymtDa9BGRQAnfNGuT%2BUXXxp5dSoeOsbUJInqYhW4FsjUBRNw%2FSAslpIJKfTrmcN81%2FIUQNc0TRtVmiiXKPFUCNfWErOAQlec%2B6mNZCJYY1EbzUg1tPFNYYLpoiNb45%2F0t1VlsyeG6WlkA2KFXybguL2BmlWms%2BC%2BDeANHe2r%2Bq0h9JVtz%2BYBB3CzzQdeerNfGtyml%2BTz5DiBvv0h9F5FNcqJ4Uf1CbLGaRVIlCXLHam3xV3Fk%2FpYYQerVcK6t6YWWeRO0x92Uj1TyF1H4aCPO%2BuAjxDdY0WJfdLROdRvwH69zTdBYb26Lo7h2T2MnY%2FjJ4UNGPf0CWoGMVU9BJCO6%2Bm7RySlYPw1Axogb7clhfZAUYsM%2FhBI01n5OLo2mIl1dMcIxnZNc%2FFxp3njz6Jpth%2Fu0KOe8X%2FPTgM9S58jNUVTWHYd3bEm54SfyUlEIwmSVHkdHAvZw8QfhIC8DAJULbBkKHe6nRKxvGqo1UZW2OY0%2BKpOu7kPBwFl13lcqjMeSy%2F%2BvpZDgwHonNSKYiYRrlffBfL%2BUFWdiijebzDHpJnHBjqkAfpE6DXG5ducvq1TeQISVLspLOKXhLJ0Jn1auWbgWOv02xnmSsxVrzmbEGcfsyZArqlrtxdg9N9yH30onEToRB0OnUGFrpiazcXfmdl7JS0Cn3mL4FiEHdFC%2B2lUkrwFbKVX0NhXsjQRmkeUUtT7dXPTDyzpPIxoyghxvJsm6OswiSouBbg4NB6EQaFjgxRw9KEg79jjKbCgyYvpKNs56YVN9kvk&X-Amz-Signature=e43c1f35e9930e144c0b2b6098457be4848a723301fd78f3ff27d94f87ccbebb&X-Amz-SignedHeaders=host&x-amz-checksum-mode=ENABLED&x-id=GetObject",
|
| 189 |
+
"localPath": "/Users/thibaudfrere/Documents/work-projects/huggingface/research-article-template/app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80e7-a500-fb79cebde7e3.png",
|
| 190 |
+
"sourceType": "block",
|
| 191 |
+
"transformedPath": "/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80e7-a500-fb79cebde7e3.png"
|
| 192 |
+
},
|
| 193 |
+
"lastEdited": "2025-09-24T09:22:00.000Z",
|
| 194 |
+
"createdAt": "2025-09-24T09:36:36.448Z",
|
| 195 |
+
"updatedAt": "2025-10-08T13:00:26.065Z"
|
| 196 |
+
}
|
| 197 |
+
}
|
| 198 |
+
}
|
app/scripts/notion-importer/README.md
ADDED
|
@@ -0,0 +1,291 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# Notion Importer
|
| 2 |
+
|
| 3 |
+
Complete Notion to MDX (Markdown + JSX) importer optimized for Astro with advanced media handling, interactive components, and seamless integration.
|
| 4 |
+
|
| 5 |
+
## 🚀 Quick Start
|
| 6 |
+
|
| 7 |
+
### Method 1: Using NOTION_PAGE_ID (Recommended)
|
| 8 |
+
|
| 9 |
+
```bash
|
| 10 |
+
# Install dependencies
|
| 11 |
+
npm install
|
| 12 |
+
|
| 13 |
+
# Setup environment variables
|
| 14 |
+
cp env.example .env
|
| 15 |
+
# Edit .env with your Notion token and page ID
|
| 16 |
+
|
| 17 |
+
# Complete Notion → MDX conversion (fetches title/slug automatically)
|
| 18 |
+
NOTION_TOKEN=secret_xxx NOTION_PAGE_ID=abc123 node index.mjs
|
| 19 |
+
|
| 20 |
+
# Or use .env file
|
| 21 |
+
node index.mjs
|
| 22 |
+
```
|
| 23 |
+
|
| 24 |
+
### Method 2: Using pages.json (Legacy)
|
| 25 |
+
|
| 26 |
+
```bash
|
| 27 |
+
# Install dependencies
|
| 28 |
+
npm install
|
| 29 |
+
|
| 30 |
+
# Setup environment variables
|
| 31 |
+
cp env.example .env
|
| 32 |
+
# Edit .env with your Notion token
|
| 33 |
+
|
| 34 |
+
# Configure pages in input/pages.json
|
| 35 |
+
# {
|
| 36 |
+
# "pages": [
|
| 37 |
+
# {
|
| 38 |
+
# "id": "your-page-id",
|
| 39 |
+
# "title": "Title",
|
| 40 |
+
# "slug": "slug"
|
| 41 |
+
# }
|
| 42 |
+
# ]
|
| 43 |
+
# }
|
| 44 |
+
|
| 45 |
+
# Complete Notion → MDX conversion
|
| 46 |
+
node index.mjs
|
| 47 |
+
|
| 48 |
+
# For step-by-step debugging
|
| 49 |
+
node notion-converter.mjs # Notion → Markdown
|
| 50 |
+
node mdx-converter.mjs # Markdown → MDX
|
| 51 |
+
```
|
| 52 |
+
|
| 53 |
+
## 📁 Structure
|
| 54 |
+
|
| 55 |
+
```
|
| 56 |
+
notion-importer/
|
| 57 |
+
├── index.mjs # Complete Notion → MDX pipeline
|
| 58 |
+
├── notion-converter.mjs # Notion → Markdown with notion-to-md v4
|
| 59 |
+
├── mdx-converter.mjs # Markdown → MDX with Astro components
|
| 60 |
+
├── post-processor.mjs # Markdown post-processing
|
| 61 |
+
├── package.json # Dependencies and scripts
|
| 62 |
+
├── env.example # Environment variables template
|
| 63 |
+
├── input/ # Configuration
|
| 64 |
+
│ └── pages.json # Notion pages to convert
|
| 65 |
+
└── output/ # Results
|
| 66 |
+
├── *.md # Intermediate Markdown
|
| 67 |
+
├── *.mdx # Final MDX for Astro
|
| 68 |
+
└── media/ # Downloaded media files
|
| 69 |
+
```
|
| 70 |
+
|
| 71 |
+
## ✨ Key Features
|
| 72 |
+
|
| 73 |
+
### 🎯 **Advanced Media Handling**
|
| 74 |
+
- **Local download**: Automatic download of all Notion media (images, files, PDFs)
|
| 75 |
+
- **Path transformation**: Smart path conversion for web accessibility
|
| 76 |
+
- **Image components**: Automatic conversion to Astro `Image` components with zoom/download
|
| 77 |
+
- **Media organization**: Structured media storage by page ID
|
| 78 |
+
|
| 79 |
+
### 🧮 **Interactive Components**
|
| 80 |
+
- **Callouts → Notes**: Notion callouts converted to Astro `Note` components
|
| 81 |
+
- **Enhanced tables**: Tables wrapped in styled containers
|
| 82 |
+
- **Code blocks**: Enhanced with copy functionality
|
| 83 |
+
- **Automatic imports**: Smart component and image import generation
|
| 84 |
+
|
| 85 |
+
### 🎨 **Smart Formatting**
|
| 86 |
+
- **Link fixing**: Notion internal links converted to relative links
|
| 87 |
+
- **Artifact cleanup**: Removal of Notion-specific formatting artifacts
|
| 88 |
+
- **Frontmatter generation**: Automatic YAML frontmatter from Notion properties
|
| 89 |
+
- **Astro compatibility**: Full compatibility with Astro MDX processing
|
| 90 |
+
|
| 91 |
+
### 🔧 **Robust Pipeline**
|
| 92 |
+
- **Notion preprocessing**: Advanced page configuration and media strategy
|
| 93 |
+
- **Post-processing**: Markdown cleanup and optimization
|
| 94 |
+
- **MDX conversion**: Final transformation with Astro components
|
| 95 |
+
- **Auto-copy**: Automatic copying to Astro content directory
|
| 96 |
+
|
| 97 |
+
## 📊 Example Workflow
|
| 98 |
+
|
| 99 |
+
```bash
|
| 100 |
+
# 1. Configure your Notion pages
|
| 101 |
+
# Edit input/pages.json with your page IDs
|
| 102 |
+
|
| 103 |
+
# 2. Complete automatic conversion
|
| 104 |
+
NOTION_TOKEN=your_token node index.mjs --clean
|
| 105 |
+
|
| 106 |
+
# 3. Generated results
|
| 107 |
+
ls output/
|
| 108 |
+
# → getting-started.md (Intermediate Markdown)
|
| 109 |
+
# → getting-started.mdx (Final MDX for Astro)
|
| 110 |
+
# → media/ (downloaded images and files)
|
| 111 |
+
```
|
| 112 |
+
|
| 113 |
+
### 📋 Conversion Result
|
| 114 |
+
|
| 115 |
+
The pipeline generates MDX files optimized for Astro with:
|
| 116 |
+
|
| 117 |
+
```mdx
|
| 118 |
+
---
|
| 119 |
+
title: "Getting Started with Notion"
|
| 120 |
+
published: "2024-01-15"
|
| 121 |
+
tableOfContentsAutoCollapse: true
|
| 122 |
+
---
|
| 123 |
+
|
| 124 |
+
import Image from '../components/Image.astro';
|
| 125 |
+
import Note from '../components/Note.astro';
|
| 126 |
+
import gettingStartedImage from './media/getting-started/image1.png';
|
| 127 |
+
|
| 128 |
+
## Introduction
|
| 129 |
+
|
| 130 |
+
Here is some content with a callout:
|
| 131 |
+
|
| 132 |
+
<Note type="info" title="Important">
|
| 133 |
+
This is a converted Notion callout.
|
| 134 |
+
</Note>
|
| 135 |
+
|
| 136 |
+
And an image:
|
| 137 |
+
|
| 138 |
+
<Figure
|
| 139 |
+
src={gettingStartedImage}
|
| 140 |
+
alt="Getting started screenshot"
|
| 141 |
+
zoomable
|
| 142 |
+
downloadable
|
| 143 |
+
layout="fixed"
|
| 144 |
+
/>
|
| 145 |
+
```
|
| 146 |
+
|
| 147 |
+
## ⚙️ Required Astro Configuration
|
| 148 |
+
|
| 149 |
+
To use the generated MDX files, ensure your Astro project has the required components:
|
| 150 |
+
|
| 151 |
+
```astro
|
| 152 |
+
// src/components/Figure.astro
|
| 153 |
+
---
|
| 154 |
+
export interface Props {
|
| 155 |
+
src: any;
|
| 156 |
+
alt?: string;
|
| 157 |
+
caption?: string;
|
| 158 |
+
zoomable?: boolean;
|
| 159 |
+
downloadable?: boolean;
|
| 160 |
+
layout?: string;
|
| 161 |
+
id?: string;
|
| 162 |
+
}
|
| 163 |
+
|
| 164 |
+
const { src, alt, caption, zoomable, downloadable, layout, id } = Astro.props;
|
| 165 |
+
---
|
| 166 |
+
|
| 167 |
+
<figure {id} class="figure">
|
| 168 |
+
<img src={src} alt={alt} />
|
| 169 |
+
{caption && <figcaption>{caption}</figcaption>}
|
| 170 |
+
</figure>
|
| 171 |
+
```
|
| 172 |
+
|
| 173 |
+
## 🛠️ Prerequisites
|
| 174 |
+
|
| 175 |
+
- **Node.js** with ESM support
|
| 176 |
+
- **Notion Integration**: Set up an integration in your Notion workspace
|
| 177 |
+
- **Notion Token**: Copy the "Internal Integration Token"
|
| 178 |
+
- **Shared Pages**: Share the specific Notion page(s) with your integration
|
| 179 |
+
- **Astro** to use the generated MDX
|
| 180 |
+
|
| 181 |
+
## 🎯 Technical Architecture
|
| 182 |
+
|
| 183 |
+
### 4-Stage Pipeline
|
| 184 |
+
|
| 185 |
+
1. **Notion Preprocessing** (`notion-converter.mjs`)
|
| 186 |
+
- Configuration loading from `pages.json`
|
| 187 |
+
- Notion API client initialization
|
| 188 |
+
- Media download strategy configuration
|
| 189 |
+
|
| 190 |
+
2. **Notion-to-Markdown** (notion-to-md v4)
|
| 191 |
+
- Page conversion with `NotionConverter`
|
| 192 |
+
- Media downloading with `downloadMediaTo()`
|
| 193 |
+
- File export with `DefaultExporter`
|
| 194 |
+
|
| 195 |
+
3. **Markdown Post-processing** (`post-processor.mjs`)
|
| 196 |
+
- Notion artifact cleanup
|
| 197 |
+
- Link fixing and optimization
|
| 198 |
+
- Table and code block enhancement
|
| 199 |
+
|
| 200 |
+
4. **MDX Conversion** (`mdx-converter.mjs`)
|
| 201 |
+
- Component transformation (Figure, Note)
|
| 202 |
+
- Automatic import generation
|
| 203 |
+
- Frontmatter enhancement
|
| 204 |
+
- Astro compatibility optimization
|
| 205 |
+
|
| 206 |
+
## 📊 Configuration Options
|
| 207 |
+
|
| 208 |
+
### Pages Configuration (`input/pages.json`)
|
| 209 |
+
|
| 210 |
+
```json
|
| 211 |
+
{
|
| 212 |
+
"pages": [
|
| 213 |
+
{
|
| 214 |
+
"id": "your-notion-page-id",
|
| 215 |
+
"title": "Page Title",
|
| 216 |
+
"slug": "page-slug"
|
| 217 |
+
}
|
| 218 |
+
]
|
| 219 |
+
}
|
| 220 |
+
```
|
| 221 |
+
|
| 222 |
+
### Environment Variables
|
| 223 |
+
|
| 224 |
+
Copy `env.example` to `.env` and configure:
|
| 225 |
+
|
| 226 |
+
```bash
|
| 227 |
+
cp env.example .env
|
| 228 |
+
# Edit .env with your actual Notion token
|
| 229 |
+
```
|
| 230 |
+
|
| 231 |
+
Required variables:
|
| 232 |
+
```bash
|
| 233 |
+
NOTION_TOKEN=secret_your_notion_integration_token_here
|
| 234 |
+
```
|
| 235 |
+
|
| 236 |
+
### Command Line Options
|
| 237 |
+
|
| 238 |
+
```bash
|
| 239 |
+
# Full workflow
|
| 240 |
+
node index.mjs --clean --token=your_token
|
| 241 |
+
|
| 242 |
+
# Notion to Markdown only
|
| 243 |
+
node index.mjs --notion-only
|
| 244 |
+
|
| 245 |
+
# Markdown to MDX only
|
| 246 |
+
node index.mjs --mdx-only
|
| 247 |
+
|
| 248 |
+
# Custom paths
|
| 249 |
+
node index.mjs --input=my-pages.json --output=converted/
|
| 250 |
+
```
|
| 251 |
+
|
| 252 |
+
## 📊 Conversion Statistics
|
| 253 |
+
|
| 254 |
+
For a typical Notion page:
|
| 255 |
+
- **Media files** automatically downloaded and organized
|
| 256 |
+
- **Callouts** converted to interactive Note components
|
| 257 |
+
- **Images** transformed to Figure components with zoom/download
|
| 258 |
+
- **Tables** enhanced with proper styling containers
|
| 259 |
+
- **Code blocks** enhanced with copy functionality
|
| 260 |
+
- **Links** fixed for proper internal navigation
|
| 261 |
+
|
| 262 |
+
## ✅ Project Status
|
| 263 |
+
|
| 264 |
+
### 🎉 **Complete Features**
|
| 265 |
+
- ✅ **Notion → MDX Pipeline**: Full end-to-end functional conversion
|
| 266 |
+
- ✅ **Media Management**: Automatic download and path transformation
|
| 267 |
+
- ✅ **Component Integration**: Seamless Astro component integration
|
| 268 |
+
- ✅ **Smart Formatting**: Intelligent cleanup and optimization
|
| 269 |
+
- ✅ **Robustness**: Error handling and graceful degradation
|
| 270 |
+
- ✅ **Flexibility**: Modular pipeline with step-by-step options
|
| 271 |
+
|
| 272 |
+
### 🚀 **Production Ready**
|
| 273 |
+
The toolkit is now **100% operational** for converting Notion pages to MDX/Astro with all advanced features (media handling, component integration, smart formatting).
|
| 274 |
+
|
| 275 |
+
## 🔗 Integration with notion-to-md v4
|
| 276 |
+
|
| 277 |
+
This toolkit leverages the powerful [notion-to-md v4](https://notionconvert.com/docs/v4/guides/) library with:
|
| 278 |
+
|
| 279 |
+
- **Advanced Media Strategies**: Download, upload, and direct media handling
|
| 280 |
+
- **Custom Renderers**: Block transformers and annotation transformers
|
| 281 |
+
- **Exporter Plugins**: File, buffer, and stdout output options
|
| 282 |
+
- **Database Support**: Full database property and frontmatter transformation
|
| 283 |
+
- **Page References**: Smart internal link handling
|
| 284 |
+
|
| 285 |
+
## 📚 Additional Resources
|
| 286 |
+
|
| 287 |
+
- [notion-to-md v4 Documentation](https://notionconvert.com/docs/v4/guides/)
|
| 288 |
+
- [Notion API Documentation](https://developers.notion.com/)
|
| 289 |
+
- [Astro MDX Documentation](https://docs.astro.build/en/guides/integrations-guide/mdx/)
|
| 290 |
+
- [Media Handling Strategies](https://notionconvert.com/blog/mastering-media-handling-in-notion-to-md-v4-download-upload-and-direct-strategies/)
|
| 291 |
+
- [Frontmatter Transformation](https://notionconvert.com/blog/how-to-convert-notion-properties-to-frontmatter-with-notion-to-md-v4/)
|
app/scripts/notion-importer/custom-code-renderer.mjs
ADDED
|
@@ -0,0 +1,33 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env node
|
| 2 |
+
|
| 3 |
+
/**
|
| 4 |
+
* Custom Code Block Renderer for notion-to-md
|
| 5 |
+
* Fixes the issue where code blocks end with "text" instead of proper closing
|
| 6 |
+
*/
|
| 7 |
+
|
| 8 |
+
export function createCustomCodeRenderer() {
|
| 9 |
+
return {
|
| 10 |
+
name: 'custom-code-renderer',
|
| 11 |
+
type: 'renderer',
|
| 12 |
+
|
| 13 |
+
/**
|
| 14 |
+
* Custom renderer for code blocks
|
| 15 |
+
* @param {Object} block - Notion code block
|
| 16 |
+
* @returns {string} - Properly formatted markdown code block
|
| 17 |
+
*/
|
| 18 |
+
code: (block) => {
|
| 19 |
+
const { language, rich_text } = block.code;
|
| 20 |
+
|
| 21 |
+
// Extract the actual code content from rich_text
|
| 22 |
+
const codeContent = rich_text
|
| 23 |
+
.map(text => text.plain_text)
|
| 24 |
+
.join('');
|
| 25 |
+
|
| 26 |
+
// Determine the language (default to empty string if not specified)
|
| 27 |
+
const lang = language || '';
|
| 28 |
+
|
| 29 |
+
// Return properly formatted markdown code block
|
| 30 |
+
return `\`\`\`${lang}\n${codeContent}\n\`\`\``;
|
| 31 |
+
}
|
| 32 |
+
};
|
| 33 |
+
}
|
app/scripts/notion-importer/debug-properties.mjs
ADDED
|
@@ -0,0 +1,87 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env node
|
| 2 |
+
|
| 3 |
+
import { config } from 'dotenv';
|
| 4 |
+
import { Client } from '@notionhq/client';
|
| 5 |
+
|
| 6 |
+
// Load environment variables from .env file
|
| 7 |
+
config();
|
| 8 |
+
|
| 9 |
+
const notion = new Client({
|
| 10 |
+
auth: process.env.NOTION_TOKEN,
|
| 11 |
+
});
|
| 12 |
+
|
| 13 |
+
async function debugPageProperties() {
|
| 14 |
+
const pageId = '27877f1c9c9d804d9c82f7b3905578ff';
|
| 15 |
+
|
| 16 |
+
try {
|
| 17 |
+
console.log('🔍 Debugging page properties...');
|
| 18 |
+
console.log(`📄 Page ID: ${pageId}`);
|
| 19 |
+
|
| 20 |
+
const page = await notion.pages.retrieve({ page_id: pageId });
|
| 21 |
+
|
| 22 |
+
console.log('\n📋 Available properties:');
|
| 23 |
+
console.log('========================');
|
| 24 |
+
|
| 25 |
+
for (const [key, value] of Object.entries(page.properties)) {
|
| 26 |
+
console.log(`\n🔹 ${key}:`);
|
| 27 |
+
console.log(` Type: ${value.type}`);
|
| 28 |
+
|
| 29 |
+
switch (value.type) {
|
| 30 |
+
case 'title':
|
| 31 |
+
console.log(` Value: "${value.title.map(t => t.plain_text).join('')}"`);
|
| 32 |
+
break;
|
| 33 |
+
case 'rich_text':
|
| 34 |
+
console.log(` Value: "${value.rich_text.map(t => t.plain_text).join('')}"`);
|
| 35 |
+
break;
|
| 36 |
+
case 'people':
|
| 37 |
+
console.log(` People: ${value.people.map(p => p.name || p.id).join(', ')}`);
|
| 38 |
+
break;
|
| 39 |
+
case 'select':
|
| 40 |
+
console.log(` Value: ${value.select?.name || 'null'}`);
|
| 41 |
+
break;
|
| 42 |
+
case 'multi_select':
|
| 43 |
+
console.log(` Values: [${value.multi_select.map(s => s.name).join(', ')}]`);
|
| 44 |
+
break;
|
| 45 |
+
case 'date':
|
| 46 |
+
console.log(` Value: ${value.date?.start || 'null'}`);
|
| 47 |
+
break;
|
| 48 |
+
case 'checkbox':
|
| 49 |
+
console.log(` Value: ${value.checkbox}`);
|
| 50 |
+
break;
|
| 51 |
+
case 'url':
|
| 52 |
+
console.log(` Value: ${value.url || 'null'}`);
|
| 53 |
+
break;
|
| 54 |
+
case 'email':
|
| 55 |
+
console.log(` Value: ${value.email || 'null'}`);
|
| 56 |
+
break;
|
| 57 |
+
case 'phone_number':
|
| 58 |
+
console.log(` Value: ${value.phone_number || 'null'}`);
|
| 59 |
+
break;
|
| 60 |
+
case 'number':
|
| 61 |
+
console.log(` Value: ${value.number || 'null'}`);
|
| 62 |
+
break;
|
| 63 |
+
case 'created_time':
|
| 64 |
+
console.log(` Value: ${value.created_time}`);
|
| 65 |
+
break;
|
| 66 |
+
case 'created_by':
|
| 67 |
+
console.log(` Value: ${value.created_by?.id || 'null'}`);
|
| 68 |
+
break;
|
| 69 |
+
case 'last_edited_time':
|
| 70 |
+
console.log(` Value: ${value.last_edited_time}`);
|
| 71 |
+
break;
|
| 72 |
+
case 'last_edited_by':
|
| 73 |
+
console.log(` Value: ${value.last_edited_by?.id || 'null'}`);
|
| 74 |
+
break;
|
| 75 |
+
default:
|
| 76 |
+
console.log(` Value: ${JSON.stringify(value, null, 2)}`);
|
| 77 |
+
}
|
| 78 |
+
}
|
| 79 |
+
|
| 80 |
+
console.log('\n✅ Properties debug completed!');
|
| 81 |
+
|
| 82 |
+
} catch (error) {
|
| 83 |
+
console.error('❌ Error:', error.message);
|
| 84 |
+
}
|
| 85 |
+
}
|
| 86 |
+
|
| 87 |
+
debugPageProperties();
|
app/scripts/notion-importer/env.example
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
|
|
|
|
|
|
|
| 1 |
+
NOTION_TOKEN=ntn_xxx
|
| 2 |
+
NOTION_PAGE_ID=xxx
|
app/scripts/notion-importer/index.mjs
ADDED
|
@@ -0,0 +1,324 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env node
|
| 2 |
+
|
| 3 |
+
import { config } from 'dotenv';
|
| 4 |
+
import { join, dirname, basename } from 'path';
|
| 5 |
+
import { fileURLToPath } from 'url';
|
| 6 |
+
import { copyFileSync, existsSync, mkdirSync, readFileSync, writeFileSync, readdirSync, statSync } from 'fs';
|
| 7 |
+
import { convertNotionToMarkdown } from './notion-converter.mjs';
|
| 8 |
+
import { convertToMdx } from './mdx-converter.mjs';
|
| 9 |
+
import { Client } from '@notionhq/client';
|
| 10 |
+
|
| 11 |
+
// Load environment variables from .env file (but don't override existing ones)
|
| 12 |
+
config({ override: false });
|
| 13 |
+
|
| 14 |
+
const __filename = fileURLToPath(import.meta.url);
|
| 15 |
+
const __dirname = dirname(__filename);
|
| 16 |
+
|
| 17 |
+
// Default configuration
|
| 18 |
+
const DEFAULT_INPUT = join(__dirname, 'input', 'pages.json');
|
| 19 |
+
const DEFAULT_OUTPUT = join(__dirname, 'output');
|
| 20 |
+
const ASTRO_CONTENT_PATH = join(__dirname, '..', '..', 'src', 'content', 'article.mdx');
|
| 21 |
+
const ASTRO_ASSETS_PATH = join(__dirname, '..', '..', 'src', 'content', 'assets', 'image');
|
| 22 |
+
const ASTRO_BIB_PATH = join(__dirname, '..', '..', 'src', 'content', 'bibliography.bib');
|
| 23 |
+
|
| 24 |
+
function parseArgs() {
|
| 25 |
+
const args = process.argv.slice(2);
|
| 26 |
+
const config = {
|
| 27 |
+
input: DEFAULT_INPUT,
|
| 28 |
+
output: DEFAULT_OUTPUT,
|
| 29 |
+
clean: false,
|
| 30 |
+
notionOnly: false,
|
| 31 |
+
mdxOnly: false,
|
| 32 |
+
token: process.env.NOTION_TOKEN,
|
| 33 |
+
pageId: process.env.NOTION_PAGE_ID
|
| 34 |
+
};
|
| 35 |
+
|
| 36 |
+
for (const arg of args) {
|
| 37 |
+
if (arg.startsWith('--input=')) {
|
| 38 |
+
config.input = arg.split('=')[1];
|
| 39 |
+
} else if (arg.startsWith('--output=')) {
|
| 40 |
+
config.output = arg.split('=')[1];
|
| 41 |
+
} else if (arg.startsWith('--token=')) {
|
| 42 |
+
config.token = arg.split('=')[1];
|
| 43 |
+
} else if (arg.startsWith('--page-id=')) {
|
| 44 |
+
config.pageId = arg.split('=')[1];
|
| 45 |
+
} else if (arg === '--clean') {
|
| 46 |
+
config.clean = true;
|
| 47 |
+
} else if (arg === '--notion-only') {
|
| 48 |
+
config.notionOnly = true;
|
| 49 |
+
} else if (arg === '--mdx-only') {
|
| 50 |
+
config.mdxOnly = true;
|
| 51 |
+
}
|
| 52 |
+
}
|
| 53 |
+
|
| 54 |
+
return config;
|
| 55 |
+
}
|
| 56 |
+
|
| 57 |
+
function showHelp() {
|
| 58 |
+
console.log(`
|
| 59 |
+
🚀 Notion to MDX Toolkit
|
| 60 |
+
|
| 61 |
+
Usage:
|
| 62 |
+
node index.mjs [options]
|
| 63 |
+
|
| 64 |
+
Options:
|
| 65 |
+
--input=PATH Input pages configuration file (default: input/pages.json)
|
| 66 |
+
--output=PATH Output directory (default: output/)
|
| 67 |
+
--token=TOKEN Notion API token (or set NOTION_TOKEN env var)
|
| 68 |
+
--clean Clean output directory before processing
|
| 69 |
+
--notion-only Only convert Notion to Markdown (skip MDX conversion)
|
| 70 |
+
--mdx-only Only convert existing Markdown to MDX
|
| 71 |
+
--help, -h Show this help
|
| 72 |
+
|
| 73 |
+
Environment Variables:
|
| 74 |
+
NOTION_TOKEN Your Notion integration token
|
| 75 |
+
|
| 76 |
+
Examples:
|
| 77 |
+
# Full conversion workflow
|
| 78 |
+
NOTION_TOKEN=your_token node index.mjs --clean
|
| 79 |
+
|
| 80 |
+
# Only convert Notion pages to Markdown
|
| 81 |
+
node index.mjs --notion-only --token=your_token
|
| 82 |
+
|
| 83 |
+
# Only convert existing Markdown to MDX
|
| 84 |
+
node index.mjs --mdx-only
|
| 85 |
+
|
| 86 |
+
# Custom paths
|
| 87 |
+
node index.mjs --input=my-pages.json --output=converted/ --token=your_token
|
| 88 |
+
|
| 89 |
+
Configuration File Format (pages.json):
|
| 90 |
+
{
|
| 91 |
+
"pages": [
|
| 92 |
+
{
|
| 93 |
+
"id": "your-notion-page-id",
|
| 94 |
+
"title": "Page Title",
|
| 95 |
+
"slug": "page-slug"
|
| 96 |
+
}
|
| 97 |
+
]
|
| 98 |
+
}
|
| 99 |
+
|
| 100 |
+
Workflow:
|
| 101 |
+
1. Notion → Markdown (with media download)
|
| 102 |
+
2. Markdown → MDX (with Astro components)
|
| 103 |
+
3. Copy to Astro content directory
|
| 104 |
+
`);
|
| 105 |
+
}
|
| 106 |
+
|
| 107 |
+
function ensureDirectory(dir) {
|
| 108 |
+
if (!existsSync(dir)) {
|
| 109 |
+
mkdirSync(dir, { recursive: true });
|
| 110 |
+
}
|
| 111 |
+
}
|
| 112 |
+
|
| 113 |
+
async function cleanDirectory(dir) {
|
| 114 |
+
if (existsSync(dir)) {
|
| 115 |
+
const { execSync } = await import('child_process');
|
| 116 |
+
execSync(`rm -rf "${dir}"/*`, { stdio: 'inherit' });
|
| 117 |
+
}
|
| 118 |
+
}
|
| 119 |
+
|
| 120 |
+
function readPagesConfig(inputFile) {
|
| 121 |
+
try {
|
| 122 |
+
const content = readFileSync(inputFile, 'utf8');
|
| 123 |
+
return JSON.parse(content);
|
| 124 |
+
} catch (error) {
|
| 125 |
+
console.error(`❌ Error reading pages config: ${error.message}`);
|
| 126 |
+
return { pages: [] };
|
| 127 |
+
}
|
| 128 |
+
}
|
| 129 |
+
|
| 130 |
+
/**
|
| 131 |
+
* Create a temporary pages.json from NOTION_PAGE_ID environment variable
|
| 132 |
+
* Extracts title and generates slug from the Notion page
|
| 133 |
+
*/
|
| 134 |
+
async function createPagesConfigFromEnv(pageId, token, outputPath) {
|
| 135 |
+
try {
|
| 136 |
+
console.log('🔍 Fetching page info from Notion API...');
|
| 137 |
+
const notion = new Client({ auth: token });
|
| 138 |
+
const page = await notion.pages.retrieve({ page_id: pageId });
|
| 139 |
+
|
| 140 |
+
// Extract title
|
| 141 |
+
let title = 'Article';
|
| 142 |
+
if (page.properties.title && page.properties.title.title && page.properties.title.title.length > 0) {
|
| 143 |
+
title = page.properties.title.title[0].plain_text;
|
| 144 |
+
} else if (page.properties.Name && page.properties.Name.title && page.properties.Name.title.length > 0) {
|
| 145 |
+
title = page.properties.Name.title[0].plain_text;
|
| 146 |
+
}
|
| 147 |
+
|
| 148 |
+
// Generate slug from title
|
| 149 |
+
const slug = title
|
| 150 |
+
.toLowerCase()
|
| 151 |
+
.replace(/[^\w\s-]/g, '')
|
| 152 |
+
.replace(/\s+/g, '-')
|
| 153 |
+
.replace(/-+/g, '-')
|
| 154 |
+
.trim();
|
| 155 |
+
|
| 156 |
+
console.log(` �� Found page: "${title}" (slug: ${slug})`);
|
| 157 |
+
|
| 158 |
+
// Create pages config
|
| 159 |
+
const pagesConfig = {
|
| 160 |
+
pages: [{
|
| 161 |
+
id: pageId,
|
| 162 |
+
title: title,
|
| 163 |
+
slug: slug
|
| 164 |
+
}]
|
| 165 |
+
};
|
| 166 |
+
|
| 167 |
+
// Write to temporary file
|
| 168 |
+
writeFileSync(outputPath, JSON.stringify(pagesConfig, null, 4));
|
| 169 |
+
console.log(` ✅ Created temporary pages config`);
|
| 170 |
+
|
| 171 |
+
return pagesConfig;
|
| 172 |
+
} catch (error) {
|
| 173 |
+
console.error(`❌ Error fetching page from Notion: ${error.message}`);
|
| 174 |
+
throw error;
|
| 175 |
+
}
|
| 176 |
+
}
|
| 177 |
+
|
| 178 |
+
function copyToAstroContent(outputDir) {
|
| 179 |
+
console.log('📋 Copying MDX files to Astro content directory...');
|
| 180 |
+
|
| 181 |
+
try {
|
| 182 |
+
// Ensure Astro directories exist
|
| 183 |
+
mkdirSync(dirname(ASTRO_CONTENT_PATH), { recursive: true });
|
| 184 |
+
mkdirSync(ASTRO_ASSETS_PATH, { recursive: true });
|
| 185 |
+
|
| 186 |
+
// Copy MDX file
|
| 187 |
+
const files = readdirSync(outputDir);
|
| 188 |
+
const mdxFiles = files.filter(file => file.endsWith('.mdx'));
|
| 189 |
+
if (mdxFiles.length > 0) {
|
| 190 |
+
const mdxFile = join(outputDir, mdxFiles[0]); // Take the first MDX file
|
| 191 |
+
// Read and write instead of copy to avoid EPERM issues
|
| 192 |
+
const mdxContent = readFileSync(mdxFile, 'utf8');
|
| 193 |
+
writeFileSync(ASTRO_CONTENT_PATH, mdxContent);
|
| 194 |
+
console.log(` ✅ Copied MDX to ${ASTRO_CONTENT_PATH}`);
|
| 195 |
+
}
|
| 196 |
+
|
| 197 |
+
// Copy images
|
| 198 |
+
const mediaDir = join(outputDir, 'media');
|
| 199 |
+
if (existsSync(mediaDir)) {
|
| 200 |
+
const imageExtensions = ['.png', '.jpg', '.jpeg', '.gif', '.svg'];
|
| 201 |
+
let imageCount = 0;
|
| 202 |
+
|
| 203 |
+
function copyImagesRecursively(dir) {
|
| 204 |
+
const files = readdirSync(dir);
|
| 205 |
+
for (const file of files) {
|
| 206 |
+
const filePath = join(dir, file);
|
| 207 |
+
const stat = statSync(filePath);
|
| 208 |
+
|
| 209 |
+
if (stat.isDirectory()) {
|
| 210 |
+
copyImagesRecursively(filePath);
|
| 211 |
+
} else if (imageExtensions.some(ext => file.toLowerCase().endsWith(ext))) {
|
| 212 |
+
const filename = basename(filePath);
|
| 213 |
+
const destPath = join(ASTRO_ASSETS_PATH, filename);
|
| 214 |
+
copyFileSync(filePath, destPath);
|
| 215 |
+
imageCount++;
|
| 216 |
+
}
|
| 217 |
+
}
|
| 218 |
+
}
|
| 219 |
+
|
| 220 |
+
copyImagesRecursively(mediaDir);
|
| 221 |
+
console.log(` ✅ Copied ${imageCount} image(s) to ${ASTRO_ASSETS_PATH}`);
|
| 222 |
+
|
| 223 |
+
// Update image paths in MDX file
|
| 224 |
+
const mdxContent = readFileSync(ASTRO_CONTENT_PATH, 'utf8');
|
| 225 |
+
let updatedContent = mdxContent.replace(/\.\/media\//g, './assets/image/');
|
| 226 |
+
// Remove the subdirectory from image paths since we copy images directly to assets/image/
|
| 227 |
+
updatedContent = updatedContent.replace(/\.\/assets\/image\/[^\/]+\//g, './assets/image/');
|
| 228 |
+
writeFileSync(ASTRO_CONTENT_PATH, updatedContent);
|
| 229 |
+
console.log(` ✅ Updated image paths in MDX file`);
|
| 230 |
+
}
|
| 231 |
+
|
| 232 |
+
// Create empty bibliography.bib
|
| 233 |
+
writeFileSync(ASTRO_BIB_PATH, '');
|
| 234 |
+
console.log(` ✅ Created empty bibliography at ${ASTRO_BIB_PATH}`);
|
| 235 |
+
|
| 236 |
+
} catch (error) {
|
| 237 |
+
console.warn(` ⚠️ Failed to copy to Astro: ${error.message}`);
|
| 238 |
+
}
|
| 239 |
+
}
|
| 240 |
+
|
| 241 |
+
|
| 242 |
+
async function main() {
|
| 243 |
+
const args = process.argv.slice(2);
|
| 244 |
+
|
| 245 |
+
if (args.includes('--help') || args.includes('-h')) {
|
| 246 |
+
showHelp();
|
| 247 |
+
process.exit(0);
|
| 248 |
+
}
|
| 249 |
+
|
| 250 |
+
const config = parseArgs();
|
| 251 |
+
|
| 252 |
+
console.log('🚀 Notion to MDX Toolkit');
|
| 253 |
+
console.log('========================');
|
| 254 |
+
|
| 255 |
+
try {
|
| 256 |
+
// Prepare input config file
|
| 257 |
+
let inputConfigFile = config.input;
|
| 258 |
+
let pageIdFromEnv = null;
|
| 259 |
+
|
| 260 |
+
// If NOTION_PAGE_ID is provided via env var, create temporary pages.json
|
| 261 |
+
if (config.pageId && config.token) {
|
| 262 |
+
console.log('✨ Using NOTION_PAGE_ID from environment variable');
|
| 263 |
+
const tempConfigPath = join(config.output, '.temp-pages.json');
|
| 264 |
+
ensureDirectory(config.output);
|
| 265 |
+
await createPagesConfigFromEnv(config.pageId, config.token, tempConfigPath);
|
| 266 |
+
inputConfigFile = tempConfigPath;
|
| 267 |
+
pageIdFromEnv = config.pageId;
|
| 268 |
+
} else if (!existsSync(config.input)) {
|
| 269 |
+
console.error(`❌ No NOTION_PAGE_ID environment variable and no pages.json found at: ${config.input}`);
|
| 270 |
+
console.log('💡 Either set NOTION_PAGE_ID env var or create input/pages.json');
|
| 271 |
+
process.exit(1);
|
| 272 |
+
}
|
| 273 |
+
|
| 274 |
+
if (config.clean) {
|
| 275 |
+
console.log('🧹 Cleaning output directory...');
|
| 276 |
+
await cleanDirectory(config.output);
|
| 277 |
+
}
|
| 278 |
+
|
| 279 |
+
if (config.mdxOnly) {
|
| 280 |
+
// Only convert existing Markdown to MDX
|
| 281 |
+
console.log('📝 MDX conversion only mode');
|
| 282 |
+
await convertToMdx(config.output, config.output);
|
| 283 |
+
copyToAstroContent(config.output);
|
| 284 |
+
|
| 285 |
+
} else if (config.notionOnly) {
|
| 286 |
+
// Only convert Notion to Markdown
|
| 287 |
+
console.log('📄 Notion conversion only mode');
|
| 288 |
+
await convertNotionToMarkdown(inputConfigFile, config.output, config.token);
|
| 289 |
+
|
| 290 |
+
} else {
|
| 291 |
+
// Full workflow
|
| 292 |
+
console.log('🔄 Full conversion workflow');
|
| 293 |
+
|
| 294 |
+
// Step 1: Convert Notion to Markdown
|
| 295 |
+
console.log('\n📄 Step 1: Converting Notion pages to Markdown...');
|
| 296 |
+
await convertNotionToMarkdown(inputConfigFile, config.output, config.token);
|
| 297 |
+
|
| 298 |
+
// Step 2: Convert Markdown to MDX with Notion metadata
|
| 299 |
+
console.log('\n📝 Step 2: Converting Markdown to MDX...');
|
| 300 |
+
const pagesConfig = readPagesConfig(inputConfigFile);
|
| 301 |
+
const firstPage = pagesConfig.pages && pagesConfig.pages.length > 0 ? pagesConfig.pages[0] : null;
|
| 302 |
+
const pageId = pageIdFromEnv || (firstPage ? firstPage.id : null);
|
| 303 |
+
await convertToMdx(config.output, config.output, pageId, config.token);
|
| 304 |
+
|
| 305 |
+
// Step 3: Copy to Astro content directory
|
| 306 |
+
console.log('\n📋 Step 3: Copying to Astro content directory...');
|
| 307 |
+
copyToAstroContent(config.output);
|
| 308 |
+
}
|
| 309 |
+
|
| 310 |
+
console.log('\n🎉 Conversion completed successfully!');
|
| 311 |
+
|
| 312 |
+
} catch (error) {
|
| 313 |
+
console.error('❌ Error:', error.message);
|
| 314 |
+
process.exit(1);
|
| 315 |
+
}
|
| 316 |
+
}
|
| 317 |
+
|
| 318 |
+
// Export functions for use as module
|
| 319 |
+
export { convertNotionToMarkdown, convertToMdx };
|
| 320 |
+
|
| 321 |
+
// Run CLI if called directly
|
| 322 |
+
if (import.meta.url === `file://${process.argv[1]}`) {
|
| 323 |
+
main();
|
| 324 |
+
}
|
app/scripts/notion-importer/input/pages.json
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"pages": [
|
| 3 |
+
{
|
| 4 |
+
"id": "27877f1c9c9d804d9c82f7b3905578ff",
|
| 5 |
+
"title": "The Smol Training Guide",
|
| 6 |
+
"slug": "smol-training-guide"
|
| 7 |
+
}
|
| 8 |
+
]
|
| 9 |
+
}
|
app/scripts/notion-importer/mdx-converter.mjs
ADDED
|
@@ -0,0 +1,551 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env node
|
| 2 |
+
|
| 3 |
+
import { readFileSync, writeFileSync, existsSync, mkdirSync, readdirSync, statSync } from 'fs';
|
| 4 |
+
import { join, dirname, basename, extname } from 'path';
|
| 5 |
+
import { fileURLToPath } from 'url';
|
| 6 |
+
import matter from 'gray-matter';
|
| 7 |
+
import { extractAndGenerateNotionFrontmatter } from './notion-metadata-extractor.mjs';
|
| 8 |
+
|
| 9 |
+
const __filename = fileURLToPath(import.meta.url);
|
| 10 |
+
const __dirname = dirname(__filename);
|
| 11 |
+
|
| 12 |
+
// Configuration
|
| 13 |
+
const DEFAULT_INPUT = join(__dirname, 'output');
|
| 14 |
+
const DEFAULT_OUTPUT = join(__dirname, 'output');
|
| 15 |
+
|
| 16 |
+
function parseArgs() {
|
| 17 |
+
const args = process.argv.slice(2);
|
| 18 |
+
const config = {
|
| 19 |
+
input: DEFAULT_INPUT,
|
| 20 |
+
output: DEFAULT_OUTPUT,
|
| 21 |
+
};
|
| 22 |
+
|
| 23 |
+
for (const arg of args) {
|
| 24 |
+
if (arg.startsWith('--input=')) {
|
| 25 |
+
config.input = arg.substring('--input='.length);
|
| 26 |
+
} else if (arg.startsWith('--output=')) {
|
| 27 |
+
config.output = arg.substring('--output='.length);
|
| 28 |
+
} else if (arg === '--help' || arg === '-h') {
|
| 29 |
+
console.log(`
|
| 30 |
+
📝 Notion Markdown to MDX Converter
|
| 31 |
+
|
| 32 |
+
Usage:
|
| 33 |
+
node mdx-converter.mjs [options]
|
| 34 |
+
|
| 35 |
+
Options:
|
| 36 |
+
--input=PATH Input directory or file (default: ${DEFAULT_INPUT})
|
| 37 |
+
--output=PATH Output directory (default: ${DEFAULT_OUTPUT})
|
| 38 |
+
--help, -h Show this help
|
| 39 |
+
|
| 40 |
+
Examples:
|
| 41 |
+
# Convert all markdown files in output directory
|
| 42 |
+
node mdx-converter.mjs
|
| 43 |
+
|
| 44 |
+
# Convert specific file
|
| 45 |
+
node mdx-converter.mjs --input=article.md --output=converted/
|
| 46 |
+
|
| 47 |
+
# Convert directory
|
| 48 |
+
node mdx-converter.mjs --input=markdown-files/ --output=mdx-files/
|
| 49 |
+
`);
|
| 50 |
+
process.exit(0);
|
| 51 |
+
} else if (!config.input) {
|
| 52 |
+
config.input = arg;
|
| 53 |
+
} else if (!config.output) {
|
| 54 |
+
config.output = arg;
|
| 55 |
+
}
|
| 56 |
+
}
|
| 57 |
+
return config;
|
| 58 |
+
}
|
| 59 |
+
|
| 60 |
+
/**
|
| 61 |
+
* Track which Astro components are used during transformations
|
| 62 |
+
*/
|
| 63 |
+
const usedComponents = new Set();
|
| 64 |
+
|
| 65 |
+
/**
|
| 66 |
+
* Track individual image imports needed
|
| 67 |
+
*/
|
| 68 |
+
const imageImports = new Map(); // src -> varName
|
| 69 |
+
|
| 70 |
+
/**
|
| 71 |
+
* Generate a variable name from image path
|
| 72 |
+
* @param {string} src - Image source path
|
| 73 |
+
* @returns {string} - Valid variable name
|
| 74 |
+
*/
|
| 75 |
+
function generateImageVarName(src) {
|
| 76 |
+
// Extract filename without extension and make it a valid JS variable
|
| 77 |
+
const filename = src.split('/').pop().replace(/\.[^.]+$/, '');
|
| 78 |
+
return filename.replace(/[^a-zA-Z0-9]/g, '_').replace(/^[0-9]/, 'img_$&');
|
| 79 |
+
}
|
| 80 |
+
|
| 81 |
+
/**
|
| 82 |
+
* Add required component imports to the frontmatter
|
| 83 |
+
* @param {string} content - MDX content
|
| 84 |
+
* @returns {string} - Content with component imports
|
| 85 |
+
*/
|
| 86 |
+
function addComponentImports(content) {
|
| 87 |
+
console.log(' 📦 Adding component and image imports...');
|
| 88 |
+
|
| 89 |
+
let imports = [];
|
| 90 |
+
|
| 91 |
+
// Add component imports
|
| 92 |
+
if (usedComponents.size > 0) {
|
| 93 |
+
const componentImports = Array.from(usedComponents)
|
| 94 |
+
.map(component => `import ${component} from '../components/${component}.astro';`);
|
| 95 |
+
imports.push(...componentImports);
|
| 96 |
+
console.log(` ✅ Importing components: ${Array.from(usedComponents).join(', ')}`);
|
| 97 |
+
}
|
| 98 |
+
|
| 99 |
+
// Add image imports
|
| 100 |
+
if (imageImports.size > 0) {
|
| 101 |
+
const imageImportStatements = Array.from(imageImports.entries())
|
| 102 |
+
.map(([src, varName]) => `import ${varName} from '${src}';`);
|
| 103 |
+
imports.push(...imageImportStatements);
|
| 104 |
+
console.log(` ✅ Importing ${imageImports.size} image(s)`);
|
| 105 |
+
}
|
| 106 |
+
|
| 107 |
+
if (imports.length === 0) {
|
| 108 |
+
console.log(' ℹ️ No imports needed');
|
| 109 |
+
return content;
|
| 110 |
+
}
|
| 111 |
+
|
| 112 |
+
const importBlock = imports.join('\n');
|
| 113 |
+
|
| 114 |
+
// Insert imports after frontmatter
|
| 115 |
+
const frontmatterEnd = content.indexOf('---', 3) + 3;
|
| 116 |
+
if (frontmatterEnd > 2) {
|
| 117 |
+
return content.slice(0, frontmatterEnd) + '\n\n' + importBlock + '\n' + content.slice(frontmatterEnd);
|
| 118 |
+
} else {
|
| 119 |
+
// No frontmatter, add at beginning
|
| 120 |
+
return importBlock + '\n\n' + content;
|
| 121 |
+
}
|
| 122 |
+
}
|
| 123 |
+
|
| 124 |
+
/**
|
| 125 |
+
* Transform Notion images to Image components
|
| 126 |
+
* @param {string} content - MDX content
|
| 127 |
+
* @returns {string} - Content with Image components
|
| 128 |
+
*/
|
| 129 |
+
function transformImages(content) {
|
| 130 |
+
console.log(' 🖼️ Transforming images to Image components...');
|
| 131 |
+
|
| 132 |
+
let hasImages = false;
|
| 133 |
+
|
| 134 |
+
// Helper function to clean source paths
|
| 135 |
+
const cleanSrcPath = (src) => {
|
| 136 |
+
// Convert Notion media paths to relative paths
|
| 137 |
+
return src.replace(/^\/media\//, './media/')
|
| 138 |
+
.replace(/^\.\/media\//, './media/');
|
| 139 |
+
};
|
| 140 |
+
|
| 141 |
+
// Helper to clean caption text
|
| 142 |
+
const cleanCaption = (caption) => {
|
| 143 |
+
return caption
|
| 144 |
+
.replace(/<[^>]*>/g, '') // Remove HTML tags
|
| 145 |
+
.replace(/\n/g, ' ') // Replace newlines with spaces
|
| 146 |
+
.replace(/\r/g, ' ') // Replace carriage returns with spaces
|
| 147 |
+
.replace(/\s+/g, ' ') // Replace multiple spaces with single space
|
| 148 |
+
.replace(/'/g, "\\'") // Escape quotes
|
| 149 |
+
.trim(); // Trim whitespace
|
| 150 |
+
};
|
| 151 |
+
|
| 152 |
+
// Helper to clean alt text
|
| 153 |
+
const cleanAltText = (alt, maxLength = 100) => {
|
| 154 |
+
const cleaned = alt
|
| 155 |
+
.replace(/<[^>]*>/g, '') // Remove HTML tags
|
| 156 |
+
.replace(/\n/g, ' ') // Replace newlines with spaces
|
| 157 |
+
.replace(/\r/g, ' ') // Replace carriage returns with spaces
|
| 158 |
+
.replace(/\s+/g, ' ') // Replace multiple spaces with single space
|
| 159 |
+
.trim(); // Trim whitespace
|
| 160 |
+
|
| 161 |
+
return cleaned.length > maxLength
|
| 162 |
+
? cleaned.substring(0, maxLength) + '...'
|
| 163 |
+
: cleaned;
|
| 164 |
+
};
|
| 165 |
+
|
| 166 |
+
// Create Image component with import
|
| 167 |
+
const createImageComponent = (src, alt = '', caption = '') => {
|
| 168 |
+
const cleanSrc = cleanSrcPath(src);
|
| 169 |
+
|
| 170 |
+
// Skip PDF URLs and external URLs - they should remain as links only
|
| 171 |
+
if (cleanSrc.includes('.pdf') || cleanSrc.includes('arxiv.org/pdf') ||
|
| 172 |
+
(cleanSrc.startsWith('http') && !cleanSrc.includes('/media/'))) {
|
| 173 |
+
console.log(` ⚠️ Skipping external/PDF URL: ${cleanSrc}`);
|
| 174 |
+
// Return the original markdown image syntax for external URLs
|
| 175 |
+
return ``;
|
| 176 |
+
}
|
| 177 |
+
|
| 178 |
+
const varName = generateImageVarName(cleanSrc);
|
| 179 |
+
imageImports.set(cleanSrc, varName);
|
| 180 |
+
usedComponents.add('Image');
|
| 181 |
+
|
| 182 |
+
const props = [];
|
| 183 |
+
props.push(`src={${varName}}`);
|
| 184 |
+
props.push('zoomable');
|
| 185 |
+
props.push('downloadable');
|
| 186 |
+
props.push('layout="fixed"');
|
| 187 |
+
if (alt) props.push(`alt="${alt}"`);
|
| 188 |
+
if (caption) props.push(`caption={'${caption}'}`);
|
| 189 |
+
|
| 190 |
+
return `<Image\n ${props.join('\n ')}\n/>`;
|
| 191 |
+
};
|
| 192 |
+
|
| 193 |
+
// Transform markdown images: 
|
| 194 |
+
content = content.replace(/!\[([^\]]*)\]\(([^)]+)\)/g, (match, alt, src) => {
|
| 195 |
+
const cleanSrc = cleanSrcPath(src);
|
| 196 |
+
const cleanAlt = cleanAltText(alt || 'Image');
|
| 197 |
+
hasImages = true;
|
| 198 |
+
|
| 199 |
+
return createImageComponent(cleanSrc, cleanAlt);
|
| 200 |
+
});
|
| 201 |
+
|
| 202 |
+
// Transform images with captions (Notion sometimes adds captions as separate text)
|
| 203 |
+
content = content.replace(/!\[([^\]]*)\]\(([^)]+)\)\s*\n\s*([^\n]+)/g, (match, alt, src, caption) => {
|
| 204 |
+
const cleanSrc = cleanSrcPath(src);
|
| 205 |
+
const cleanAlt = cleanAltText(alt || 'Image');
|
| 206 |
+
const cleanCap = cleanCaption(caption);
|
| 207 |
+
hasImages = true;
|
| 208 |
+
|
| 209 |
+
return createImageComponent(cleanSrc, cleanAlt, cleanCap);
|
| 210 |
+
});
|
| 211 |
+
|
| 212 |
+
if (hasImages) {
|
| 213 |
+
console.log(' ✅ Image components with imports will be created');
|
| 214 |
+
}
|
| 215 |
+
|
| 216 |
+
return content;
|
| 217 |
+
}
|
| 218 |
+
|
| 219 |
+
/**
|
| 220 |
+
* Transform Notion callouts to Note components
|
| 221 |
+
* @param {string} content - MDX content
|
| 222 |
+
* @returns {string} - Content with Note components
|
| 223 |
+
*/
|
| 224 |
+
function transformCallouts(content) {
|
| 225 |
+
console.log(' 📝 Transforming callouts to Note components...');
|
| 226 |
+
|
| 227 |
+
let transformedCount = 0;
|
| 228 |
+
|
| 229 |
+
// Transform blockquotes that look like Notion callouts
|
| 230 |
+
content = content.replace(/^> \*\*([^*]+)\*\*\s*\n> (.+?)(?=\n> \*\*|\n\n|\n$)/gms, (match, title, content) => {
|
| 231 |
+
transformedCount++;
|
| 232 |
+
usedComponents.add('Note');
|
| 233 |
+
|
| 234 |
+
const cleanContent = content
|
| 235 |
+
.replace(/^> /gm, '') // Remove blockquote markers
|
| 236 |
+
.replace(/\n+/g, '\n') // Normalize newlines
|
| 237 |
+
.trim();
|
| 238 |
+
|
| 239 |
+
return `<Note type="${title.toLowerCase()}" title="${title}">\n${cleanContent}\n</Note>\n\n`;
|
| 240 |
+
});
|
| 241 |
+
|
| 242 |
+
if (transformedCount > 0) {
|
| 243 |
+
console.log(` ✅ Transformed ${transformedCount} callout(s) to Note components`);
|
| 244 |
+
}
|
| 245 |
+
|
| 246 |
+
return content;
|
| 247 |
+
}
|
| 248 |
+
|
| 249 |
+
/**
|
| 250 |
+
* Transform Notion databases/tables to enhanced table components
|
| 251 |
+
* @param {string} content - MDX content
|
| 252 |
+
* @returns {string} - Content with enhanced tables
|
| 253 |
+
*/
|
| 254 |
+
function transformTables(content) {
|
| 255 |
+
console.log(' 📊 Enhancing tables...');
|
| 256 |
+
|
| 257 |
+
let enhancedCount = 0;
|
| 258 |
+
|
| 259 |
+
// Wrap tables in a container for better styling
|
| 260 |
+
content = content.replace(/^(\|[^|\n]+\|[\s\S]*?)(?=\n\n|\n$)/gm, (match) => {
|
| 261 |
+
if (match.includes('|') && match.split('\n').length > 2) {
|
| 262 |
+
enhancedCount++;
|
| 263 |
+
return `<div class="table-container">\n\n${match}\n\n</div>`;
|
| 264 |
+
}
|
| 265 |
+
return match;
|
| 266 |
+
});
|
| 267 |
+
|
| 268 |
+
if (enhancedCount > 0) {
|
| 269 |
+
console.log(` ✅ Enhanced ${enhancedCount} table(s)`);
|
| 270 |
+
}
|
| 271 |
+
|
| 272 |
+
return content;
|
| 273 |
+
}
|
| 274 |
+
|
| 275 |
+
/**
|
| 276 |
+
* Transform Notion code blocks to enhanced code components
|
| 277 |
+
* @param {string} content - MDX content
|
| 278 |
+
* @returns {string} - Content with enhanced code blocks
|
| 279 |
+
*/
|
| 280 |
+
function transformCodeBlocks(content) {
|
| 281 |
+
console.log(' 💻 Enhancing code blocks...');
|
| 282 |
+
|
| 283 |
+
let enhancedCount = 0;
|
| 284 |
+
|
| 285 |
+
// Add copy functionality to code blocks
|
| 286 |
+
content = content.replace(/^```(\w+)\n([\s\S]*?)\n```$/gm, (match, lang, code) => {
|
| 287 |
+
enhancedCount++;
|
| 288 |
+
return `\`\`\`${lang} copy\n${code}\n\`\`\``;
|
| 289 |
+
});
|
| 290 |
+
|
| 291 |
+
if (enhancedCount > 0) {
|
| 292 |
+
console.log(` ✅ Enhanced ${enhancedCount} code block(s)`);
|
| 293 |
+
}
|
| 294 |
+
|
| 295 |
+
return content;
|
| 296 |
+
}
|
| 297 |
+
|
| 298 |
+
/**
|
| 299 |
+
* Fix Notion-specific formatting issues
|
| 300 |
+
* @param {string} content - MDX content
|
| 301 |
+
* @returns {string} - Content with fixed formatting
|
| 302 |
+
*/
|
| 303 |
+
function fixNotionFormatting(content) {
|
| 304 |
+
console.log(' 🔧 Fixing Notion formatting issues...');
|
| 305 |
+
|
| 306 |
+
let fixedCount = 0;
|
| 307 |
+
|
| 308 |
+
// Fix Notion's toggle lists that don't convert well
|
| 309 |
+
content = content.replace(/^(\s*)•\s*(.+)$/gm, (match, indent, text) => {
|
| 310 |
+
fixedCount++;
|
| 311 |
+
return `${indent}- ${text}`;
|
| 312 |
+
});
|
| 313 |
+
|
| 314 |
+
// Fix Notion's numbered lists that might have issues
|
| 315 |
+
content = content.replace(/^(\s*)\d+\.\s*(.+)$/gm, (match, indent, text) => {
|
| 316 |
+
// Only fix if it's not already properly formatted
|
| 317 |
+
if (!text.includes('\n') || text.split('\n').length === 1) {
|
| 318 |
+
return match; // Keep as is
|
| 319 |
+
}
|
| 320 |
+
fixedCount++;
|
| 321 |
+
return `${indent}1. ${text}`;
|
| 322 |
+
});
|
| 323 |
+
|
| 324 |
+
// Fix Notion's bold/italic combinations
|
| 325 |
+
content = content.replace(/\*\*([^*]+)\*\*([^*]+)\*\*([^*]+)\*\*/g, (match, part1, part2, part3) => {
|
| 326 |
+
fixedCount++;
|
| 327 |
+
return `**${part1}${part2}${part3}**`;
|
| 328 |
+
});
|
| 329 |
+
|
| 330 |
+
if (fixedCount > 0) {
|
| 331 |
+
console.log(` ✅ Fixed ${fixedCount} formatting issue(s)`);
|
| 332 |
+
}
|
| 333 |
+
|
| 334 |
+
return content;
|
| 335 |
+
}
|
| 336 |
+
|
| 337 |
+
/**
|
| 338 |
+
* Ensure proper frontmatter for MDX with Notion metadata
|
| 339 |
+
* @param {string} content - MDX content
|
| 340 |
+
* @param {string} pageId - Notion page ID (optional)
|
| 341 |
+
* @param {string} notionToken - Notion API token (optional)
|
| 342 |
+
* @returns {string} - Content with proper frontmatter
|
| 343 |
+
*/
|
| 344 |
+
async function ensureFrontmatter(content, pageId = null, notionToken = null) {
|
| 345 |
+
console.log(' 📄 Ensuring proper frontmatter...');
|
| 346 |
+
|
| 347 |
+
if (!content.startsWith('---')) {
|
| 348 |
+
let frontmatter;
|
| 349 |
+
|
| 350 |
+
if (pageId && notionToken) {
|
| 351 |
+
try {
|
| 352 |
+
console.log(' 🔍 Extracting Notion metadata...');
|
| 353 |
+
frontmatter = await extractAndGenerateNotionFrontmatter(pageId, notionToken);
|
| 354 |
+
console.log(' ✅ Generated rich frontmatter from Notion');
|
| 355 |
+
} catch (error) {
|
| 356 |
+
console.log(' ⚠️ Failed to extract Notion metadata, using basic frontmatter');
|
| 357 |
+
frontmatter = generateBasicFrontmatter();
|
| 358 |
+
}
|
| 359 |
+
} else {
|
| 360 |
+
frontmatter = generateBasicFrontmatter();
|
| 361 |
+
console.log(' ✅ Generated basic frontmatter');
|
| 362 |
+
}
|
| 363 |
+
|
| 364 |
+
return frontmatter + content;
|
| 365 |
+
}
|
| 366 |
+
|
| 367 |
+
// Parse existing frontmatter and enhance it
|
| 368 |
+
try {
|
| 369 |
+
const { data, content: body } = matter(content);
|
| 370 |
+
|
| 371 |
+
// If we have Notion metadata available, try to enhance the frontmatter
|
| 372 |
+
if (pageId && notionToken && (!data.notion_id || data.notion_id !== pageId)) {
|
| 373 |
+
try {
|
| 374 |
+
console.log(' 🔍 Enhancing frontmatter with Notion metadata...');
|
| 375 |
+
const notionFrontmatter = await extractAndGenerateNotionFrontmatter(pageId, notionToken);
|
| 376 |
+
const { data: notionData } = matter(notionFrontmatter);
|
| 377 |
+
|
| 378 |
+
// Merge Notion metadata with existing frontmatter
|
| 379 |
+
const enhancedData = { ...data, ...notionData };
|
| 380 |
+
const enhancedContent = matter.stringify(body, enhancedData);
|
| 381 |
+
console.log(' ✅ Enhanced frontmatter with Notion metadata');
|
| 382 |
+
return enhancedContent;
|
| 383 |
+
} catch (error) {
|
| 384 |
+
console.log(' ⚠️ Could not enhance with Notion metadata, keeping existing');
|
| 385 |
+
}
|
| 386 |
+
}
|
| 387 |
+
|
| 388 |
+
// Ensure required fields
|
| 389 |
+
if (!data.title) data.title = 'Notion Article';
|
| 390 |
+
if (!data.published) data.published = new Date().toISOString().split('T')[0];
|
| 391 |
+
if (!data.tableOfContentsAutoCollapse) data.tableOfContentsAutoCollapse = true;
|
| 392 |
+
|
| 393 |
+
const enhancedContent = matter.stringify(body, data);
|
| 394 |
+
console.log(' ✅ Enhanced existing frontmatter');
|
| 395 |
+
return enhancedContent;
|
| 396 |
+
} catch (error) {
|
| 397 |
+
console.log(' ⚠️ Could not parse frontmatter, keeping as is');
|
| 398 |
+
return content;
|
| 399 |
+
}
|
| 400 |
+
}
|
| 401 |
+
|
| 402 |
+
/**
|
| 403 |
+
* Generate basic frontmatter
|
| 404 |
+
* @returns {string} - Basic frontmatter
|
| 405 |
+
*/
|
| 406 |
+
function generateBasicFrontmatter() {
|
| 407 |
+
const currentDate = new Date().toLocaleDateString('en-US', {
|
| 408 |
+
year: 'numeric',
|
| 409 |
+
month: 'short',
|
| 410 |
+
day: '2-digit'
|
| 411 |
+
});
|
| 412 |
+
return `---
|
| 413 |
+
title: "Notion Article"
|
| 414 |
+
published: "${currentDate}"
|
| 415 |
+
tableOfContentsAutoCollapse: true
|
| 416 |
+
---
|
| 417 |
+
|
| 418 |
+
`;
|
| 419 |
+
}
|
| 420 |
+
|
| 421 |
+
/**
|
| 422 |
+
* Main MDX processing function that applies all transformations
|
| 423 |
+
* @param {string} content - Raw Markdown content
|
| 424 |
+
* @param {string} pageId - Notion page ID (optional)
|
| 425 |
+
* @param {string} notionToken - Notion API token (optional)
|
| 426 |
+
* @returns {string} - Processed MDX content compatible with Astro
|
| 427 |
+
*/
|
| 428 |
+
async function processMdxContent(content, pageId = null, notionToken = null) {
|
| 429 |
+
console.log('🔧 Processing for Astro MDX compatibility...');
|
| 430 |
+
|
| 431 |
+
// Clear previous tracking
|
| 432 |
+
usedComponents.clear();
|
| 433 |
+
imageImports.clear();
|
| 434 |
+
|
| 435 |
+
let processedContent = content;
|
| 436 |
+
|
| 437 |
+
// Apply each transformation step sequentially
|
| 438 |
+
processedContent = await ensureFrontmatter(processedContent, pageId, notionToken);
|
| 439 |
+
processedContent = fixNotionFormatting(processedContent);
|
| 440 |
+
processedContent = transformCallouts(processedContent);
|
| 441 |
+
processedContent = transformImages(processedContent);
|
| 442 |
+
processedContent = transformTables(processedContent);
|
| 443 |
+
processedContent = transformCodeBlocks(processedContent);
|
| 444 |
+
|
| 445 |
+
// Add component imports at the end
|
| 446 |
+
processedContent = addComponentImports(processedContent);
|
| 447 |
+
|
| 448 |
+
return processedContent;
|
| 449 |
+
}
|
| 450 |
+
|
| 451 |
+
/**
|
| 452 |
+
* Convert a single markdown file to MDX
|
| 453 |
+
* @param {string} inputFile - Input markdown file
|
| 454 |
+
* @param {string} outputDir - Output directory
|
| 455 |
+
* @param {string} pageId - Notion page ID (optional)
|
| 456 |
+
* @param {string} notionToken - Notion API token (optional)
|
| 457 |
+
*/
|
| 458 |
+
async function convertFileToMdx(inputFile, outputDir, pageId = null, notionToken = null) {
|
| 459 |
+
const filename = basename(inputFile, '.md');
|
| 460 |
+
const outputFile = join(outputDir, `${filename}.mdx`);
|
| 461 |
+
|
| 462 |
+
console.log(`📝 Converting: ${basename(inputFile)} → ${basename(outputFile)}`);
|
| 463 |
+
|
| 464 |
+
try {
|
| 465 |
+
const markdownContent = readFileSync(inputFile, 'utf8');
|
| 466 |
+
const mdxContent = await processMdxContent(markdownContent, pageId, notionToken);
|
| 467 |
+
writeFileSync(outputFile, mdxContent);
|
| 468 |
+
|
| 469 |
+
console.log(` ✅ Converted: ${outputFile}`);
|
| 470 |
+
|
| 471 |
+
// Show file size
|
| 472 |
+
const inputSize = Math.round(markdownContent.length / 1024);
|
| 473 |
+
const outputSize = Math.round(mdxContent.length / 1024);
|
| 474 |
+
console.log(` 📊 Input: ${inputSize}KB → Output: ${outputSize}KB`);
|
| 475 |
+
|
| 476 |
+
} catch (error) {
|
| 477 |
+
console.error(` ❌ Failed to convert ${inputFile}: ${error.message}`);
|
| 478 |
+
}
|
| 479 |
+
}
|
| 480 |
+
|
| 481 |
+
/**
|
| 482 |
+
* Convert all markdown files in a directory to MDX
|
| 483 |
+
* @param {string} inputPath - Input path (file or directory)
|
| 484 |
+
* @param {string} outputDir - Output directory
|
| 485 |
+
* @param {string} pageId - Notion page ID (optional)
|
| 486 |
+
* @param {string} notionToken - Notion API token (optional)
|
| 487 |
+
*/
|
| 488 |
+
async function convertToMdx(inputPath, outputDir, pageId = null, notionToken = null) {
|
| 489 |
+
console.log('📝 Notion Markdown to Astro MDX Converter');
|
| 490 |
+
console.log(`📁 Input: ${inputPath}`);
|
| 491 |
+
console.log(`📁 Output: ${outputDir}`);
|
| 492 |
+
|
| 493 |
+
// Check if input exists
|
| 494 |
+
if (!existsSync(inputPath)) {
|
| 495 |
+
console.error(`❌ Input not found: ${inputPath}`);
|
| 496 |
+
process.exit(1);
|
| 497 |
+
}
|
| 498 |
+
|
| 499 |
+
try {
|
| 500 |
+
// Ensure output directory exists
|
| 501 |
+
if (!existsSync(outputDir)) {
|
| 502 |
+
mkdirSync(outputDir, { recursive: true });
|
| 503 |
+
}
|
| 504 |
+
|
| 505 |
+
let filesToConvert = [];
|
| 506 |
+
|
| 507 |
+
if (statSync(inputPath).isDirectory()) {
|
| 508 |
+
// Convert all .md files in directory
|
| 509 |
+
const files = readdirSync(inputPath);
|
| 510 |
+
filesToConvert = files
|
| 511 |
+
.filter(file => file.endsWith('.md'))
|
| 512 |
+
.map(file => join(inputPath, file));
|
| 513 |
+
} else if (inputPath.endsWith('.md')) {
|
| 514 |
+
// Convert single file
|
| 515 |
+
filesToConvert = [inputPath];
|
| 516 |
+
} else {
|
| 517 |
+
console.error('❌ Input must be a .md file or directory containing .md files');
|
| 518 |
+
process.exit(1);
|
| 519 |
+
}
|
| 520 |
+
|
| 521 |
+
if (filesToConvert.length === 0) {
|
| 522 |
+
console.log('ℹ️ No .md files found to convert');
|
| 523 |
+
return;
|
| 524 |
+
}
|
| 525 |
+
|
| 526 |
+
console.log(`🔄 Found ${filesToConvert.length} file(s) to convert`);
|
| 527 |
+
|
| 528 |
+
// Convert each file
|
| 529 |
+
for (const file of filesToConvert) {
|
| 530 |
+
await convertFileToMdx(file, outputDir, pageId, notionToken);
|
| 531 |
+
}
|
| 532 |
+
|
| 533 |
+
console.log(`✅ Conversion completed! ${filesToConvert.length} file(s) processed`);
|
| 534 |
+
|
| 535 |
+
} catch (error) {
|
| 536 |
+
console.error('❌ Conversion failed:', error.message);
|
| 537 |
+
process.exit(1);
|
| 538 |
+
}
|
| 539 |
+
}
|
| 540 |
+
|
| 541 |
+
export { convertToMdx };
|
| 542 |
+
|
| 543 |
+
function main() {
|
| 544 |
+
const config = parseArgs();
|
| 545 |
+
convertToMdx(config.input, config.output);
|
| 546 |
+
console.log('🎉 MDX conversion completed!');
|
| 547 |
+
}
|
| 548 |
+
|
| 549 |
+
if (import.meta.url === `file://${process.argv[1]}`) {
|
| 550 |
+
main();
|
| 551 |
+
}
|
app/scripts/notion-importer/notion-converter.mjs
ADDED
|
@@ -0,0 +1,259 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env node
|
| 2 |
+
|
| 3 |
+
import { config } from 'dotenv';
|
| 4 |
+
import { Client } from '@notionhq/client';
|
| 5 |
+
import { NotionConverter } from 'notion-to-md';
|
| 6 |
+
import { DefaultExporter } from 'notion-to-md/plugins/exporter';
|
| 7 |
+
import { readFileSync, writeFileSync, existsSync, mkdirSync } from 'fs';
|
| 8 |
+
import { join, dirname, basename } from 'path';
|
| 9 |
+
import { fileURLToPath } from 'url';
|
| 10 |
+
import { postProcessMarkdown } from './post-processor.mjs';
|
| 11 |
+
import { createCustomCodeRenderer } from './custom-code-renderer.mjs';
|
| 12 |
+
|
| 13 |
+
// Load environment variables from .env file (but don't override existing ones)
|
| 14 |
+
config({ override: false });
|
| 15 |
+
|
| 16 |
+
const __filename = fileURLToPath(import.meta.url);
|
| 17 |
+
const __dirname = dirname(__filename);
|
| 18 |
+
|
| 19 |
+
// Configuration
|
| 20 |
+
const DEFAULT_INPUT = join(__dirname, 'input', 'pages.json');
|
| 21 |
+
const DEFAULT_OUTPUT = join(__dirname, 'output');
|
| 22 |
+
|
| 23 |
+
function parseArgs() {
|
| 24 |
+
const args = process.argv.slice(2);
|
| 25 |
+
const config = {
|
| 26 |
+
input: DEFAULT_INPUT,
|
| 27 |
+
output: DEFAULT_OUTPUT,
|
| 28 |
+
clean: false,
|
| 29 |
+
token: process.env.NOTION_TOKEN
|
| 30 |
+
};
|
| 31 |
+
|
| 32 |
+
for (const arg of args) {
|
| 33 |
+
if (arg.startsWith('--input=')) {
|
| 34 |
+
config.input = arg.split('=')[1];
|
| 35 |
+
} else if (arg.startsWith('--output=')) {
|
| 36 |
+
config.output = arg.split('=')[1];
|
| 37 |
+
} else if (arg.startsWith('--token=')) {
|
| 38 |
+
config.token = arg.split('=')[1];
|
| 39 |
+
} else if (arg === '--clean') {
|
| 40 |
+
config.clean = true;
|
| 41 |
+
}
|
| 42 |
+
}
|
| 43 |
+
|
| 44 |
+
return config;
|
| 45 |
+
}
|
| 46 |
+
|
| 47 |
+
function ensureDirectory(dir) {
|
| 48 |
+
if (!existsSync(dir)) {
|
| 49 |
+
mkdirSync(dir, { recursive: true });
|
| 50 |
+
}
|
| 51 |
+
}
|
| 52 |
+
|
| 53 |
+
function loadPagesConfig(configFile) {
|
| 54 |
+
if (!existsSync(configFile)) {
|
| 55 |
+
console.error(`❌ Configuration file not found: ${configFile}`);
|
| 56 |
+
console.log('📝 Create a pages.json file with your Notion page IDs:');
|
| 57 |
+
console.log(`
|
| 58 |
+
{
|
| 59 |
+
"pages": [
|
| 60 |
+
{
|
| 61 |
+
"id": "your-notion-page-id-1",
|
| 62 |
+
"title": "Page Title 1",
|
| 63 |
+
"slug": "page-1"
|
| 64 |
+
},
|
| 65 |
+
{
|
| 66 |
+
"id": "your-notion-page-id-2",
|
| 67 |
+
"title": "Page Title 2",
|
| 68 |
+
"slug": "page-2"
|
| 69 |
+
}
|
| 70 |
+
]
|
| 71 |
+
}
|
| 72 |
+
`);
|
| 73 |
+
process.exit(1);
|
| 74 |
+
}
|
| 75 |
+
|
| 76 |
+
try {
|
| 77 |
+
const config = JSON.parse(readFileSync(configFile, 'utf8'));
|
| 78 |
+
return config.pages || [];
|
| 79 |
+
} catch (error) {
|
| 80 |
+
console.error(`❌ Error reading configuration: ${error.message}`);
|
| 81 |
+
process.exit(1);
|
| 82 |
+
}
|
| 83 |
+
}
|
| 84 |
+
|
| 85 |
+
/**
|
| 86 |
+
* Convert a single Notion page to Markdown with advanced media handling
|
| 87 |
+
* @param {Object} notion - Notion client
|
| 88 |
+
* @param {string} pageId - Notion page ID
|
| 89 |
+
* @param {string} outputDir - Output directory
|
| 90 |
+
* @param {string} pageTitle - Page title for file naming
|
| 91 |
+
* @returns {Promise<string>} - Path to generated markdown file
|
| 92 |
+
*/
|
| 93 |
+
async function convertNotionPage(notion, pageId, outputDir, pageTitle) {
|
| 94 |
+
console.log(`📄 Converting Notion page: ${pageTitle} (${pageId})`);
|
| 95 |
+
|
| 96 |
+
try {
|
| 97 |
+
// Create media directory for this page
|
| 98 |
+
const mediaDir = join(outputDir, 'media', pageId);
|
| 99 |
+
ensureDirectory(mediaDir);
|
| 100 |
+
|
| 101 |
+
// Configure the DefaultExporter to save to a file
|
| 102 |
+
const outputFile = join(outputDir, `${pageTitle}.md`);
|
| 103 |
+
const exporter = new DefaultExporter({
|
| 104 |
+
outputType: 'file',
|
| 105 |
+
outputPath: outputFile,
|
| 106 |
+
});
|
| 107 |
+
|
| 108 |
+
// Create the converter with media downloading strategy
|
| 109 |
+
const n2m = new NotionConverter(notion)
|
| 110 |
+
.withExporter(exporter)
|
| 111 |
+
// Download media to local directory with path transformation
|
| 112 |
+
.downloadMediaTo({
|
| 113 |
+
outputDir: mediaDir,
|
| 114 |
+
// Transform paths to be web-accessible
|
| 115 |
+
transformPath: (localPath) => `/media/${pageId}/${basename(localPath)}`,
|
| 116 |
+
});
|
| 117 |
+
|
| 118 |
+
// Convert the page
|
| 119 |
+
const result = await n2m.convert(pageId);
|
| 120 |
+
|
| 121 |
+
console.log(` ✅ Converted to: ${outputFile}`);
|
| 122 |
+
console.log(` 📊 Content length: ${result.content.length} characters`);
|
| 123 |
+
console.log(` 🖼️ Media saved to: ${mediaDir}`);
|
| 124 |
+
|
| 125 |
+
return outputFile;
|
| 126 |
+
|
| 127 |
+
} catch (error) {
|
| 128 |
+
console.error(` ❌ Failed to convert page ${pageId}: ${error.message}`);
|
| 129 |
+
throw error;
|
| 130 |
+
}
|
| 131 |
+
}
|
| 132 |
+
|
| 133 |
+
/**
|
| 134 |
+
* Process Notion pages with advanced configuration
|
| 135 |
+
* @param {string} inputFile - Path to pages configuration
|
| 136 |
+
* @param {string} outputDir - Output directory
|
| 137 |
+
* @param {string} notionToken - Notion API token
|
| 138 |
+
*/
|
| 139 |
+
export async function convertNotionToMarkdown(inputFile, outputDir, notionToken) {
|
| 140 |
+
console.log('🚀 Notion to Markdown Converter');
|
| 141 |
+
console.log(`📁 Input: ${inputFile}`);
|
| 142 |
+
console.log(`📁 Output: ${outputDir}`);
|
| 143 |
+
|
| 144 |
+
// Validate Notion token
|
| 145 |
+
if (!notionToken) {
|
| 146 |
+
console.error('❌ NOTION_TOKEN not found. Please set it as environment variable or use --token=YOUR_TOKEN');
|
| 147 |
+
process.exit(1);
|
| 148 |
+
}
|
| 149 |
+
|
| 150 |
+
// Ensure output directory exists
|
| 151 |
+
ensureDirectory(outputDir);
|
| 152 |
+
|
| 153 |
+
try {
|
| 154 |
+
// Initialize Notion client
|
| 155 |
+
const notion = new Client({
|
| 156 |
+
auth: notionToken,
|
| 157 |
+
});
|
| 158 |
+
|
| 159 |
+
// Load pages configuration
|
| 160 |
+
const pages = loadPagesConfig(inputFile);
|
| 161 |
+
console.log(`📋 Found ${pages.length} page(s) to convert`);
|
| 162 |
+
|
| 163 |
+
const convertedFiles = [];
|
| 164 |
+
|
| 165 |
+
// Convert each page
|
| 166 |
+
for (const page of pages) {
|
| 167 |
+
try {
|
| 168 |
+
const outputFile = await convertNotionPage(
|
| 169 |
+
notion,
|
| 170 |
+
page.id,
|
| 171 |
+
outputDir,
|
| 172 |
+
page.slug || page.title?.toLowerCase().replace(/\s+/g, '-') || page.id
|
| 173 |
+
);
|
| 174 |
+
convertedFiles.push(outputFile);
|
| 175 |
+
} catch (error) {
|
| 176 |
+
console.error(`❌ Failed to convert page ${page.id}: ${error.message}`);
|
| 177 |
+
// Continue with other pages
|
| 178 |
+
}
|
| 179 |
+
}
|
| 180 |
+
|
| 181 |
+
// Post-process all converted files
|
| 182 |
+
console.log('🔧 Post-processing converted files...');
|
| 183 |
+
for (const file of convertedFiles) {
|
| 184 |
+
try {
|
| 185 |
+
let content = readFileSync(file, 'utf8');
|
| 186 |
+
content = postProcessMarkdown(content);
|
| 187 |
+
writeFileSync(file, content);
|
| 188 |
+
console.log(` ✅ Post-processed: ${basename(file)}`);
|
| 189 |
+
} catch (error) {
|
| 190 |
+
console.error(` ❌ Failed to post-process ${file}: ${error.message}`);
|
| 191 |
+
}
|
| 192 |
+
}
|
| 193 |
+
|
| 194 |
+
console.log(`✅ Conversion completed! ${convertedFiles.length} file(s) generated`);
|
| 195 |
+
|
| 196 |
+
} catch (error) {
|
| 197 |
+
console.error('❌ Conversion failed:', error.message);
|
| 198 |
+
process.exit(1);
|
| 199 |
+
}
|
| 200 |
+
}
|
| 201 |
+
|
| 202 |
+
function main() {
|
| 203 |
+
const config = parseArgs();
|
| 204 |
+
|
| 205 |
+
if (config.clean) {
|
| 206 |
+
console.log('🧹 Cleaning output directory...');
|
| 207 |
+
// Clean output directory logic would go here
|
| 208 |
+
}
|
| 209 |
+
|
| 210 |
+
convertNotionToMarkdown(config.input, config.output, config.token);
|
| 211 |
+
console.log('🎉 Notion conversion completed!');
|
| 212 |
+
}
|
| 213 |
+
|
| 214 |
+
// Show help if requested
|
| 215 |
+
if (process.argv.includes('--help') || process.argv.includes('-h')) {
|
| 216 |
+
console.log(`
|
| 217 |
+
🚀 Notion to Markdown Converter
|
| 218 |
+
|
| 219 |
+
Usage:
|
| 220 |
+
node notion-converter.mjs [options]
|
| 221 |
+
|
| 222 |
+
Options:
|
| 223 |
+
--input=PATH Input pages configuration file (default: input/pages.json)
|
| 224 |
+
--output=PATH Output directory (default: output/)
|
| 225 |
+
--token=TOKEN Notion API token (or set NOTION_TOKEN env var)
|
| 226 |
+
--clean Clean output directory before conversion
|
| 227 |
+
--help, -h Show this help
|
| 228 |
+
|
| 229 |
+
Environment Variables:
|
| 230 |
+
NOTION_TOKEN Your Notion integration token
|
| 231 |
+
|
| 232 |
+
Examples:
|
| 233 |
+
# Basic conversion with environment token
|
| 234 |
+
NOTION_TOKEN=your_token node notion-converter.mjs
|
| 235 |
+
|
| 236 |
+
# Custom paths and token
|
| 237 |
+
node notion-converter.mjs --input=my-pages.json --output=converted/ --token=your_token
|
| 238 |
+
|
| 239 |
+
# Clean output first
|
| 240 |
+
node notion-converter.mjs --clean
|
| 241 |
+
|
| 242 |
+
Configuration File Format (pages.json):
|
| 243 |
+
{
|
| 244 |
+
"pages": [
|
| 245 |
+
{
|
| 246 |
+
"id": "your-notion-page-id",
|
| 247 |
+
"title": "Page Title",
|
| 248 |
+
"slug": "page-slug"
|
| 249 |
+
}
|
| 250 |
+
]
|
| 251 |
+
}
|
| 252 |
+
`);
|
| 253 |
+
process.exit(0);
|
| 254 |
+
}
|
| 255 |
+
|
| 256 |
+
// Run CLI if called directly
|
| 257 |
+
if (import.meta.url === `file://${process.argv[1]}`) {
|
| 258 |
+
main();
|
| 259 |
+
}
|
app/scripts/notion-importer/notion-metadata-extractor.mjs
ADDED
|
@@ -0,0 +1,303 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env node
|
| 2 |
+
|
| 3 |
+
import { Client } from '@notionhq/client';
|
| 4 |
+
|
| 5 |
+
/**
|
| 6 |
+
* Notion Metadata Extractor
|
| 7 |
+
* Extracts document metadata from Notion pages for frontmatter generation
|
| 8 |
+
*/
|
| 9 |
+
|
| 10 |
+
/**
|
| 11 |
+
* Extract metadata from Notion page
|
| 12 |
+
* @param {string} pageId - Notion page ID
|
| 13 |
+
* @param {string} notionToken - Notion API token
|
| 14 |
+
* @returns {object} - Extracted metadata object
|
| 15 |
+
*/
|
| 16 |
+
export async function extractNotionMetadata(pageId, notionToken) {
|
| 17 |
+
const notion = new Client({
|
| 18 |
+
auth: notionToken,
|
| 19 |
+
});
|
| 20 |
+
|
| 21 |
+
const metadata = {};
|
| 22 |
+
|
| 23 |
+
try {
|
| 24 |
+
// Get page information
|
| 25 |
+
const page = await notion.pages.retrieve({ page_id: pageId });
|
| 26 |
+
|
| 27 |
+
// Extract title from page properties
|
| 28 |
+
if (page.properties.title && page.properties.title.title && page.properties.title.title.length > 0) {
|
| 29 |
+
metadata.title = page.properties.title.title[0].plain_text;
|
| 30 |
+
}
|
| 31 |
+
|
| 32 |
+
// Extract creation date
|
| 33 |
+
if (page.created_time) {
|
| 34 |
+
metadata.published = new Date(page.created_time).toLocaleDateString('en-US', {
|
| 35 |
+
year: 'numeric',
|
| 36 |
+
month: 'short',
|
| 37 |
+
day: '2-digit'
|
| 38 |
+
});
|
| 39 |
+
metadata.created_time = page.created_time;
|
| 40 |
+
}
|
| 41 |
+
|
| 42 |
+
// Extract last edited date
|
| 43 |
+
if (page.last_edited_time) {
|
| 44 |
+
metadata.last_edited_time = page.last_edited_time;
|
| 45 |
+
}
|
| 46 |
+
|
| 47 |
+
// Extract created by
|
| 48 |
+
if (page.created_by && page.created_by.id) {
|
| 49 |
+
metadata.created_by = page.created_by.id;
|
| 50 |
+
}
|
| 51 |
+
|
| 52 |
+
// Extract last edited by
|
| 53 |
+
if (page.last_edited_by && page.last_edited_by.id) {
|
| 54 |
+
metadata.last_edited_by = page.last_edited_by.id;
|
| 55 |
+
}
|
| 56 |
+
|
| 57 |
+
// Extract page URL
|
| 58 |
+
metadata.notion_url = page.url;
|
| 59 |
+
|
| 60 |
+
// Extract page ID
|
| 61 |
+
metadata.notion_id = page.id;
|
| 62 |
+
|
| 63 |
+
// Extract parent information
|
| 64 |
+
if (page.parent) {
|
| 65 |
+
metadata.parent = {
|
| 66 |
+
type: page.parent.type,
|
| 67 |
+
id: page.parent[page.parent.type]?.id || page.parent[page.parent.type]
|
| 68 |
+
};
|
| 69 |
+
}
|
| 70 |
+
|
| 71 |
+
// Extract cover image if available
|
| 72 |
+
if (page.cover) {
|
| 73 |
+
metadata.cover = {
|
| 74 |
+
type: page.cover.type,
|
| 75 |
+
url: page.cover[page.cover.type]?.url || page.cover[page.cover.type]
|
| 76 |
+
};
|
| 77 |
+
}
|
| 78 |
+
|
| 79 |
+
// Extract icon if available
|
| 80 |
+
if (page.icon) {
|
| 81 |
+
metadata.icon = {
|
| 82 |
+
type: page.icon.type,
|
| 83 |
+
emoji: page.icon.emoji,
|
| 84 |
+
url: page.icon.external?.url || page.icon.file?.url
|
| 85 |
+
};
|
| 86 |
+
}
|
| 87 |
+
|
| 88 |
+
// Extract authors and custom properties
|
| 89 |
+
const customProperties = {};
|
| 90 |
+
for (const [key, value] of Object.entries(page.properties)) {
|
| 91 |
+
if (key !== 'title') { // Skip title as it's handled separately
|
| 92 |
+
const extractedValue = extractPropertyValue(value);
|
| 93 |
+
|
| 94 |
+
// Check for author-related properties
|
| 95 |
+
if (key.toLowerCase().includes('author') ||
|
| 96 |
+
key.toLowerCase().includes('writer') ||
|
| 97 |
+
key.toLowerCase().includes('creator') ||
|
| 98 |
+
value.type === 'people') {
|
| 99 |
+
metadata.authors = extractedValue;
|
| 100 |
+
} else {
|
| 101 |
+
customProperties[key] = extractedValue;
|
| 102 |
+
}
|
| 103 |
+
}
|
| 104 |
+
}
|
| 105 |
+
|
| 106 |
+
// If no authors found in properties, try to get from created_by
|
| 107 |
+
if (!metadata.authors && page.created_by) {
|
| 108 |
+
try {
|
| 109 |
+
const user = await notion.users.retrieve({ user_id: page.created_by.id });
|
| 110 |
+
metadata.authors = [{
|
| 111 |
+
name: user.name || user.id,
|
| 112 |
+
id: user.id
|
| 113 |
+
}];
|
| 114 |
+
} catch (error) {
|
| 115 |
+
console.log(' ⚠️ Could not fetch author from created_by:', error.message);
|
| 116 |
+
// Fallback to basic info
|
| 117 |
+
metadata.authors = [{
|
| 118 |
+
name: page.created_by.name || page.created_by.id,
|
| 119 |
+
id: page.created_by.id
|
| 120 |
+
}];
|
| 121 |
+
}
|
| 122 |
+
}
|
| 123 |
+
|
| 124 |
+
if (Object.keys(customProperties).length > 0) {
|
| 125 |
+
metadata.properties = customProperties;
|
| 126 |
+
}
|
| 127 |
+
|
| 128 |
+
// Try to extract description from page content (first paragraph)
|
| 129 |
+
try {
|
| 130 |
+
const blocks = await notion.blocks.children.list({ block_id: pageId });
|
| 131 |
+
const firstParagraph = blocks.results.find(block =>
|
| 132 |
+
block.type === 'paragraph' &&
|
| 133 |
+
block.paragraph.rich_text &&
|
| 134 |
+
block.paragraph.rich_text.length > 0
|
| 135 |
+
);
|
| 136 |
+
|
| 137 |
+
if (firstParagraph) {
|
| 138 |
+
const description = firstParagraph.paragraph.rich_text
|
| 139 |
+
.map(text => text.plain_text)
|
| 140 |
+
.join('')
|
| 141 |
+
.trim();
|
| 142 |
+
|
| 143 |
+
if (description && description.length > 0) {
|
| 144 |
+
metadata.description = description.substring(0, 200) + (description.length > 200 ? '...' : '');
|
| 145 |
+
}
|
| 146 |
+
}
|
| 147 |
+
} catch (error) {
|
| 148 |
+
console.log(' ⚠️ Could not extract description from page content');
|
| 149 |
+
}
|
| 150 |
+
|
| 151 |
+
// Generate tags from page properties
|
| 152 |
+
const tags = [];
|
| 153 |
+
for (const [key, value] of Object.entries(page.properties)) {
|
| 154 |
+
if (value.type === 'multi_select' && value.multi_select) {
|
| 155 |
+
value.multi_select.forEach(option => {
|
| 156 |
+
tags.push(option.name);
|
| 157 |
+
});
|
| 158 |
+
} else if (value.type === 'select' && value.select) {
|
| 159 |
+
tags.push(value.select.name);
|
| 160 |
+
}
|
| 161 |
+
}
|
| 162 |
+
|
| 163 |
+
if (tags.length > 0) {
|
| 164 |
+
metadata.tags = tags;
|
| 165 |
+
}
|
| 166 |
+
|
| 167 |
+
} catch (error) {
|
| 168 |
+
console.error('Error extracting Notion metadata:', error.message);
|
| 169 |
+
// Return basic metadata if extraction fails
|
| 170 |
+
metadata.title = "Notion Article";
|
| 171 |
+
metadata.published = new Date().toLocaleDateString('en-US', {
|
| 172 |
+
year: 'numeric',
|
| 173 |
+
month: 'short',
|
| 174 |
+
day: '2-digit'
|
| 175 |
+
});
|
| 176 |
+
}
|
| 177 |
+
|
| 178 |
+
return metadata;
|
| 179 |
+
}
|
| 180 |
+
|
| 181 |
+
/**
|
| 182 |
+
* Extract value from Notion property
|
| 183 |
+
* @param {object} property - Notion property object
|
| 184 |
+
* @returns {any} - Extracted value
|
| 185 |
+
*/
|
| 186 |
+
function extractPropertyValue(property) {
|
| 187 |
+
switch (property.type) {
|
| 188 |
+
case 'rich_text':
|
| 189 |
+
return property.rich_text.map(text => text.plain_text).join('');
|
| 190 |
+
case 'title':
|
| 191 |
+
return property.title.map(text => text.plain_text).join('');
|
| 192 |
+
case 'number':
|
| 193 |
+
return property.number;
|
| 194 |
+
case 'select':
|
| 195 |
+
return property.select?.name || null;
|
| 196 |
+
case 'multi_select':
|
| 197 |
+
return property.multi_select.map(option => option.name);
|
| 198 |
+
case 'date':
|
| 199 |
+
return property.date?.start || null;
|
| 200 |
+
case 'checkbox':
|
| 201 |
+
return property.checkbox;
|
| 202 |
+
case 'url':
|
| 203 |
+
return property.url;
|
| 204 |
+
case 'email':
|
| 205 |
+
return property.email;
|
| 206 |
+
case 'phone_number':
|
| 207 |
+
return property.phone_number;
|
| 208 |
+
case 'created_time':
|
| 209 |
+
return property.created_time;
|
| 210 |
+
case 'created_by':
|
| 211 |
+
return property.created_by?.id || null;
|
| 212 |
+
case 'last_edited_time':
|
| 213 |
+
return property.last_edited_time;
|
| 214 |
+
case 'last_edited_by':
|
| 215 |
+
return property.last_edited_by?.id || null;
|
| 216 |
+
case 'people':
|
| 217 |
+
return property.people.map(person => ({
|
| 218 |
+
name: person.name || person.id,
|
| 219 |
+
id: person.id
|
| 220 |
+
}));
|
| 221 |
+
default:
|
| 222 |
+
return null;
|
| 223 |
+
}
|
| 224 |
+
}
|
| 225 |
+
|
| 226 |
+
/**
|
| 227 |
+
* Generate YAML frontmatter from metadata object
|
| 228 |
+
* @param {object} metadata - Metadata object
|
| 229 |
+
* @returns {string} - YAML frontmatter string
|
| 230 |
+
*/
|
| 231 |
+
export function generateNotionFrontmatter(metadata) {
|
| 232 |
+
let frontmatter = '---\n';
|
| 233 |
+
|
| 234 |
+
// Title
|
| 235 |
+
if (metadata.title) {
|
| 236 |
+
frontmatter += `title: "${metadata.title}"\n`;
|
| 237 |
+
}
|
| 238 |
+
|
| 239 |
+
// Description
|
| 240 |
+
if (metadata.description) {
|
| 241 |
+
frontmatter += `description: "${metadata.description}"\n`;
|
| 242 |
+
}
|
| 243 |
+
|
| 244 |
+
// Publication date
|
| 245 |
+
if (metadata.published) {
|
| 246 |
+
frontmatter += `published: "${metadata.published}"\n`;
|
| 247 |
+
}
|
| 248 |
+
|
| 249 |
+
// Authors
|
| 250 |
+
if (metadata.authors && metadata.authors.length > 0) {
|
| 251 |
+
frontmatter += 'authors:\n';
|
| 252 |
+
metadata.authors.forEach(author => {
|
| 253 |
+
if (typeof author === 'string') {
|
| 254 |
+
frontmatter += ` - name: "${author}"\n`;
|
| 255 |
+
} else if (author.name) {
|
| 256 |
+
frontmatter += ` - name: "${author.name}"\n`;
|
| 257 |
+
}
|
| 258 |
+
});
|
| 259 |
+
}
|
| 260 |
+
|
| 261 |
+
// Tags
|
| 262 |
+
if (metadata.tags && metadata.tags.length > 0) {
|
| 263 |
+
frontmatter += 'tags:\n';
|
| 264 |
+
metadata.tags.forEach(tag => {
|
| 265 |
+
frontmatter += ` - "${tag}"\n`;
|
| 266 |
+
});
|
| 267 |
+
}
|
| 268 |
+
|
| 269 |
+
// Notion metadata removed - keeping only standard frontmatter fields
|
| 270 |
+
|
| 271 |
+
// Cover image
|
| 272 |
+
if (metadata.cover && metadata.cover.url) {
|
| 273 |
+
frontmatter += `cover: "${metadata.cover.url}"\n`;
|
| 274 |
+
}
|
| 275 |
+
|
| 276 |
+
// Icon
|
| 277 |
+
if (metadata.icon) {
|
| 278 |
+
if (metadata.icon.emoji) {
|
| 279 |
+
frontmatter += `icon: "${metadata.icon.emoji}"\n`;
|
| 280 |
+
} else if (metadata.icon.url) {
|
| 281 |
+
frontmatter += `icon: "${metadata.icon.url}"\n`;
|
| 282 |
+
}
|
| 283 |
+
}
|
| 284 |
+
|
| 285 |
+
// Custom properties removed - keeping frontmatter clean and standard
|
| 286 |
+
|
| 287 |
+
// Default Astro configuration
|
| 288 |
+
frontmatter += 'tableOfContentsAutoCollapse: true\n';
|
| 289 |
+
frontmatter += '---\n\n';
|
| 290 |
+
|
| 291 |
+
return frontmatter;
|
| 292 |
+
}
|
| 293 |
+
|
| 294 |
+
/**
|
| 295 |
+
* Extract and generate frontmatter from Notion page
|
| 296 |
+
* @param {string} pageId - Notion page ID
|
| 297 |
+
* @param {string} notionToken - Notion API token
|
| 298 |
+
* @returns {string} - Complete YAML frontmatter
|
| 299 |
+
*/
|
| 300 |
+
export async function extractAndGenerateNotionFrontmatter(pageId, notionToken) {
|
| 301 |
+
const metadata = await extractNotionMetadata(pageId, notionToken);
|
| 302 |
+
return generateNotionFrontmatter(metadata);
|
| 303 |
+
}
|
app/scripts/notion-importer/output/.temp-pages.json
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"pages": [
|
| 3 |
+
{
|
| 4 |
+
"id": "27877f1c9c9d804d9c82f7b3905578ff",
|
| 5 |
+
"title": "smol",
|
| 6 |
+
"slug": "smol"
|
| 7 |
+
}
|
| 8 |
+
]
|
| 9 |
+
}
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8013-b668-f14bd1ac0ec0.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8014-834f-d700b623256b.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-801d-841a-e35011491566.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8031-ac8d-c5678af1bdd5.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8048-9b7e-db4fa7485915.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-804d-bd0a-e0b1c15e504f.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8075-ae2e-dc24fe9296ca.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-8078-b6da-c7a4c67c8f35.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-808d-9c6d-fae817ac8868.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-808f-b712-c7c608da3fc6.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80a9-b4d0-f2129716632d.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80aa-b968-c54c9fe7e5d7.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80b6-be07-e8646502f82a.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80b9-8cfb-f0a6aaaa8760.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80e7-a500-fb79cebde7e3.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/media/27877f1c9c9d804d9c82f7b3905578ff/image_27877f1c-9c9d-80e9-b729-dbd328930bed.png
ADDED
|
Git LFS Details
|
app/scripts/notion-importer/output/smol-training-guide.md
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
app/scripts/notion-importer/output/smol-training-guide.mdx
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
app/scripts/notion-importer/output/smol.md
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
app/scripts/notion-importer/output/smol.mdx
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
app/scripts/notion-importer/package-lock.json
ADDED
|
Binary file (89.3 kB). View file
|
|
|
app/scripts/notion-importer/package.json
ADDED
|
Binary file (1.19 kB). View file
|
|
|
app/scripts/notion-importer/post-processor.mjs
ADDED
|
@@ -0,0 +1,369 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env node
|
| 2 |
+
|
| 3 |
+
import { readFileSync, writeFileSync, existsSync } from 'fs';
|
| 4 |
+
import { join, dirname, basename } from 'path';
|
| 5 |
+
import { fileURLToPath } from 'url';
|
| 6 |
+
|
| 7 |
+
const __filename = fileURLToPath(import.meta.url);
|
| 8 |
+
const __dirname = dirname(__filename);
|
| 9 |
+
|
| 10 |
+
/**
|
| 11 |
+
* Post-process Notion-generated Markdown for better MDX compatibility
|
| 12 |
+
* @param {string} content - Raw markdown content from Notion
|
| 13 |
+
* @returns {string} - Processed markdown content
|
| 14 |
+
*/
|
| 15 |
+
export function postProcessMarkdown(content) {
|
| 16 |
+
console.log('🔧 Post-processing Notion Markdown for MDX compatibility...');
|
| 17 |
+
|
| 18 |
+
let processedContent = content;
|
| 19 |
+
|
| 20 |
+
// Apply each transformation step
|
| 21 |
+
processedContent = cleanNotionArtifacts(processedContent);
|
| 22 |
+
processedContent = fixNotionLinks(processedContent);
|
| 23 |
+
processedContent = optimizeImages(processedContent);
|
| 24 |
+
processedContent = shiftHeadingLevels(processedContent);
|
| 25 |
+
processedContent = cleanEmptyLines(processedContent);
|
| 26 |
+
processedContent = fixCodeBlocks(processedContent);
|
| 27 |
+
processedContent = fixCodeBlockEndings(processedContent);
|
| 28 |
+
processedContent = optimizeTables(processedContent);
|
| 29 |
+
|
| 30 |
+
return processedContent;
|
| 31 |
+
}
|
| 32 |
+
|
| 33 |
+
/**
|
| 34 |
+
* Clean Notion-specific artifacts and formatting
|
| 35 |
+
* @param {string} content - Markdown content
|
| 36 |
+
* @returns {string} - Cleaned content
|
| 37 |
+
*/
|
| 38 |
+
function cleanNotionArtifacts(content) {
|
| 39 |
+
console.log(' 🧹 Cleaning Notion artifacts...');
|
| 40 |
+
|
| 41 |
+
let cleanedCount = 0;
|
| 42 |
+
|
| 43 |
+
// Remove Notion's internal page references that don't convert well
|
| 44 |
+
content = content.replace(/\[([^\]]+)\]\(https:\/\/www\.notion\.so\/[^)]+\)/g, (match, text) => {
|
| 45 |
+
cleanedCount++;
|
| 46 |
+
return text; // Keep just the text, remove the broken link
|
| 47 |
+
});
|
| 48 |
+
|
| 49 |
+
// Clean up Notion's callout blocks that might not render properly
|
| 50 |
+
content = content.replace(/^> \*\*([^*]+)\*\*\s*\n/gm, '> **$1**\n\n');
|
| 51 |
+
|
| 52 |
+
// Remove Notion's page dividers that don't have markdown equivalents
|
| 53 |
+
content = content.replace(/^---+\s*$/gm, '');
|
| 54 |
+
|
| 55 |
+
// Clean up empty blockquotes
|
| 56 |
+
content = content.replace(/^>\s*$/gm, '');
|
| 57 |
+
|
| 58 |
+
if (cleanedCount > 0) {
|
| 59 |
+
console.log(` ✅ Cleaned ${cleanedCount} Notion artifact(s)`);
|
| 60 |
+
}
|
| 61 |
+
|
| 62 |
+
return content;
|
| 63 |
+
}
|
| 64 |
+
|
| 65 |
+
/**
|
| 66 |
+
* Fix Notion internal links to be more MDX-friendly
|
| 67 |
+
* @param {string} content - Markdown content
|
| 68 |
+
* @returns {string} - Content with fixed links
|
| 69 |
+
*/
|
| 70 |
+
function fixNotionLinks(content) {
|
| 71 |
+
console.log(' 🔗 Fixing Notion internal links...');
|
| 72 |
+
|
| 73 |
+
let fixedCount = 0;
|
| 74 |
+
|
| 75 |
+
// Convert Notion page links to relative links (assuming they'll be converted to MDX)
|
| 76 |
+
content = content.replace(/\[([^\]]+)\]\(https:\/\/www\.notion\.so\/[^/]+\/([^?#)]+)\)/g, (match, text, pageId) => {
|
| 77 |
+
fixedCount++;
|
| 78 |
+
// Convert to relative link - this will need to be updated based on your routing
|
| 79 |
+
return `[${text}](#${pageId})`;
|
| 80 |
+
});
|
| 81 |
+
|
| 82 |
+
// Fix broken notion.so links that might be malformed
|
| 83 |
+
content = content.replace(/\[([^\]]+)\]\(https:\/\/www\.notion\.so\/[^)]*\)/g, (match, text) => {
|
| 84 |
+
fixedCount++;
|
| 85 |
+
return text; // Remove broken links, keep text
|
| 86 |
+
});
|
| 87 |
+
|
| 88 |
+
if (fixedCount > 0) {
|
| 89 |
+
console.log(` ✅ Fixed ${fixedCount} Notion link(s)`);
|
| 90 |
+
}
|
| 91 |
+
|
| 92 |
+
return content;
|
| 93 |
+
}
|
| 94 |
+
|
| 95 |
+
/**
|
| 96 |
+
* Optimize images for better MDX compatibility
|
| 97 |
+
* @param {string} content - Markdown content
|
| 98 |
+
* @returns {string} - Content with optimized images
|
| 99 |
+
*/
|
| 100 |
+
function optimizeImages(content) {
|
| 101 |
+
console.log(' 🖼️ Optimizing images...');
|
| 102 |
+
|
| 103 |
+
let optimizedCount = 0;
|
| 104 |
+
|
| 105 |
+
// Ensure images have proper alt text
|
| 106 |
+
content = content.replace(/!\[\]\(([^)]+)\)/g, (match, src) => {
|
| 107 |
+
optimizedCount++;
|
| 108 |
+
const filename = basename(src);
|
| 109 |
+
return ``;
|
| 110 |
+
});
|
| 111 |
+
|
| 112 |
+
// Clean up image paths that might have query parameters
|
| 113 |
+
content = content.replace(/!\[([^\]]*)\]\(([^)]+)\?[^)]*\)/g, (match, alt, src) => {
|
| 114 |
+
optimizedCount++;
|
| 115 |
+
return ``;
|
| 116 |
+
});
|
| 117 |
+
|
| 118 |
+
if (optimizedCount > 0) {
|
| 119 |
+
console.log(` ✅ Optimized ${optimizedCount} image(s)`);
|
| 120 |
+
}
|
| 121 |
+
|
| 122 |
+
return content;
|
| 123 |
+
}
|
| 124 |
+
|
| 125 |
+
/**
|
| 126 |
+
* Shift all heading levels down by one (H1 → H2, H2 → H3, etc.)
|
| 127 |
+
* @param {string} content - Markdown content
|
| 128 |
+
* @returns {string} - Content with shifted heading levels
|
| 129 |
+
*/
|
| 130 |
+
function shiftHeadingLevels(content) {
|
| 131 |
+
console.log(' 📝 Shifting heading levels down by one...');
|
| 132 |
+
|
| 133 |
+
let shiftedCount = 0;
|
| 134 |
+
|
| 135 |
+
// Shift heading levels: H1 → H2, H2 → H3, H3 → H4, H4 → H5, H5 → H6
|
| 136 |
+
// Process from highest to lowest to avoid conflicts
|
| 137 |
+
content = content.replace(/^##### (.*$)/gim, '###### $1');
|
| 138 |
+
content = content.replace(/^#### (.*$)/gim, '##### $1');
|
| 139 |
+
content = content.replace(/^### (.*$)/gim, '#### $1');
|
| 140 |
+
content = content.replace(/^## (.*$)/gim, '### $1');
|
| 141 |
+
content = content.replace(/^# (.*$)/gim, '## $1');
|
| 142 |
+
|
| 143 |
+
// Count the number of headings shifted
|
| 144 |
+
const headingMatches = content.match(/^#{1,6} /gm);
|
| 145 |
+
if (headingMatches) {
|
| 146 |
+
shiftedCount = headingMatches.length;
|
| 147 |
+
}
|
| 148 |
+
|
| 149 |
+
console.log(` ✅ Shifted ${shiftedCount} heading level(s)`);
|
| 150 |
+
return content;
|
| 151 |
+
}
|
| 152 |
+
|
| 153 |
+
/**
|
| 154 |
+
* Fix code block endings that end with "text" instead of proper closing
|
| 155 |
+
* @param {string} content - Markdown content
|
| 156 |
+
* @returns {string} - Content with fixed code block endings
|
| 157 |
+
*/
|
| 158 |
+
function fixCodeBlockEndings(content) {
|
| 159 |
+
console.log(' 💻 Fixing code block endings...');
|
| 160 |
+
|
| 161 |
+
let fixedCount = 0;
|
| 162 |
+
|
| 163 |
+
// Fix code blocks that end with ```text instead of ```
|
| 164 |
+
content = content.replace(/```text\n/g, '```\n');
|
| 165 |
+
|
| 166 |
+
// Count the number of fixes
|
| 167 |
+
const textEndingMatches = content.match(/```text\n/g);
|
| 168 |
+
if (textEndingMatches) {
|
| 169 |
+
fixedCount = textEndingMatches.length;
|
| 170 |
+
}
|
| 171 |
+
|
| 172 |
+
if (fixedCount > 0) {
|
| 173 |
+
console.log(` ✅ Fixed ${fixedCount} code block ending(s)`);
|
| 174 |
+
}
|
| 175 |
+
|
| 176 |
+
return content;
|
| 177 |
+
}
|
| 178 |
+
|
| 179 |
+
/**
|
| 180 |
+
* Clean up excessive empty lines
|
| 181 |
+
* @param {string} content - Markdown content
|
| 182 |
+
* @returns {string} - Content with cleaned spacing
|
| 183 |
+
*/
|
| 184 |
+
function cleanEmptyLines(content) {
|
| 185 |
+
console.log(' 📝 Cleaning excessive empty lines...');
|
| 186 |
+
|
| 187 |
+
// Replace 3+ consecutive newlines with 2 newlines
|
| 188 |
+
const cleanedContent = content.replace(/\n{3,}/g, '\n\n');
|
| 189 |
+
|
| 190 |
+
const originalLines = content.split('\n').length;
|
| 191 |
+
const cleanedLines = cleanedContent.split('\n').length;
|
| 192 |
+
const removedLines = originalLines - cleanedLines;
|
| 193 |
+
|
| 194 |
+
if (removedLines > 0) {
|
| 195 |
+
console.log(` ✅ Removed ${removedLines} excessive empty line(s)`);
|
| 196 |
+
}
|
| 197 |
+
|
| 198 |
+
return cleanedContent;
|
| 199 |
+
}
|
| 200 |
+
|
| 201 |
+
/**
|
| 202 |
+
* Fix code blocks for better MDX compatibility
|
| 203 |
+
* @param {string} content - Markdown content
|
| 204 |
+
* @returns {string} - Content with fixed code blocks
|
| 205 |
+
*/
|
| 206 |
+
function fixCodeBlocks(content) {
|
| 207 |
+
console.log(' 💻 Fixing code blocks...');
|
| 208 |
+
|
| 209 |
+
let fixedCount = 0;
|
| 210 |
+
|
| 211 |
+
// Ensure code blocks have proper language identifiers
|
| 212 |
+
content = content.replace(/^```\s*$/gm, '```text');
|
| 213 |
+
|
| 214 |
+
// Fix code blocks that might have Notion-specific formatting
|
| 215 |
+
content = content.replace(/^```(\w+)\s*\n([\s\S]*?)\n```$/gm, (match, lang, code) => {
|
| 216 |
+
// Clean up any Notion artifacts in code
|
| 217 |
+
const cleanCode = code.replace(/\u00A0/g, ' '); // Replace non-breaking spaces
|
| 218 |
+
return `\`\`\`${lang}\n${cleanCode}\n\`\`\``;
|
| 219 |
+
});
|
| 220 |
+
|
| 221 |
+
if (fixedCount > 0) {
|
| 222 |
+
console.log(` ✅ Fixed ${fixedCount} code block(s)`);
|
| 223 |
+
}
|
| 224 |
+
|
| 225 |
+
return content;
|
| 226 |
+
}
|
| 227 |
+
|
| 228 |
+
/**
|
| 229 |
+
* Optimize tables for better MDX rendering
|
| 230 |
+
* @param {string} content - Markdown content
|
| 231 |
+
* @returns {string} - Content with optimized tables
|
| 232 |
+
*/
|
| 233 |
+
function optimizeTables(content) {
|
| 234 |
+
console.log(' 📊 Optimizing tables...');
|
| 235 |
+
|
| 236 |
+
let optimizedCount = 0;
|
| 237 |
+
|
| 238 |
+
// Fix tables that might have inconsistent column counts
|
| 239 |
+
content = content.replace(/^\|(.+)\|\s*$/gm, (match, row) => {
|
| 240 |
+
const cells = row.split('|').map(cell => cell.trim());
|
| 241 |
+
const cleanCells = cells.filter(cell => cell.length > 0);
|
| 242 |
+
|
| 243 |
+
if (cleanCells.length > 0) {
|
| 244 |
+
optimizedCount++;
|
| 245 |
+
return `| ${cleanCells.join(' | ')} |`;
|
| 246 |
+
}
|
| 247 |
+
return match;
|
| 248 |
+
});
|
| 249 |
+
|
| 250 |
+
// Ensure table headers are properly formatted
|
| 251 |
+
content = content.replace(/^\|(.+)\|\s*\n\|([-:\s|]+)\|\s*$/gm, (match, header, separator) => {
|
| 252 |
+
const headerCells = header.split('|').map(cell => cell.trim()).filter(cell => cell.length > 0);
|
| 253 |
+
const separatorCells = separator.split('|').map(cell => cell.trim()).filter(cell => cell.length > 0);
|
| 254 |
+
|
| 255 |
+
if (headerCells.length !== separatorCells.length) {
|
| 256 |
+
optimizedCount++;
|
| 257 |
+
const newSeparator = headerCells.map(() => '---').join(' | ');
|
| 258 |
+
return `| ${headerCells.join(' | ')} |\n| ${newSeparator} |`;
|
| 259 |
+
}
|
| 260 |
+
return match;
|
| 261 |
+
});
|
| 262 |
+
|
| 263 |
+
if (optimizedCount > 0) {
|
| 264 |
+
console.log(` ✅ Optimized ${optimizedCount} table(s)`);
|
| 265 |
+
}
|
| 266 |
+
|
| 267 |
+
return content;
|
| 268 |
+
}
|
| 269 |
+
|
| 270 |
+
/**
|
| 271 |
+
* Extract frontmatter from Notion page properties
|
| 272 |
+
* @param {Object} pageProperties - Notion page properties
|
| 273 |
+
* @returns {string} - YAML frontmatter
|
| 274 |
+
*/
|
| 275 |
+
export function generateFrontmatter(pageProperties) {
|
| 276 |
+
console.log(' 📄 Generating frontmatter from Notion properties...');
|
| 277 |
+
|
| 278 |
+
const frontmatter = {
|
| 279 |
+
title: pageProperties.title || 'Untitled',
|
| 280 |
+
published: new Date().toISOString().split('T')[0],
|
| 281 |
+
tableOfContentsAutoCollapse: true
|
| 282 |
+
};
|
| 283 |
+
|
| 284 |
+
// Add other properties if they exist
|
| 285 |
+
if (pageProperties.description) {
|
| 286 |
+
frontmatter.description = pageProperties.description;
|
| 287 |
+
}
|
| 288 |
+
if (pageProperties.tags) {
|
| 289 |
+
frontmatter.tags = pageProperties.tags;
|
| 290 |
+
}
|
| 291 |
+
if (pageProperties.author) {
|
| 292 |
+
frontmatter.author = pageProperties.author;
|
| 293 |
+
}
|
| 294 |
+
|
| 295 |
+
// Convert to YAML string
|
| 296 |
+
const yamlLines = Object.entries(frontmatter)
|
| 297 |
+
.map(([key, value]) => {
|
| 298 |
+
if (Array.isArray(value)) {
|
| 299 |
+
return `${key}:\n${value.map(v => ` - ${v}`).join('\n')}`;
|
| 300 |
+
}
|
| 301 |
+
return `${key}: "${value}"`;
|
| 302 |
+
});
|
| 303 |
+
|
| 304 |
+
return `---\n${yamlLines.join('\n')}\n---\n\n`;
|
| 305 |
+
}
|
| 306 |
+
|
| 307 |
+
function main() {
|
| 308 |
+
const args = process.argv.slice(2);
|
| 309 |
+
|
| 310 |
+
if (args.includes('--help') || args.includes('-h')) {
|
| 311 |
+
console.log(`
|
| 312 |
+
🔧 Notion Markdown Post-Processor
|
| 313 |
+
|
| 314 |
+
Usage:
|
| 315 |
+
node post-processor.mjs [options] [input-file] [output-file]
|
| 316 |
+
|
| 317 |
+
Options:
|
| 318 |
+
--verbose Show detailed processing information
|
| 319 |
+
--help, -h Show this help
|
| 320 |
+
|
| 321 |
+
Examples:
|
| 322 |
+
# Process a single file
|
| 323 |
+
node post-processor.mjs input.md output.md
|
| 324 |
+
|
| 325 |
+
# Process with verbose output
|
| 326 |
+
node post-processor.mjs --verbose input.md output.md
|
| 327 |
+
`);
|
| 328 |
+
process.exit(0);
|
| 329 |
+
}
|
| 330 |
+
|
| 331 |
+
const verbose = args.includes('--verbose');
|
| 332 |
+
const inputFile = args.find(arg => !arg.startsWith('--') && arg.endsWith('.md'));
|
| 333 |
+
const outputFile = args.find(arg => !arg.startsWith('--') && arg !== inputFile && arg.endsWith('.md'));
|
| 334 |
+
|
| 335 |
+
if (!inputFile) {
|
| 336 |
+
console.error('❌ Please provide an input markdown file');
|
| 337 |
+
process.exit(1);
|
| 338 |
+
}
|
| 339 |
+
|
| 340 |
+
if (!existsSync(inputFile)) {
|
| 341 |
+
console.error(`❌ Input file not found: ${inputFile}`);
|
| 342 |
+
process.exit(1);
|
| 343 |
+
}
|
| 344 |
+
|
| 345 |
+
try {
|
| 346 |
+
console.log(`📖 Reading: ${inputFile}`);
|
| 347 |
+
const content = readFileSync(inputFile, 'utf8');
|
| 348 |
+
|
| 349 |
+
const processedContent = postProcessMarkdown(content);
|
| 350 |
+
|
| 351 |
+
const finalOutputFile = outputFile || inputFile.replace('.md', '.processed.md');
|
| 352 |
+
writeFileSync(finalOutputFile, processedContent);
|
| 353 |
+
|
| 354 |
+
console.log(`✅ Processed: ${finalOutputFile}`);
|
| 355 |
+
|
| 356 |
+
if (verbose) {
|
| 357 |
+
console.log(`📊 Input: ${content.length} chars → Output: ${processedContent.length} chars`);
|
| 358 |
+
}
|
| 359 |
+
|
| 360 |
+
} catch (error) {
|
| 361 |
+
console.error('❌ Processing failed:', error.message);
|
| 362 |
+
process.exit(1);
|
| 363 |
+
}
|
| 364 |
+
}
|
| 365 |
+
|
| 366 |
+
// Run CLI if called directly
|
| 367 |
+
if (import.meta.url === `file://${process.argv[1]}`) {
|
| 368 |
+
main();
|
| 369 |
+
}
|
app/scripts/notion-importer/test-access.mjs
ADDED
|
@@ -0,0 +1,39 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env node
|
| 2 |
+
|
| 3 |
+
import { config } from 'dotenv';
|
| 4 |
+
import { Client } from '@notionhq/client';
|
| 5 |
+
|
| 6 |
+
// Load environment variables from .env file
|
| 7 |
+
config();
|
| 8 |
+
|
| 9 |
+
const notion = new Client({
|
| 10 |
+
auth: process.env.NOTION_TOKEN,
|
| 11 |
+
});
|
| 12 |
+
|
| 13 |
+
async function testAccess() {
|
| 14 |
+
const pageId = '27877f1c9c9d804d9c82f7b3905578ff';
|
| 15 |
+
|
| 16 |
+
try {
|
| 17 |
+
console.log('🔍 Testing access to Notion page...');
|
| 18 |
+
console.log(`📄 Page ID: ${pageId}`);
|
| 19 |
+
|
| 20 |
+
const response = await notion.pages.retrieve({ page_id: pageId });
|
| 21 |
+
|
| 22 |
+
console.log('✅ Access successful!');
|
| 23 |
+
console.log(`📝 Page title: ${response.properties.title?.title?.[0]?.text?.content || 'No title'}`);
|
| 24 |
+
console.log(`📅 Created: ${response.created_time}`);
|
| 25 |
+
console.log(`👤 Created by: ${response.created_by.id}`);
|
| 26 |
+
|
| 27 |
+
} catch (error) {
|
| 28 |
+
console.error('❌ Access failed:', error.message);
|
| 29 |
+
|
| 30 |
+
if (error.code === 'unauthorized') {
|
| 31 |
+
console.log('\n💡 Solutions:');
|
| 32 |
+
console.log('1. Check that your NOTION_TOKEN is correct');
|
| 33 |
+
console.log('2. Make sure the page is shared with your integration');
|
| 34 |
+
console.log('3. Verify that the integration has the right permissions');
|
| 35 |
+
}
|
| 36 |
+
}
|
| 37 |
+
}
|
| 38 |
+
|
| 39 |
+
testAccess();
|
app/scripts/notion-importer/yarn.lock
ADDED
|
@@ -0,0 +1,1118 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.
|
| 2 |
+
# yarn lockfile v1
|
| 3 |
+
|
| 4 |
+
|
| 5 |
+
"@cspotcode/source-map-support@^0.8.0":
|
| 6 |
+
version "0.8.1"
|
| 7 |
+
resolved "https://registry.npmjs.org/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz"
|
| 8 |
+
integrity sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==
|
| 9 |
+
dependencies:
|
| 10 |
+
"@jridgewell/trace-mapping" "0.3.9"
|
| 11 |
+
|
| 12 |
+
"@jridgewell/resolve-uri@^3.0.3":
|
| 13 |
+
version "3.1.2"
|
| 14 |
+
resolved "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz"
|
| 15 |
+
integrity sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==
|
| 16 |
+
|
| 17 |
+
"@jridgewell/sourcemap-codec@^1.4.10":
|
| 18 |
+
version "1.5.5"
|
| 19 |
+
resolved "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz"
|
| 20 |
+
integrity sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==
|
| 21 |
+
|
| 22 |
+
"@jridgewell/trace-mapping@0.3.9":
|
| 23 |
+
version "0.3.9"
|
| 24 |
+
resolved "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz"
|
| 25 |
+
integrity sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==
|
| 26 |
+
dependencies:
|
| 27 |
+
"@jridgewell/resolve-uri" "^3.0.3"
|
| 28 |
+
"@jridgewell/sourcemap-codec" "^1.4.10"
|
| 29 |
+
|
| 30 |
+
"@notionhq/client@^2.0.0", "@notionhq/client@^2.2.15":
|
| 31 |
+
version "2.3.0"
|
| 32 |
+
resolved "https://registry.npmjs.org/@notionhq/client/-/client-2.3.0.tgz"
|
| 33 |
+
integrity sha512-l7WqTCpQqC+HibkB9chghONQTYcxNQT0/rOJemBfmuKQRTu2vuV8B3yA395iKaUdDo7HI+0KvQaz9687Xskzkw==
|
| 34 |
+
dependencies:
|
| 35 |
+
"@types/node-fetch" "^2.5.10"
|
| 36 |
+
node-fetch "^2.6.1"
|
| 37 |
+
|
| 38 |
+
"@tsconfig/node10@^1.0.7":
|
| 39 |
+
version "1.0.11"
|
| 40 |
+
resolved "https://registry.npmjs.org/@tsconfig/node10/-/node10-1.0.11.tgz"
|
| 41 |
+
integrity sha512-DcRjDCujK/kCk/cUe8Xz8ZSpm8mS3mNNpta+jGCA6USEDfktlNvm1+IuZ9eTcDbNk41BHwpHHeW+N1lKCz4zOw==
|
| 42 |
+
|
| 43 |
+
"@tsconfig/node12@^1.0.7":
|
| 44 |
+
version "1.0.11"
|
| 45 |
+
resolved "https://registry.npmjs.org/@tsconfig/node12/-/node12-1.0.11.tgz"
|
| 46 |
+
integrity sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag==
|
| 47 |
+
|
| 48 |
+
"@tsconfig/node14@^1.0.0":
|
| 49 |
+
version "1.0.3"
|
| 50 |
+
resolved "https://registry.npmjs.org/@tsconfig/node14/-/node14-1.0.3.tgz"
|
| 51 |
+
integrity sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow==
|
| 52 |
+
|
| 53 |
+
"@tsconfig/node16@^1.0.2":
|
| 54 |
+
version "1.0.4"
|
| 55 |
+
resolved "https://registry.npmjs.org/@tsconfig/node16/-/node16-1.0.4.tgz"
|
| 56 |
+
integrity sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA==
|
| 57 |
+
|
| 58 |
+
"@types/debug@^4.0.0":
|
| 59 |
+
version "4.1.12"
|
| 60 |
+
resolved "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz"
|
| 61 |
+
integrity sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==
|
| 62 |
+
dependencies:
|
| 63 |
+
"@types/ms" "*"
|
| 64 |
+
|
| 65 |
+
"@types/estree-jsx@^1.0.0":
|
| 66 |
+
version "1.0.5"
|
| 67 |
+
resolved "https://registry.npmjs.org/@types/estree-jsx/-/estree-jsx-1.0.5.tgz"
|
| 68 |
+
integrity sha512-52CcUVNFyfb1A2ALocQw/Dd1BQFNmSdkuC3BkZ6iqhdMfQz7JWOFRuJFloOzjk+6WijU56m9oKXFAXc7o3Towg==
|
| 69 |
+
dependencies:
|
| 70 |
+
"@types/estree" "*"
|
| 71 |
+
|
| 72 |
+
"@types/estree@*", "@types/estree@^1.0.0":
|
| 73 |
+
version "1.0.8"
|
| 74 |
+
resolved "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz"
|
| 75 |
+
integrity sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==
|
| 76 |
+
|
| 77 |
+
"@types/hast@^3.0.0":
|
| 78 |
+
version "3.0.4"
|
| 79 |
+
resolved "https://registry.npmjs.org/@types/hast/-/hast-3.0.4.tgz"
|
| 80 |
+
integrity sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==
|
| 81 |
+
dependencies:
|
| 82 |
+
"@types/unist" "*"
|
| 83 |
+
|
| 84 |
+
"@types/mdast@^4.0.0":
|
| 85 |
+
version "4.0.4"
|
| 86 |
+
resolved "https://registry.npmjs.org/@types/mdast/-/mdast-4.0.4.tgz"
|
| 87 |
+
integrity sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==
|
| 88 |
+
dependencies:
|
| 89 |
+
"@types/unist" "*"
|
| 90 |
+
|
| 91 |
+
"@types/ms@*":
|
| 92 |
+
version "2.1.0"
|
| 93 |
+
resolved "https://registry.npmjs.org/@types/ms/-/ms-2.1.0.tgz"
|
| 94 |
+
integrity sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==
|
| 95 |
+
|
| 96 |
+
"@types/node-fetch@^2.5.10":
|
| 97 |
+
version "2.6.13"
|
| 98 |
+
resolved "https://registry.npmjs.org/@types/node-fetch/-/node-fetch-2.6.13.tgz"
|
| 99 |
+
integrity sha512-QGpRVpzSaUs30JBSGPjOg4Uveu384erbHBoT1zeONvyCfwQxIkUshLAOqN/k9EjGviPRmWTTe6aH2qySWKTVSw==
|
| 100 |
+
dependencies:
|
| 101 |
+
"@types/node" "*"
|
| 102 |
+
form-data "^4.0.4"
|
| 103 |
+
|
| 104 |
+
"@types/node@*":
|
| 105 |
+
version "24.5.2"
|
| 106 |
+
resolved "https://registry.npmjs.org/@types/node/-/node-24.5.2.tgz"
|
| 107 |
+
integrity sha512-FYxk1I7wPv3K2XBaoyH2cTnocQEu8AOZ60hPbsyukMPLv5/5qr7V1i8PLHdl6Zf87I+xZXFvPCXYjiTFq+YSDQ==
|
| 108 |
+
dependencies:
|
| 109 |
+
undici-types "~7.12.0"
|
| 110 |
+
|
| 111 |
+
"@types/unist@*", "@types/unist@^3.0.0":
|
| 112 |
+
version "3.0.3"
|
| 113 |
+
resolved "https://registry.npmjs.org/@types/unist/-/unist-3.0.3.tgz"
|
| 114 |
+
integrity sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==
|
| 115 |
+
|
| 116 |
+
"@types/unist@^2.0.0":
|
| 117 |
+
version "2.0.11"
|
| 118 |
+
resolved "https://registry.npmjs.org/@types/unist/-/unist-2.0.11.tgz"
|
| 119 |
+
integrity sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==
|
| 120 |
+
|
| 121 |
+
acorn-jsx@^5.0.0:
|
| 122 |
+
version "5.3.2"
|
| 123 |
+
resolved "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz"
|
| 124 |
+
integrity sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==
|
| 125 |
+
|
| 126 |
+
acorn-walk@^8.1.1:
|
| 127 |
+
version "8.3.4"
|
| 128 |
+
resolved "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.4.tgz"
|
| 129 |
+
integrity sha512-ueEepnujpqee2o5aIYnvHU6C0A42MNdsIDeqy5BydrkuC5R1ZuUFnm27EeFJGoEHJQgn3uleRvmTXaJgfXbt4g==
|
| 130 |
+
dependencies:
|
| 131 |
+
acorn "^8.11.0"
|
| 132 |
+
|
| 133 |
+
"acorn@^6.0.0 || ^7.0.0 || ^8.0.0", acorn@^8.0.0, acorn@^8.11.0, acorn@^8.4.1:
|
| 134 |
+
version "8.15.0"
|
| 135 |
+
resolved "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz"
|
| 136 |
+
integrity sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==
|
| 137 |
+
|
| 138 |
+
arg@^4.1.0:
|
| 139 |
+
version "4.1.3"
|
| 140 |
+
resolved "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz"
|
| 141 |
+
integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==
|
| 142 |
+
|
| 143 |
+
argparse@^1.0.7:
|
| 144 |
+
version "1.0.10"
|
| 145 |
+
resolved "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz"
|
| 146 |
+
integrity sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==
|
| 147 |
+
dependencies:
|
| 148 |
+
sprintf-js "~1.0.2"
|
| 149 |
+
|
| 150 |
+
asynckit@^0.4.0:
|
| 151 |
+
version "0.4.0"
|
| 152 |
+
resolved "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz"
|
| 153 |
+
integrity sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==
|
| 154 |
+
|
| 155 |
+
bail@^2.0.0:
|
| 156 |
+
version "2.0.2"
|
| 157 |
+
resolved "https://registry.npmjs.org/bail/-/bail-2.0.2.tgz"
|
| 158 |
+
integrity sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==
|
| 159 |
+
|
| 160 |
+
call-bind-apply-helpers@^1.0.1, call-bind-apply-helpers@^1.0.2:
|
| 161 |
+
version "1.0.2"
|
| 162 |
+
resolved "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz"
|
| 163 |
+
integrity sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==
|
| 164 |
+
dependencies:
|
| 165 |
+
es-errors "^1.3.0"
|
| 166 |
+
function-bind "^1.1.2"
|
| 167 |
+
|
| 168 |
+
ccount@^2.0.0:
|
| 169 |
+
version "2.0.1"
|
| 170 |
+
resolved "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz"
|
| 171 |
+
integrity sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==
|
| 172 |
+
|
| 173 |
+
character-entities-html4@^2.0.0:
|
| 174 |
+
version "2.1.0"
|
| 175 |
+
resolved "https://registry.npmjs.org/character-entities-html4/-/character-entities-html4-2.1.0.tgz"
|
| 176 |
+
integrity sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==
|
| 177 |
+
|
| 178 |
+
character-entities-legacy@^3.0.0:
|
| 179 |
+
version "3.0.0"
|
| 180 |
+
resolved "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz"
|
| 181 |
+
integrity sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==
|
| 182 |
+
|
| 183 |
+
character-entities@^2.0.0:
|
| 184 |
+
version "2.0.2"
|
| 185 |
+
resolved "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz"
|
| 186 |
+
integrity sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==
|
| 187 |
+
|
| 188 |
+
character-reference-invalid@^2.0.0:
|
| 189 |
+
version "2.0.1"
|
| 190 |
+
resolved "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-2.0.1.tgz"
|
| 191 |
+
integrity sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==
|
| 192 |
+
|
| 193 |
+
combined-stream@^1.0.8:
|
| 194 |
+
version "1.0.8"
|
| 195 |
+
resolved "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz"
|
| 196 |
+
integrity sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==
|
| 197 |
+
dependencies:
|
| 198 |
+
delayed-stream "~1.0.0"
|
| 199 |
+
|
| 200 |
+
create-require@^1.1.0:
|
| 201 |
+
version "1.1.1"
|
| 202 |
+
resolved "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz"
|
| 203 |
+
integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==
|
| 204 |
+
|
| 205 |
+
data-uri-to-buffer@^4.0.0:
|
| 206 |
+
version "4.0.1"
|
| 207 |
+
resolved "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-4.0.1.tgz"
|
| 208 |
+
integrity sha512-0R9ikRb668HB7QDxT1vkpuUBtqc53YyAwMwGeUFKRojY/NWKvdZ+9UYtRfGmhqNbRkTSVpMbmyhXipFFv2cb/A==
|
| 209 |
+
|
| 210 |
+
debug@^4.0.0:
|
| 211 |
+
version "4.4.3"
|
| 212 |
+
resolved "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz"
|
| 213 |
+
integrity sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==
|
| 214 |
+
dependencies:
|
| 215 |
+
ms "^2.1.3"
|
| 216 |
+
|
| 217 |
+
decode-named-character-reference@^1.0.0:
|
| 218 |
+
version "1.2.0"
|
| 219 |
+
resolved "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.2.0.tgz"
|
| 220 |
+
integrity sha512-c6fcElNV6ShtZXmsgNgFFV5tVX2PaV4g+MOAkb8eXHvn6sryJBrZa9r0zV6+dtTyoCKxtDy5tyQ5ZwQuidtd+Q==
|
| 221 |
+
dependencies:
|
| 222 |
+
character-entities "^2.0.0"
|
| 223 |
+
|
| 224 |
+
delayed-stream@~1.0.0:
|
| 225 |
+
version "1.0.0"
|
| 226 |
+
resolved "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz"
|
| 227 |
+
integrity sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==
|
| 228 |
+
|
| 229 |
+
dequal@^2.0.0:
|
| 230 |
+
version "2.0.3"
|
| 231 |
+
resolved "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz"
|
| 232 |
+
integrity sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==
|
| 233 |
+
|
| 234 |
+
devlop@^1.0.0, devlop@^1.1.0:
|
| 235 |
+
version "1.1.0"
|
| 236 |
+
resolved "https://registry.npmjs.org/devlop/-/devlop-1.1.0.tgz"
|
| 237 |
+
integrity sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==
|
| 238 |
+
dependencies:
|
| 239 |
+
dequal "^2.0.0"
|
| 240 |
+
|
| 241 |
+
diff@^4.0.1:
|
| 242 |
+
version "4.0.2"
|
| 243 |
+
resolved "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz"
|
| 244 |
+
integrity sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==
|
| 245 |
+
|
| 246 |
+
dotenv@^17.2.2:
|
| 247 |
+
version "17.2.2"
|
| 248 |
+
resolved "https://registry.npmjs.org/dotenv/-/dotenv-17.2.2.tgz"
|
| 249 |
+
integrity sha512-Sf2LSQP+bOlhKWWyhFsn0UsfdK/kCWRv1iuA2gXAwt3dyNabr6QSj00I2V10pidqz69soatm9ZwZvpQMTIOd5Q==
|
| 250 |
+
|
| 251 |
+
dunder-proto@^1.0.1:
|
| 252 |
+
version "1.0.1"
|
| 253 |
+
resolved "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz"
|
| 254 |
+
integrity sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==
|
| 255 |
+
dependencies:
|
| 256 |
+
call-bind-apply-helpers "^1.0.1"
|
| 257 |
+
es-errors "^1.3.0"
|
| 258 |
+
gopd "^1.2.0"
|
| 259 |
+
|
| 260 |
+
es-define-property@^1.0.1:
|
| 261 |
+
version "1.0.1"
|
| 262 |
+
resolved "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz"
|
| 263 |
+
integrity sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==
|
| 264 |
+
|
| 265 |
+
es-errors@^1.3.0:
|
| 266 |
+
version "1.3.0"
|
| 267 |
+
resolved "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz"
|
| 268 |
+
integrity sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==
|
| 269 |
+
|
| 270 |
+
es-object-atoms@^1.0.0, es-object-atoms@^1.1.1:
|
| 271 |
+
version "1.1.1"
|
| 272 |
+
resolved "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz"
|
| 273 |
+
integrity sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==
|
| 274 |
+
dependencies:
|
| 275 |
+
es-errors "^1.3.0"
|
| 276 |
+
|
| 277 |
+
es-set-tostringtag@^2.1.0:
|
| 278 |
+
version "2.1.0"
|
| 279 |
+
resolved "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz"
|
| 280 |
+
integrity sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==
|
| 281 |
+
dependencies:
|
| 282 |
+
es-errors "^1.3.0"
|
| 283 |
+
get-intrinsic "^1.2.6"
|
| 284 |
+
has-tostringtag "^1.0.2"
|
| 285 |
+
hasown "^2.0.2"
|
| 286 |
+
|
| 287 |
+
esprima@^4.0.0:
|
| 288 |
+
version "4.0.1"
|
| 289 |
+
resolved "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz"
|
| 290 |
+
integrity sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==
|
| 291 |
+
|
| 292 |
+
estree-util-is-identifier-name@^3.0.0:
|
| 293 |
+
version "3.0.0"
|
| 294 |
+
resolved "https://registry.npmjs.org/estree-util-is-identifier-name/-/estree-util-is-identifier-name-3.0.0.tgz"
|
| 295 |
+
integrity sha512-hFtqIDZTIUZ9BXLb8y4pYGyk6+wekIivNVTcmvk8NoOh+VeRn5y6cEHzbURrWbfp1fIqdVipilzj+lfaadNZmg==
|
| 296 |
+
|
| 297 |
+
estree-util-visit@^2.0.0:
|
| 298 |
+
version "2.0.0"
|
| 299 |
+
resolved "https://registry.npmjs.org/estree-util-visit/-/estree-util-visit-2.0.0.tgz"
|
| 300 |
+
integrity sha512-m5KgiH85xAhhW8Wta0vShLcUvOsh3LLPI2YVwcbio1l7E09NTLL1EyMZFM1OyWowoH0skScNbhOPl4kcBgzTww==
|
| 301 |
+
dependencies:
|
| 302 |
+
"@types/estree-jsx" "^1.0.0"
|
| 303 |
+
"@types/unist" "^3.0.0"
|
| 304 |
+
|
| 305 |
+
extend-shallow@^2.0.1:
|
| 306 |
+
version "2.0.1"
|
| 307 |
+
resolved "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz"
|
| 308 |
+
integrity sha512-zCnTtlxNoAiDc3gqY2aYAWFx7XWWiasuF2K8Me5WbN8otHKTUKBwjPtNpRs/rbUZm7KxWAaNj7P1a/p52GbVug==
|
| 309 |
+
dependencies:
|
| 310 |
+
is-extendable "^0.1.0"
|
| 311 |
+
|
| 312 |
+
extend@^3.0.0:
|
| 313 |
+
version "3.0.2"
|
| 314 |
+
resolved "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz"
|
| 315 |
+
integrity sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==
|
| 316 |
+
|
| 317 |
+
fetch-blob@^3.1.2, fetch-blob@^3.1.4:
|
| 318 |
+
version "3.2.0"
|
| 319 |
+
resolved "https://registry.npmjs.org/fetch-blob/-/fetch-blob-3.2.0.tgz"
|
| 320 |
+
integrity sha512-7yAQpD2UMJzLi1Dqv7qFYnPbaPx7ZfFK6PiIxQ4PfkGPyNyl2Ugx+a/umUonmKqjhM4DnfbMvdX6otXq83soQQ==
|
| 321 |
+
dependencies:
|
| 322 |
+
node-domexception "^1.0.0"
|
| 323 |
+
web-streams-polyfill "^3.0.3"
|
| 324 |
+
|
| 325 |
+
form-data@^4.0.4:
|
| 326 |
+
version "4.0.4"
|
| 327 |
+
resolved "https://registry.npmjs.org/form-data/-/form-data-4.0.4.tgz"
|
| 328 |
+
integrity sha512-KrGhL9Q4zjj0kiUt5OO4Mr/A/jlI2jDYs5eHBpYHPcBEVSiipAvn2Ko2HnPe20rmcuuvMHNdZFp+4IlGTMF0Ow==
|
| 329 |
+
dependencies:
|
| 330 |
+
asynckit "^0.4.0"
|
| 331 |
+
combined-stream "^1.0.8"
|
| 332 |
+
es-set-tostringtag "^2.1.0"
|
| 333 |
+
hasown "^2.0.2"
|
| 334 |
+
mime-types "^2.1.12"
|
| 335 |
+
|
| 336 |
+
formdata-polyfill@^4.0.10:
|
| 337 |
+
version "4.0.10"
|
| 338 |
+
resolved "https://registry.npmjs.org/formdata-polyfill/-/formdata-polyfill-4.0.10.tgz"
|
| 339 |
+
integrity sha512-buewHzMvYL29jdeQTVILecSaZKnt/RJWjoZCF5OW60Z67/GmSLBkOFM7qh1PI3zFNtJbaZL5eQu1vLfazOwj4g==
|
| 340 |
+
dependencies:
|
| 341 |
+
fetch-blob "^3.1.2"
|
| 342 |
+
|
| 343 |
+
function-bind@^1.1.2:
|
| 344 |
+
version "1.1.2"
|
| 345 |
+
resolved "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz"
|
| 346 |
+
integrity sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==
|
| 347 |
+
|
| 348 |
+
get-intrinsic@^1.2.6:
|
| 349 |
+
version "1.3.0"
|
| 350 |
+
resolved "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz"
|
| 351 |
+
integrity sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==
|
| 352 |
+
dependencies:
|
| 353 |
+
call-bind-apply-helpers "^1.0.2"
|
| 354 |
+
es-define-property "^1.0.1"
|
| 355 |
+
es-errors "^1.3.0"
|
| 356 |
+
es-object-atoms "^1.1.1"
|
| 357 |
+
function-bind "^1.1.2"
|
| 358 |
+
get-proto "^1.0.1"
|
| 359 |
+
gopd "^1.2.0"
|
| 360 |
+
has-symbols "^1.1.0"
|
| 361 |
+
hasown "^2.0.2"
|
| 362 |
+
math-intrinsics "^1.1.0"
|
| 363 |
+
|
| 364 |
+
get-proto@^1.0.1:
|
| 365 |
+
version "1.0.1"
|
| 366 |
+
resolved "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz"
|
| 367 |
+
integrity sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==
|
| 368 |
+
dependencies:
|
| 369 |
+
dunder-proto "^1.0.1"
|
| 370 |
+
es-object-atoms "^1.0.0"
|
| 371 |
+
|
| 372 |
+
gopd@^1.2.0:
|
| 373 |
+
version "1.2.0"
|
| 374 |
+
resolved "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz"
|
| 375 |
+
integrity sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==
|
| 376 |
+
|
| 377 |
+
gray-matter@^4.0.3:
|
| 378 |
+
version "4.0.3"
|
| 379 |
+
resolved "https://registry.npmjs.org/gray-matter/-/gray-matter-4.0.3.tgz"
|
| 380 |
+
integrity sha512-5v6yZd4JK3eMI3FqqCouswVqwugaA9r4dNZB1wwcmrD02QkV5H0y7XBQW8QwQqEaZY1pM9aqORSORhJRdNK44Q==
|
| 381 |
+
dependencies:
|
| 382 |
+
js-yaml "^3.13.1"
|
| 383 |
+
kind-of "^6.0.2"
|
| 384 |
+
section-matter "^1.0.0"
|
| 385 |
+
strip-bom-string "^1.0.0"
|
| 386 |
+
|
| 387 |
+
has-symbols@^1.0.3, has-symbols@^1.1.0:
|
| 388 |
+
version "1.1.0"
|
| 389 |
+
resolved "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz"
|
| 390 |
+
integrity sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==
|
| 391 |
+
|
| 392 |
+
has-tostringtag@^1.0.2:
|
| 393 |
+
version "1.0.2"
|
| 394 |
+
resolved "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz"
|
| 395 |
+
integrity sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==
|
| 396 |
+
dependencies:
|
| 397 |
+
has-symbols "^1.0.3"
|
| 398 |
+
|
| 399 |
+
hasown@^2.0.2:
|
| 400 |
+
version "2.0.2"
|
| 401 |
+
resolved "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz"
|
| 402 |
+
integrity sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==
|
| 403 |
+
dependencies:
|
| 404 |
+
function-bind "^1.1.2"
|
| 405 |
+
|
| 406 |
+
is-alphabetical@^2.0.0:
|
| 407 |
+
version "2.0.1"
|
| 408 |
+
resolved "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-2.0.1.tgz"
|
| 409 |
+
integrity sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==
|
| 410 |
+
|
| 411 |
+
is-alphanumerical@^2.0.0:
|
| 412 |
+
version "2.0.1"
|
| 413 |
+
resolved "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-2.0.1.tgz"
|
| 414 |
+
integrity sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==
|
| 415 |
+
dependencies:
|
| 416 |
+
is-alphabetical "^2.0.0"
|
| 417 |
+
is-decimal "^2.0.0"
|
| 418 |
+
|
| 419 |
+
is-decimal@^2.0.0:
|
| 420 |
+
version "2.0.1"
|
| 421 |
+
resolved "https://registry.npmjs.org/is-decimal/-/is-decimal-2.0.1.tgz"
|
| 422 |
+
integrity sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==
|
| 423 |
+
|
| 424 |
+
is-extendable@^0.1.0:
|
| 425 |
+
version "0.1.1"
|
| 426 |
+
resolved "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz"
|
| 427 |
+
integrity sha512-5BMULNob1vgFX6EjQw5izWDxrecWK9AM72rugNr0TFldMOi0fj6Jk+zeKIt0xGj4cEfQIJth4w3OKWOJ4f+AFw==
|
| 428 |
+
|
| 429 |
+
is-hexadecimal@^2.0.0:
|
| 430 |
+
version "2.0.1"
|
| 431 |
+
resolved "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-2.0.1.tgz"
|
| 432 |
+
integrity sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==
|
| 433 |
+
|
| 434 |
+
is-plain-obj@^4.0.0:
|
| 435 |
+
version "4.1.0"
|
| 436 |
+
resolved "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz"
|
| 437 |
+
integrity sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==
|
| 438 |
+
|
| 439 |
+
js-yaml@^3.13.1:
|
| 440 |
+
version "3.14.1"
|
| 441 |
+
resolved "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz"
|
| 442 |
+
integrity sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==
|
| 443 |
+
dependencies:
|
| 444 |
+
argparse "^1.0.7"
|
| 445 |
+
esprima "^4.0.0"
|
| 446 |
+
|
| 447 |
+
kind-of@^6.0.0, kind-of@^6.0.2:
|
| 448 |
+
version "6.0.3"
|
| 449 |
+
resolved "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz"
|
| 450 |
+
integrity sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==
|
| 451 |
+
|
| 452 |
+
longest-streak@^3.0.0:
|
| 453 |
+
version "3.1.0"
|
| 454 |
+
resolved "https://registry.npmjs.org/longest-streak/-/longest-streak-3.1.0.tgz"
|
| 455 |
+
integrity sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==
|
| 456 |
+
|
| 457 |
+
make-error@^1.1.1:
|
| 458 |
+
version "1.3.6"
|
| 459 |
+
resolved "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz"
|
| 460 |
+
integrity sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==
|
| 461 |
+
|
| 462 |
+
math-intrinsics@^1.1.0:
|
| 463 |
+
version "1.1.0"
|
| 464 |
+
resolved "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz"
|
| 465 |
+
integrity sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==
|
| 466 |
+
|
| 467 |
+
mdast-util-from-markdown@^2.0.0:
|
| 468 |
+
version "2.0.2"
|
| 469 |
+
resolved "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-2.0.2.tgz"
|
| 470 |
+
integrity sha512-uZhTV/8NBuw0WHkPTrCqDOl0zVe1BIng5ZtHoDk49ME1qqcjYmmLmOf0gELgcRMxN4w2iuIeVso5/6QymSrgmA==
|
| 471 |
+
dependencies:
|
| 472 |
+
"@types/mdast" "^4.0.0"
|
| 473 |
+
"@types/unist" "^3.0.0"
|
| 474 |
+
decode-named-character-reference "^1.0.0"
|
| 475 |
+
devlop "^1.0.0"
|
| 476 |
+
mdast-util-to-string "^4.0.0"
|
| 477 |
+
micromark "^4.0.0"
|
| 478 |
+
micromark-util-decode-numeric-character-reference "^2.0.0"
|
| 479 |
+
micromark-util-decode-string "^2.0.0"
|
| 480 |
+
micromark-util-normalize-identifier "^2.0.0"
|
| 481 |
+
micromark-util-symbol "^2.0.0"
|
| 482 |
+
micromark-util-types "^2.0.0"
|
| 483 |
+
unist-util-stringify-position "^4.0.0"
|
| 484 |
+
|
| 485 |
+
mdast-util-mdx-expression@^2.0.0:
|
| 486 |
+
version "2.0.1"
|
| 487 |
+
resolved "https://registry.npmjs.org/mdast-util-mdx-expression/-/mdast-util-mdx-expression-2.0.1.tgz"
|
| 488 |
+
integrity sha512-J6f+9hUp+ldTZqKRSg7Vw5V6MqjATc+3E4gf3CFNcuZNWD8XdyI6zQ8GqH7f8169MM6P7hMBRDVGnn7oHB9kXQ==
|
| 489 |
+
dependencies:
|
| 490 |
+
"@types/estree-jsx" "^1.0.0"
|
| 491 |
+
"@types/hast" "^3.0.0"
|
| 492 |
+
"@types/mdast" "^4.0.0"
|
| 493 |
+
devlop "^1.0.0"
|
| 494 |
+
mdast-util-from-markdown "^2.0.0"
|
| 495 |
+
mdast-util-to-markdown "^2.0.0"
|
| 496 |
+
|
| 497 |
+
mdast-util-mdx-jsx@^3.0.0:
|
| 498 |
+
version "3.2.0"
|
| 499 |
+
resolved "https://registry.npmjs.org/mdast-util-mdx-jsx/-/mdast-util-mdx-jsx-3.2.0.tgz"
|
| 500 |
+
integrity sha512-lj/z8v0r6ZtsN/cGNNtemmmfoLAFZnjMbNyLzBafjzikOM+glrjNHPlf6lQDOTccj9n5b0PPihEBbhneMyGs1Q==
|
| 501 |
+
dependencies:
|
| 502 |
+
"@types/estree-jsx" "^1.0.0"
|
| 503 |
+
"@types/hast" "^3.0.0"
|
| 504 |
+
"@types/mdast" "^4.0.0"
|
| 505 |
+
"@types/unist" "^3.0.0"
|
| 506 |
+
ccount "^2.0.0"
|
| 507 |
+
devlop "^1.1.0"
|
| 508 |
+
mdast-util-from-markdown "^2.0.0"
|
| 509 |
+
mdast-util-to-markdown "^2.0.0"
|
| 510 |
+
parse-entities "^4.0.0"
|
| 511 |
+
stringify-entities "^4.0.0"
|
| 512 |
+
unist-util-stringify-position "^4.0.0"
|
| 513 |
+
vfile-message "^4.0.0"
|
| 514 |
+
|
| 515 |
+
mdast-util-mdx@^3.0.0:
|
| 516 |
+
version "3.0.0"
|
| 517 |
+
resolved "https://registry.npmjs.org/mdast-util-mdx/-/mdast-util-mdx-3.0.0.tgz"
|
| 518 |
+
integrity sha512-JfbYLAW7XnYTTbUsmpu0kdBUVe+yKVJZBItEjwyYJiDJuZ9w4eeaqks4HQO+R7objWgS2ymV60GYpI14Ug554w==
|
| 519 |
+
dependencies:
|
| 520 |
+
mdast-util-from-markdown "^2.0.0"
|
| 521 |
+
mdast-util-mdx-expression "^2.0.0"
|
| 522 |
+
mdast-util-mdx-jsx "^3.0.0"
|
| 523 |
+
mdast-util-mdxjs-esm "^2.0.0"
|
| 524 |
+
mdast-util-to-markdown "^2.0.0"
|
| 525 |
+
|
| 526 |
+
mdast-util-mdxjs-esm@^2.0.0:
|
| 527 |
+
version "2.0.1"
|
| 528 |
+
resolved "https://registry.npmjs.org/mdast-util-mdxjs-esm/-/mdast-util-mdxjs-esm-2.0.1.tgz"
|
| 529 |
+
integrity sha512-EcmOpxsZ96CvlP03NghtH1EsLtr0n9Tm4lPUJUBccV9RwUOneqSycg19n5HGzCf+10LozMRSObtVr3ee1WoHtg==
|
| 530 |
+
dependencies:
|
| 531 |
+
"@types/estree-jsx" "^1.0.0"
|
| 532 |
+
"@types/hast" "^3.0.0"
|
| 533 |
+
"@types/mdast" "^4.0.0"
|
| 534 |
+
devlop "^1.0.0"
|
| 535 |
+
mdast-util-from-markdown "^2.0.0"
|
| 536 |
+
mdast-util-to-markdown "^2.0.0"
|
| 537 |
+
|
| 538 |
+
mdast-util-phrasing@^4.0.0:
|
| 539 |
+
version "4.1.0"
|
| 540 |
+
resolved "https://registry.npmjs.org/mdast-util-phrasing/-/mdast-util-phrasing-4.1.0.tgz"
|
| 541 |
+
integrity sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==
|
| 542 |
+
dependencies:
|
| 543 |
+
"@types/mdast" "^4.0.0"
|
| 544 |
+
unist-util-is "^6.0.0"
|
| 545 |
+
|
| 546 |
+
mdast-util-to-markdown@^2.0.0:
|
| 547 |
+
version "2.1.2"
|
| 548 |
+
resolved "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-2.1.2.tgz"
|
| 549 |
+
integrity sha512-xj68wMTvGXVOKonmog6LwyJKrYXZPvlwabaryTjLh9LuvovB/KAH+kvi8Gjj+7rJjsFi23nkUxRQv1KqSroMqA==
|
| 550 |
+
dependencies:
|
| 551 |
+
"@types/mdast" "^4.0.0"
|
| 552 |
+
"@types/unist" "^3.0.0"
|
| 553 |
+
longest-streak "^3.0.0"
|
| 554 |
+
mdast-util-phrasing "^4.0.0"
|
| 555 |
+
mdast-util-to-string "^4.0.0"
|
| 556 |
+
micromark-util-classify-character "^2.0.0"
|
| 557 |
+
micromark-util-decode-string "^2.0.0"
|
| 558 |
+
unist-util-visit "^5.0.0"
|
| 559 |
+
zwitch "^2.0.0"
|
| 560 |
+
|
| 561 |
+
mdast-util-to-string@^4.0.0:
|
| 562 |
+
version "4.0.0"
|
| 563 |
+
resolved "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-4.0.0.tgz"
|
| 564 |
+
integrity sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==
|
| 565 |
+
dependencies:
|
| 566 |
+
"@types/mdast" "^4.0.0"
|
| 567 |
+
|
| 568 |
+
micromark-core-commonmark@^2.0.0:
|
| 569 |
+
version "2.0.3"
|
| 570 |
+
resolved "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-2.0.3.tgz"
|
| 571 |
+
integrity sha512-RDBrHEMSxVFLg6xvnXmb1Ayr2WzLAWjeSATAoxwKYJV94TeNavgoIdA0a9ytzDSVzBy2YKFK+emCPOEibLeCrg==
|
| 572 |
+
dependencies:
|
| 573 |
+
decode-named-character-reference "^1.0.0"
|
| 574 |
+
devlop "^1.0.0"
|
| 575 |
+
micromark-factory-destination "^2.0.0"
|
| 576 |
+
micromark-factory-label "^2.0.0"
|
| 577 |
+
micromark-factory-space "^2.0.0"
|
| 578 |
+
micromark-factory-title "^2.0.0"
|
| 579 |
+
micromark-factory-whitespace "^2.0.0"
|
| 580 |
+
micromark-util-character "^2.0.0"
|
| 581 |
+
micromark-util-chunked "^2.0.0"
|
| 582 |
+
micromark-util-classify-character "^2.0.0"
|
| 583 |
+
micromark-util-html-tag-name "^2.0.0"
|
| 584 |
+
micromark-util-normalize-identifier "^2.0.0"
|
| 585 |
+
micromark-util-resolve-all "^2.0.0"
|
| 586 |
+
micromark-util-subtokenize "^2.0.0"
|
| 587 |
+
micromark-util-symbol "^2.0.0"
|
| 588 |
+
micromark-util-types "^2.0.0"
|
| 589 |
+
|
| 590 |
+
micromark-extension-mdx-expression@^3.0.0:
|
| 591 |
+
version "3.0.1"
|
| 592 |
+
resolved "https://registry.npmjs.org/micromark-extension-mdx-expression/-/micromark-extension-mdx-expression-3.0.1.tgz"
|
| 593 |
+
integrity sha512-dD/ADLJ1AeMvSAKBwO22zG22N4ybhe7kFIZ3LsDI0GlsNr2A3KYxb0LdC1u5rj4Nw+CHKY0RVdnHX8vj8ejm4Q==
|
| 594 |
+
dependencies:
|
| 595 |
+
"@types/estree" "^1.0.0"
|
| 596 |
+
devlop "^1.0.0"
|
| 597 |
+
micromark-factory-mdx-expression "^2.0.0"
|
| 598 |
+
micromark-factory-space "^2.0.0"
|
| 599 |
+
micromark-util-character "^2.0.0"
|
| 600 |
+
micromark-util-events-to-acorn "^2.0.0"
|
| 601 |
+
micromark-util-symbol "^2.0.0"
|
| 602 |
+
micromark-util-types "^2.0.0"
|
| 603 |
+
|
| 604 |
+
micromark-extension-mdx-jsx@^3.0.0:
|
| 605 |
+
version "3.0.2"
|
| 606 |
+
resolved "https://registry.npmjs.org/micromark-extension-mdx-jsx/-/micromark-extension-mdx-jsx-3.0.2.tgz"
|
| 607 |
+
integrity sha512-e5+q1DjMh62LZAJOnDraSSbDMvGJ8x3cbjygy2qFEi7HCeUT4BDKCvMozPozcD6WmOt6sVvYDNBKhFSz3kjOVQ==
|
| 608 |
+
dependencies:
|
| 609 |
+
"@types/estree" "^1.0.0"
|
| 610 |
+
devlop "^1.0.0"
|
| 611 |
+
estree-util-is-identifier-name "^3.0.0"
|
| 612 |
+
micromark-factory-mdx-expression "^2.0.0"
|
| 613 |
+
micromark-factory-space "^2.0.0"
|
| 614 |
+
micromark-util-character "^2.0.0"
|
| 615 |
+
micromark-util-events-to-acorn "^2.0.0"
|
| 616 |
+
micromark-util-symbol "^2.0.0"
|
| 617 |
+
micromark-util-types "^2.0.0"
|
| 618 |
+
vfile-message "^4.0.0"
|
| 619 |
+
|
| 620 |
+
micromark-extension-mdx-md@^2.0.0:
|
| 621 |
+
version "2.0.0"
|
| 622 |
+
resolved "https://registry.npmjs.org/micromark-extension-mdx-md/-/micromark-extension-mdx-md-2.0.0.tgz"
|
| 623 |
+
integrity sha512-EpAiszsB3blw4Rpba7xTOUptcFeBFi+6PY8VnJ2hhimH+vCQDirWgsMpz7w1XcZE7LVrSAUGb9VJpG9ghlYvYQ==
|
| 624 |
+
dependencies:
|
| 625 |
+
micromark-util-types "^2.0.0"
|
| 626 |
+
|
| 627 |
+
micromark-extension-mdxjs-esm@^3.0.0:
|
| 628 |
+
version "3.0.0"
|
| 629 |
+
resolved "https://registry.npmjs.org/micromark-extension-mdxjs-esm/-/micromark-extension-mdxjs-esm-3.0.0.tgz"
|
| 630 |
+
integrity sha512-DJFl4ZqkErRpq/dAPyeWp15tGrcrrJho1hKK5uBS70BCtfrIFg81sqcTVu3Ta+KD1Tk5vAtBNElWxtAa+m8K9A==
|
| 631 |
+
dependencies:
|
| 632 |
+
"@types/estree" "^1.0.0"
|
| 633 |
+
devlop "^1.0.0"
|
| 634 |
+
micromark-core-commonmark "^2.0.0"
|
| 635 |
+
micromark-util-character "^2.0.0"
|
| 636 |
+
micromark-util-events-to-acorn "^2.0.0"
|
| 637 |
+
micromark-util-symbol "^2.0.0"
|
| 638 |
+
micromark-util-types "^2.0.0"
|
| 639 |
+
unist-util-position-from-estree "^2.0.0"
|
| 640 |
+
vfile-message "^4.0.0"
|
| 641 |
+
|
| 642 |
+
micromark-extension-mdxjs@^3.0.0:
|
| 643 |
+
version "3.0.0"
|
| 644 |
+
resolved "https://registry.npmjs.org/micromark-extension-mdxjs/-/micromark-extension-mdxjs-3.0.0.tgz"
|
| 645 |
+
integrity sha512-A873fJfhnJ2siZyUrJ31l34Uqwy4xIFmvPY1oj+Ean5PHcPBYzEsvqvWGaWcfEIr11O5Dlw3p2y0tZWpKHDejQ==
|
| 646 |
+
dependencies:
|
| 647 |
+
acorn "^8.0.0"
|
| 648 |
+
acorn-jsx "^5.0.0"
|
| 649 |
+
micromark-extension-mdx-expression "^3.0.0"
|
| 650 |
+
micromark-extension-mdx-jsx "^3.0.0"
|
| 651 |
+
micromark-extension-mdx-md "^2.0.0"
|
| 652 |
+
micromark-extension-mdxjs-esm "^3.0.0"
|
| 653 |
+
micromark-util-combine-extensions "^2.0.0"
|
| 654 |
+
micromark-util-types "^2.0.0"
|
| 655 |
+
|
| 656 |
+
micromark-factory-destination@^2.0.0:
|
| 657 |
+
version "2.0.1"
|
| 658 |
+
resolved "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-2.0.1.tgz"
|
| 659 |
+
integrity sha512-Xe6rDdJlkmbFRExpTOmRj9N3MaWmbAgdpSrBQvCFqhezUn4AHqJHbaEnfbVYYiexVSs//tqOdY/DxhjdCiJnIA==
|
| 660 |
+
dependencies:
|
| 661 |
+
micromark-util-character "^2.0.0"
|
| 662 |
+
micromark-util-symbol "^2.0.0"
|
| 663 |
+
micromark-util-types "^2.0.0"
|
| 664 |
+
|
| 665 |
+
micromark-factory-label@^2.0.0:
|
| 666 |
+
version "2.0.1"
|
| 667 |
+
resolved "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-2.0.1.tgz"
|
| 668 |
+
integrity sha512-VFMekyQExqIW7xIChcXn4ok29YE3rnuyveW3wZQWWqF4Nv9Wk5rgJ99KzPvHjkmPXF93FXIbBp6YdW3t71/7Vg==
|
| 669 |
+
dependencies:
|
| 670 |
+
devlop "^1.0.0"
|
| 671 |
+
micromark-util-character "^2.0.0"
|
| 672 |
+
micromark-util-symbol "^2.0.0"
|
| 673 |
+
micromark-util-types "^2.0.0"
|
| 674 |
+
|
| 675 |
+
micromark-factory-mdx-expression@^2.0.0:
|
| 676 |
+
version "2.0.3"
|
| 677 |
+
resolved "https://registry.npmjs.org/micromark-factory-mdx-expression/-/micromark-factory-mdx-expression-2.0.3.tgz"
|
| 678 |
+
integrity sha512-kQnEtA3vzucU2BkrIa8/VaSAsP+EJ3CKOvhMuJgOEGg9KDC6OAY6nSnNDVRiVNRqj7Y4SlSzcStaH/5jge8JdQ==
|
| 679 |
+
dependencies:
|
| 680 |
+
"@types/estree" "^1.0.0"
|
| 681 |
+
devlop "^1.0.0"
|
| 682 |
+
micromark-factory-space "^2.0.0"
|
| 683 |
+
micromark-util-character "^2.0.0"
|
| 684 |
+
micromark-util-events-to-acorn "^2.0.0"
|
| 685 |
+
micromark-util-symbol "^2.0.0"
|
| 686 |
+
micromark-util-types "^2.0.0"
|
| 687 |
+
unist-util-position-from-estree "^2.0.0"
|
| 688 |
+
vfile-message "^4.0.0"
|
| 689 |
+
|
| 690 |
+
micromark-factory-space@^2.0.0:
|
| 691 |
+
version "2.0.1"
|
| 692 |
+
resolved "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-2.0.1.tgz"
|
| 693 |
+
integrity sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==
|
| 694 |
+
dependencies:
|
| 695 |
+
micromark-util-character "^2.0.0"
|
| 696 |
+
micromark-util-types "^2.0.0"
|
| 697 |
+
|
| 698 |
+
micromark-factory-title@^2.0.0:
|
| 699 |
+
version "2.0.1"
|
| 700 |
+
resolved "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-2.0.1.tgz"
|
| 701 |
+
integrity sha512-5bZ+3CjhAd9eChYTHsjy6TGxpOFSKgKKJPJxr293jTbfry2KDoWkhBb6TcPVB4NmzaPhMs1Frm9AZH7OD4Cjzw==
|
| 702 |
+
dependencies:
|
| 703 |
+
micromark-factory-space "^2.0.0"
|
| 704 |
+
micromark-util-character "^2.0.0"
|
| 705 |
+
micromark-util-symbol "^2.0.0"
|
| 706 |
+
micromark-util-types "^2.0.0"
|
| 707 |
+
|
| 708 |
+
micromark-factory-whitespace@^2.0.0:
|
| 709 |
+
version "2.0.1"
|
| 710 |
+
resolved "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-2.0.1.tgz"
|
| 711 |
+
integrity sha512-Ob0nuZ3PKt/n0hORHyvoD9uZhr+Za8sFoP+OnMcnWK5lngSzALgQYKMr9RJVOWLqQYuyn6ulqGWSXdwf6F80lQ==
|
| 712 |
+
dependencies:
|
| 713 |
+
micromark-factory-space "^2.0.0"
|
| 714 |
+
micromark-util-character "^2.0.0"
|
| 715 |
+
micromark-util-symbol "^2.0.0"
|
| 716 |
+
micromark-util-types "^2.0.0"
|
| 717 |
+
|
| 718 |
+
micromark-util-character@^2.0.0:
|
| 719 |
+
version "2.1.1"
|
| 720 |
+
resolved "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-2.1.1.tgz"
|
| 721 |
+
integrity sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==
|
| 722 |
+
dependencies:
|
| 723 |
+
micromark-util-symbol "^2.0.0"
|
| 724 |
+
micromark-util-types "^2.0.0"
|
| 725 |
+
|
| 726 |
+
micromark-util-chunked@^2.0.0:
|
| 727 |
+
version "2.0.1"
|
| 728 |
+
resolved "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-2.0.1.tgz"
|
| 729 |
+
integrity sha512-QUNFEOPELfmvv+4xiNg2sRYeS/P84pTW0TCgP5zc9FpXetHY0ab7SxKyAQCNCc1eK0459uoLI1y5oO5Vc1dbhA==
|
| 730 |
+
dependencies:
|
| 731 |
+
micromark-util-symbol "^2.0.0"
|
| 732 |
+
|
| 733 |
+
micromark-util-classify-character@^2.0.0:
|
| 734 |
+
version "2.0.1"
|
| 735 |
+
resolved "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-2.0.1.tgz"
|
| 736 |
+
integrity sha512-K0kHzM6afW/MbeWYWLjoHQv1sgg2Q9EccHEDzSkxiP/EaagNzCm7T/WMKZ3rjMbvIpvBiZgwR3dKMygtA4mG1Q==
|
| 737 |
+
dependencies:
|
| 738 |
+
micromark-util-character "^2.0.0"
|
| 739 |
+
micromark-util-symbol "^2.0.0"
|
| 740 |
+
micromark-util-types "^2.0.0"
|
| 741 |
+
|
| 742 |
+
micromark-util-combine-extensions@^2.0.0:
|
| 743 |
+
version "2.0.1"
|
| 744 |
+
resolved "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-2.0.1.tgz"
|
| 745 |
+
integrity sha512-OnAnH8Ujmy59JcyZw8JSbK9cGpdVY44NKgSM7E9Eh7DiLS2E9RNQf0dONaGDzEG9yjEl5hcqeIsj4hfRkLH/Bg==
|
| 746 |
+
dependencies:
|
| 747 |
+
micromark-util-chunked "^2.0.0"
|
| 748 |
+
micromark-util-types "^2.0.0"
|
| 749 |
+
|
| 750 |
+
micromark-util-decode-numeric-character-reference@^2.0.0:
|
| 751 |
+
version "2.0.2"
|
| 752 |
+
resolved "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-2.0.2.tgz"
|
| 753 |
+
integrity sha512-ccUbYk6CwVdkmCQMyr64dXz42EfHGkPQlBj5p7YVGzq8I7CtjXZJrubAYezf7Rp+bjPseiROqe7G6foFd+lEuw==
|
| 754 |
+
dependencies:
|
| 755 |
+
micromark-util-symbol "^2.0.0"
|
| 756 |
+
|
| 757 |
+
micromark-util-decode-string@^2.0.0:
|
| 758 |
+
version "2.0.1"
|
| 759 |
+
resolved "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-2.0.1.tgz"
|
| 760 |
+
integrity sha512-nDV/77Fj6eH1ynwscYTOsbK7rR//Uj0bZXBwJZRfaLEJ1iGBR6kIfNmlNqaqJf649EP0F3NWNdeJi03elllNUQ==
|
| 761 |
+
dependencies:
|
| 762 |
+
decode-named-character-reference "^1.0.0"
|
| 763 |
+
micromark-util-character "^2.0.0"
|
| 764 |
+
micromark-util-decode-numeric-character-reference "^2.0.0"
|
| 765 |
+
micromark-util-symbol "^2.0.0"
|
| 766 |
+
|
| 767 |
+
micromark-util-encode@^2.0.0:
|
| 768 |
+
version "2.0.1"
|
| 769 |
+
resolved "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-2.0.1.tgz"
|
| 770 |
+
integrity sha512-c3cVx2y4KqUnwopcO9b/SCdo2O67LwJJ/UyqGfbigahfegL9myoEFoDYZgkT7f36T0bLrM9hZTAaAyH+PCAXjw==
|
| 771 |
+
|
| 772 |
+
micromark-util-events-to-acorn@^2.0.0:
|
| 773 |
+
version "2.0.3"
|
| 774 |
+
resolved "https://registry.npmjs.org/micromark-util-events-to-acorn/-/micromark-util-events-to-acorn-2.0.3.tgz"
|
| 775 |
+
integrity sha512-jmsiEIiZ1n7X1Rr5k8wVExBQCg5jy4UXVADItHmNk1zkwEVhBuIUKRu3fqv+hs4nxLISi2DQGlqIOGiFxgbfHg==
|
| 776 |
+
dependencies:
|
| 777 |
+
"@types/estree" "^1.0.0"
|
| 778 |
+
"@types/unist" "^3.0.0"
|
| 779 |
+
devlop "^1.0.0"
|
| 780 |
+
estree-util-visit "^2.0.0"
|
| 781 |
+
micromark-util-symbol "^2.0.0"
|
| 782 |
+
micromark-util-types "^2.0.0"
|
| 783 |
+
vfile-message "^4.0.0"
|
| 784 |
+
|
| 785 |
+
micromark-util-html-tag-name@^2.0.0:
|
| 786 |
+
version "2.0.1"
|
| 787 |
+
resolved "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-2.0.1.tgz"
|
| 788 |
+
integrity sha512-2cNEiYDhCWKI+Gs9T0Tiysk136SnR13hhO8yW6BGNyhOC4qYFnwF1nKfD3HFAIXA5c45RrIG1ub11GiXeYd1xA==
|
| 789 |
+
|
| 790 |
+
micromark-util-normalize-identifier@^2.0.0:
|
| 791 |
+
version "2.0.1"
|
| 792 |
+
resolved "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-2.0.1.tgz"
|
| 793 |
+
integrity sha512-sxPqmo70LyARJs0w2UclACPUUEqltCkJ6PhKdMIDuJ3gSf/Q+/GIe3WKl0Ijb/GyH9lOpUkRAO2wp0GVkLvS9Q==
|
| 794 |
+
dependencies:
|
| 795 |
+
micromark-util-symbol "^2.0.0"
|
| 796 |
+
|
| 797 |
+
micromark-util-resolve-all@^2.0.0:
|
| 798 |
+
version "2.0.1"
|
| 799 |
+
resolved "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-2.0.1.tgz"
|
| 800 |
+
integrity sha512-VdQyxFWFT2/FGJgwQnJYbe1jjQoNTS4RjglmSjTUlpUMa95Htx9NHeYW4rGDJzbjvCsl9eLjMQwGeElsqmzcHg==
|
| 801 |
+
dependencies:
|
| 802 |
+
micromark-util-types "^2.0.0"
|
| 803 |
+
|
| 804 |
+
micromark-util-sanitize-uri@^2.0.0:
|
| 805 |
+
version "2.0.1"
|
| 806 |
+
resolved "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-2.0.1.tgz"
|
| 807 |
+
integrity sha512-9N9IomZ/YuGGZZmQec1MbgxtlgougxTodVwDzzEouPKo3qFWvymFHWcnDi2vzV1ff6kas9ucW+o3yzJK9YB1AQ==
|
| 808 |
+
dependencies:
|
| 809 |
+
micromark-util-character "^2.0.0"
|
| 810 |
+
micromark-util-encode "^2.0.0"
|
| 811 |
+
micromark-util-symbol "^2.0.0"
|
| 812 |
+
|
| 813 |
+
micromark-util-subtokenize@^2.0.0:
|
| 814 |
+
version "2.1.0"
|
| 815 |
+
resolved "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-2.1.0.tgz"
|
| 816 |
+
integrity sha512-XQLu552iSctvnEcgXw6+Sx75GflAPNED1qx7eBJ+wydBb2KCbRZe+NwvIEEMM83uml1+2WSXpBAcp9IUCgCYWA==
|
| 817 |
+
dependencies:
|
| 818 |
+
devlop "^1.0.0"
|
| 819 |
+
micromark-util-chunked "^2.0.0"
|
| 820 |
+
micromark-util-symbol "^2.0.0"
|
| 821 |
+
micromark-util-types "^2.0.0"
|
| 822 |
+
|
| 823 |
+
micromark-util-symbol@^2.0.0:
|
| 824 |
+
version "2.0.1"
|
| 825 |
+
resolved "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-2.0.1.tgz"
|
| 826 |
+
integrity sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==
|
| 827 |
+
|
| 828 |
+
micromark-util-types@^2.0.0:
|
| 829 |
+
version "2.0.2"
|
| 830 |
+
resolved "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-2.0.2.tgz"
|
| 831 |
+
integrity sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA==
|
| 832 |
+
|
| 833 |
+
micromark@^4.0.0:
|
| 834 |
+
version "4.0.2"
|
| 835 |
+
resolved "https://registry.npmjs.org/micromark/-/micromark-4.0.2.tgz"
|
| 836 |
+
integrity sha512-zpe98Q6kvavpCr1NPVSCMebCKfD7CA2NqZ+rykeNhONIJBpc1tFKt9hucLGwha3jNTNI8lHpctWJWoimVF4PfA==
|
| 837 |
+
dependencies:
|
| 838 |
+
"@types/debug" "^4.0.0"
|
| 839 |
+
debug "^4.0.0"
|
| 840 |
+
decode-named-character-reference "^1.0.0"
|
| 841 |
+
devlop "^1.0.0"
|
| 842 |
+
micromark-core-commonmark "^2.0.0"
|
| 843 |
+
micromark-factory-space "^2.0.0"
|
| 844 |
+
micromark-util-character "^2.0.0"
|
| 845 |
+
micromark-util-chunked "^2.0.0"
|
| 846 |
+
micromark-util-combine-extensions "^2.0.0"
|
| 847 |
+
micromark-util-decode-numeric-character-reference "^2.0.0"
|
| 848 |
+
micromark-util-encode "^2.0.0"
|
| 849 |
+
micromark-util-normalize-identifier "^2.0.0"
|
| 850 |
+
micromark-util-resolve-all "^2.0.0"
|
| 851 |
+
micromark-util-sanitize-uri "^2.0.0"
|
| 852 |
+
micromark-util-subtokenize "^2.0.0"
|
| 853 |
+
micromark-util-symbol "^2.0.0"
|
| 854 |
+
micromark-util-types "^2.0.0"
|
| 855 |
+
|
| 856 |
+
mime-db@1.52.0:
|
| 857 |
+
version "1.52.0"
|
| 858 |
+
resolved "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz"
|
| 859 |
+
integrity sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==
|
| 860 |
+
|
| 861 |
+
mime-types@^2.1.12, mime-types@^2.1.35:
|
| 862 |
+
version "2.1.35"
|
| 863 |
+
resolved "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz"
|
| 864 |
+
integrity sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==
|
| 865 |
+
dependencies:
|
| 866 |
+
mime-db "1.52.0"
|
| 867 |
+
|
| 868 |
+
mime@^3.0.0:
|
| 869 |
+
version "3.0.0"
|
| 870 |
+
resolved "https://registry.npmjs.org/mime/-/mime-3.0.0.tgz"
|
| 871 |
+
integrity sha512-jSCU7/VB1loIWBZe14aEYHU/+1UMEHoaO7qxCOVJOw9GgH72VAWppxNcjU+x9a2k3GSIBXNKxXQFqRvvZ7vr3A==
|
| 872 |
+
|
| 873 |
+
ms@^2.1.3:
|
| 874 |
+
version "2.1.3"
|
| 875 |
+
resolved "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz"
|
| 876 |
+
integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==
|
| 877 |
+
|
| 878 |
+
node-domexception@^1.0.0:
|
| 879 |
+
version "1.0.0"
|
| 880 |
+
resolved "https://registry.npmjs.org/node-domexception/-/node-domexception-1.0.0.tgz"
|
| 881 |
+
integrity sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ==
|
| 882 |
+
|
| 883 |
+
node-fetch@^2.6.1:
|
| 884 |
+
version "2.7.0"
|
| 885 |
+
resolved "https://registry.npmjs.org/node-fetch/-/node-fetch-2.7.0.tgz"
|
| 886 |
+
integrity sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==
|
| 887 |
+
dependencies:
|
| 888 |
+
whatwg-url "^5.0.0"
|
| 889 |
+
|
| 890 |
+
node-fetch@^2.7.0:
|
| 891 |
+
version "2.7.0"
|
| 892 |
+
resolved "https://registry.npmjs.org/node-fetch/-/node-fetch-2.7.0.tgz"
|
| 893 |
+
integrity sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==
|
| 894 |
+
dependencies:
|
| 895 |
+
whatwg-url "^5.0.0"
|
| 896 |
+
|
| 897 |
+
node-fetch@^3.3.2:
|
| 898 |
+
version "3.3.2"
|
| 899 |
+
resolved "https://registry.npmjs.org/node-fetch/-/node-fetch-3.3.2.tgz"
|
| 900 |
+
integrity sha512-dRB78srN/l6gqWulah9SrxeYnxeddIG30+GOqK/9OlLVyLg3HPnr6SqOWTWOXKRwC2eGYCkZ59NNuSgvSrpgOA==
|
| 901 |
+
dependencies:
|
| 902 |
+
data-uri-to-buffer "^4.0.0"
|
| 903 |
+
fetch-blob "^3.1.4"
|
| 904 |
+
formdata-polyfill "^4.0.10"
|
| 905 |
+
|
| 906 |
+
notion-to-md@^4.0.0-alpha:
|
| 907 |
+
version "4.0.0-alpha.7"
|
| 908 |
+
resolved "https://registry.npmjs.org/notion-to-md/-/notion-to-md-4.0.0-alpha.7.tgz"
|
| 909 |
+
integrity sha512-3kocKMEVcivy2ccuv2uZDJQFKXdvRmsujbN2GeOwP6yoNqhj/c/fmXroqPkk4XXRqNdJB2jzf5NPhPSWpuZkdA==
|
| 910 |
+
dependencies:
|
| 911 |
+
mime "^3.0.0"
|
| 912 |
+
node-fetch "^2.7.0"
|
| 913 |
+
ts-node "^10.9.2"
|
| 914 |
+
|
| 915 |
+
parse-entities@^4.0.0:
|
| 916 |
+
version "4.0.2"
|
| 917 |
+
resolved "https://registry.npmjs.org/parse-entities/-/parse-entities-4.0.2.tgz"
|
| 918 |
+
integrity sha512-GG2AQYWoLgL877gQIKeRPGO1xF9+eG1ujIb5soS5gPvLQ1y2o8FL90w2QWNdf9I361Mpp7726c+lj3U0qK1uGw==
|
| 919 |
+
dependencies:
|
| 920 |
+
"@types/unist" "^2.0.0"
|
| 921 |
+
character-entities-legacy "^3.0.0"
|
| 922 |
+
character-reference-invalid "^2.0.0"
|
| 923 |
+
decode-named-character-reference "^1.0.0"
|
| 924 |
+
is-alphanumerical "^2.0.0"
|
| 925 |
+
is-decimal "^2.0.0"
|
| 926 |
+
is-hexadecimal "^2.0.0"
|
| 927 |
+
|
| 928 |
+
remark-mdx@^3.0.0:
|
| 929 |
+
version "3.1.1"
|
| 930 |
+
resolved "https://registry.npmjs.org/remark-mdx/-/remark-mdx-3.1.1.tgz"
|
| 931 |
+
integrity sha512-Pjj2IYlUY3+D8x00UJsIOg5BEvfMyeI+2uLPn9VO9Wg4MEtN/VTIq2NEJQfde9PnX15KgtHyl9S0BcTnWrIuWg==
|
| 932 |
+
dependencies:
|
| 933 |
+
mdast-util-mdx "^3.0.0"
|
| 934 |
+
micromark-extension-mdxjs "^3.0.0"
|
| 935 |
+
|
| 936 |
+
remark-parse@^11.0.0:
|
| 937 |
+
version "11.0.0"
|
| 938 |
+
resolved "https://registry.npmjs.org/remark-parse/-/remark-parse-11.0.0.tgz"
|
| 939 |
+
integrity sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==
|
| 940 |
+
dependencies:
|
| 941 |
+
"@types/mdast" "^4.0.0"
|
| 942 |
+
mdast-util-from-markdown "^2.0.0"
|
| 943 |
+
micromark-util-types "^2.0.0"
|
| 944 |
+
unified "^11.0.0"
|
| 945 |
+
|
| 946 |
+
remark-stringify@^11.0.0:
|
| 947 |
+
version "11.0.0"
|
| 948 |
+
resolved "https://registry.npmjs.org/remark-stringify/-/remark-stringify-11.0.0.tgz"
|
| 949 |
+
integrity sha512-1OSmLd3awB/t8qdoEOMazZkNsfVTeY4fTsgzcQFdXNq8ToTN4ZGwrMnlda4K6smTFKD+GRV6O48i6Z4iKgPPpw==
|
| 950 |
+
dependencies:
|
| 951 |
+
"@types/mdast" "^4.0.0"
|
| 952 |
+
mdast-util-to-markdown "^2.0.0"
|
| 953 |
+
unified "^11.0.0"
|
| 954 |
+
|
| 955 |
+
section-matter@^1.0.0:
|
| 956 |
+
version "1.0.0"
|
| 957 |
+
resolved "https://registry.npmjs.org/section-matter/-/section-matter-1.0.0.tgz"
|
| 958 |
+
integrity sha512-vfD3pmTzGpufjScBh50YHKzEu2lxBWhVEHsNGoEXmCmn2hKGfeNLYMzCJpe8cD7gqX7TJluOVpBkAequ6dgMmA==
|
| 959 |
+
dependencies:
|
| 960 |
+
extend-shallow "^2.0.1"
|
| 961 |
+
kind-of "^6.0.0"
|
| 962 |
+
|
| 963 |
+
sprintf-js@~1.0.2:
|
| 964 |
+
version "1.0.3"
|
| 965 |
+
resolved "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz"
|
| 966 |
+
integrity sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==
|
| 967 |
+
|
| 968 |
+
stringify-entities@^4.0.0:
|
| 969 |
+
version "4.0.4"
|
| 970 |
+
resolved "https://registry.npmjs.org/stringify-entities/-/stringify-entities-4.0.4.tgz"
|
| 971 |
+
integrity sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==
|
| 972 |
+
dependencies:
|
| 973 |
+
character-entities-html4 "^2.0.0"
|
| 974 |
+
character-entities-legacy "^3.0.0"
|
| 975 |
+
|
| 976 |
+
strip-bom-string@^1.0.0:
|
| 977 |
+
version "1.0.0"
|
| 978 |
+
resolved "https://registry.npmjs.org/strip-bom-string/-/strip-bom-string-1.0.0.tgz"
|
| 979 |
+
integrity sha512-uCC2VHvQRYu+lMh4My/sFNmF2klFymLX1wHJeXnbEJERpV/ZsVuonzerjfrGpIGF7LBVa1O7i9kjiWvJiFck8g==
|
| 980 |
+
|
| 981 |
+
tr46@~0.0.3:
|
| 982 |
+
version "0.0.3"
|
| 983 |
+
resolved "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz"
|
| 984 |
+
integrity sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==
|
| 985 |
+
|
| 986 |
+
trough@^2.0.0:
|
| 987 |
+
version "2.2.0"
|
| 988 |
+
resolved "https://registry.npmjs.org/trough/-/trough-2.2.0.tgz"
|
| 989 |
+
integrity sha512-tmMpK00BjZiUyVyvrBK7knerNgmgvcV/KLVyuma/SC+TQN167GrMRciANTz09+k3zW8L8t60jWO1GpfkZdjTaw==
|
| 990 |
+
|
| 991 |
+
ts-node@^10.9.2:
|
| 992 |
+
version "10.9.2"
|
| 993 |
+
resolved "https://registry.npmjs.org/ts-node/-/ts-node-10.9.2.tgz"
|
| 994 |
+
integrity sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==
|
| 995 |
+
dependencies:
|
| 996 |
+
"@cspotcode/source-map-support" "^0.8.0"
|
| 997 |
+
"@tsconfig/node10" "^1.0.7"
|
| 998 |
+
"@tsconfig/node12" "^1.0.7"
|
| 999 |
+
"@tsconfig/node14" "^1.0.0"
|
| 1000 |
+
"@tsconfig/node16" "^1.0.2"
|
| 1001 |
+
acorn "^8.4.1"
|
| 1002 |
+
acorn-walk "^8.1.1"
|
| 1003 |
+
arg "^4.1.0"
|
| 1004 |
+
create-require "^1.1.0"
|
| 1005 |
+
diff "^4.0.1"
|
| 1006 |
+
make-error "^1.1.1"
|
| 1007 |
+
v8-compile-cache-lib "^3.0.1"
|
| 1008 |
+
yn "3.1.1"
|
| 1009 |
+
|
| 1010 |
+
typescript@>=2.7:
|
| 1011 |
+
version "5.9.2"
|
| 1012 |
+
resolved "https://registry.npmjs.org/typescript/-/typescript-5.9.2.tgz"
|
| 1013 |
+
integrity sha512-CWBzXQrc/qOkhidw1OzBTQuYRbfyxDXJMVJ1XNwUHGROVmuaeiEm3OslpZ1RV96d7SKKjZKrSJu3+t/xlw3R9A==
|
| 1014 |
+
|
| 1015 |
+
undici-types@~7.12.0:
|
| 1016 |
+
version "7.12.0"
|
| 1017 |
+
resolved "https://registry.npmjs.org/undici-types/-/undici-types-7.12.0.tgz"
|
| 1018 |
+
integrity sha512-goOacqME2GYyOZZfb5Lgtu+1IDmAlAEu5xnD3+xTzS10hT0vzpf0SPjkXwAw9Jm+4n/mQGDP3LO8CPbYROeBfQ==
|
| 1019 |
+
|
| 1020 |
+
unified@^11.0.0, unified@^11.0.4:
|
| 1021 |
+
version "11.0.5"
|
| 1022 |
+
resolved "https://registry.npmjs.org/unified/-/unified-11.0.5.tgz"
|
| 1023 |
+
integrity sha512-xKvGhPWw3k84Qjh8bI3ZeJjqnyadK+GEFtazSfZv/rKeTkTjOJho6mFqh2SM96iIcZokxiOpg78GazTSg8+KHA==
|
| 1024 |
+
dependencies:
|
| 1025 |
+
"@types/unist" "^3.0.0"
|
| 1026 |
+
bail "^2.0.0"
|
| 1027 |
+
devlop "^1.0.0"
|
| 1028 |
+
extend "^3.0.0"
|
| 1029 |
+
is-plain-obj "^4.0.0"
|
| 1030 |
+
trough "^2.0.0"
|
| 1031 |
+
vfile "^6.0.0"
|
| 1032 |
+
|
| 1033 |
+
unist-util-is@^6.0.0:
|
| 1034 |
+
version "6.0.0"
|
| 1035 |
+
resolved "https://registry.npmjs.org/unist-util-is/-/unist-util-is-6.0.0.tgz"
|
| 1036 |
+
integrity sha512-2qCTHimwdxLfz+YzdGfkqNlH0tLi9xjTnHddPmJwtIG9MGsdbutfTc4P+haPD7l7Cjxf/WZj+we5qfVPvvxfYw==
|
| 1037 |
+
dependencies:
|
| 1038 |
+
"@types/unist" "^3.0.0"
|
| 1039 |
+
|
| 1040 |
+
unist-util-position-from-estree@^2.0.0:
|
| 1041 |
+
version "2.0.0"
|
| 1042 |
+
resolved "https://registry.npmjs.org/unist-util-position-from-estree/-/unist-util-position-from-estree-2.0.0.tgz"
|
| 1043 |
+
integrity sha512-KaFVRjoqLyF6YXCbVLNad/eS4+OfPQQn2yOd7zF/h5T/CSL2v8NpN6a5TPvtbXthAGw5nG+PuTtq+DdIZr+cRQ==
|
| 1044 |
+
dependencies:
|
| 1045 |
+
"@types/unist" "^3.0.0"
|
| 1046 |
+
|
| 1047 |
+
unist-util-stringify-position@^4.0.0:
|
| 1048 |
+
version "4.0.0"
|
| 1049 |
+
resolved "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-4.0.0.tgz"
|
| 1050 |
+
integrity sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==
|
| 1051 |
+
dependencies:
|
| 1052 |
+
"@types/unist" "^3.0.0"
|
| 1053 |
+
|
| 1054 |
+
unist-util-visit-parents@^6.0.0:
|
| 1055 |
+
version "6.0.1"
|
| 1056 |
+
resolved "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-6.0.1.tgz"
|
| 1057 |
+
integrity sha512-L/PqWzfTP9lzzEa6CKs0k2nARxTdZduw3zyh8d2NVBnsyvHjSX4TWse388YrrQKbvI8w20fGjGlhgT96WwKykw==
|
| 1058 |
+
dependencies:
|
| 1059 |
+
"@types/unist" "^3.0.0"
|
| 1060 |
+
unist-util-is "^6.0.0"
|
| 1061 |
+
|
| 1062 |
+
unist-util-visit@^5.0.0:
|
| 1063 |
+
version "5.0.0"
|
| 1064 |
+
resolved "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-5.0.0.tgz"
|
| 1065 |
+
integrity sha512-MR04uvD+07cwl/yhVuVWAtw+3GOR/knlL55Nd/wAdblk27GCVt3lqpTivy/tkJcZoNPzTwS1Y+KMojlLDhoTzg==
|
| 1066 |
+
dependencies:
|
| 1067 |
+
"@types/unist" "^3.0.0"
|
| 1068 |
+
unist-util-is "^6.0.0"
|
| 1069 |
+
unist-util-visit-parents "^6.0.0"
|
| 1070 |
+
|
| 1071 |
+
v8-compile-cache-lib@^3.0.1:
|
| 1072 |
+
version "3.0.1"
|
| 1073 |
+
resolved "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz"
|
| 1074 |
+
integrity sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==
|
| 1075 |
+
|
| 1076 |
+
vfile-message@^4.0.0:
|
| 1077 |
+
version "4.0.3"
|
| 1078 |
+
resolved "https://registry.npmjs.org/vfile-message/-/vfile-message-4.0.3.tgz"
|
| 1079 |
+
integrity sha512-QTHzsGd1EhbZs4AsQ20JX1rC3cOlt/IWJruk893DfLRr57lcnOeMaWG4K0JrRta4mIJZKth2Au3mM3u03/JWKw==
|
| 1080 |
+
dependencies:
|
| 1081 |
+
"@types/unist" "^3.0.0"
|
| 1082 |
+
unist-util-stringify-position "^4.0.0"
|
| 1083 |
+
|
| 1084 |
+
vfile@^6.0.0:
|
| 1085 |
+
version "6.0.3"
|
| 1086 |
+
resolved "https://registry.npmjs.org/vfile/-/vfile-6.0.3.tgz"
|
| 1087 |
+
integrity sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q==
|
| 1088 |
+
dependencies:
|
| 1089 |
+
"@types/unist" "^3.0.0"
|
| 1090 |
+
vfile-message "^4.0.0"
|
| 1091 |
+
|
| 1092 |
+
web-streams-polyfill@^3.0.3:
|
| 1093 |
+
version "3.3.3"
|
| 1094 |
+
resolved "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.3.3.tgz"
|
| 1095 |
+
integrity sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw==
|
| 1096 |
+
|
| 1097 |
+
webidl-conversions@^3.0.0:
|
| 1098 |
+
version "3.0.1"
|
| 1099 |
+
resolved "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz"
|
| 1100 |
+
integrity sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==
|
| 1101 |
+
|
| 1102 |
+
whatwg-url@^5.0.0:
|
| 1103 |
+
version "5.0.0"
|
| 1104 |
+
resolved "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz"
|
| 1105 |
+
integrity sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==
|
| 1106 |
+
dependencies:
|
| 1107 |
+
tr46 "~0.0.3"
|
| 1108 |
+
webidl-conversions "^3.0.0"
|
| 1109 |
+
|
| 1110 |
+
yn@3.1.1:
|
| 1111 |
+
version "3.1.1"
|
| 1112 |
+
resolved "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz"
|
| 1113 |
+
integrity sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==
|
| 1114 |
+
|
| 1115 |
+
zwitch@^2.0.0:
|
| 1116 |
+
version "2.0.4"
|
| 1117 |
+
resolved "https://registry.npmjs.org/zwitch/-/zwitch-2.0.4.tgz"
|
| 1118 |
+
integrity sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==
|