renovate-log-parser 0.1.1 → 0.2.0
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/README.md +119 -34
- package/dist/commands/install-analyze-skill.d.ts +0 -1
- package/dist/commands/install-analyze-skill.js +15 -12
- package/dist/commands/install-analyze-skill.js.map +1 -1
- package/dist/commands/web.d.ts +2 -1
- package/dist/commands/web.js +23 -11
- package/dist/commands/web.js.map +1 -1
- package/dist/core/skill-template.js +17 -3
- package/dist/core/skill-template.js.map +1 -1
- package/dist/server/api.d.ts +16 -0
- package/dist/server/api.js +173 -0
- package/dist/server/api.js.map +1 -0
- package/dist/server/http-error.d.ts +18 -0
- package/dist/server/http-error.js +23 -0
- package/dist/server/http-error.js.map +1 -0
- package/dist/server/index.d.ts +34 -0
- package/dist/server/index.js +54 -0
- package/dist/server/index.js.map +1 -0
- package/dist/server/log-registry.d.ts +34 -0
- package/dist/server/log-registry.js +157 -0
- package/dist/server/log-registry.js.map +1 -0
- package/dist/server/server-main.d.ts +1 -0
- package/dist/server/server-main.js +31 -0
- package/dist/server/server-main.js.map +1 -0
- package/dist/server/translate-filters.d.ts +58 -0
- package/dist/server/translate-filters.js +119 -0
- package/dist/server/translate-filters.js.map +1 -0
- package/package.json +13 -5
- package/web/.output/public/200.html +1 -0
- package/web/.output/public/404.html +1 -0
- package/web/.output/public/_nuxt/BDNMzG2s.js +1 -0
- package/web/.output/public/_nuxt/BjDV6v2h.js +1 -0
- package/web/.output/public/_nuxt/CVlqYHPc.js +6 -0
- package/web/.output/public/_nuxt/CuOsDQlp.js +1 -0
- package/web/.output/public/_nuxt/CztOM3Aq.js +28 -0
- package/web/.output/public/_nuxt/D3wuHpM_.js +3 -0
- package/web/.output/public/_nuxt/DK3Fl9T5.js +1 -0
- package/web/.output/public/_nuxt/DUXEQ2Eh.js +3 -0
- package/web/.output/public/_nuxt/DVWtRbHb.js +1 -0
- package/web/.output/public/_nuxt/DeS15jQo.js +1 -0
- package/web/.output/public/_nuxt/XP9RigIT.js +1 -0
- package/web/.output/public/_nuxt/builds/latest.json +1 -1
- package/web/.output/public/_nuxt/builds/meta/f68582c9-55a9-4352-b85a-d7f8de6f7202.json +1 -0
- package/web/.output/public/_nuxt/entry.BlZrUrUl.css +2 -0
- package/web/.output/public/_nuxt/error-404.zKZBzOko.css +1 -0
- package/web/.output/public/_nuxt/error-500.DwXcJPfY.css +1 -0
- package/web/.output/public/_nuxt/lGYp6_9X.js +1 -0
- package/web/.output/public/_nuxt/pages.BDcbBSnU.css +1 -0
- package/web/.output/public/_nuxt/public-sans-latin-400-italic.B1appi_f.woff2 +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-400-italic.DsCWG5h0.woff +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-400-normal.8Rpg0ruU.woff2 +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-400-normal.SBbinRkI.woff +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-500-normal.NlrCPXnF.woff2 +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-500-normal.vCxiVFAq.woff +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-600-normal.BR59oU-I.woff +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-600-normal.Fru-LXNs.woff2 +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-700-normal.BqJmxWdE.woff2 +0 -0
- package/web/.output/public/_nuxt/public-sans-latin-700-normal.Dm-oTPSL.woff +0 -0
- package/web/.output/public/favicon-dark.svg +32 -0
- package/web/.output/public/favicon-light.svg +32 -0
- package/web/.output/public/index.html +1 -0
- package/web/.output/nitro.json +0 -15
- package/web/.output/public/_fonts/57NSSoFy1VLVs2gqly8Ls9awBnZMFyXGrefpmqvdqmc-zJfbBtpgM4cDmcXBsqZNW79_kFnlpPd62b48glgdydA.woff2 +0 -0
- package/web/.output/public/_fonts/8VR2wSMN-3U4NbWAVYXlkRV6hA0jFBXP-0RtL3X7fko-x2gYI4qfmkRdxyQQUPaBZdZdgl1TeVrquF_TxHeM4lM.woff2 +0 -0
- package/web/.output/public/_fonts/GsKUclqeNLJ96g5AU593ug6yanivOiwjW_7zESNPChw-jHA4tBeM1bjF7LATGUpfBuSTyomIFrWBTzjF7txVYfg.woff2 +0 -0
- package/web/.output/public/_fonts/Ld1FnTo3yTIwDyGfTQ5-Fws9AWsCbKfMvgxduXr7JcY-W25bL8NF1fjpLRSOgJb7RoZPHqGQNwMTM7S9tHVoxx8.woff2 +0 -0
- package/web/.output/public/_fonts/NdzqRASp2bovDUhQT1IRE_EMqKJ2KYQdTCfFcBvL8yw-KhwZiS86o3fErOe5GGMExHUemmI_dBfaEFxjISZrBd0.woff2 +0 -0
- package/web/.output/public/_fonts/iTkrULNFJJkTvihIg1Vqi5IODRH_9btXCioVF5l98I8-AndUyau2HR2felA_ra8V2mutQgschhasE5FD1dXGJX8.woff2 +0 -0
- package/web/.output/public/_nuxt/BWja8e3M.js +0 -37
- package/web/.output/public/_nuxt/BgApMHS1.js +0 -1
- package/web/.output/public/_nuxt/CGPWRqbc.js +0 -1
- package/web/.output/public/_nuxt/DlAUqK2U.js +0 -1
- package/web/.output/public/_nuxt/Sgtec1U0.js +0 -1
- package/web/.output/public/_nuxt/builds/meta/785e7885-8d38-4aac-a7f6-735f68d27e63.json +0 -1
- package/web/.output/public/_nuxt/entry.9mB-pyEY.css +0 -1
- package/web/.output/public/_nuxt/error-404.B_PvSG-P.css +0 -1
- package/web/.output/public/_nuxt/error-500.CghkKCEr.css +0 -1
- package/web/.output/public/_nuxt/index.BlvAG7F6.css +0 -1
- package/web/.output/public/favicon.ico +0 -0
- package/web/.output/server/chunks/_/error-500.mjs +0 -19
- package/web/.output/server/chunks/_/error-500.mjs.map +0 -1
- package/web/.output/server/chunks/_/icons.mjs +0 -6153
- package/web/.output/server/chunks/_/icons.mjs.map +0 -1
- package/web/.output/server/chunks/_/icons2.mjs +0 -11494
- package/web/.output/server/chunks/_/icons2.mjs.map +0 -1
- package/web/.output/server/chunks/build/_plugin-vue_export-helper-1tPrXgE0.mjs +0 -10
- package/web/.output/server/chunks/build/_plugin-vue_export-helper-1tPrXgE0.mjs.map +0 -1
- package/web/.output/server/chunks/build/client.precomputed.mjs +0 -4
- package/web/.output/server/chunks/build/client.precomputed.mjs.map +0 -1
- package/web/.output/server/chunks/build/error-404-DOK13euR.mjs +0 -106
- package/web/.output/server/chunks/build/error-404-DOK13euR.mjs.map +0 -1
- package/web/.output/server/chunks/build/error-404-styles.9cNA4arh.mjs +0 -8
- package/web/.output/server/chunks/build/error-404-styles.9cNA4arh.mjs.map +0 -1
- package/web/.output/server/chunks/build/error-500-DKHEaocY.mjs +0 -89
- package/web/.output/server/chunks/build/error-500-DKHEaocY.mjs.map +0 -1
- package/web/.output/server/chunks/build/error-500-styles.BX54ZlkH.mjs +0 -8
- package/web/.output/server/chunks/build/error-500-styles.BX54ZlkH.mjs.map +0 -1
- package/web/.output/server/chunks/build/index-D_lNB6LA.mjs +0 -19675
- package/web/.output/server/chunks/build/index-D_lNB6LA.mjs.map +0 -1
- package/web/.output/server/chunks/build/index-styles.V2iua2bE.mjs +0 -8
- package/web/.output/server/chunks/build/index-styles.V2iua2bE.mjs.map +0 -1
- package/web/.output/server/chunks/build/server.mjs +0 -7910
- package/web/.output/server/chunks/build/server.mjs.map +0 -1
- package/web/.output/server/chunks/build/styles.mjs +0 -10
- package/web/.output/server/chunks/build/styles.mjs.map +0 -1
- package/web/.output/server/chunks/nitro/nitro.mjs +0 -6944
- package/web/.output/server/chunks/nitro/nitro.mjs.map +0 -1
- package/web/.output/server/chunks/routes/api/fields.get.mjs +0 -27
- package/web/.output/server/chunks/routes/api/fields.get.mjs.map +0 -1
- package/web/.output/server/chunks/routes/api/findings.get.mjs +0 -30
- package/web/.output/server/chunks/routes/api/findings.get.mjs.map +0 -1
- package/web/.output/server/chunks/routes/api/log/contents.post.mjs +0 -29
- package/web/.output/server/chunks/routes/api/log/contents.post.mjs.map +0 -1
- package/web/.output/server/chunks/routes/api/log/path.post.mjs +0 -30
- package/web/.output/server/chunks/routes/api/log/path.post.mjs.map +0 -1
- package/web/.output/server/chunks/routes/api/repositories.get.mjs +0 -27
- package/web/.output/server/chunks/routes/api/repositories.get.mjs.map +0 -1
- package/web/.output/server/chunks/routes/api/rows.get.mjs +0 -48
- package/web/.output/server/chunks/routes/api/rows.get.mjs.map +0 -1
- package/web/.output/server/chunks/routes/renderer.mjs +0 -451
- package/web/.output/server/chunks/routes/renderer.mjs.map +0 -1
- package/web/.output/server/chunks/virtual/_virtual_spa-template.mjs +0 -4
- package/web/.output/server/chunks/virtual/_virtual_spa-template.mjs.map +0 -1
- package/web/.output/server/index.mjs +0 -16
- package/web/.output/server/index.mjs.map +0 -1
- package/web/.output/server/node_modules/.nitro/hookable@5.5.3/dist/index.mjs +0 -290
- package/web/.output/server/node_modules/.nitro/hookable@5.5.3/package.json +0 -49
- package/web/.output/server/node_modules/.nitro/hookable@6.1.1/dist/index.mjs +0 -257
- package/web/.output/server/node_modules/.nitro/hookable@6.1.1/package.json +0 -53
- package/web/.output/server/node_modules/@babel/parser/lib/index.js +0 -14599
- package/web/.output/server/node_modules/@babel/parser/package.json +0 -50
- package/web/.output/server/node_modules/@floating-ui/core/dist/floating-ui.core.mjs +0 -1038
- package/web/.output/server/node_modules/@floating-ui/core/package.json +0 -63
- package/web/.output/server/node_modules/@floating-ui/dom/dist/floating-ui.dom.mjs +0 -789
- package/web/.output/server/node_modules/@floating-ui/dom/package.json +0 -72
- package/web/.output/server/node_modules/@floating-ui/utils/dist/floating-ui.utils.dom.mjs +0 -165
- package/web/.output/server/node_modules/@floating-ui/utils/dist/floating-ui.utils.mjs +0 -136
- package/web/.output/server/node_modules/@floating-ui/utils/package.json +0 -70
- package/web/.output/server/node_modules/@floating-ui/vue/dist/floating-ui.vue.mjs +0 -190
- package/web/.output/server/node_modules/@floating-ui/vue/package.json +0 -71
- package/web/.output/server/node_modules/@iconify/utils/lib/colors/index.js +0 -295
- package/web/.output/server/node_modules/@iconify/utils/lib/colors/keywords.js +0 -701
- package/web/.output/server/node_modules/@iconify/utils/lib/css/common.js +0 -75
- package/web/.output/server/node_modules/@iconify/utils/lib/css/format.js +0 -39
- package/web/.output/server/node_modules/@iconify/utils/lib/css/icon.js +0 -47
- package/web/.output/server/node_modules/@iconify/utils/lib/css/icons.js +0 -128
- package/web/.output/server/node_modules/@iconify/utils/lib/customisations/bool.js +0 -19
- package/web/.output/server/node_modules/@iconify/utils/lib/customisations/defaults.js +0 -13
- package/web/.output/server/node_modules/@iconify/utils/lib/customisations/flip.js +0 -17
- package/web/.output/server/node_modules/@iconify/utils/lib/customisations/merge.js +0 -16
- package/web/.output/server/node_modules/@iconify/utils/lib/customisations/rotate.js +0 -30
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/cleanup.js +0 -78
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/convert.js +0 -100
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/data.js +0 -28
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/format.js +0 -58
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/parse.js +0 -48
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/regex/base.js +0 -203
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/regex/create.js +0 -33
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/regex/numbers.js +0 -132
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/regex/similar.js +0 -165
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/regex/tree.js +0 -79
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/replace/find.js +0 -92
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/replace/replace.js +0 -26
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/test/components.js +0 -76
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/test/missing.js +0 -66
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/test/name.js +0 -45
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/test/parse.js +0 -103
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/test/similar.js +0 -36
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/test/tree.js +0 -92
- package/web/.output/server/node_modules/@iconify/utils/lib/emoji/test/variations.js +0 -62
- package/web/.output/server/node_modules/@iconify/utils/lib/icon/defaults.js +0 -25
- package/web/.output/server/node_modules/@iconify/utils/lib/icon/merge.js +0 -16
- package/web/.output/server/node_modules/@iconify/utils/lib/icon/name.js +0 -57
- package/web/.output/server/node_modules/@iconify/utils/lib/icon/square.js +0 -33
- package/web/.output/server/node_modules/@iconify/utils/lib/icon/transformations.js +0 -12
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/convert-info.js +0 -125
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/expand.js +0 -19
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/get-icon.js +0 -25
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/get-icons.js +0 -36
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/minify.js +0 -91
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/parse.js +0 -46
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/tree.js +0 -23
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/validate-basic.js +0 -42
- package/web/.output/server/node_modules/@iconify/utils/lib/icon-set/validate.js +0 -123
- package/web/.output/server/node_modules/@iconify/utils/lib/index.js +0 -52
- package/web/.output/server/node_modules/@iconify/utils/lib/loader/custom.js +0 -30
- package/web/.output/server/node_modules/@iconify/utils/lib/loader/loader.js +0 -26
- package/web/.output/server/node_modules/@iconify/utils/lib/loader/modern.js +0 -27
- package/web/.output/server/node_modules/@iconify/utils/lib/loader/utils.js +0 -105
- package/web/.output/server/node_modules/@iconify/utils/lib/misc/objects.js +0 -26
- package/web/.output/server/node_modules/@iconify/utils/lib/misc/strings.js +0 -26
- package/web/.output/server/node_modules/@iconify/utils/lib/misc/title.js +0 -9
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/build.js +0 -113
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/defs.js +0 -31
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/encode-svg-for-css.js +0 -13
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/html.js +0 -9
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/id.js +0 -41
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/inner-html.js +0 -22
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/parse.js +0 -67
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/pretty.js +0 -54
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/size.js +0 -27
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/trim.js +0 -7
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/url.js +0 -22
- package/web/.output/server/node_modules/@iconify/utils/lib/svg/viewbox.js +0 -8
- package/web/.output/server/node_modules/@iconify/utils/package.json +0 -119
- package/web/.output/server/node_modules/@iconify/vue/dist/iconify.mjs +0 -1896
- package/web/.output/server/node_modules/@iconify/vue/package.json +0 -62
- package/web/.output/server/node_modules/@tanstack/virtual-core/dist/esm/index.js +0 -1268
- package/web/.output/server/node_modules/@tanstack/virtual-core/dist/esm/lazy-measurements.js +0 -34
- package/web/.output/server/node_modules/@tanstack/virtual-core/dist/esm/utils.js +0 -74
- package/web/.output/server/node_modules/@tanstack/virtual-core/package.json +0 -56
- package/web/.output/server/node_modules/@tanstack/vue-virtual/dist/esm/index.js +0 -66
- package/web/.output/server/node_modules/@tanstack/vue-virtual/package.json +0 -68
- package/web/.output/server/node_modules/@vue/compiler-core/dist/compiler-core.cjs.prod.js +0 -6759
- package/web/.output/server/node_modules/@vue/compiler-core/package.json +0 -58
- package/web/.output/server/node_modules/@vue/compiler-dom/dist/compiler-dom.cjs.prod.js +0 -689
- package/web/.output/server/node_modules/@vue/compiler-dom/package.json +0 -57
- package/web/.output/server/node_modules/@vue/compiler-ssr/dist/compiler-ssr.cjs.js +0 -1413
- package/web/.output/server/node_modules/@vue/compiler-ssr/package.json +0 -34
- package/web/.output/server/node_modules/@vue/devtools-api/dist/index.js +0 -2
- package/web/.output/server/node_modules/@vue/devtools-api/package.json +0 -34
- package/web/.output/server/node_modules/@vue/devtools-kit/dist/index.js +0 -5670
- package/web/.output/server/node_modules/@vue/devtools-kit/node_modules/hookable/dist/index.mjs +0 -290
- package/web/.output/server/node_modules/@vue/devtools-kit/node_modules/hookable/package.json +0 -49
- package/web/.output/server/node_modules/@vue/devtools-kit/package.json +0 -44
- package/web/.output/server/node_modules/@vue/devtools-shared/dist/index.js +0 -239
- package/web/.output/server/node_modules/@vue/devtools-shared/package.json +0 -33
- package/web/.output/server/node_modules/@vue/reactivity/dist/reactivity.cjs.prod.js +0 -1899
- package/web/.output/server/node_modules/@vue/reactivity/package.json +0 -55
- package/web/.output/server/node_modules/@vue/runtime-core/dist/runtime-core.cjs.prod.js +0 -6940
- package/web/.output/server/node_modules/@vue/runtime-core/package.json +0 -52
- package/web/.output/server/node_modules/@vue/runtime-dom/dist/runtime-dom.cjs.prod.js +0 -1822
- package/web/.output/server/node_modules/@vue/runtime-dom/package.json +0 -60
- package/web/.output/server/node_modules/@vue/server-renderer/dist/server-renderer.cjs.prod.js +0 -896
- package/web/.output/server/node_modules/@vue/server-renderer/package.json +0 -55
- package/web/.output/server/node_modules/@vue/shared/dist/shared.cjs.prod.js +0 -604
- package/web/.output/server/node_modules/@vue/shared/package.json +0 -47
- package/web/.output/server/node_modules/@vueuse/core/dist/index.js +0 -8464
- package/web/.output/server/node_modules/@vueuse/core/package.json +0 -49
- package/web/.output/server/node_modules/@vueuse/shared/dist/index.js +0 -2013
- package/web/.output/server/node_modules/@vueuse/shared/package.json +0 -42
- package/web/.output/server/node_modules/aria-hidden/dist/es5/index.js +0 -174
- package/web/.output/server/node_modules/aria-hidden/package.json +0 -71
- package/web/.output/server/node_modules/birpc/dist/index.mjs +0 -291
- package/web/.output/server/node_modules/birpc/package.json +0 -57
- package/web/.output/server/node_modules/consola/dist/chunks/prompt.mjs +0 -280
- package/web/.output/server/node_modules/consola/dist/core.mjs +0 -512
- package/web/.output/server/node_modules/consola/dist/index.mjs +0 -651
- package/web/.output/server/node_modules/consola/dist/shared/consola.DRwqZj3T.mjs +0 -72
- package/web/.output/server/node_modules/consola/dist/shared/consola.DXBYu-KD.mjs +0 -288
- package/web/.output/server/node_modules/consola/package.json +0 -136
- package/web/.output/server/node_modules/devalue/index.js +0 -4
- package/web/.output/server/node_modules/devalue/package.json +0 -40
- package/web/.output/server/node_modules/devalue/src/base64.js +0 -60
- package/web/.output/server/node_modules/devalue/src/constants.js +0 -12
- package/web/.output/server/node_modules/devalue/src/parse.js +0 -283
- package/web/.output/server/node_modules/devalue/src/stringify.js +0 -401
- package/web/.output/server/node_modules/devalue/src/uneval.js +0 -552
- package/web/.output/server/node_modules/devalue/src/utils.js +0 -160
- package/web/.output/server/node_modules/entities/dist/commonjs/decode-codepoint.js +0 -77
- package/web/.output/server/node_modules/entities/dist/commonjs/decode.js +0 -568
- package/web/.output/server/node_modules/entities/dist/commonjs/generated/decode-data-html.js +0 -7
- package/web/.output/server/node_modules/entities/dist/commonjs/generated/decode-data-xml.js +0 -7
- package/web/.output/server/node_modules/entities/dist/commonjs/internal/bin-trie-flags.js +0 -21
- package/web/.output/server/node_modules/entities/dist/commonjs/internal/decode-shared.js +0 -31
- package/web/.output/server/node_modules/entities/dist/commonjs/package.json +0 -3
- package/web/.output/server/node_modules/entities/package.json +0 -120
- package/web/.output/server/node_modules/estree-walker/dist/umd/estree-walker.js +0 -344
- package/web/.output/server/node_modules/estree-walker/package.json +0 -37
- package/web/.output/server/node_modules/hookable/dist/index.mjs +0 -257
- package/web/.output/server/node_modules/hookable/package.json +0 -53
- package/web/.output/server/node_modules/nostics/dist/index.mjs +0 -179
- package/web/.output/server/node_modules/nostics/package.json +0 -124
- package/web/.output/server/node_modules/perfect-debounce/dist/index.mjs +0 -89
- package/web/.output/server/node_modules/perfect-debounce/package.json +0 -41
- package/web/.output/server/node_modules/rou3/dist/index.mjs +0 -501
- package/web/.output/server/node_modules/rou3/package.json +0 -48
- package/web/.output/server/node_modules/source-map-js/lib/array-set.js +0 -121
- package/web/.output/server/node_modules/source-map-js/lib/base64-vlq.js +0 -140
- package/web/.output/server/node_modules/source-map-js/lib/base64.js +0 -67
- package/web/.output/server/node_modules/source-map-js/lib/binary-search.js +0 -111
- package/web/.output/server/node_modules/source-map-js/lib/mapping-list.js +0 -79
- package/web/.output/server/node_modules/source-map-js/lib/quick-sort.js +0 -132
- package/web/.output/server/node_modules/source-map-js/lib/source-map-consumer.js +0 -1188
- package/web/.output/server/node_modules/source-map-js/lib/source-map-generator.js +0 -444
- package/web/.output/server/node_modules/source-map-js/lib/source-node.js +0 -413
- package/web/.output/server/node_modules/source-map-js/lib/util.js +0 -594
- package/web/.output/server/node_modules/source-map-js/package.json +0 -71
- package/web/.output/server/node_modules/source-map-js/source-map.js +0 -8
- package/web/.output/server/node_modules/srvx/dist/_chunks/_body-limit.mjs +0 -39
- package/web/.output/server/node_modules/srvx/dist/_chunks/_plugins.mjs +0 -56
- package/web/.output/server/node_modules/srvx/dist/_chunks/_trust-proxy.mjs +0 -58
- package/web/.output/server/node_modules/srvx/dist/_chunks/_url.mjs +0 -134
- package/web/.output/server/node_modules/srvx/dist/_chunks/_utils.mjs +0 -15
- package/web/.output/server/node_modules/srvx/dist/_chunks/_utils2.mjs +0 -75
- package/web/.output/server/node_modules/srvx/dist/adapters/node.mjs +0 -976
- package/web/.output/server/node_modules/srvx/package.json +0 -102
- package/web/.output/server/node_modules/tailwind-merge/dist/bundle-mjs.mjs +0 -3365
- package/web/.output/server/node_modules/tailwind-merge/package.json +0 -93
- package/web/.output/server/node_modules/tailwind-variants/dist/chunk-LQJYWU4O.js +0 -112
- package/web/.output/server/node_modules/tailwind-variants/dist/chunk-RZF76H2U.js +0 -269
- package/web/.output/server/node_modules/tailwind-variants/dist/index.js +0 -38
- package/web/.output/server/node_modules/tailwind-variants/package.json +0 -122
- package/web/.output/server/node_modules/tailwindcss/dist/chunk-X4GG3EDV.mjs +0 -1
- package/web/.output/server/node_modules/tailwindcss/dist/colors.mjs +0 -1
- package/web/.output/server/node_modules/tailwindcss/package.json +0 -89
- package/web/.output/server/node_modules/ufo/dist/index.mjs +0 -645
- package/web/.output/server/node_modules/ufo/package.json +0 -48
- package/web/.output/server/node_modules/unhead/dist/index.mjs +0 -9
- package/web/.output/server/node_modules/unhead/dist/parser.mjs +0 -508
- package/web/.output/server/node_modules/unhead/dist/plugins.mjs +0 -101
- package/web/.output/server/node_modules/unhead/dist/scripts.mjs +0 -30
- package/web/.output/server/node_modules/unhead/dist/server.mjs +0 -180
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.B3VbJo7Y.mjs +0 -207
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.BYvz9V1x.mjs +0 -43
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.BnoAbrHA.mjs +0 -269
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.CaI5ZD4O.mjs +0 -182
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.CbpEuj3y.mjs +0 -71
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.D4vSFytZ.mjs +0 -236
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.DQc16pHI.mjs +0 -196
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.Dh1cQCTe.mjs +0 -44
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.TxTMM7cM.mjs +0 -166
- package/web/.output/server/node_modules/unhead/dist/shared/unhead.yem5I2v_.mjs +0 -38
- package/web/.output/server/node_modules/unhead/dist/utils.mjs +0 -5
- package/web/.output/server/node_modules/unhead/node_modules/hookable/dist/index.mjs +0 -257
- package/web/.output/server/node_modules/unhead/node_modules/hookable/package.json +0 -53
- package/web/.output/server/node_modules/unhead/package.json +0 -105
- package/web/.output/server/node_modules/vue/dist/vue.cjs.js +0 -80
- package/web/.output/server/node_modules/vue/dist/vue.cjs.prod.js +0 -66
- package/web/.output/server/node_modules/vue/index.js +0 -7
- package/web/.output/server/node_modules/vue/index.mjs +0 -1
- package/web/.output/server/node_modules/vue/package.json +0 -112
- package/web/.output/server/node_modules/vue/server-renderer/index.mjs +0 -1
- package/web/.output/server/node_modules/vue-bundle-renderer/dist/runtime.mjs +0 -249
- package/web/.output/server/node_modules/vue-bundle-renderer/package.json +0 -57
- package/web/.output/server/node_modules/vue-demi/lib/index.mjs +0 -34
- package/web/.output/server/node_modules/vue-demi/package.json +0 -47
- package/web/.output/server/node_modules/vue-router/dist/devtools-Bpr7ZAVB.js +0 -1056
- package/web/.output/server/node_modules/vue-router/dist/useApi-CROJJdhE.js +0 -436
- package/web/.output/server/node_modules/vue-router/dist/vue-router.js +0 -1543
- package/web/.output/server/node_modules/vue-router/package.json +0 -214
- package/web/.output/server/node_modules/vue-router/vue-router.node.mjs +0 -2
- package/web/.output/server/package.json +0 -51
|
@@ -0,0 +1,173 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The `/api` Express router — the whole web backend.
|
|
3
|
+
*
|
|
4
|
+
* Every route operates on the process-wide "current log" held by the
|
|
5
|
+
* {@link ./log-registry.js log registry}; the two POST routes are what make a
|
|
6
|
+
* log current. Handlers throw {@link HttpError}s, which {@link apiErrorHandler}
|
|
7
|
+
* renders as JSON.
|
|
8
|
+
*/
|
|
9
|
+
import express, { Router, } from "express";
|
|
10
|
+
import { buildQuery, buildCountQuery } from "../core/query-builder.js";
|
|
11
|
+
import { extractExpr } from "../core/filters.js";
|
|
12
|
+
import { createError, HttpError } from "./http-error.js";
|
|
13
|
+
import { loadLogFromBytes, loadLogFromPath, requireCurrentFindings, requireCurrentParser, } from "./log-registry.js";
|
|
14
|
+
import { parseFilterWire, translateFilters } from "./translate-filters.js";
|
|
15
|
+
/** Default page size for `GET /api/rows` when the client omits a limit. */
|
|
16
|
+
const DEFAULT_LIMIT = 100;
|
|
17
|
+
/** Upload cap for `POST /api/log/contents` — Renovate debug logs get big. */
|
|
18
|
+
const MAX_UPLOAD_SIZE = "2gb";
|
|
19
|
+
/** Build the API router. */
|
|
20
|
+
export function createApiRouter() {
|
|
21
|
+
const router = Router();
|
|
22
|
+
/**
|
|
23
|
+
* GET /api/fields — the distinct set of root-level JSON keys across the
|
|
24
|
+
* current log. Powers the "ignored fields" checkboxes in the UI. The
|
|
25
|
+
* synthetic keys the Parser uses for blank / malformed lines are excluded.
|
|
26
|
+
*/
|
|
27
|
+
router.get("/fields", (_req, res) => {
|
|
28
|
+
const parser = requireCurrentParser();
|
|
29
|
+
const rows = parser.query("SELECT DISTINCT je.key AS key FROM logs, json_each(logs.logentry) AS je");
|
|
30
|
+
const synthetic = new Set(["_blank", "_parseError", "_raw"]);
|
|
31
|
+
res.json(rows
|
|
32
|
+
.map((r) => r.key)
|
|
33
|
+
.filter((key) => !synthetic.has(key))
|
|
34
|
+
.sort());
|
|
35
|
+
});
|
|
36
|
+
/**
|
|
37
|
+
* GET /api/repositories — the distinct `repository` values across the current
|
|
38
|
+
* log, excluding git-URL sub-repos (e.g. pre-commit hooks) whose `repository`
|
|
39
|
+
* is an `https://…` URL rather than an `owner/repo` slug — these aren't real
|
|
40
|
+
* repos and just clutter the dropdown (mirrors the exclusion in
|
|
41
|
+
* `analyzer.ts`'s per-repo stats). The UI adds a "Repository-independent"
|
|
42
|
+
* pseudo-entry for entries with no `repository` — that is not returned here.
|
|
43
|
+
*/
|
|
44
|
+
router.get("/repositories", (_req, res) => {
|
|
45
|
+
const parser = requireCurrentParser();
|
|
46
|
+
const expr = extractExpr("repository");
|
|
47
|
+
const rows = parser.query(`SELECT DISTINCT ${expr} AS repo FROM logs WHERE ${expr} IS NOT NULL ORDER BY repo`);
|
|
48
|
+
res.json(rows.map((r) => r.repo).filter((repo) => !repo.startsWith("https://")));
|
|
49
|
+
});
|
|
50
|
+
/**
|
|
51
|
+
* GET /api/findings — the error-detector report for the current log.
|
|
52
|
+
*
|
|
53
|
+
* Per-finding `details` are stripped: the Problems panel only needs
|
|
54
|
+
* category/severity/message/line/repo, and the full entry is already reachable
|
|
55
|
+
* via `GET /api/rows` + the details slide-over.
|
|
56
|
+
*/
|
|
57
|
+
router.get("/findings", (_req, res) => {
|
|
58
|
+
const report = requireCurrentFindings();
|
|
59
|
+
const findings = report.findings.map(
|
|
60
|
+
// eslint-disable-next-line @typescript-eslint/no-unused-vars -- drop `details` from the wire payload
|
|
61
|
+
({ details, ...rest }) => rest);
|
|
62
|
+
res.json({
|
|
63
|
+
summary: report.summary,
|
|
64
|
+
counts: report.counts,
|
|
65
|
+
findings,
|
|
66
|
+
});
|
|
67
|
+
});
|
|
68
|
+
/**
|
|
69
|
+
* GET /api/rows — the paginated, filtered row feed for the current log.
|
|
70
|
+
* Query params:
|
|
71
|
+
* - `filters` : URL-encoded JSON of the reactive filter object (optional)
|
|
72
|
+
* - `offset` : rows to skip (default 0)
|
|
73
|
+
* - `limit` : max rows to return (default 100)
|
|
74
|
+
*
|
|
75
|
+
* Returns `{ total, offset, limit, rows }` where each row is a `RowDTO`:
|
|
76
|
+
* `{ _oL, ...entry }` with the ignored root fields stripped (`msg` is never
|
|
77
|
+
* stripped). `total` is the count matching the filters, ignoring pagination,
|
|
78
|
+
* so the client can drive virtualization.
|
|
79
|
+
*/
|
|
80
|
+
router.get("/rows", (req, res) => {
|
|
81
|
+
const parser = requireCurrentParser();
|
|
82
|
+
const wire = parseFilterWire(queryParam(req, "filters"));
|
|
83
|
+
const { filters, ignoredFields } = translateFilters(wire);
|
|
84
|
+
const offset = Math.max(0, parseIntParam(queryParam(req, "offset"), 0));
|
|
85
|
+
const limit = Math.max(0, parseIntParam(queryParam(req, "limit"), DEFAULT_LIMIT));
|
|
86
|
+
const countQuery = buildCountQuery(filters);
|
|
87
|
+
const total = parser.query(countQuery.sql, countQuery.params)[0]?.n ?? 0;
|
|
88
|
+
const dataQuery = buildQuery(filters, { limit, offset }, "line, logentry");
|
|
89
|
+
const rows = parser
|
|
90
|
+
.queryEntries(dataQuery.sql, dataQuery.params)
|
|
91
|
+
.map(({ line, entry }) => projectRow(line, entry, ignoredFields));
|
|
92
|
+
res.json({ total, offset, limit, rows });
|
|
93
|
+
});
|
|
94
|
+
/**
|
|
95
|
+
* POST /api/log/path — load a log from an absolute local path and make it the
|
|
96
|
+
* current log. Body: `{ "path": "<absolute>" }`. Blocks until the log is
|
|
97
|
+
* parsed (or a valid cache is reused). Returns the load metadata.
|
|
98
|
+
*
|
|
99
|
+
* This reads any local absolute path unrestricted — the tool is a local,
|
|
100
|
+
* single-user utility.
|
|
101
|
+
*/
|
|
102
|
+
router.post("/log/path", express.json(), (req, res) => {
|
|
103
|
+
const path = req.body?.path;
|
|
104
|
+
if (typeof path !== "string") {
|
|
105
|
+
throw createError({
|
|
106
|
+
statusCode: 400,
|
|
107
|
+
statusMessage: 'Request body must include a string "path".',
|
|
108
|
+
});
|
|
109
|
+
}
|
|
110
|
+
res.json(loadLogFromPath(path));
|
|
111
|
+
});
|
|
112
|
+
/**
|
|
113
|
+
* POST /api/log/contents — load a log from uploaded bytes (file picker). The
|
|
114
|
+
* bytes are written to a temp file named by their md5, which becomes the log's
|
|
115
|
+
* `path`. The file contents are sent as the raw request body.
|
|
116
|
+
*/
|
|
117
|
+
router.post("/log/contents", express.raw({ type: () => true, limit: MAX_UPLOAD_SIZE }), (req, res) => {
|
|
118
|
+
const bytes = Buffer.isBuffer(req.body) ? req.body : Buffer.alloc(0);
|
|
119
|
+
if (bytes.length === 0) {
|
|
120
|
+
throw createError({
|
|
121
|
+
statusCode: 400,
|
|
122
|
+
statusMessage: "Request body was empty.",
|
|
123
|
+
});
|
|
124
|
+
}
|
|
125
|
+
res.json(loadLogFromBytes(bytes));
|
|
126
|
+
});
|
|
127
|
+
return router;
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* Render errors as JSON. The client composables read `statusMessage` (h3's
|
|
131
|
+
* shape), so keep that key even though there is no h3 anymore.
|
|
132
|
+
*/
|
|
133
|
+
export function apiErrorHandler(err, _req, res, next) {
|
|
134
|
+
if (res.headersSent) {
|
|
135
|
+
next(err);
|
|
136
|
+
return;
|
|
137
|
+
}
|
|
138
|
+
const statusCode = err instanceof HttpError ? err.statusCode : 500;
|
|
139
|
+
const statusMessage = err instanceof HttpError
|
|
140
|
+
? err.statusMessage
|
|
141
|
+
: err instanceof Error
|
|
142
|
+
? err.message
|
|
143
|
+
: "Internal server error.";
|
|
144
|
+
if (statusCode >= 500)
|
|
145
|
+
console.error(err);
|
|
146
|
+
res
|
|
147
|
+
.status(statusCode)
|
|
148
|
+
.json({ statusCode, statusMessage, message: statusMessage });
|
|
149
|
+
}
|
|
150
|
+
/** Build a RowDTO: original line + entry with ignored fields stripped. */
|
|
151
|
+
function projectRow(line, entry, ignoredFields) {
|
|
152
|
+
const stripped = new Set(ignoredFields.filter((f) => f !== "msg"));
|
|
153
|
+
const dto = { _oL: line };
|
|
154
|
+
for (const [key, value] of Object.entries(entry)) {
|
|
155
|
+
if (stripped.has(key))
|
|
156
|
+
continue;
|
|
157
|
+
dto[key] = value;
|
|
158
|
+
}
|
|
159
|
+
return dto;
|
|
160
|
+
}
|
|
161
|
+
/** Read a query parameter as a string (repeated/structured params ignored). */
|
|
162
|
+
function queryParam(req, name) {
|
|
163
|
+
const value = req.query[name];
|
|
164
|
+
return typeof value === "string" ? value : undefined;
|
|
165
|
+
}
|
|
166
|
+
/** Parse a query-string integer, falling back to a default when absent/NaN. */
|
|
167
|
+
function parseIntParam(value, fallback) {
|
|
168
|
+
if (value === undefined)
|
|
169
|
+
return fallback;
|
|
170
|
+
const parsed = Number.parseInt(value, 10);
|
|
171
|
+
return Number.isNaN(parsed) ? fallback : parsed;
|
|
172
|
+
}
|
|
173
|
+
//# sourceMappingURL=api.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"api.js","sourceRoot":"","sources":["../../src/server/api.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Minimal HTTP error type for the Express API.
|
|
3
|
+
*
|
|
4
|
+
* Replaces h3's `createError`: handlers and the log registry throw these, and
|
|
5
|
+
* the Express error middleware in `api.ts` turns them into a JSON response.
|
|
6
|
+
* Anything that is not an {@link HttpError} is treated as a 500.
|
|
7
|
+
*/
|
|
8
|
+
/** An error carrying the HTTP status it should be reported with. */
|
|
9
|
+
export declare class HttpError extends Error {
|
|
10
|
+
readonly statusCode: number;
|
|
11
|
+
readonly statusMessage: string;
|
|
12
|
+
constructor(statusCode: number, statusMessage: string);
|
|
13
|
+
}
|
|
14
|
+
/** Create an {@link HttpError} (h3-compatible call shape). */
|
|
15
|
+
export declare function createError(options: {
|
|
16
|
+
statusCode: number;
|
|
17
|
+
statusMessage: string;
|
|
18
|
+
}): HttpError;
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Minimal HTTP error type for the Express API.
|
|
3
|
+
*
|
|
4
|
+
* Replaces h3's `createError`: handlers and the log registry throw these, and
|
|
5
|
+
* the Express error middleware in `api.ts` turns them into a JSON response.
|
|
6
|
+
* Anything that is not an {@link HttpError} is treated as a 500.
|
|
7
|
+
*/
|
|
8
|
+
/** An error carrying the HTTP status it should be reported with. */
|
|
9
|
+
export class HttpError extends Error {
|
|
10
|
+
statusCode;
|
|
11
|
+
statusMessage;
|
|
12
|
+
constructor(statusCode, statusMessage) {
|
|
13
|
+
super(statusMessage);
|
|
14
|
+
this.name = "HttpError";
|
|
15
|
+
this.statusCode = statusCode;
|
|
16
|
+
this.statusMessage = statusMessage;
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
/** Create an {@link HttpError} (h3-compatible call shape). */
|
|
20
|
+
export function createError(options) {
|
|
21
|
+
return new HttpError(options.statusCode, options.statusMessage);
|
|
22
|
+
}
|
|
23
|
+
//# sourceMappingURL=http-error.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"http-error.js","sourceRoot":"","sources":["../../src/server/http-error.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,oEAAoE;AACpE,MAAM,OAAO,SAAU,SAAQ,KAAK;IACzB,UAAU,CAAS;IACnB,aAAa,CAAS;IAE/B,YAAY,UAAkB,EAAE,aAAqB;QACnD,KAAK,CAAC,aAAa,CAAC,CAAC;QACrB,IAAI,CAAC,IAAI,GAAG,WAAW,CAAC;QACxB,IAAI,CAAC,UAAU,GAAG,UAAU,CAAC;QAC7B,IAAI,CAAC,aAAa,GAAG,aAAa,CAAC;IACrC,CAAC;CACF;AAED,8DAA8D;AAC9D,MAAM,UAAU,WAAW,CAAC,OAG3B;IACC,OAAO,IAAI,SAAS,CAAC,OAAO,CAAC,UAAU,EAAE,OAAO,CAAC,aAAa,CAAC,CAAC;AAClE,CAAC"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The Express application that backs the `web` command.
|
|
3
|
+
*
|
|
4
|
+
* It does two things:
|
|
5
|
+
* 1. serves the JSON API under `/api` (see {@link ./api.js}), and
|
|
6
|
+
* 2. serves the statically-rendered Nuxt SPA (`web/.output/public`), falling
|
|
7
|
+
* back to `index.html` for unknown paths so client-side routing works.
|
|
8
|
+
*
|
|
9
|
+
* There is deliberately no server-side rendering: the SPA is a static bundle,
|
|
10
|
+
* so this process only ever pushes bytes and answers API calls.
|
|
11
|
+
*/
|
|
12
|
+
import { type Express } from "express";
|
|
13
|
+
/** Options for {@link createApp}. */
|
|
14
|
+
export interface AppOptions {
|
|
15
|
+
/**
|
|
16
|
+
* Directory holding the built SPA. Defaults to the `web/.output/public`
|
|
17
|
+
* shipped inside this package. When it does not exist, only `/api` is served.
|
|
18
|
+
*/
|
|
19
|
+
staticDir?: string;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Directory of the prebuilt SPA shipped in this package.
|
|
23
|
+
* Layout after `tsc`: dist/server/index.js → ../../web/.output/public
|
|
24
|
+
*/
|
|
25
|
+
export declare function defaultStaticDir(): string;
|
|
26
|
+
/** Build the Express app (API + static SPA). */
|
|
27
|
+
export declare function createApp(options?: AppOptions): Express;
|
|
28
|
+
/** Options for {@link startServer}. */
|
|
29
|
+
export interface ServeOptions extends AppOptions {
|
|
30
|
+
port: number;
|
|
31
|
+
host: string;
|
|
32
|
+
}
|
|
33
|
+
/** Start the HTTP server and resolve once it is listening. */
|
|
34
|
+
export declare function startServer(options: ServeOptions): Promise<void>;
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The Express application that backs the `web` command.
|
|
3
|
+
*
|
|
4
|
+
* It does two things:
|
|
5
|
+
* 1. serves the JSON API under `/api` (see {@link ./api.js}), and
|
|
6
|
+
* 2. serves the statically-rendered Nuxt SPA (`web/.output/public`), falling
|
|
7
|
+
* back to `index.html` for unknown paths so client-side routing works.
|
|
8
|
+
*
|
|
9
|
+
* There is deliberately no server-side rendering: the SPA is a static bundle,
|
|
10
|
+
* so this process only ever pushes bytes and answers API calls.
|
|
11
|
+
*/
|
|
12
|
+
import express from "express";
|
|
13
|
+
import { existsSync } from "node:fs";
|
|
14
|
+
import { join } from "node:path";
|
|
15
|
+
import { fileURLToPath } from "node:url";
|
|
16
|
+
import { createApiRouter, apiErrorHandler } from "./api.js";
|
|
17
|
+
/**
|
|
18
|
+
* Directory of the prebuilt SPA shipped in this package.
|
|
19
|
+
* Layout after `tsc`: dist/server/index.js → ../../web/.output/public
|
|
20
|
+
*/
|
|
21
|
+
export function defaultStaticDir() {
|
|
22
|
+
return fileURLToPath(new URL("../../web/.output/public", import.meta.url));
|
|
23
|
+
}
|
|
24
|
+
/** Build the Express app (API + static SPA). */
|
|
25
|
+
export function createApp(options = {}) {
|
|
26
|
+
const app = express();
|
|
27
|
+
const staticDir = options.staticDir ?? defaultStaticDir();
|
|
28
|
+
app.use("/api", createApiRouter());
|
|
29
|
+
app.use("/api", apiErrorHandler);
|
|
30
|
+
const indexHtml = join(staticDir, "index.html");
|
|
31
|
+
if (existsSync(indexHtml)) {
|
|
32
|
+
app.use(express.static(staticDir));
|
|
33
|
+
// SPA fallback: anything not matched above (and not an API call) gets the
|
|
34
|
+
// app shell, which then routes client-side.
|
|
35
|
+
app.use((req, res, next) => {
|
|
36
|
+
if (req.method !== "GET" && req.method !== "HEAD")
|
|
37
|
+
return next();
|
|
38
|
+
res.sendFile("index.html", { root: staticDir });
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
return app;
|
|
42
|
+
}
|
|
43
|
+
/** Start the HTTP server and resolve once it is listening. */
|
|
44
|
+
export function startServer(options) {
|
|
45
|
+
const app = createApp(options);
|
|
46
|
+
return new Promise((resolve, reject) => {
|
|
47
|
+
const server = app.listen(options.port, options.host, () => {
|
|
48
|
+
console.log(`renovate-log-parser web UI listening on http://${options.host}:${options.port}`);
|
|
49
|
+
resolve();
|
|
50
|
+
});
|
|
51
|
+
server.on("error", reject);
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/server/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AACH,OAAO,OAAyB,MAAM,SAAS,CAAC;AAChD,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AACrC,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AACzC,OAAO,EAAE,eAAe,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC;AAW5D;;;GAGG;AACH,MAAM,UAAU,gBAAgB;IAC9B,OAAO,aAAa,CAAC,IAAI,GAAG,CAAC,0BAA0B,EAAE,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;AAC7E,CAAC;AAED,gDAAgD;AAChD,MAAM,UAAU,SAAS,CAAC,UAAsB,EAAE;IAChD,MAAM,GAAG,GAAG,OAAO,EAAE,CAAC;IACtB,MAAM,SAAS,GAAG,OAAO,CAAC,SAAS,IAAI,gBAAgB,EAAE,CAAC;IAE1D,GAAG,CAAC,GAAG,CAAC,MAAM,EAAE,eAAe,EAAE,CAAC,CAAC;IACnC,GAAG,CAAC,GAAG,CAAC,MAAM,EAAE,eAAe,CAAC,CAAC;IAEjC,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,EAAE,YAAY,CAAC,CAAC;IAChD,IAAI,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;QAC1B,GAAG,CAAC,GAAG,CAAC,OAAO,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,CAAC;QACnC,0EAA0E;QAC1E,4CAA4C;QAC5C,GAAG,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,GAAG,EAAE,IAAI,EAAE,EAAE;YACzB,IAAI,GAAG,CAAC,MAAM,KAAK,KAAK,IAAI,GAAG,CAAC,MAAM,KAAK,MAAM;gBAAE,OAAO,IAAI,EAAE,CAAC;YACjE,GAAG,CAAC,QAAQ,CAAC,YAAY,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,CAAC,CAAC;QAClD,CAAC,CAAC,CAAC;IACL,CAAC;IAED,OAAO,GAAG,CAAC;AACb,CAAC;AAQD,8DAA8D;AAC9D,MAAM,UAAU,WAAW,CAAC,OAAqB;IAC/C,MAAM,GAAG,GAAG,SAAS,CAAC,OAAO,CAAC,CAAC;IAC/B,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE;QACrC,MAAM,MAAM,GAAG,GAAG,CAAC,MAAM,CAAC,OAAO,CAAC,IAAI,EAAE,OAAO,CAAC,IAAI,EAAE,GAAG,EAAE;YACzD,OAAO,CAAC,GAAG,CACT,kDAAkD,OAAO,CAAC,IAAI,IAAI,OAAO,CAAC,IAAI,EAAE,CACjF,CAAC;YACF,OAAO,EAAE,CAAC;QACZ,CAAC,CAAC,CAAC;QACH,MAAM,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;IAC7B,CAAC,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { Parser } from "../core/parser.js";
|
|
2
|
+
import { type DetectionReport } from "../core/error-detector.js";
|
|
3
|
+
/** Public metadata returned to the client after a successful load. */
|
|
4
|
+
export interface LoadedLogInfo {
|
|
5
|
+
md5: string;
|
|
6
|
+
path: string;
|
|
7
|
+
totalLines: number;
|
|
8
|
+
levelCounts: Record<string, number>;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Load a log from an absolute filesystem path and make it current.
|
|
12
|
+
*
|
|
13
|
+
* @throws {HttpError} when the path is not absolute / missing, or the parse
|
|
14
|
+
* fails — the route layer maps these to HTTP responses.
|
|
15
|
+
*/
|
|
16
|
+
export declare function loadLogFromPath(rawPath: string): LoadedLogInfo;
|
|
17
|
+
/**
|
|
18
|
+
* Persist uploaded bytes to a temp file (named by their md5) and load it. The
|
|
19
|
+
* temp copy becomes the log's `path`, mirroring the on-disk load path.
|
|
20
|
+
*/
|
|
21
|
+
export declare function loadLogFromBytes(bytes: Uint8Array): LoadedLogInfo;
|
|
22
|
+
/**
|
|
23
|
+
* Return the parser for the current log, or throw a 409 when none is loaded.
|
|
24
|
+
* The GET routes call this first.
|
|
25
|
+
*/
|
|
26
|
+
export declare function requireCurrentParser(): Parser;
|
|
27
|
+
/**
|
|
28
|
+
* Return the error-detector report for the current log, computing (and caching)
|
|
29
|
+
* it on first request. Runs without ignore rules — the web surfaces every
|
|
30
|
+
* finding. Throws a 409 when no log is loaded (via {@link requireCurrentEntry}).
|
|
31
|
+
*/
|
|
32
|
+
export declare function requireCurrentFindings(): DetectionReport;
|
|
33
|
+
/** Count entries per numeric `level` via a single grouped SQL scan. */
|
|
34
|
+
export declare function computeLevelCounts(parser: Parser): Record<string, number>;
|
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Stateful, process-wide log registry for the web backend.
|
|
3
|
+
*
|
|
4
|
+
* The `web` command runs a single long-lived Express process for one user, so we
|
|
5
|
+
* keep every loaded log's open {@link Parser} (and its SQLite handle) in memory
|
|
6
|
+
* keyed by content md5, plus a `current` pointer. A successful load sets
|
|
7
|
+
* `current`; the GET routes always operate on `current` — there is no per-request
|
|
8
|
+
* `md5` override. Loading a new file simply moves the pointer (the previous
|
|
9
|
+
* handle stays cached for cheap re-selection).
|
|
10
|
+
*/
|
|
11
|
+
import { createHash } from "node:crypto";
|
|
12
|
+
import { existsSync, writeFileSync } from "node:fs";
|
|
13
|
+
import { tmpdir } from "node:os";
|
|
14
|
+
import { isAbsolute, join } from "node:path";
|
|
15
|
+
import { Parser } from "../core/parser.js";
|
|
16
|
+
import { extractExpr } from "../core/filters.js";
|
|
17
|
+
import { ErrorDetector } from "../core/error-detector.js";
|
|
18
|
+
import { createError } from "./http-error.js";
|
|
19
|
+
/** md5 -> loaded log. Persists for the lifetime of the server process. */
|
|
20
|
+
const registry = new Map();
|
|
21
|
+
/** The md5 of the log the GET routes currently operate on. */
|
|
22
|
+
let current = null;
|
|
23
|
+
/** Prefix for uploaded-file temp copies (distinct from Parser's cache files). */
|
|
24
|
+
const UPLOAD_PREFIX = "renovate-log-parser-upload-";
|
|
25
|
+
const UPLOAD_SUFFIX = ".jsonl";
|
|
26
|
+
/**
|
|
27
|
+
* Load a log from an absolute filesystem path and make it current.
|
|
28
|
+
*
|
|
29
|
+
* @throws {HttpError} when the path is not absolute / missing, or the parse
|
|
30
|
+
* fails — the route layer maps these to HTTP responses.
|
|
31
|
+
*/
|
|
32
|
+
export function loadLogFromPath(rawPath) {
|
|
33
|
+
if (typeof rawPath !== "string" || rawPath.length === 0) {
|
|
34
|
+
throw createError({
|
|
35
|
+
statusCode: 400,
|
|
36
|
+
statusMessage: 'A "path" is required.',
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
if (!isAbsolute(rawPath)) {
|
|
40
|
+
throw createError({
|
|
41
|
+
statusCode: 400,
|
|
42
|
+
statusMessage: `Path must be absolute: ${rawPath}`,
|
|
43
|
+
});
|
|
44
|
+
}
|
|
45
|
+
if (!existsSync(rawPath)) {
|
|
46
|
+
throw createError({
|
|
47
|
+
statusCode: 400,
|
|
48
|
+
statusMessage: `Log file not found: ${rawPath}`,
|
|
49
|
+
});
|
|
50
|
+
}
|
|
51
|
+
return loadInto(rawPath);
|
|
52
|
+
}
|
|
53
|
+
/**
|
|
54
|
+
* Persist uploaded bytes to a temp file (named by their md5) and load it. The
|
|
55
|
+
* temp copy becomes the log's `path`, mirroring the on-disk load path.
|
|
56
|
+
*/
|
|
57
|
+
export function loadLogFromBytes(bytes) {
|
|
58
|
+
if (bytes.length === 0) {
|
|
59
|
+
throw createError({
|
|
60
|
+
statusCode: 400,
|
|
61
|
+
statusMessage: "Uploaded file is empty.",
|
|
62
|
+
});
|
|
63
|
+
}
|
|
64
|
+
const md5 = createHash("md5").update(bytes).digest("hex");
|
|
65
|
+
const tempPath = join(tmpdir(), `${UPLOAD_PREFIX}${md5}${UPLOAD_SUFFIX}`);
|
|
66
|
+
if (!existsSync(tempPath)) {
|
|
67
|
+
writeFileSync(tempPath, bytes);
|
|
68
|
+
}
|
|
69
|
+
return loadInto(tempPath);
|
|
70
|
+
}
|
|
71
|
+
/** Shared load path: reuse the cached parser if present, else parse fresh. */
|
|
72
|
+
function loadInto(absolutePath) {
|
|
73
|
+
let md5;
|
|
74
|
+
let parser;
|
|
75
|
+
// Reuse an already-open parser whose source path matches (cheap re-select).
|
|
76
|
+
const existing = [...registry.values()].find((e) => e.path === absolutePath);
|
|
77
|
+
if (existing) {
|
|
78
|
+
parser = existing.parser;
|
|
79
|
+
md5 = parser.loaded.md5;
|
|
80
|
+
}
|
|
81
|
+
else {
|
|
82
|
+
parser = new Parser();
|
|
83
|
+
let result;
|
|
84
|
+
try {
|
|
85
|
+
result = parser.load(absolutePath);
|
|
86
|
+
}
|
|
87
|
+
catch (err) {
|
|
88
|
+
parser.close();
|
|
89
|
+
throw createError({
|
|
90
|
+
statusCode: 400,
|
|
91
|
+
statusMessage: err instanceof Error ? err.message : "Failed to parse log file.",
|
|
92
|
+
});
|
|
93
|
+
}
|
|
94
|
+
md5 = result.md5;
|
|
95
|
+
registry.set(md5, { path: absolutePath, parser });
|
|
96
|
+
}
|
|
97
|
+
current = md5;
|
|
98
|
+
const info = parser.loaded;
|
|
99
|
+
return {
|
|
100
|
+
md5,
|
|
101
|
+
path: info.path,
|
|
102
|
+
totalLines: info.totalLines,
|
|
103
|
+
levelCounts: computeLevelCounts(parser),
|
|
104
|
+
};
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* Return the parser for the current log, or throw a 409 when none is loaded.
|
|
108
|
+
* The GET routes call this first.
|
|
109
|
+
*/
|
|
110
|
+
export function requireCurrentParser() {
|
|
111
|
+
return requireCurrentEntry().parser;
|
|
112
|
+
}
|
|
113
|
+
/**
|
|
114
|
+
* Return the error-detector report for the current log, computing (and caching)
|
|
115
|
+
* it on first request. Runs without ignore rules — the web surfaces every
|
|
116
|
+
* finding. Throws a 409 when no log is loaded (via {@link requireCurrentEntry}).
|
|
117
|
+
*/
|
|
118
|
+
export function requireCurrentFindings() {
|
|
119
|
+
const entry = requireCurrentEntry();
|
|
120
|
+
if (!entry.report) {
|
|
121
|
+
entry.report = new ErrorDetector(entry.parser).run();
|
|
122
|
+
}
|
|
123
|
+
return entry.report;
|
|
124
|
+
}
|
|
125
|
+
/** Resolve the current registry entry, or throw a 409 when none is loaded. */
|
|
126
|
+
function requireCurrentEntry() {
|
|
127
|
+
if (current === null) {
|
|
128
|
+
throw createError({
|
|
129
|
+
statusCode: 409,
|
|
130
|
+
statusMessage: "No log is loaded. POST a log to /api/log/path first.",
|
|
131
|
+
});
|
|
132
|
+
}
|
|
133
|
+
const entry = registry.get(current);
|
|
134
|
+
if (!entry) {
|
|
135
|
+
// Defensive: pointer without an entry should never happen.
|
|
136
|
+
current = null;
|
|
137
|
+
throw createError({ statusCode: 409, statusMessage: "No log is loaded." });
|
|
138
|
+
}
|
|
139
|
+
return entry;
|
|
140
|
+
}
|
|
141
|
+
/** Count entries per numeric `level` via a single grouped SQL scan. */
|
|
142
|
+
export function computeLevelCounts(parser) {
|
|
143
|
+
const levelExpr = extractExpr("level");
|
|
144
|
+
const rows = parser.query(`SELECT ${levelExpr} AS level, COUNT(*) AS n FROM logs GROUP BY ${levelExpr}`);
|
|
145
|
+
const counts = {};
|
|
146
|
+
for (const { level, n } of rows) {
|
|
147
|
+
if (typeof level === "number")
|
|
148
|
+
counts[String(level)] = n;
|
|
149
|
+
}
|
|
150
|
+
// Re-key in ascending numeric level order for a stable, readable response.
|
|
151
|
+
const sorted = {};
|
|
152
|
+
for (const key of Object.keys(counts).sort((a, b) => Number(a) - Number(b))) {
|
|
153
|
+
sorted[key] = counts[key];
|
|
154
|
+
}
|
|
155
|
+
return sorted;
|
|
156
|
+
}
|
|
157
|
+
//# sourceMappingURL=log-registry.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"log-registry.js","sourceRoot":"","sources":["../../src/server/log-registry.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Entry point of the web server process.
|
|
3
|
+
*
|
|
4
|
+
* The `web` CLI command spawns this file as a child process with `PORT`/`HOST`
|
|
5
|
+
* in the environment. It is also the dev-mode entry (`npm run dev:api`), in
|
|
6
|
+
* which case the Nuxt dev server proxies `/api` here and the static SPA
|
|
7
|
+
* directory is simply absent.
|
|
8
|
+
*
|
|
9
|
+
* Configuration: `--port` / `--host` flags win over the `PORT` / `HOST`
|
|
10
|
+
* environment variables (flags keep the dev script platform-independent).
|
|
11
|
+
*/
|
|
12
|
+
import { startServer } from "./index.js";
|
|
13
|
+
/** Read a `--name value` / `--name=value` flag from argv. */
|
|
14
|
+
function flag(name) {
|
|
15
|
+
const argv = process.argv.slice(2);
|
|
16
|
+
const index = argv.indexOf(`--${name}`);
|
|
17
|
+
if (index !== -1)
|
|
18
|
+
return argv[index + 1];
|
|
19
|
+
const inline = argv.find((a) => a.startsWith(`--${name}=`));
|
|
20
|
+
return inline?.slice(name.length + 3);
|
|
21
|
+
}
|
|
22
|
+
const port = Number.parseInt(flag("port") ?? process.env.PORT ?? "3000", 10);
|
|
23
|
+
const host = flag("host") ?? process.env.HOST ?? "localhost";
|
|
24
|
+
startServer({
|
|
25
|
+
port: Number.isNaN(port) ? 3000 : port,
|
|
26
|
+
host,
|
|
27
|
+
}).catch((err) => {
|
|
28
|
+
console.error(err);
|
|
29
|
+
process.exitCode = 1;
|
|
30
|
+
});
|
|
31
|
+
//# sourceMappingURL=server-main.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server-main.js","sourceRoot":"","sources":["../../src/server/server-main.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AACH,OAAO,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAEzC,6DAA6D;AAC7D,SAAS,IAAI,CAAC,IAAY;IACxB,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;IACnC,MAAM,KAAK,GAAG,IAAI,CAAC,OAAO,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC;IACxC,IAAI,KAAK,KAAK,CAAC,CAAC;QAAE,OAAO,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;IACzC,MAAM,MAAM,GAAG,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,KAAK,IAAI,GAAG,CAAC,CAAC,CAAC;IAC5D,OAAO,MAAM,EAAE,KAAK,CAAC,IAAI,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;AACxC,CAAC;AAED,MAAM,IAAI,GAAG,MAAM,CAAC,QAAQ,CAAC,IAAI,CAAC,MAAM,CAAC,IAAI,OAAO,CAAC,GAAG,CAAC,IAAI,IAAI,MAAM,EAAE,EAAE,CAAC,CAAC;AAC7E,MAAM,IAAI,GAAG,IAAI,CAAC,MAAM,CAAC,IAAI,OAAO,CAAC,GAAG,CAAC,IAAI,IAAI,WAAW,CAAC;AAE7D,WAAW,CAAC;IACV,IAAI,EAAE,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI;IACtC,IAAI;CACL,CAAC,CAAC,KAAK,CAAC,CAAC,GAAY,EAAE,EAAE;IACxB,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IACnB,OAAO,CAAC,QAAQ,GAAG,CAAC,CAAC;AACvB,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Translate the web UI's reactive filter object (the `filters` wire format) into
|
|
3
|
+
* the shared {@link Filter} model that the {@link buildQuery} query builder
|
|
4
|
+
* understands.
|
|
5
|
+
*
|
|
6
|
+
* Wire shape (all keys optional):
|
|
7
|
+
* ```jsonc
|
|
8
|
+
* {
|
|
9
|
+
* "levels": [20, 30, 40],
|
|
10
|
+
* "repositories": { "mode": "include"|"exclude", "values": [...], "independent": true },
|
|
11
|
+
* "ignoredFields": ["v", "time", ...], // response projection, NOT a WHERE clause
|
|
12
|
+
* "search": { "field": "msg", "pattern": "*abort*" },
|
|
13
|
+
* "pills": [ { "id": "…", "enabled": true, "filter": { …core Filter… } } ]
|
|
14
|
+
* }
|
|
15
|
+
* ```
|
|
16
|
+
* Disabled pills are dropped. `ignoredFields` is returned separately because it
|
|
17
|
+
* shapes the row projection rather than row matching.
|
|
18
|
+
*/
|
|
19
|
+
import type { Filter } from "../core/filters.js";
|
|
20
|
+
/** Repository include/exclude selection. */
|
|
21
|
+
interface RepositoriesSelection {
|
|
22
|
+
mode?: "include" | "exclude";
|
|
23
|
+
values?: unknown;
|
|
24
|
+
independent?: unknown;
|
|
25
|
+
}
|
|
26
|
+
/** A single dynamic pill wrapping a core Filter with an enable toggle. */
|
|
27
|
+
interface Pill {
|
|
28
|
+
id?: string;
|
|
29
|
+
enabled?: boolean;
|
|
30
|
+
filter?: Filter;
|
|
31
|
+
}
|
|
32
|
+
/** The full reactive filter object sent by the client. */
|
|
33
|
+
export interface FilterWire {
|
|
34
|
+
levels?: unknown;
|
|
35
|
+
repositories?: RepositoriesSelection;
|
|
36
|
+
ignoredFields?: unknown;
|
|
37
|
+
search?: {
|
|
38
|
+
field?: unknown;
|
|
39
|
+
pattern?: unknown;
|
|
40
|
+
scope?: unknown;
|
|
41
|
+
};
|
|
42
|
+
pills?: Pill[];
|
|
43
|
+
}
|
|
44
|
+
/** Result of translating the wire object. */
|
|
45
|
+
export interface TranslatedFilters {
|
|
46
|
+
filters: Filter[];
|
|
47
|
+
/** Root keys to strip from each row (`msg` is never strippable). */
|
|
48
|
+
ignoredFields: string[];
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Parse the JSON-encoded `filters` query parameter into a {@link FilterWire}.
|
|
52
|
+
* Returns an empty object for a missing/blank value so an unfiltered request
|
|
53
|
+
* still works; malformed JSON is a 400.
|
|
54
|
+
*/
|
|
55
|
+
export declare function parseFilterWire(raw: string | undefined): FilterWire;
|
|
56
|
+
/** Translate the wire object into concrete filters + the projection list. */
|
|
57
|
+
export declare function translateFilters(wire: FilterWire): TranslatedFilters;
|
|
58
|
+
export {};
|