@sebbo2002/semantic-release-docker 4.0.3-develop.9 → 4.0.4-develop.1

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/dist/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { Context } from 'semantic-release';
1
+ import { PublishContext } from 'semantic-release';
2
2
 
3
3
  interface PluginConfig {
4
4
  images: string | string[];
@@ -38,16 +38,16 @@ interface PublishResponse {
38
38
 
39
39
  declare function parseConfig(config: PluginConfig): NormalizedPluginConfig;
40
40
  declare function getBaseImage(input: string): string;
41
- declare function isPreRelease(context: Context): boolean;
41
+ declare function isPreRelease(context: PublishContext): boolean;
42
42
  declare function getMajorAndMinorPart(version: string | undefined): MajorAndMinorPart;
43
- declare function getTagTasks(config: NormalizedPluginConfig, context: Context): TagTask[];
43
+ declare function getTagTasks(config: NormalizedPluginConfig, context: PublishContext): TagTask[];
44
44
  declare function getUrlFromImage(image: string): string | undefined;
45
45
  declare function exec(file: string, args: string[]): Promise<void>;
46
46
  declare function isRegCtlAvailable(): Promise<boolean>;
47
47
  declare function tagImage(input: string, output: string): Promise<void>;
48
48
  declare function pushImage(image: string): Promise<void>;
49
49
  declare function copyImage(input: string, output: string): Promise<void>;
50
- declare function publish(pluginConfig: PluginConfig, context: Context): Promise<boolean | PublishResponse>;
50
+ declare function publish(pluginConfig: PluginConfig, context: PublishContext): Promise<boolean | PublishResponse>;
51
51
  declare const _default: {
52
52
  publish: typeof publish;
53
53
  };
package/dist/index.js CHANGED
@@ -1,2 +1,2 @@
1
- var g=(t,e,r)=>new Promise((o,i)=>{var s=a=>{try{n(r.next(a))}catch(l){i(l)}},u=a=>{try{n(r.throw(a))}catch(l){i(l)}},n=a=>a.done?o(a.value):Promise.resolve(a.value).then(s,u);n((r=r.apply(t,e)).next())});import{execa as p}from"execa";var f;function h(t){let e={images:[],tag:{latest:!0,major:!0,minor:!0,version:!0,channel:!0}};if(typeof t.images=="string")e.images.push(t.images);else if(Array.isArray(t.images))t.images.filter(o=>typeof o=="string").forEach(o=>e.images.push(o));else throw new Error("Configuration invalid: No image defined!");return Object.keys(e.tag).forEach(o=>{let i=t.tag?t.tag[o]:void 0;(i===!0||i===!1)&&(e.tag[o]=i)}),e}function m(t){let e=t.split("@")[0].split(":");return e[1]&&e[1].includes("/")&&(e=[e[0]+":"+e[1],e[2]]),e[0]}function d(t){return!!(t.nextRelease&&t.nextRelease.version.includes("-"))}function $(t){if(!t)return{major:null,minor:null};let e=t.split(".",2);return{major:e[0],minor:e[1]}}function y(t,e){let r=[];if(!e.nextRelease)return[];let o=e.nextRelease.version;return t.images.forEach(i=>{var n;let s=m(i);if(t.tag.version&&o&&r.push({input:i,output:`${s}:${o}`}),!d(e)){let{major:a,minor:l}=$(o);t.tag.latest&&r.push({input:i,output:`${s}:latest`}),t.tag.major&&a&&r.push({input:i,output:`${s}:${a}`}),t.tag.minor&&a&&l&&r.push({input:i,output:`${s}:${a}.${l}`})}let u=(n=e.nextRelease)==null?void 0:n.channel;t.tag.channel&&u&&r.push({input:i,output:`${s}:${u}`})}),r}function P(t){let e=m(t).split("/");if(e[0]==="ghcr.io"&&e.length===3)return`https://github.com/${e[1]}/${e[2]}/pkgs/container/${e[2]}`;if(e[0]==="registry.gitlab.com"&&e.length>=3)return`https://gitlab.com/${e[1]}/${e[2]}/container_registry`;let r=e[0].includes(".");if(!r&&e.length===2)return`https://hub.docker.com/r/${e[0]}/${e[1]}/tags`;if(!r&&e.length===1)return`https://hub.docker.com/_/${e[0]}/tags`}function c(t,e){return g(this,null,function*(){try{yield p(t,e)}catch(r){throw typeof r=="object"&&r!==null&&"command"in r&&"message"in r?new Error(`Unable to run "${r.command}": ${r.message}`):new Error(`Unable to run "${e.join(" ")}": ${r}`)}})}function C(){return g(this,null,function*(){if(f!==void 0)return f;try{return yield p("which",["regctl"]),f=!0,!0}catch(t){return f=!1,!1}})}function w(t,e){return g(this,null,function*(){yield c("docker",["tag",t,e])})}function b(t){return g(this,null,function*(){yield c("docker",["push",t])})}function x(t,e){return g(this,null,function*(){yield c("regctl",["image","copy",t,e])})}function k(t,e){return g(this,null,function*(){var u;if(!e.nextRelease)return e.logger.log("No release schedules, so no images to tag."),!1;let r=h(t),o=y(r,e);if(!o.length)return!1;for(let n of o){if(yield C()){e.logger.log(`Copy with regctl ${n.input} \u2192 ${n.output}`);try{yield x(n.input,n.output);continue}catch(a){e.logger.error(a),e.logger.log("Retry without regctl\u2026")}}e.logger.log(`Tag ${n.input} \u2192 ${n.output}`),yield w(n.input,n.output),e.logger.log(`Push ${n.output}`),yield b(n.output)}let i=(u=e.nextRelease)==null?void 0:u.channel,s=o[0];return{name:`Docker container (${s.output})`,url:P(s.output),channel:i}})}var j={publish:k};export{x as copyImage,j as default,c as exec,m as getBaseImage,$ as getMajorAndMinorPart,y as getTagTasks,P as getUrlFromImage,d as isPreRelease,C as isRegCtlAvailable,h as parseConfig,k as publish,b as pushImage,w as tagImage};
1
+ import{execa as f}from"execa";var u;function p(t){let e={images:[],tag:{latest:!0,major:!0,minor:!0,version:!0,channel:!0}};if(typeof t.images=="string")e.images.push(t.images);else if(Array.isArray(t.images))t.images.filter(n=>typeof n=="string").forEach(n=>e.images.push(n));else throw new Error("Configuration invalid: No image defined!");return Object.keys(e.tag).forEach(n=>{let i=t.tag?t.tag[n]:void 0;(i===!0||i===!1)&&(e.tag[n]=i)}),e}function c(t){let e=t.split("@")[0].split(":");return e[1]&&e[1].includes("/")&&(e=[e[0]+":"+e[1],e[2]]),e[0]}function m(t){return!!(t.nextRelease&&t.nextRelease.version.includes("-"))}function h(t){if(!t)return{major:null,minor:null};let e=t.split(".",2);return{major:e[0],minor:e[1]}}function d(t,e){let r=[];if(!e.nextRelease)return[];let n=e.nextRelease.version;return t.images.forEach(i=>{let a=c(i);if(t.tag.version&&n&&r.push({input:i,output:`${a}:${n}`}),!m(e)){let{major:s,minor:l}=h(n);t.tag.latest&&r.push({input:i,output:`${a}:latest`}),t.tag.major&&s&&r.push({input:i,output:`${a}:${s}`}),t.tag.minor&&s&&l&&r.push({input:i,output:`${a}:${s}.${l}`})}let o=e.nextRelease?.channel;t.tag.channel&&o&&r.push({input:i,output:`${a}:${o}`})}),r}function $(t){let e=c(t).split("/");if(e[0]==="ghcr.io"&&e.length===3)return`https://github.com/${e[1]}/${e[2]}/pkgs/container/${e[2]}`;if(e[0]==="registry.gitlab.com"&&e.length>=3)return`https://gitlab.com/${e[1]}/${e[2]}/container_registry`;let r=e[0].includes(".");if(!r&&e.length===2)return`https://hub.docker.com/r/${e[0]}/${e[1]}/tags`;if(!r&&e.length===1)return`https://hub.docker.com/_/${e[0]}/tags`}async function g(t,e){try{await f(t,e)}catch(r){throw typeof r=="object"&&r!==null&&"command"in r&&"message"in r?new Error(`Unable to run "${r.command}": ${r.message}`):new Error(`Unable to run "${e.join(" ")}": ${r}`)}}async function P(){if(u!==void 0)return u;try{return await f("which",["regctl"]),u=!0,!0}catch{return u=!1,!1}}async function y(t,e){await g("docker",["tag",t,e])}async function b(t){await g("docker",["push",t])}async function C(t,e){await g("regctl",["image","copy",t,e])}async function w(t,e){if(!e.nextRelease)return e.logger.log("No release schedules, so no images to tag."),!1;let r=p(t),n=d(r,e);if(!n.length)return!1;for(let o of n){if(await P()){e.logger.log(`Copy with regctl ${o.input} \u2192 ${o.output}`);try{await C(o.input,o.output);continue}catch(s){e.logger.error(s),e.logger.log("Retry without regctl\u2026")}}e.logger.log(`Tag ${o.input} \u2192 ${o.output}`),await y(o.input,o.output),e.logger.log(`Push ${o.output}`),await b(o.output)}let i=e.nextRelease?.channel,a=n[0];return{name:`Docker container (${a.output})`,url:$(a.output),channel:i}}var k={publish:w};export{C as copyImage,k as default,g as exec,c as getBaseImage,h as getMajorAndMinorPart,d as getTagTasks,$ as getUrlFromImage,m as isPreRelease,P as isRegCtlAvailable,p as parseConfig,w as publish,b as pushImage,y as tagImage};
2
2
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/lib/index.ts"],"sourcesContent":["import { Context } from 'semantic-release';\nimport {\n MajorAndMinorPart,\n NormalizedPluginConfigTags,\n NormalizedPluginConfig,\n PluginConfig,\n PluginConfigTagKeys,\n TagTask,\n PublishResponse\n} from './types.js';\nimport { execa } from 'execa';\n\nexport {\n PluginConfig,\n NormalizedPluginConfigTags,\n NormalizedPluginConfig,\n PluginConfigTagKeys,\n MajorAndMinorPart,\n TagTask\n};\n\nlet IS_REGCTL_AVAILABLE: boolean | undefined= undefined;\n\nexport function parseConfig (config: PluginConfig): NormalizedPluginConfig {\n const result: NormalizedPluginConfig = {\n images: [],\n tag: {\n latest: true,\n major: true,\n minor: true,\n version: true,\n channel: true\n }\n };\n\n if (typeof config.images === 'string') {\n result.images.push(config.images);\n } else if (Array.isArray(config.images)) {\n config.images\n .filter(image => typeof image === 'string')\n .forEach(image => result.images.push(image));\n } else {\n throw new Error('Configuration invalid: No image defined!');\n }\n\n const tagNames = Object.keys(result.tag) as PluginConfigTagKeys[];\n tagNames.forEach(name => {\n const value = config.tag ? config.tag[name] : undefined;\n if (value === true || value === false) {\n result.tag[name] = value;\n }\n });\n\n return result;\n}\n\nexport function getBaseImage (input: string): string {\n let p = input.split('@')[0].split(':');\n\n // it's a \":port\"\n if (p[1] && p[1].includes('/')) {\n p = [p[0] + ':' + p[1], p[2]];\n }\n\n return p[0];\n}\n\nexport function isPreRelease (context: Context): boolean {\n return Boolean(context.nextRelease && context.nextRelease.version.includes('-'));\n}\n\nexport function getMajorAndMinorPart (version: string | undefined): MajorAndMinorPart {\n if (!version) {\n return {\n major: null,\n minor: null\n };\n }\n\n const parts = version.split('.', 2);\n return {\n major: parts[0],\n minor: parts[1]\n };\n}\n\nexport function getTagTasks (config: NormalizedPluginConfig, context: Context): TagTask[] {\n const result: TagTask[] = [];\n\n if (!context.nextRelease) {\n return [];\n }\n\n const version = context.nextRelease.version;\n config.images.forEach(input => {\n const outputBase = getBaseImage(input);\n\n // version\n if (config.tag.version && version) {\n result.push({\n input,\n output: `${outputBase}:${version}`\n });\n }\n\n if (!isPreRelease(context)) {\n const { major, minor } = getMajorAndMinorPart(version);\n\n // latest\n if (config.tag.latest) {\n result.push({\n input,\n output: `${outputBase}:latest`\n });\n }\n\n // major\n if (config.tag.major && major) {\n result.push({\n input,\n output: `${outputBase}:${major}`\n });\n }\n\n // minor\n if (config.tag.minor && major && minor) {\n result.push({\n input,\n output: `${outputBase}:${major}.${minor}`\n });\n }\n }\n\n // channel\n const channel = context.nextRelease?.channel;\n if (config.tag.channel && channel) {\n result.push({\n input,\n output: `${outputBase}:${channel}`\n });\n }\n });\n\n return result;\n}\n\nexport function getUrlFromImage (image: string): string | undefined {\n const parts = getBaseImage(image).split('/');\n if (parts[0] === 'ghcr.io' && parts.length === 3) {\n return `https://github.com/${parts[1]}/${parts[2]}/pkgs/container/${parts[2]}`;\n }\n if (parts[0] === 'registry.gitlab.com' && parts.length >= 3) {\n return `https://gitlab.com/${parts[1]}/${parts[2]}/container_registry`;\n }\n\n const couldBeAHostname = parts[0].includes('.');\n if (!couldBeAHostname && parts.length === 2) {\n return `https://hub.docker.com/r/${parts[0]}/${parts[1]}/tags`;\n }\n if (!couldBeAHostname && parts.length === 1) {\n return `https://hub.docker.com/_/${parts[0]}/tags`;\n }\n}\n\nexport async function exec (file: string, args: string[]): Promise<void> {\n try {\n await execa(file, args);\n } catch (error) {\n if (typeof error === 'object' && error !== null && 'command' in error && 'message' in error) {\n\n // eslint-disable-next-line @typescript-eslint/ban-ts-comment\n // @ts-ignore\n throw new Error(`Unable to run \"${error.command}\": ${error.message}`);\n } else {\n throw new Error(`Unable to run \"${args.join(' ')}\": ${error}`);\n }\n }\n}\n\nexport async function isRegCtlAvailable (): Promise<boolean> {\n if(IS_REGCTL_AVAILABLE !== undefined) {\n return IS_REGCTL_AVAILABLE;\n }\n\n try {\n await execa('which', ['regctl']);\n IS_REGCTL_AVAILABLE = true;\n return true;\n }\n catch(error) {\n IS_REGCTL_AVAILABLE = false;\n return false;\n }\n}\n\nexport async function tagImage (input: string, output: string): Promise<void> {\n await exec('docker', ['tag', input, output]);\n}\n\nexport async function pushImage (image: string): Promise<void> {\n await exec('docker', ['push', image]);\n}\n\nexport async function copyImage (input: string, output: string): Promise<void> {\n await exec('regctl', ['image', 'copy', input, output]);\n}\n\nexport async function publish (pluginConfig: PluginConfig, context: Context): Promise<boolean | PublishResponse> {\n if (!context.nextRelease) {\n context.logger.log('No release schedules, so no images to tag.');\n return false;\n }\n\n const config = parseConfig(pluginConfig);\n const tasks = getTagTasks(config, context);\n if (!tasks.length) {\n return false;\n }\n\n for (const task of tasks) {\n if(await isRegCtlAvailable()) {\n context.logger.log(`Copy with regctl ${task.input} → ${task.output}`);\n\n try {\n await copyImage(task.input, task.output);\n continue;\n }\n catch(error) {\n context.logger.error(error);\n context.logger.log('Retry without regctl…');\n }\n }\n\n context.logger.log(`Tag ${task.input} → ${task.output}`);\n await tagImage(task.input, task.output);\n\n context.logger.log(`Push ${task.output}`);\n await pushImage(task.output);\n }\n\n const channel = context.nextRelease?.channel;\n const firstTask = tasks[0];\n return {\n name: `Docker container (${firstTask.output})`,\n url: getUrlFromImage(firstTask.output),\n channel\n };\n}\n\nexport default {\n publish\n};\n"],"mappings":"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","names":["execa","IS_REGCTL_AVAILABLE","parseConfig","config","result","image","name","value","getBaseImage","input","p","isPreRelease","context","getMajorAndMinorPart","version","parts","getTagTasks","_a","outputBase","major","minor","channel","getUrlFromImage","couldBeAHostname","exec","file","args","__async","execa","error","isRegCtlAvailable","tagImage","output","pushImage","copyImage","publish","pluginConfig","tasks","task","firstTask","lib_default"]}
1
+ {"version":3,"sources":["../src/lib/index.ts"],"sourcesContent":["import { PublishContext } from 'semantic-release';\nimport {\n MajorAndMinorPart,\n NormalizedPluginConfigTags,\n NormalizedPluginConfig,\n PluginConfig,\n PluginConfigTagKeys,\n TagTask,\n PublishResponse\n} from './types.js';\nimport { execa } from 'execa';\n\nexport {\n PluginConfig,\n NormalizedPluginConfigTags,\n NormalizedPluginConfig,\n PluginConfigTagKeys,\n MajorAndMinorPart,\n TagTask\n};\n\nlet IS_REGCTL_AVAILABLE: boolean | undefined = undefined;\n\nexport function parseConfig (config: PluginConfig): NormalizedPluginConfig {\n const result: NormalizedPluginConfig = {\n images: [],\n tag: {\n latest: true,\n major: true,\n minor: true,\n version: true,\n channel: true\n }\n };\n\n if (typeof config.images === 'string') {\n result.images.push(config.images);\n } else if (Array.isArray(config.images)) {\n config.images\n .filter(image => typeof image === 'string')\n .forEach(image => result.images.push(image));\n } else {\n throw new Error('Configuration invalid: No image defined!');\n }\n\n const tagNames = Object.keys(result.tag) as PluginConfigTagKeys[];\n tagNames.forEach(name => {\n const value = config.tag ? config.tag[name] : undefined;\n if (value === true || value === false) {\n result.tag[name] = value;\n }\n });\n\n return result;\n}\n\nexport function getBaseImage (input: string): string {\n let p = input.split('@')[0].split(':');\n\n // it's a \":port\"\n if (p[1] && p[1].includes('/')) {\n p = [p[0] + ':' + p[1], p[2]];\n }\n\n return p[0];\n}\n\nexport function isPreRelease (context: PublishContext): boolean {\n return Boolean(context.nextRelease && context.nextRelease.version.includes('-'));\n}\n\nexport function getMajorAndMinorPart (version: string | undefined): MajorAndMinorPart {\n if (!version) {\n return {\n major: null,\n minor: null\n };\n }\n\n const parts = version.split('.', 2);\n return {\n major: parts[0],\n minor: parts[1]\n };\n}\n\nexport function getTagTasks (config: NormalizedPluginConfig, context: PublishContext): TagTask[] {\n const result: TagTask[] = [];\n\n if (!context.nextRelease) {\n return [];\n }\n\n const version = context.nextRelease.version;\n config.images.forEach(input => {\n const outputBase = getBaseImage(input);\n\n // version\n if (config.tag.version && version) {\n result.push({\n input,\n output: `${outputBase}:${version}`\n });\n }\n\n if (!isPreRelease(context)) {\n const { major, minor } = getMajorAndMinorPart(version);\n\n // latest\n if (config.tag.latest) {\n result.push({\n input,\n output: `${outputBase}:latest`\n });\n }\n\n // major\n if (config.tag.major && major) {\n result.push({\n input,\n output: `${outputBase}:${major}`\n });\n }\n\n // minor\n if (config.tag.minor && major && minor) {\n result.push({\n input,\n output: `${outputBase}:${major}.${minor}`\n });\n }\n }\n\n // channel\n const channel = context.nextRelease?.channel;\n if (config.tag.channel && channel) {\n result.push({\n input,\n output: `${outputBase}:${channel}`\n });\n }\n });\n\n return result;\n}\n\nexport function getUrlFromImage (image: string): string | undefined {\n const parts = getBaseImage(image).split('/');\n if (parts[0] === 'ghcr.io' && parts.length === 3) {\n return `https://github.com/${parts[1]}/${parts[2]}/pkgs/container/${parts[2]}`;\n }\n if (parts[0] === 'registry.gitlab.com' && parts.length >= 3) {\n return `https://gitlab.com/${parts[1]}/${parts[2]}/container_registry`;\n }\n\n const couldBeAHostname = parts[0].includes('.');\n if (!couldBeAHostname && parts.length === 2) {\n return `https://hub.docker.com/r/${parts[0]}/${parts[1]}/tags`;\n }\n if (!couldBeAHostname && parts.length === 1) {\n return `https://hub.docker.com/_/${parts[0]}/tags`;\n }\n}\n\nexport async function exec (file: string, args: string[]): Promise<void> {\n try {\n await execa(file, args);\n } catch (error) {\n if (typeof error === 'object' && error !== null && 'command' in error && 'message' in error) {\n\n // eslint-disable-next-line @typescript-eslint/ban-ts-comment\n // @ts-ignore\n throw new Error(`Unable to run \"${error.command}\": ${error.message}`);\n } else {\n throw new Error(`Unable to run \"${args.join(' ')}\": ${error}`);\n }\n }\n}\n\nexport async function isRegCtlAvailable (): Promise<boolean> {\n if(IS_REGCTL_AVAILABLE !== undefined) {\n return IS_REGCTL_AVAILABLE;\n }\n\n try {\n await execa('which', ['regctl']);\n IS_REGCTL_AVAILABLE = true;\n return true;\n }\n\n // eslint-disable-next-line @typescript-eslint/no-unused-vars\n catch(error) {\n IS_REGCTL_AVAILABLE = false;\n return false;\n }\n}\n\nexport async function tagImage (input: string, output: string): Promise<void> {\n await exec('docker', ['tag', input, output]);\n}\n\nexport async function pushImage (image: string): Promise<void> {\n await exec('docker', ['push', image]);\n}\n\nexport async function copyImage (input: string, output: string): Promise<void> {\n await exec('regctl', ['image', 'copy', input, output]);\n}\n\nexport async function publish (pluginConfig: PluginConfig, context: PublishContext): Promise<boolean | PublishResponse> {\n if (!context.nextRelease) {\n context.logger.log('No release schedules, so no images to tag.');\n return false;\n }\n\n const config = parseConfig(pluginConfig);\n const tasks = getTagTasks(config, context);\n if (!tasks.length) {\n return false;\n }\n\n for (const task of tasks) {\n if(await isRegCtlAvailable()) {\n context.logger.log(`Copy with regctl ${task.input} → ${task.output}`);\n\n try {\n await copyImage(task.input, task.output);\n continue;\n }\n catch(error) {\n context.logger.error(error);\n context.logger.log('Retry without regctl…');\n }\n }\n\n context.logger.log(`Tag ${task.input} → ${task.output}`);\n await tagImage(task.input, task.output);\n\n context.logger.log(`Push ${task.output}`);\n await pushImage(task.output);\n }\n\n const channel = context.nextRelease?.channel;\n const firstTask = tasks[0];\n return {\n name: `Docker container (${firstTask.output})`,\n url: getUrlFromImage(firstTask.output),\n channel\n };\n}\n\nexport default {\n publish\n};\n"],"mappings":"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","names":["execa","IS_REGCTL_AVAILABLE","parseConfig","config","result","image","name","value","getBaseImage","input","p","isPreRelease","context","getMajorAndMinorPart","version","parts","getTagTasks","outputBase","major","minor","channel","getUrlFromImage","couldBeAHostname","exec","file","args","execa","error","isRegCtlAvailable","tagImage","output","pushImage","copyImage","publish","pluginConfig","tasks","task","firstTask","lib_default"]}
package/package.json CHANGED
@@ -4,32 +4,34 @@
4
4
  "url": "https://github.com/sebbo2002/semantic-release-docker/issues"
5
5
  },
6
6
  "dependencies": {
7
- "execa": "^8.0.1"
7
+ "execa": "^9.3.0"
8
8
  },
9
9
  "description": "Plugin for semantic-release that tags a previously built Docker image and pushes it to one or more Docker registries",
10
10
  "devDependencies": {
11
+ "@eslint/js": "^9.9.0",
11
12
  "@qiwi/semantic-release-gh-pages-plugin": "^5.2.12",
12
13
  "@semantic-release/changelog": "^6.0.3",
13
14
  "@semantic-release/exec": "^6.0.3",
14
15
  "@semantic-release/git": "^10.0.1",
15
- "@semantic-release/npm": "^11.0.2",
16
- "@types/mocha": "^10.0.6",
17
- "@types/node": "^20.11.5",
16
+ "@semantic-release/npm": "^12.0.1",
17
+ "@types/eslint__js": "^8.42.3",
18
+ "@types/express": "^4.17.21",
19
+ "@types/mocha": "^10.0.7",
20
+ "@types/node": "^22.1.0",
18
21
  "@types/semantic-release": "^20.0.6",
19
- "@typescript-eslint/eslint-plugin": "^6.18.1",
20
- "@typescript-eslint/parser": "^6.18.1",
21
- "c8": "^9.1.0",
22
- "eslint": "^8.56.0",
23
- "eslint-plugin-jsonc": "^2.13.0",
22
+ "c8": "^10.1.2",
23
+ "eslint": "^9.8.0",
24
+ "eslint-plugin-jsonc": "^2.16.0",
24
25
  "license-checker": "^25.0.1",
25
- "mocha": "^10.2.0",
26
+ "mocha": "^10.7.3",
26
27
  "mochawesome": "^7.1.3",
27
28
  "semantic-release-license": "^1.0.3",
28
29
  "source-map-support": "^0.5.21",
29
30
  "ts-node": "^10.9.2",
30
- "tsup": "^8.0.1",
31
- "typedoc": "^0.25.7",
32
- "typescript": "^5.3.3"
31
+ "tsup": "^8.2.4",
32
+ "typedoc": "^0.26.5",
33
+ "typescript": "^5.5.4",
34
+ "typescript-eslint": "^8.0.0-alpha.62"
33
35
  },
34
36
  "engines": {
35
37
  "node": ">=18.0.0"
@@ -52,9 +54,9 @@
52
54
  "build-all": "./.github/workflows/build.sh",
53
55
  "coverage": "c8 mocha",
54
56
  "license-check": "license-checker --production --summary",
55
- "lint": "eslint . --ext .ts,.json",
57
+ "lint": "eslint .",
56
58
  "test": "docker pull alpine:latest && mocha"
57
59
  },
58
60
  "type": "module",
59
- "version": "4.0.3-develop.9"
61
+ "version": "4.0.4-develop.1"
60
62
  }