@js-recon/js-recon 1.3.1-beta.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.gitattributes +2 -0
- package/.github/ISSUE_TEMPLATE/bug_report.md +29 -0
- package/.github/ISSUE_TEMPLATE/feature_request.md +20 -0
- package/.github/ISSUE_TEMPLATE/new_tech_support_request.md +26 -0
- package/.github/workflows/build-and-prettify.yaml +121 -0
- package/.github/workflows/pr_checker.yml +22 -0
- package/.github/workflows/publish-js-recon.yml +169 -0
- package/.prettierignore +2 -0
- package/.prettierrc +6 -0
- package/CHANGELOG.md +692 -0
- package/CLAUDE.md +290 -0
- package/Dockerfile +34 -0
- package/LICENSE +21 -0
- package/README.md +101 -0
- package/SECURITY.md +37 -0
- package/build/analyze/engine/astEngine.js +224 -0
- package/build/analyze/engine/astEngine.js.map +1 -0
- package/build/analyze/engine/index.js +59 -0
- package/build/analyze/engine/index.js.map +1 -0
- package/build/analyze/engine/requestEngine.js +100 -0
- package/build/analyze/engine/requestEngine.js.map +1 -0
- package/build/analyze/helpers/engineHelpers/findDirectAssignment.js +37 -0
- package/build/analyze/helpers/engineHelpers/findDirectAssignment.js.map +1 -0
- package/build/analyze/helpers/engineHelpers/findMemberExpressionAssignment.js +29 -0
- package/build/analyze/helpers/engineHelpers/findMemberExpressionAssignment.js.map +1 -0
- package/build/analyze/helpers/engineHelpers/resolveFunctionIdentifier.js +38 -0
- package/build/analyze/helpers/engineHelpers/resolveFunctionIdentifier.js.map +1 -0
- package/build/analyze/helpers/engineHelpers/taintFlow.js +250 -0
- package/build/analyze/helpers/engineHelpers/taintFlow.js.map +1 -0
- package/build/analyze/helpers/initRules.js +111 -0
- package/build/analyze/helpers/initRules.js.map +1 -0
- package/build/analyze/helpers/outputHelper.js +14 -0
- package/build/analyze/helpers/outputHelper.js.map +1 -0
- package/build/analyze/helpers/schemas.js +57 -0
- package/build/analyze/helpers/schemas.js.map +1 -0
- package/build/analyze/helpers/validate.js +89 -0
- package/build/analyze/helpers/validate.js.map +1 -0
- package/build/analyze/index.js +150 -0
- package/build/analyze/index.js.map +1 -0
- package/build/analyze/types/index.js +2 -0
- package/build/analyze/types/index.js.map +1 -0
- package/build/api_gateway/checkFeasibility.js +41 -0
- package/build/api_gateway/checkFeasibility.js.map +1 -0
- package/build/api_gateway/checkFireWallBlocking.js +33 -0
- package/build/api_gateway/checkFireWallBlocking.js.map +1 -0
- package/build/api_gateway/genReq.js +205 -0
- package/build/api_gateway/genReq.js.map +1 -0
- package/build/api_gateway/index.js +291 -0
- package/build/api_gateway/index.js.map +1 -0
- package/build/endpoints/gen_report/gen_json.js +30 -0
- package/build/endpoints/gen_report/gen_json.js.map +1 -0
- package/build/endpoints/gen_report/utility/iterate_n_store.js +64 -0
- package/build/endpoints/gen_report/utility/iterate_n_store.js.map +1 -0
- package/build/endpoints/index.js +101 -0
- package/build/endpoints/index.js.map +1 -0
- package/build/endpoints/next_js/client_jsFilesHref.js +100 -0
- package/build/endpoints/next_js/client_jsFilesHref.js.map +1 -0
- package/build/endpoints/next_js/client_jsonParse.js +89 -0
- package/build/endpoints/next_js/client_jsonParse.js.map +1 -0
- package/build/endpoints/next_js/client_mappedJsonFile.js +103 -0
- package/build/endpoints/next_js/client_mappedJsonFile.js.map +1 -0
- package/build/endpoints/next_js/client_subsequentRequests.js +211 -0
- package/build/endpoints/next_js/client_subsequentRequests.js.map +1 -0
- package/build/fingerprint/index.js +123 -0
- package/build/fingerprint/index.js.map +1 -0
- package/build/globalConfig.js +16 -0
- package/build/globalConfig.js.map +1 -0
- package/build/index.js +332 -0
- package/build/index.js.map +1 -0
- package/build/lazyLoad/angular/angular_getFromMainJs.js +55 -0
- package/build/lazyLoad/angular/angular_getFromMainJs.js.map +1 -0
- package/build/lazyLoad/angular/angular_getFromPageSource.js +43 -0
- package/build/lazyLoad/angular/angular_getFromPageSource.js.map +1 -0
- package/build/lazyLoad/downloadFilesUtil.js +127 -0
- package/build/lazyLoad/downloadFilesUtil.js.map +1 -0
- package/build/lazyLoad/downloadLoadedJsUtil.js +44 -0
- package/build/lazyLoad/downloadLoadedJsUtil.js.map +1 -0
- package/build/lazyLoad/downloadQueue.js +191 -0
- package/build/lazyLoad/downloadQueue.js.map +1 -0
- package/build/lazyLoad/globals.js +107 -0
- package/build/lazyLoad/globals.js.map +1 -0
- package/build/lazyLoad/index.js +377 -0
- package/build/lazyLoad/index.js.map +1 -0
- package/build/lazyLoad/next_js/NextJsCrawler.js +332 -0
- package/build/lazyLoad/next_js/NextJsCrawler.js.map +1 -0
- package/build/lazyLoad/next_js/next_GetJSScript.js +126 -0
- package/build/lazyLoad/next_js/next_GetJSScript.js.map +1 -0
- package/build/lazyLoad/next_js/next_GetLazyResourcesBuildManifestJs.js +83 -0
- package/build/lazyLoad/next_js/next_GetLazyResourcesBuildManifestJs.js.map +1 -0
- package/build/lazyLoad/next_js/next_GetLazyResourcesWebpackJs.js +222 -0
- package/build/lazyLoad/next_js/next_GetLazyResourcesWebpackJs.js.map +1 -0
- package/build/lazyLoad/next_js/next_SubsequentRequests.js +208 -0
- package/build/lazyLoad/next_js/next_SubsequentRequests.js.map +1 -0
- package/build/lazyLoad/next_js/next_bruteForceJsFiles.js +37 -0
- package/build/lazyLoad/next_js/next_bruteForceJsFiles.js.map +1 -0
- package/build/lazyLoad/next_js/next_buildId.js +55 -0
- package/build/lazyLoad/next_js/next_buildId.js.map +1 -0
- package/build/lazyLoad/next_js/next_getClientSidePaths.js +83 -0
- package/build/lazyLoad/next_js/next_getClientSidePaths.js.map +1 -0
- package/build/lazyLoad/next_js/next_globals.js +8 -0
- package/build/lazyLoad/next_js/next_globals.js.map +1 -0
- package/build/lazyLoad/next_js/next_parseLayoutJs.js +116 -0
- package/build/lazyLoad/next_js/next_parseLayoutJs.js.map +1 -0
- package/build/lazyLoad/next_js/next_promiseResolve.js +85 -0
- package/build/lazyLoad/next_js/next_promiseResolve.js.map +1 -0
- package/build/lazyLoad/next_js/next_scriptTagsSubsequentRequests.js +51 -0
- package/build/lazyLoad/next_js/next_scriptTagsSubsequentRequests.js.map +1 -0
- package/build/lazyLoad/nuxt_js/nuxt_astParse.js +202 -0
- package/build/lazyLoad/nuxt_js/nuxt_astParse.js.map +1 -0
- package/build/lazyLoad/nuxt_js/nuxt_getFromPageSource.js +82 -0
- package/build/lazyLoad/nuxt_js/nuxt_getFromPageSource.js.map +1 -0
- package/build/lazyLoad/nuxt_js/nuxt_stringAnalysisJSFiles.js +108 -0
- package/build/lazyLoad/nuxt_js/nuxt_stringAnalysisJSFiles.js.map +1 -0
- package/build/lazyLoad/react/react_followImports.js +105 -0
- package/build/lazyLoad/react/react_followImports.js.map +1 -0
- package/build/lazyLoad/react/react_getScriptTags.js +52 -0
- package/build/lazyLoad/react/react_getScriptTags.js.map +1 -0
- package/build/lazyLoad/react/react_sourcemapUrls.js +44 -0
- package/build/lazyLoad/react/react_sourcemapUrls.js.map +1 -0
- package/build/lazyLoad/react/react_webpackChunkPaths.js +188 -0
- package/build/lazyLoad/react/react_webpackChunkPaths.js.map +1 -0
- package/build/lazyLoad/sourcemap.js +188 -0
- package/build/lazyLoad/sourcemap.js.map +1 -0
- package/build/lazyLoad/svelte/svelte_discoverPagesFromJs.js +162 -0
- package/build/lazyLoad/svelte/svelte_discoverPagesFromJs.js.map +1 -0
- package/build/lazyLoad/svelte/svelte_getFromPageSource.js +91 -0
- package/build/lazyLoad/svelte/svelte_getFromPageSource.js.map +1 -0
- package/build/lazyLoad/svelte/svelte_recursivePageCrawl.js +180 -0
- package/build/lazyLoad/svelte/svelte_recursivePageCrawl.js.map +1 -0
- package/build/lazyLoad/svelte/svelte_stringAnalysisJSFiles.js +123 -0
- package/build/lazyLoad/svelte/svelte_stringAnalysisJSFiles.js.map +1 -0
- package/build/lazyLoad/techDetect/checkAngularJS.js +70 -0
- package/build/lazyLoad/techDetect/checkAngularJS.js.map +1 -0
- package/build/lazyLoad/techDetect/checkNextJS.js +45 -0
- package/build/lazyLoad/techDetect/checkNextJS.js.map +1 -0
- package/build/lazyLoad/techDetect/checkNuxtJS.js +39 -0
- package/build/lazyLoad/techDetect/checkNuxtJS.js.map +1 -0
- package/build/lazyLoad/techDetect/checkReact.js +86 -0
- package/build/lazyLoad/techDetect/checkReact.js.map +1 -0
- package/build/lazyLoad/techDetect/checkSvelte.js +69 -0
- package/build/lazyLoad/techDetect/checkSvelte.js.map +1 -0
- package/build/lazyLoad/techDetect/checkVueJS.js +118 -0
- package/build/lazyLoad/techDetect/checkVueJS.js.map +1 -0
- package/build/lazyLoad/techDetect/index.js +161 -0
- package/build/lazyLoad/techDetect/index.js.map +1 -0
- package/build/lazyLoad/vue/vue_RuntimeJs.js +169 -0
- package/build/lazyLoad/vue/vue_RuntimeJs.js.map +1 -0
- package/build/lazyLoad/vue/vue_SingleJsFileOnHome.js +102 -0
- package/build/lazyLoad/vue/vue_SingleJsFileOnHome.js.map +1 -0
- package/build/lazyLoad/vue/vue_discoverJsFiles.js +82 -0
- package/build/lazyLoad/vue/vue_discoverJsFiles.js.map +1 -0
- package/build/lazyLoad/vue/vue_getClientSidePaths.js +155 -0
- package/build/lazyLoad/vue/vue_getClientSidePaths.js.map +1 -0
- package/build/lazyLoad/vue/vue_jsImports.js +76 -0
- package/build/lazyLoad/vue/vue_jsImports.js.map +1 -0
- package/build/lazyLoad/vue/vue_pageSrc.js +60 -0
- package/build/lazyLoad/vue/vue_pageSrc.js.map +1 -0
- package/build/lazyLoad/vue/vue_reconstructSourceMaps.js +64 -0
- package/build/lazyLoad/vue/vue_reconstructSourceMaps.js.map +1 -0
- package/build/lazyLoad/vue/vue_recursiveClientSidePathDownload.js +142 -0
- package/build/lazyLoad/vue/vue_recursiveClientSidePathDownload.js.map +1 -0
- package/build/lazyLoad/vue/vue_severalJsFilesHome.js +57 -0
- package/build/lazyLoad/vue/vue_severalJsFilesHome.js.map +1 -0
- package/build/lazyLoad/vue/vue_sourcemapExtract.js +166 -0
- package/build/lazyLoad/vue/vue_sourcemapExtract.js.map +1 -0
- package/build/lazyLoad/vue/vue_stringJsFiles.js +148 -0
- package/build/lazyLoad/vue/vue_stringJsFiles.js.map +1 -0
- package/build/lazyLoad/vue/vue_viteMapDeps.js +89 -0
- package/build/lazyLoad/vue/vue_viteMapDeps.js.map +1 -0
- package/build/load/index.js +316 -0
- package/build/load/index.js.map +1 -0
- package/build/map/graphql/resolveGraphql.js +296 -0
- package/build/map/graphql/resolveGraphql.js.map +1 -0
- package/build/map/index.js +261 -0
- package/build/map/index.js.map +1 -0
- package/build/map/next_js/getAxiosInstances.js +64 -0
- package/build/map/next_js/getAxiosInstances.js.map +1 -0
- package/build/map/next_js/getExports.js +101 -0
- package/build/map/next_js/getExports.js.map +1 -0
- package/build/map/next_js/getFetchInstances.js +139 -0
- package/build/map/next_js/getFetchInstances.js.map +1 -0
- package/build/map/next_js/getTurbopackConnections.js +255 -0
- package/build/map/next_js/getTurbopackConnections.js.map +1 -0
- package/build/map/next_js/getWebpackConnections.js +235 -0
- package/build/map/next_js/getWebpackConnections.js.map +1 -0
- package/build/map/next_js/interactive.js +69 -0
- package/build/map/next_js/interactive.js.map +1 -0
- package/build/map/next_js/interactive_helpers/commandHandler.js +310 -0
- package/build/map/next_js/interactive_helpers/commandHandler.js.map +1 -0
- package/build/map/next_js/interactive_helpers/commandHelpers.js +245 -0
- package/build/map/next_js/interactive_helpers/commandHelpers.js.map +1 -0
- package/build/map/next_js/interactive_helpers/esqueryGen.js +370 -0
- package/build/map/next_js/interactive_helpers/esqueryGen.js.map +1 -0
- package/build/map/next_js/interactive_helpers/helpMenu.js +12 -0
- package/build/map/next_js/interactive_helpers/helpMenu.js.map +1 -0
- package/build/map/next_js/interactive_helpers/inputPatch.js +207 -0
- package/build/map/next_js/interactive_helpers/inputPatch.js.map +1 -0
- package/build/map/next_js/interactive_helpers/keybindings.js +90 -0
- package/build/map/next_js/interactive_helpers/keybindings.js.map +1 -0
- package/build/map/next_js/interactive_helpers/printer.js +23 -0
- package/build/map/next_js/interactive_helpers/printer.js.map +1 -0
- package/build/map/next_js/interactive_helpers/ui.js +88 -0
- package/build/map/next_js/interactive_helpers/ui.js.map +1 -0
- package/build/map/next_js/resolveAxios.js +152 -0
- package/build/map/next_js/resolveAxios.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/astNodeToJsonString.js +64 -0
- package/build/map/next_js/resolveAxiosHelpers/astNodeToJsonString.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/directCallsWithoutAssignment.js +48 -0
- package/build/map/next_js/resolveAxiosHelpers/directCallsWithoutAssignment.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/findAxiosClients.js +34 -0
- package/build/map/next_js/resolveAxiosHelpers/findAxiosClients.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/findAxiosInstance.js +39 -0
- package/build/map/next_js/resolveAxiosHelpers/findAxiosInstance.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/findCrossChunkParams.js +312 -0
- package/build/map/next_js/resolveAxiosHelpers/findCrossChunkParams.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/handleAxiosCreate.js +173 -0
- package/build/map/next_js/resolveAxiosHelpers/handleAxiosCreate.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/handleZDotCreate.js +261 -0
- package/build/map/next_js/resolveAxiosHelpers/handleZDotCreate.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/interceptorHeaders.js +206 -0
- package/build/map/next_js/resolveAxiosHelpers/interceptorHeaders.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/processAxiosCall.js +168 -0
- package/build/map/next_js/resolveAxiosHelpers/processAxiosCall.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/processDirectAxiosCall.js +121 -0
- package/build/map/next_js/resolveAxiosHelpers/processDirectAxiosCall.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/processExportedEndpoints.js +274 -0
- package/build/map/next_js/resolveAxiosHelpers/processExportedEndpoints.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/traceAxiosInstanceExports.js +518 -0
- package/build/map/next_js/resolveAxiosHelpers/traceAxiosInstanceExports.js.map +1 -0
- package/build/map/next_js/resolveAxiosHelpers/traceBody.js +913 -0
- package/build/map/next_js/resolveAxiosHelpers/traceBody.js.map +1 -0
- package/build/map/next_js/resolveFetch.js +533 -0
- package/build/map/next_js/resolveFetch.js.map +1 -0
- package/build/map/next_js/resolveNewRequest.js +749 -0
- package/build/map/next_js/resolveNewRequest.js.map +1 -0
- package/build/map/next_js/resolveServerActions.js +449 -0
- package/build/map/next_js/resolveServerActions.js.map +1 -0
- package/build/map/next_js/utils.js +1600 -0
- package/build/map/next_js/utils.js.map +1 -0
- package/build/map/react_js/getReactConnections.js +303 -0
- package/build/map/react_js/getReactConnections.js.map +1 -0
- package/build/map/react_js/interactive.js +4 -0
- package/build/map/react_js/interactive.js.map +1 -0
- package/build/map/react_js/react_resolveFetch.js +6 -0
- package/build/map/react_js/react_resolveFetch.js.map +1 -0
- package/build/map/svelte_js/interactive.js +58 -0
- package/build/map/svelte_js/interactive.js.map +1 -0
- package/build/map/svelte_js/interactive_helpers/commandHandler.js +4 -0
- package/build/map/svelte_js/interactive_helpers/commandHandler.js.map +1 -0
- package/build/map/vue_js/bodyResolver.js +477 -0
- package/build/map/vue_js/bodyResolver.js.map +1 -0
- package/build/map/vue_js/crossFileResolver.js +438 -0
- package/build/map/vue_js/crossFileResolver.js.map +1 -0
- package/build/map/vue_js/getViteConnections.js +343 -0
- package/build/map/vue_js/getViteConnections.js.map +1 -0
- package/build/map/vue_js/interactive.js +67 -0
- package/build/map/vue_js/interactive.js.map +1 -0
- package/build/map/vue_js/interactive_helpers/commandHandler.js +307 -0
- package/build/map/vue_js/interactive_helpers/commandHandler.js.map +1 -0
- package/build/map/vue_js/interactive_helpers/commandHelpers.js +39 -0
- package/build/map/vue_js/interactive_helpers/commandHelpers.js.map +1 -0
- package/build/map/vue_js/interactive_helpers/helpMenu.js +12 -0
- package/build/map/vue_js/interactive_helpers/helpMenu.js.map +1 -0
- package/build/map/vue_js/taint_utils.js +621 -0
- package/build/map/vue_js/taint_utils.js.map +1 -0
- package/build/map/vue_js/vue_resolveFetch.js +416 -0
- package/build/map/vue_js/vue_resolveFetch.js.map +1 -0
- package/build/map/vue_js/vue_resolveHttpClient.js +738 -0
- package/build/map/vue_js/vue_resolveHttpClient.js.map +1 -0
- package/build/map/vue_js/vue_resolveXhr.js +282 -0
- package/build/map/vue_js/vue_resolveXhr.js.map +1 -0
- package/build/mcp/chatOneShot.js +101 -0
- package/build/mcp/chatOneShot.js.map +1 -0
- package/build/mcp/claudeCodeCreds.js +150 -0
- package/build/mcp/claudeCodeCreds.js.map +1 -0
- package/build/mcp/cli.js +372 -0
- package/build/mcp/cli.js.map +1 -0
- package/build/mcp/commands.js +227 -0
- package/build/mcp/commands.js.map +1 -0
- package/build/mcp/config.js +68 -0
- package/build/mcp/config.js.map +1 -0
- package/build/mcp/index.js +50 -0
- package/build/mcp/index.js.map +1 -0
- package/build/mcp/intent.js +204 -0
- package/build/mcp/intent.js.map +1 -0
- package/build/mcp/jobs.js +199 -0
- package/build/mcp/jobs.js.map +1 -0
- package/build/mcp/mcpServer.js +241 -0
- package/build/mcp/mcpServer.js.map +1 -0
- package/build/mcp/providers.js +170 -0
- package/build/mcp/providers.js.map +1 -0
- package/build/mcp/skills.js +115 -0
- package/build/mcp/skills.js.map +1 -0
- package/build/mcp/tools.js +185 -0
- package/build/mcp/tools.js.map +1 -0
- package/build/refactor/index.js +85 -0
- package/build/refactor/index.js.map +1 -0
- package/build/refactor/next/index.js +109 -0
- package/build/refactor/next/index.js.map +1 -0
- package/build/refactor/react/index.js +636 -0
- package/build/refactor/react/index.js.map +1 -0
- package/build/report/index.js +68 -0
- package/build/report/index.js.map +1 -0
- package/build/report/utility/dataTables/genDataTablesPage.js +158 -0
- package/build/report/utility/dataTables/genDataTablesPage.js.map +1 -0
- package/build/report/utility/genHtml.js +516 -0
- package/build/report/utility/genHtml.js.map +1 -0
- package/build/report/utility/initReportDb.js +96 -0
- package/build/report/utility/initReportDb.js.map +1 -0
- package/build/report/utility/markdownGen/addAnalyze.js +53 -0
- package/build/report/utility/markdownGen/addAnalyze.js.map +1 -0
- package/build/report/utility/markdownGen/addMappedJson.js +33 -0
- package/build/report/utility/markdownGen/addMappedJson.js.map +1 -0
- package/build/report/utility/populateDb/populateAnalysisFindings.js +31 -0
- package/build/report/utility/populateDb/populateAnalysisFindings.js.map +1 -0
- package/build/report/utility/populateDb/populateEndpoints.js +50 -0
- package/build/report/utility/populateDb/populateEndpoints.js.map +1 -0
- package/build/report/utility/populateDb/populateMappedJson.js +31 -0
- package/build/report/utility/populateDb/populateMappedJson.js.map +1 -0
- package/build/report/utility/populateDb/populateMappedOpenapi.js +49 -0
- package/build/report/utility/populateDb/populateMappedOpenapi.js.map +1 -0
- package/build/run/index.js +446 -0
- package/build/run/index.js.map +1 -0
- package/build/run/interruptHandler.js +93 -0
- package/build/run/interruptHandler.js.map +1 -0
- package/build/strings/index.js +239 -0
- package/build/strings/index.js.map +1 -0
- package/build/strings/openapi.js +63 -0
- package/build/strings/openapi.js.map +1 -0
- package/build/strings/permutate.js +62 -0
- package/build/strings/permutate.js.map +1 -0
- package/build/strings/secrets.js +102 -0
- package/build/strings/secrets.js.map +1 -0
- package/build/utility/ai.js +97 -0
- package/build/utility/ai.js.map +1 -0
- package/build/utility/configureSandbox.js +14 -0
- package/build/utility/configureSandbox.js.map +1 -0
- package/build/utility/globals.js +322 -0
- package/build/utility/globals.js.map +1 -0
- package/build/utility/interfaces.js +2 -0
- package/build/utility/interfaces.js.map +1 -0
- package/build/utility/makeReq.js +448 -0
- package/build/utility/makeReq.js.map +1 -0
- package/build/utility/openapiGenerator.js +254 -0
- package/build/utility/openapiGenerator.js.map +1 -0
- package/build/utility/postmanGenerator.js +216 -0
- package/build/utility/postmanGenerator.js.map +1 -0
- package/build/utility/progressLog.js +50 -0
- package/build/utility/progressLog.js.map +1 -0
- package/build/utility/puppeteerInstance.js +5 -0
- package/build/utility/puppeteerInstance.js.map +1 -0
- package/build/utility/replaceUrlPlaceholders.js +48 -0
- package/build/utility/replaceUrlPlaceholders.js.map +1 -0
- package/build/utility/resolvePath.js +44 -0
- package/build/utility/resolvePath.js.map +1 -0
- package/build/utility/runSandboxed.js +42 -0
- package/build/utility/runSandboxed.js.map +1 -0
- package/build/utility/urlUtils.js +21 -0
- package/build/utility/urlUtils.js.map +1 -0
- package/contributing/nextjs.md +410 -0
- package/package.json +75 -0
|
@@ -0,0 +1,332 @@
|
|
|
1
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
2
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
3
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
4
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
5
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
6
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
7
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
|
+
});
|
|
9
|
+
};
|
|
10
|
+
import chalk from "chalk";
|
|
11
|
+
import { URL } from "url";
|
|
12
|
+
import next_getJSScript from "./next_GetJSScript.js";
|
|
13
|
+
import next_GetLazyResourcesWebpackJs from "./next_GetLazyResourcesWebpackJs.js";
|
|
14
|
+
import next_getLazyResourcesBuildManifestJs from "./next_GetLazyResourcesBuildManifestJs.js";
|
|
15
|
+
import subsequentRequests from "./next_SubsequentRequests.js";
|
|
16
|
+
import next_promiseResolve from "./next_promiseResolve.js";
|
|
17
|
+
import next_parseLayoutJs from "./next_parseLayoutJs.js";
|
|
18
|
+
import next_scriptTagsSubsequentRequests from "./next_scriptTagsSubsequentRequests.js";
|
|
19
|
+
import next_bruteForceJsFiles from "./next_bruteForceJsFiles.js";
|
|
20
|
+
import next_getClientSidePaths from "./next_getClientSidePaths.js";
|
|
21
|
+
import * as lazyLoadGlobals from "../globals.js";
|
|
22
|
+
/**
|
|
23
|
+
* Encapsulates the Next.js JS file discovery logic with recursive crawling.
|
|
24
|
+
*
|
|
25
|
+
* After running all discovery methods once, the crawler re-runs path-sensitive
|
|
26
|
+
* methods (promiseResolve, parseLayoutJs, getJSScript) on any *newly* found
|
|
27
|
+
* URLs until no new JS files are discovered, ensuring full coverage.
|
|
28
|
+
*/
|
|
29
|
+
class NextJsCrawler {
|
|
30
|
+
constructor(options) {
|
|
31
|
+
/**
|
|
32
|
+
* Maximum number of page URLs visited across the entire crawl instance.
|
|
33
|
+
* Prevents runaway crawls on sites with many locale/language variants where
|
|
34
|
+
* each locale page links to every other locale, causing exponential growth.
|
|
35
|
+
*/
|
|
36
|
+
this.MAX_VISITED_PAGES = 200;
|
|
37
|
+
this.visitedPageCount = 0;
|
|
38
|
+
/** Set to true by stop() to abort the crawl loop gracefully. */
|
|
39
|
+
this.stopped = false;
|
|
40
|
+
this.url = options.url;
|
|
41
|
+
this.output = options.output;
|
|
42
|
+
this.subsequentRequestsFlag = options.subsequentRequestsFlag;
|
|
43
|
+
this.urlsFile = options.urlsFile;
|
|
44
|
+
this.threads = options.threads;
|
|
45
|
+
this.research = options.research;
|
|
46
|
+
this.MAX_ITERATIONS = options.maxIterations;
|
|
47
|
+
this.onUrlsDiscovered = options.onUrlsDiscovered;
|
|
48
|
+
this.discoveredUrls = new Set();
|
|
49
|
+
this.pageScriptFingerprints = new Map();
|
|
50
|
+
this.techniqueEfficiencyMapping = {};
|
|
51
|
+
}
|
|
52
|
+
// ── helpers ──────────────────────────────────────────────────────────
|
|
53
|
+
/**
|
|
54
|
+
* Normalizes a page URL to origin+pathname, stripping query and fragment.
|
|
55
|
+
* Used as the key for pageScriptFingerprints.
|
|
56
|
+
*/
|
|
57
|
+
normalizePageUrl(u) {
|
|
58
|
+
try {
|
|
59
|
+
const parsed = new URL(u);
|
|
60
|
+
return parsed.origin + parsed.pathname;
|
|
61
|
+
}
|
|
62
|
+
catch (_a) {
|
|
63
|
+
return u;
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
/** Produces a stable fingerprint for a set of script URLs. */
|
|
67
|
+
scriptFingerprint(scripts) {
|
|
68
|
+
return [...new Set(scripts)].sort().join(",");
|
|
69
|
+
}
|
|
70
|
+
/** Signal the crawl loop to stop after the current iteration. */
|
|
71
|
+
stop() {
|
|
72
|
+
this.stopped = true;
|
|
73
|
+
}
|
|
74
|
+
/** Register newly found URLs and return only the ones that are truly new. */
|
|
75
|
+
registerUrls(urls) {
|
|
76
|
+
const newUrls = [];
|
|
77
|
+
for (const u of urls) {
|
|
78
|
+
if (!this.discoveredUrls.has(u)) {
|
|
79
|
+
this.discoveredUrls.add(u);
|
|
80
|
+
newUrls.push(u);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
return newUrls;
|
|
84
|
+
}
|
|
85
|
+
/** Emit newly discovered downloadable assets to the onUrlsDiscovered callback. */
|
|
86
|
+
emitDownloadable(urls) {
|
|
87
|
+
if (!this.onUrlsDiscovered)
|
|
88
|
+
return;
|
|
89
|
+
const downloadable = urls.filter((u) => {
|
|
90
|
+
try {
|
|
91
|
+
const p = new URL(u).pathname;
|
|
92
|
+
return p.endsWith(".js") || p.endsWith(".js.map");
|
|
93
|
+
}
|
|
94
|
+
catch (_a) {
|
|
95
|
+
return false;
|
|
96
|
+
}
|
|
97
|
+
});
|
|
98
|
+
if (downloadable.length > 0)
|
|
99
|
+
this.onUrlsDiscovered(downloadable);
|
|
100
|
+
}
|
|
101
|
+
/** Snapshot the current size so we can detect growth. */
|
|
102
|
+
get size() {
|
|
103
|
+
return this.discoveredUrls.size;
|
|
104
|
+
}
|
|
105
|
+
// ── initial discovery (run-once methods) ─────────────────────────────
|
|
106
|
+
/**
|
|
107
|
+
* Runs the heavyweight / one-shot discovery methods that only need to
|
|
108
|
+
* execute once (puppeteer-based webpack analysis, build-manifest, etc.).
|
|
109
|
+
*/
|
|
110
|
+
initialDiscovery() {
|
|
111
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
112
|
+
// 1. Script tags on the landing page
|
|
113
|
+
const jsFromScriptTag = yield next_getJSScript(this.url);
|
|
114
|
+
this.techniqueEfficiencyMapping["next_getJSScript"] = [
|
|
115
|
+
...(this.techniqueEfficiencyMapping["next_getJSScript"] || []),
|
|
116
|
+
...jsFromScriptTag,
|
|
117
|
+
];
|
|
118
|
+
this.emitDownloadable(this.registerUrls(jsFromScriptTag));
|
|
119
|
+
// Record the landing page's script fingerprint so the recursive loop
|
|
120
|
+
// never re-probes it.
|
|
121
|
+
const landingNorm = this.normalizePageUrl(this.url);
|
|
122
|
+
this.pageScriptFingerprints.set(landingNorm, new Set([this.scriptFingerprint(jsFromScriptTag)]));
|
|
123
|
+
// 1b. Client-side paths from <a href> tags on the landing page.
|
|
124
|
+
// These are page URLs (not JS), so they'll be picked up by the
|
|
125
|
+
// recursivePass loop which visits any newly registered non-JS URL.
|
|
126
|
+
const pathsFromAnchors = yield next_getClientSidePaths(this.url);
|
|
127
|
+
this.techniqueEfficiencyMapping["next_getClientSidePaths"] = [
|
|
128
|
+
...(this.techniqueEfficiencyMapping["next_getClientSidePaths"] || []),
|
|
129
|
+
...pathsFromAnchors,
|
|
130
|
+
];
|
|
131
|
+
this.emitDownloadable(this.registerUrls(pathsFromAnchors));
|
|
132
|
+
// 2. Webpack runtime analysis (puppeteer – expensive, run once per target).
|
|
133
|
+
// Skip in subsequent-requests passes: the webpack chunk URL builders are static
|
|
134
|
+
// and were already resolved in the initial lazyload call; re-running this costs
|
|
135
|
+
// 3-6 minutes per call without discovering new URLs.
|
|
136
|
+
if (!this.subsequentRequestsFlag) {
|
|
137
|
+
const jsFromWebpack = yield next_GetLazyResourcesWebpackJs(this.url);
|
|
138
|
+
this.techniqueEfficiencyMapping["next_GetLazyResourcesWebpackJs"] = jsFromWebpack;
|
|
139
|
+
lazyLoadGlobals.pushToJsUrls(jsFromWebpack);
|
|
140
|
+
this.emitDownloadable(this.registerUrls(jsFromWebpack));
|
|
141
|
+
}
|
|
142
|
+
// 3. _buildManifest.js
|
|
143
|
+
const jsFromBuildManifest = yield next_getLazyResourcesBuildManifestJs(this.url);
|
|
144
|
+
this.techniqueEfficiencyMapping["next_getLazyResourcesBuildManifestJs"] = jsFromBuildManifest;
|
|
145
|
+
lazyLoadGlobals.pushToJsUrls(jsFromBuildManifest);
|
|
146
|
+
this.emitDownloadable(this.registerUrls(jsFromBuildManifest));
|
|
147
|
+
// 4. Subsequent requests (RSC / script-tags on known endpoints)
|
|
148
|
+
if (this.subsequentRequestsFlag) {
|
|
149
|
+
const jsFromSubsequent = yield subsequentRequests(this.url, this.urlsFile, this.threads, this.output, lazyLoadGlobals.getJsUrls());
|
|
150
|
+
this.techniqueEfficiencyMapping["subsequentRequests"] = [...jsFromSubsequent];
|
|
151
|
+
this.emitDownloadable(this.registerUrls([...jsFromSubsequent]));
|
|
152
|
+
const jsFromScriptTagsSR = yield next_scriptTagsSubsequentRequests(this.url, this.urlsFile);
|
|
153
|
+
this.techniqueEfficiencyMapping["next_scriptTagsSubsequentRequests"] = jsFromScriptTagsSR;
|
|
154
|
+
lazyLoadGlobals.pushToJsUrls(jsFromScriptTagsSR);
|
|
155
|
+
this.emitDownloadable(this.registerUrls(jsFromScriptTagsSR));
|
|
156
|
+
}
|
|
157
|
+
// Also pull in anything the globals accumulated
|
|
158
|
+
this.emitDownloadable(this.registerUrls(lazyLoadGlobals.getJsUrls()));
|
|
159
|
+
this.emitDownloadable(this.registerUrls(lazyLoadGlobals.getJsonUrls()));
|
|
160
|
+
});
|
|
161
|
+
}
|
|
162
|
+
// ── recursive discovery ──────────────────────────────────────────────
|
|
163
|
+
/**
|
|
164
|
+
* Runs the lightweight methods that can discover *more* URLs from an
|
|
165
|
+
* existing set of JS file URLs. These are cheap enough to repeat.
|
|
166
|
+
*
|
|
167
|
+
* @param jsUrls The JS URLs to analyse in this pass.
|
|
168
|
+
* @returns Newly discovered URLs in this pass.
|
|
169
|
+
*/
|
|
170
|
+
recursivePass(jsUrls) {
|
|
171
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
172
|
+
let newInThisPass = [];
|
|
173
|
+
// Promise.all pattern analysis on JS file contents
|
|
174
|
+
const jsFromPromise = yield next_promiseResolve(jsUrls);
|
|
175
|
+
this.techniqueEfficiencyMapping["next_promiseResolve"] = [
|
|
176
|
+
...(this.techniqueEfficiencyMapping["next_promiseResolve"] || []),
|
|
177
|
+
...jsFromPromise,
|
|
178
|
+
];
|
|
179
|
+
const newFromPromise = this.registerUrls(jsFromPromise);
|
|
180
|
+
this.emitDownloadable(newFromPromise);
|
|
181
|
+
newInThisPass.push(...newFromPromise);
|
|
182
|
+
// Layout.js parsing → discovers new client-side page paths → visits them
|
|
183
|
+
const jsFromLayout = yield next_parseLayoutJs(this.url, jsUrls);
|
|
184
|
+
this.techniqueEfficiencyMapping["next_parseLayoutJs"] = [
|
|
185
|
+
...(this.techniqueEfficiencyMapping["next_parseLayoutJs"] || []),
|
|
186
|
+
...jsFromLayout,
|
|
187
|
+
];
|
|
188
|
+
const newFromLayout = this.registerUrls(jsFromLayout);
|
|
189
|
+
this.emitDownloadable(newFromLayout);
|
|
190
|
+
newInThisPass.push(...newFromLayout);
|
|
191
|
+
// Build a queue of unvisited page URLs to walk. Seed it with:
|
|
192
|
+
// - unvisited page URLs from the input batch (anchor-derived URLs
|
|
193
|
+
// registered by initialDiscovery, or pages from earlier passes
|
|
194
|
+
// that haven't been visited yet)
|
|
195
|
+
// - new page URLs discovered above (parseLayoutJs etc.)
|
|
196
|
+
// For every page URL visited we run script-tag extraction AND
|
|
197
|
+
// <a href> extraction, then enqueue any new page URLs that surfaces.
|
|
198
|
+
// visitedPageUrls breaks cycles.
|
|
199
|
+
const isPageUrl = (u) => {
|
|
200
|
+
let parsed;
|
|
201
|
+
try {
|
|
202
|
+
parsed = new URL(u);
|
|
203
|
+
}
|
|
204
|
+
catch (_a) {
|
|
205
|
+
return false;
|
|
206
|
+
}
|
|
207
|
+
return !parsed.pathname.endsWith(".js") && !parsed.pathname.endsWith(".js.map");
|
|
208
|
+
};
|
|
209
|
+
const pageQueue = [];
|
|
210
|
+
const enqueued = new Set(); // tracks full URLs to avoid duplicate entries per pass
|
|
211
|
+
const enqueueIfPage = (u) => {
|
|
212
|
+
if (this.visitedPageCount + pageQueue.length >= this.MAX_VISITED_PAGES)
|
|
213
|
+
return;
|
|
214
|
+
if (enqueued.has(u))
|
|
215
|
+
return; // exact URL already queued this pass
|
|
216
|
+
if (!isPageUrl(u))
|
|
217
|
+
return;
|
|
218
|
+
enqueued.add(u);
|
|
219
|
+
pageQueue.push(u);
|
|
220
|
+
};
|
|
221
|
+
for (const u of jsUrls)
|
|
222
|
+
enqueueIfPage(u);
|
|
223
|
+
for (const u of newInThisPass)
|
|
224
|
+
enqueueIfPage(u);
|
|
225
|
+
for (const u of pageQueue) {
|
|
226
|
+
if (this.stopped)
|
|
227
|
+
break; // honour stop() at each iteration boundary
|
|
228
|
+
if (this.visitedPageCount >= this.MAX_VISITED_PAGES) {
|
|
229
|
+
console.error(chalk.yellow(`[!] Visited page limit reached (${this.MAX_VISITED_PAGES}). Skipping remaining page queue entries.`));
|
|
230
|
+
break;
|
|
231
|
+
}
|
|
232
|
+
this.visitedPageCount++;
|
|
233
|
+
const normalized = this.normalizePageUrl(u);
|
|
234
|
+
// Fetch scripts first — used for both fingerprinting and URL registration.
|
|
235
|
+
const extra = yield next_getJSScript(u);
|
|
236
|
+
if (!extra || !Array.isArray(extra)) {
|
|
237
|
+
console.error(`[NextJsCrawler] Invalid return value from next_getJSScript for URL: ${u}`);
|
|
238
|
+
console.error(`[NextJsCrawler] Returned value:`, extra);
|
|
239
|
+
process.exit(1);
|
|
240
|
+
}
|
|
241
|
+
// Content-entropy dedup: skip this variant if its script set matches
|
|
242
|
+
// a fingerprint already recorded for this pathname.
|
|
243
|
+
const fp = this.scriptFingerprint(extra);
|
|
244
|
+
const knownFPs = this.pageScriptFingerprints.get(normalized);
|
|
245
|
+
if (knownFPs === null || knownFPs === void 0 ? void 0 : knownFPs.has(fp))
|
|
246
|
+
continue;
|
|
247
|
+
// New content for this pathname — record fingerprint and process.
|
|
248
|
+
if (!this.pageScriptFingerprints.has(normalized)) {
|
|
249
|
+
this.pageScriptFingerprints.set(normalized, new Set());
|
|
250
|
+
}
|
|
251
|
+
this.pageScriptFingerprints.get(normalized).add(fp);
|
|
252
|
+
this.techniqueEfficiencyMapping["next_getJSScript"] = [
|
|
253
|
+
...(this.techniqueEfficiencyMapping["next_getJSScript"] || []),
|
|
254
|
+
...extra,
|
|
255
|
+
];
|
|
256
|
+
const newFromScripts = this.registerUrls(extra);
|
|
257
|
+
this.emitDownloadable(newFromScripts);
|
|
258
|
+
newInThisPass.push(...newFromScripts);
|
|
259
|
+
for (const x of newFromScripts)
|
|
260
|
+
enqueueIfPage(x);
|
|
261
|
+
// Harvest <a href> links from this page so we keep expanding
|
|
262
|
+
// the crawl frontier.
|
|
263
|
+
const morePaths = yield next_getClientSidePaths(u);
|
|
264
|
+
this.techniqueEfficiencyMapping["next_getClientSidePaths"] = [
|
|
265
|
+
...(this.techniqueEfficiencyMapping["next_getClientSidePaths"] || []),
|
|
266
|
+
...morePaths,
|
|
267
|
+
];
|
|
268
|
+
const newFromAnchors = this.registerUrls(morePaths);
|
|
269
|
+
this.emitDownloadable(newFromAnchors);
|
|
270
|
+
newInThisPass.push(...newFromAnchors);
|
|
271
|
+
for (const x of newFromAnchors)
|
|
272
|
+
enqueueIfPage(x);
|
|
273
|
+
}
|
|
274
|
+
return newInThisPass;
|
|
275
|
+
});
|
|
276
|
+
}
|
|
277
|
+
// ── public API ───────────────────────────────────────────────────────
|
|
278
|
+
/**
|
|
279
|
+
* Main entry-point. Runs initial discovery, then iterates recursive
|
|
280
|
+
* passes until convergence (no new URLs) or the iteration cap.
|
|
281
|
+
*
|
|
282
|
+
* @returns The complete, deduplicated list of JS/asset URLs to download.
|
|
283
|
+
*/
|
|
284
|
+
crawl() {
|
|
285
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
286
|
+
// Phase 1 – initial heavyweight discovery
|
|
287
|
+
yield this.initialDiscovery();
|
|
288
|
+
// Phase 2 – recursive lightweight passes
|
|
289
|
+
let currentBatch = [...this.discoveredUrls];
|
|
290
|
+
let iteration = 0;
|
|
291
|
+
while (iteration < this.MAX_ITERATIONS && !this.stopped) {
|
|
292
|
+
iteration++;
|
|
293
|
+
const sizeBefore = this.size;
|
|
294
|
+
console.log(chalk.cyan(`[i] Recursive crawl pass ${iteration} – ${sizeBefore} URLs known`));
|
|
295
|
+
const newUrls = yield this.recursivePass(currentBatch);
|
|
296
|
+
if (newUrls.length === 0) {
|
|
297
|
+
console.log(chalk.green(`[✓] Recursive crawl converged after ${iteration} pass(es)`));
|
|
298
|
+
break;
|
|
299
|
+
}
|
|
300
|
+
console.log(chalk.green(`[+] Pass ${iteration} discovered ${newUrls.length} new URL(s)`));
|
|
301
|
+
// Next pass only analyses the newly found URLs
|
|
302
|
+
currentBatch = newUrls;
|
|
303
|
+
}
|
|
304
|
+
if (this.stopped) {
|
|
305
|
+
console.error(chalk.yellow(`[!] Crawler stopped — downloading all discovered files`));
|
|
306
|
+
}
|
|
307
|
+
else if (iteration >= this.MAX_ITERATIONS) {
|
|
308
|
+
console.error(chalk.yellow(`[!] Reached max recursive crawl iterations (${this.MAX_ITERATIONS})`));
|
|
309
|
+
}
|
|
310
|
+
// Phase 3 – brute-force .map files on the final set (skip if stopped by timeout)
|
|
311
|
+
if (!this.stopped) {
|
|
312
|
+
const allJsUrls = [...this.discoveredUrls].filter((u) => u.endsWith(".js") || u.endsWith(".js.map"));
|
|
313
|
+
const jsFromBrute = yield next_bruteForceJsFiles(allJsUrls);
|
|
314
|
+
this.techniqueEfficiencyMapping["next_bruteForceJsFiles"] = jsFromBrute;
|
|
315
|
+
this.emitDownloadable(this.registerUrls(jsFromBrute));
|
|
316
|
+
}
|
|
317
|
+
// Only return downloadable assets. Anchor-derived page URLs live in
|
|
318
|
+
// discoveredUrls to drive the crawl, but must not reach downloadFiles.
|
|
319
|
+
return [...this.discoveredUrls].filter((u) => {
|
|
320
|
+
try {
|
|
321
|
+
const p = new URL(u).pathname;
|
|
322
|
+
return p.endsWith(".js") || p.endsWith(".js.map");
|
|
323
|
+
}
|
|
324
|
+
catch (_a) {
|
|
325
|
+
return false;
|
|
326
|
+
}
|
|
327
|
+
});
|
|
328
|
+
});
|
|
329
|
+
}
|
|
330
|
+
}
|
|
331
|
+
export default NextJsCrawler;
|
|
332
|
+
//# sourceMappingURL=NextJsCrawler.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"NextJsCrawler.js","sourceRoot":"","sources":["../../../src/lazyLoad/next_js/NextJsCrawler.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
2
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
3
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
4
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
5
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
6
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
7
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
|
+
});
|
|
9
|
+
};
|
|
10
|
+
// lazyLoad/nextGetJSScript.js
|
|
11
|
+
import chalk from "chalk";
|
|
12
|
+
import { URL } from "url";
|
|
13
|
+
import * as cheerio from "cheerio";
|
|
14
|
+
import makeRequest from "../../utility/makeReq.js";
|
|
15
|
+
import { getJsUrls } from "../globals.js";
|
|
16
|
+
import { getCacheOnly } from "../../utility/globals.js";
|
|
17
|
+
const sleep = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
|
|
18
|
+
/**
|
|
19
|
+
* Scrapes all lazy-loaded JavaScript file URLs from the provided Next.js page.
|
|
20
|
+
*
|
|
21
|
+
* The function fetches the HTML with `makeRequest`, parses `script` tags via `cheerio`,
|
|
22
|
+
* and normalizes discovered `src` attributes (absolute, relative, or inline chunk hints)
|
|
23
|
+
* into absolute URLs using the shared lazy-load URL registry.
|
|
24
|
+
*
|
|
25
|
+
* @param {string} url - The URL of the webpage to fetch and parse.
|
|
26
|
+
* @returns {Promise<string[]>} - A promise that resolves to an array of absolute URLs
|
|
27
|
+
* pointing to JavaScript files found in the page.
|
|
28
|
+
*/
|
|
29
|
+
const MAX_FETCH_ATTEMPTS = 5;
|
|
30
|
+
const next_getJSScript = (url) => __awaiter(void 0, void 0, void 0, function* () {
|
|
31
|
+
const toReturn = [];
|
|
32
|
+
// get the page source — bounded retry so an unreachable host can't hang the crawler
|
|
33
|
+
let res = null;
|
|
34
|
+
const maxAttempts = getCacheOnly() ? 1 : MAX_FETCH_ATTEMPTS;
|
|
35
|
+
for (let attempt = 1; attempt <= maxAttempts; attempt++) {
|
|
36
|
+
res = yield makeRequest(url, {});
|
|
37
|
+
if (res)
|
|
38
|
+
break;
|
|
39
|
+
if (attempt < maxAttempts) {
|
|
40
|
+
console.error(chalk.yellow(`[!] Request to ${url} failed, retrying (${attempt}/${maxAttempts})...`));
|
|
41
|
+
yield sleep(1000);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
if (!res) {
|
|
45
|
+
if (!getCacheOnly()) {
|
|
46
|
+
console.error(chalk.red(`[!] Giving up on ${url} after ${maxAttempts} attempts`));
|
|
47
|
+
}
|
|
48
|
+
return toReturn;
|
|
49
|
+
}
|
|
50
|
+
const pageSource = yield res.text();
|
|
51
|
+
// cheerio to parse the page source
|
|
52
|
+
const $ = cheerio.load(pageSource);
|
|
53
|
+
// find all script tags
|
|
54
|
+
const scriptTags = $("script");
|
|
55
|
+
// iterate through script tags
|
|
56
|
+
for (const scriptTag of scriptTags) {
|
|
57
|
+
// get the src attribute
|
|
58
|
+
const src = $(scriptTag).attr("src");
|
|
59
|
+
// see if the src is a JS file
|
|
60
|
+
if (src !== undefined && src.match(/(https:\/\/[a-zA-Z0-9_\_\.]+\/.+\.js\??.*|\/.+\.js\??.*)/)) {
|
|
61
|
+
// if the src starts with /, like `/static/js/a.js` find the absolute URL
|
|
62
|
+
if (src.startsWith("/")) {
|
|
63
|
+
const absoluteUrl = new URL(url).origin + src;
|
|
64
|
+
if (!getJsUrls().includes(absoluteUrl)) {
|
|
65
|
+
toReturn.push(absoluteUrl);
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
else if (src.startsWith("http")) {
|
|
69
|
+
const urlObj = new URL(src);
|
|
70
|
+
const ext = urlObj.pathname.split(".").pop();
|
|
71
|
+
if (ext === "js") {
|
|
72
|
+
if (!getJsUrls().includes(src)) {
|
|
73
|
+
toReturn.push(src);
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
else if (src.match(/^[^/]/)) {
|
|
78
|
+
// if the src is a relative URL, like `static/js/a.js` find the absolute URL
|
|
79
|
+
// Get directory URL (origin + path without filename)
|
|
80
|
+
const pathParts = new URL(url).pathname.split("/");
|
|
81
|
+
pathParts.pop(); // remove filename from last
|
|
82
|
+
const directory = new URL(url).origin + pathParts.join("/") + "/";
|
|
83
|
+
if (!getJsUrls().includes(directory + src)) {
|
|
84
|
+
toReturn.push(directory + src);
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
else {
|
|
88
|
+
if (!getJsUrls().includes(src)) {
|
|
89
|
+
toReturn.push(src);
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
else {
|
|
94
|
+
// if the script tag is inline, it could contain static JS URL
|
|
95
|
+
// to get these, simply regex from the JS script
|
|
96
|
+
const js_script = $(scriptTag).html();
|
|
97
|
+
const matches = js_script === null || js_script === void 0 ? void 0 : js_script.match(/static\/chunks\/[a-zA-Z0-9_\-~.]+\.js/g);
|
|
98
|
+
if (matches) {
|
|
99
|
+
const uniqueMatches = [...new Set(matches)];
|
|
100
|
+
for (const match of uniqueMatches) {
|
|
101
|
+
// if it is using that static/chunks/ pattern, I can just get the filename
|
|
102
|
+
const filename = match.replace("static/chunks/", "");
|
|
103
|
+
// go through the already found URLs, coz they will have it (src attribute
|
|
104
|
+
// is there before inline things)
|
|
105
|
+
let js_path_dir;
|
|
106
|
+
for (const js_url of getJsUrls()) {
|
|
107
|
+
if (!js_path_dir &&
|
|
108
|
+
new URL(js_url).host === new URL(url).host &&
|
|
109
|
+
new URL(js_url).pathname.includes("static/chunks/")) {
|
|
110
|
+
js_path_dir = js_url.replace(/\/[^\/]+\.js.*$/, "");
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
if (js_path_dir) {
|
|
114
|
+
// Ensure js_path_dir was found
|
|
115
|
+
toReturn.push(js_path_dir + "/" + filename);
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
// causes too much noise after using it with subsequent requests
|
|
122
|
+
// console.log(chalk.green(`[✓] Found ${getJsUrls().length} JS files from the script tags`));
|
|
123
|
+
return toReturn;
|
|
124
|
+
});
|
|
125
|
+
export default next_getJSScript;
|
|
126
|
+
//# sourceMappingURL=next_GetJSScript.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"next_GetJSScript.js","sourceRoot":"","sources":["../../../src/lazyLoad/next_js/next_GetJSScript.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
2
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
3
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
4
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
5
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
6
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
7
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
|
+
});
|
|
9
|
+
};
|
|
10
|
+
import chalk from "chalk";
|
|
11
|
+
import * as globals from "../globals.js";
|
|
12
|
+
import makeRequest from "../../utility/makeReq.js";
|
|
13
|
+
import parser from "@babel/parser";
|
|
14
|
+
import _traverse from "@babel/traverse";
|
|
15
|
+
const traverse = _traverse.default;
|
|
16
|
+
/**
|
|
17
|
+
* Finds lazy-loaded JavaScript files from Next.js `_buildManifest.js`.
|
|
18
|
+
*
|
|
19
|
+
* Given a URL, this function finds the `_buildManifest.js` file in the given URL or file containing URLs.
|
|
20
|
+
* It then parses the file with the Babel parser and extracts all string literals from the AST.
|
|
21
|
+
* Finally, it iterates over the strings and finds any chunks (i.e., URLs containing "static/chunks/").
|
|
22
|
+
* The function returns an array of absolute URLs pointing to the lazy-loaded JS files found.
|
|
23
|
+
*
|
|
24
|
+
* @param {string} url - The URL or path to a file containing a list of URLs to process.
|
|
25
|
+
* @returns {Promise<string[] | any>} - A promise that resolves to an array of absolute URLs pointing to lazy-loaded JS files found, or undefined for invalid URL.
|
|
26
|
+
*/
|
|
27
|
+
const next_getLazyResourcesBuildManifestJs = (url) => __awaiter(void 0, void 0, void 0, function* () {
|
|
28
|
+
var _a;
|
|
29
|
+
// get the JS URLs
|
|
30
|
+
const foundUrls = globals.getJsUrls();
|
|
31
|
+
let toReturn = [];
|
|
32
|
+
let buildManifestUrl = "";
|
|
33
|
+
// iterate over them, and find the build manifest
|
|
34
|
+
for (const jsUrl of foundUrls) {
|
|
35
|
+
if (jsUrl.endsWith("_buildManifest.js")) {
|
|
36
|
+
buildManifestUrl = jsUrl;
|
|
37
|
+
break;
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
if (buildManifestUrl === "") {
|
|
41
|
+
return [];
|
|
42
|
+
}
|
|
43
|
+
// get the contents of that
|
|
44
|
+
try {
|
|
45
|
+
const response = yield makeRequest(buildManifestUrl, {});
|
|
46
|
+
if (!response)
|
|
47
|
+
return [];
|
|
48
|
+
let buildManifestContent = yield response.text();
|
|
49
|
+
// parse it with babel parser
|
|
50
|
+
const ast = parser.parse(buildManifestContent, {
|
|
51
|
+
sourceType: "unambiguous",
|
|
52
|
+
plugins: ["jsx", "typescript"],
|
|
53
|
+
errorRecovery: true,
|
|
54
|
+
});
|
|
55
|
+
let strings = [];
|
|
56
|
+
traverse(ast, {
|
|
57
|
+
StringLiteral(path) {
|
|
58
|
+
strings.push(path.node.value);
|
|
59
|
+
},
|
|
60
|
+
});
|
|
61
|
+
// iterate over the strings, and find the chunks
|
|
62
|
+
for (const stringTxt of strings) {
|
|
63
|
+
if (stringTxt.includes("static/chunks/")) {
|
|
64
|
+
// a chunk is found
|
|
65
|
+
// bui;d the relative URL
|
|
66
|
+
const foundUrl = new URL(`../../${stringTxt}`, buildManifestUrl).href;
|
|
67
|
+
globals.pushToJsUrls(foundUrl);
|
|
68
|
+
toReturn.push(foundUrl);
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
if (toReturn.length > 0) {
|
|
72
|
+
console.log(chalk.green(`[✓] Found ${toReturn.length} JS files from _buildManifest.js`));
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
catch (err) {
|
|
76
|
+
if ((err === null || err === void 0 ? void 0 : err.code) !== "ENOENT") {
|
|
77
|
+
console.error(chalk.red(`[!] Failed to parse _buildManifest.js: ${(_a = err === null || err === void 0 ? void 0 : err.message) !== null && _a !== void 0 ? _a : err}`));
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
return toReturn;
|
|
81
|
+
});
|
|
82
|
+
export default next_getLazyResourcesBuildManifestJs;
|
|
83
|
+
//# sourceMappingURL=next_GetLazyResourcesBuildManifestJs.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"next_GetLazyResourcesBuildManifestJs.js","sourceRoot":"","sources":["../../../src/lazyLoad/next_js/next_GetLazyResourcesBuildManifestJs.ts"],"names":[],"mappings":";;;;;;;;;AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,KAAK,OAAO,MAAM,eAAe,CAAC;AACzC,OAAO,WAAW,MAAM,0BAA0B,CAAC;AACnD,OAAO,MAAM,MAAM,eAAe,CAAC;AACnC,OAAO,SAAS,MAAM,iBAAiB,CAAC;AACxC,MAAM,QAAQ,GAAG,SAAS,CAAC,OAAO,CAAC;AAEnC;;;;;;;;;;GAUG;AACH,MAAM,oCAAoC,GAAG,CAAO,GAAW,EAA2B,EAAE;;IACxF,kBAAkB;IAClB,MAAM,SAAS,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC;IACtC,IAAI,QAAQ,GAAa,EAAE,CAAC;IAE5B,IAAI,gBAAgB,GAAW,EAAE,CAAC;IAClC,iDAAiD;IACjD,KAAK,MAAM,KAAK,IAAI,SAAS,EAAE,CAAC;QAC5B,IAAI,KAAK,CAAC,QAAQ,CAAC,mBAAmB,CAAC,EAAE,CAAC;YACtC,gBAAgB,GAAG,KAAK,CAAC;YACzB,MAAM;QACV,CAAC;IACL,CAAC;IAED,IAAI,gBAAgB,KAAK,EAAE,EAAE,CAAC;QAC1B,OAAO,EAAE,CAAC;IACd,CAAC;IAED,2BAA2B;IAC3B,IAAI,CAAC;QACD,MAAM,QAAQ,GAAG,MAAM,WAAW,CAAC,gBAAgB,EAAE,EAAE,CAAC,CAAC;QACzD,IAAI,CAAC,QAAQ;YAAE,OAAO,EAAE,CAAC;QAEzB,IAAI,oBAAoB,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;QAEjD,6BAA6B;QAC7B,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC,oBAAoB,EAAE;YAC3C,UAAU,EAAE,aAAa;YACzB,OAAO,EAAE,CAAC,KAAK,EAAE,YAAY,CAAC;YAC9B,aAAa,EAAE,IAAI;SACtB,CAAC,CAAC;QAEH,IAAI,OAAO,GAAa,EAAE,CAAC;QAE3B,QAAQ,CAAC,GAAG,EAAE;YACV,aAAa,CAAC,IAAI;gBACd,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;YAClC,CAAC;SACJ,CAAC,CAAC;QAEH,gDAAgD;QAEhD,KAAK,MAAM,SAAS,IAAI,OAAO,EAAE,CAAC;YAC9B,IAAI,SAAS,CAAC,QAAQ,CAAC,gBAAgB,CAAC,EAAE,CAAC;gBACvC,mBAAmB;gBACnB,yBAAyB;gBACzB,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC,SAAS,SAAS,EAAE,EAAE,gBAAgB,CAAC,CAAC,IAAI,CAAC;gBACtE,OAAO,CAAC,YAAY,CAAC,QAAQ,CAAC,CAAC;gBAC/B,QAAQ,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;YAC5B,CAAC;QACL,CAAC;QAED,IAAI,QAAQ,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACtB,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,KAAK,CAAC,aAAa,QAAQ,CAAC,MAAM,kCAAkC,CAAC,CAAC,CAAC;QAC7F,CAAC;IACL,CAAC;IAAC,OAAO,GAAQ,EAAE,CAAC;QAChB,IAAI,CAAA,GAAG,aAAH,GAAG,uBAAH,GAAG,CAAE,IAAI,MAAK,QAAQ,EAAE,CAAC;YACzB,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,0CAA0C,MAAA,GAAG,aAAH,GAAG,uBAAH,GAAG,CAAE,OAAO,mCAAI,GAAG,EAAE,CAAC,CAAC,CAAC;QAC9F,CAAC;IACL,CAAC;IAED,OAAO,QAAQ,CAAC;AACpB,CAAC,CAAA,CAAC;AAEF,eAAe,oCAAoC,CAAC"}
|