fireflyy 3.0.2 → 3.0.3
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/main.js +11 -11
- package/package.json +1 -2
package/dist/main.js
CHANGED
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
#!/usr/bin/env bun
|
|
2
|
-
import e,{ZodError as t,z as n}from"zod";import{Result as r,ResultAsync as i,err as a,errAsync as o,ok as s,okAsync as c}from"neverthrow";import l,{basename as u,join as d,resolve as f}from"path";import{colors as p}from"consola/utils";import{runGitCliff as ee}from"git-cliff";import{LogLevels as m,createConsola as te}from"consola";import
|
|
3
|
-
`),S.verbose(`GitCliffAdapter: Release notes set.`)),e.dryRun?S.verbose(`GitCliffAdapter: Prepend option will not be set for dry run.`):(t.prepend=e.changelogPath,S.verbose(`GitCliffAdapter: Prepend option set for changelog path.`)),e.hasRootDirection&&(t.repository=e.rootDirection,t.includePath=e.includePath,S.verbose(`GitCliffAdapter: Include path set to ${e.includePath}`)),e.repository&&(t.githubRepo=e.repository,S.verbose(`GitCliffAdapter: Repository set to ${e.repository}`)),S.verbose(`GitCliffAdapter: GitCliffOptions constructed.`),s(t)}executeGitCliff(e){return i.fromPromise(this.addGitHubToken(e),w).andThen(e=>{if(e.isErr())return a(e.error);let t={...e.value},n=!!t.githubToken;return S.verbose(`GitCliffAdapter: Executing git-cliff with tag: ${t.tag}`),i.fromPromise(ee(t,{stdio:`pipe`}),w).andThen(e=>{if(e.exitCode!==0)return a(C({code:`FAILED`,message:`GitCliffAdapter: git-cliff failed with exit code ${e.exitCode}`}));let r=e.escapedCommand;if(r&&S.verbose(`GitCliffAdapter: Executing ${this.redactTokenFromCommand(r)}`),!e.stdout)return a(C({code:`FAILED`,message:`GitCliffAdapter: git-cliff returned no stdout content`}));let i=String(e.stdout);return n&&(t.githubToken=``),s(i)})})}async addGitHubToken(e){let t=await
|
|
4
|
-
`).map(e=>e.trim()).filter(e=>e.length>0).map(e=>this.parseBranchLine(e));return S.verbose(`GitBranchService: Found ${r.length} ${e?`total`:`local`} branches.`),s(r)}async isProvidedBranchValid(e){S.verbose(`GitBranchService: Checking if branch "${e}" is valid...`);let t=await this.listBranches(!1);if(t.isErr())return a(t.error);if(t.value.some(t=>t.name===e&&!t.isRemote))return s(!0);let n=await this.listBranches(!0);if(n.isErr())return a(n.error);let r=n.value.some(t=>t.name===e||t.isRemote&&t.name.endsWith(`/${e}`));return S.verbose(`GitBranchService: Branch "${e}" is ${r?`valid`:`invalid`}.`),s(r)}async isCurrentBranch(e){let t=await this.currentBranch();if(t.isErr())return a(t.error);let n=t.value===e;return s(n)}async createBranch(e,t,n){let r=[`branch`,e];t&&r.push(t);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):s()}async deleteBranch(e,t=!1,n){let r=[`branch`];r.push(t?`-D`:`-d`),r.push(e);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):s()}async switchToBranch(e,t=!1,n){let r=[`switch`];t&&r.push(`-c`),r.push(e);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):s()}async getUpstreamBranch(e){let t=await T([`rev-parse`,`--abbrev-ref`,`--symbolic-full-name`,`${e||`HEAD`}@{u}`]);if(t.isErr())return s(null);let n=t.value.trim();return s(n||null)}async hasUpstream(e){let t=await this.getUpstreamBranch(e);return t.isErr()?a(t.error):s(t.value!==null)}parseBranchLine(e){let t=e.startsWith(`*`),n=e.includes(`remotes/`),r=e.replace(
|
|
2
|
+
import e,{ZodError as t,z as n}from"zod";import{Result as r,ResultAsync as i,err as a,errAsync as o,ok as s,okAsync as c}from"neverthrow";import l,{basename as u,join as d,resolve as f}from"path";import{colors as p}from"consola/utils";import{runGitCliff as ee}from"git-cliff";import{LogLevels as m,createConsola as te}from"consola";import h from"semver";import{program as g}from"commander";import{loadConfig as ne}from"c12";const re=e.string().regex(/^[\w.-]+\/[\w.-]+$/,`Repository must be in 'owner/repo' format`).or(e.literal(``)).default(``).describe(`Repository identifier in 'owner/repo' format or empty string.`),_=e.object({repository:re.describe(`Repo in 'owner/repo' format, auto-detected if omitted.`),verbose:e.boolean().default(!1).describe(`Enable verbose logging.`),dryRun:e.boolean().default(!1).describe(`Simulate execution without changes.`),branch:e.string().optional().describe(`Branch to run on, defaults to current.`)}),v=`auto`,y=`manual`,ie=[v,y],ae=e.enum(ie).or(e.literal(``)).default(``),oe=e.union([e.number(),e.literal(`0`),e.literal(`1`)]).optional(),se=e.enum([`major`,`minor`,`patch`,`prerelease`,`premajor`,`preminor`,`prepatch`,`graduate`]),ce={release:e.object({name:e.string().optional().describe(`Unscoped project name. Auto-detected from package.json.`),scope:e.string().optional().describe(`Org/user scope without "@". Auto-detected from package.json.`),base:e.string().default(``).describe(`Relative path from repository root to project root. Useful for monorepos.`),changelogPath:e.string().default(`CHANGELOG.md`).describe(`Changelog file path, relative to project root.`),bumpStrategy:ae.describe(`"auto" (from commits) or "manual" (user-specified).`),releaseType:se.optional().describe(`The release type to bump.`),preReleaseId:e.string().default(`alpha`).describe(`Pre-release ID (e.g., "alpha", "beta").`),preReleaseBase:oe.describe(`Starting version for pre-releases.`),releaseNotes:e.string().default(``).describe(`Custom release notes for changelog.`),commitMessage:e.string().default(`chore(release): release {{name}}@{{version}}`).describe(`Commit message template with placeholders.`),tagName:e.string().default(`{{name}}@{{version}}`).describe(`Tag name template with placeholders.`),skipBump:e.coerce.boolean().default(!1).describe(`Skip version bump step.`),skipChangelog:e.coerce.boolean().default(!1).describe(`Skip changelog generation step.`),skipPush:e.coerce.boolean().default(!1).describe(`Skip push step.`),skipGitHubRelease:e.coerce.boolean().default(!1).describe(`Skip GitHub release step.`),skipGit:e.coerce.boolean().default(!1).describe(`Skip all git-related steps.`),skipPreflightCheck:e.coerce.boolean().default(!1).describe(`Skip preflight checks.`),releaseTitle:e.string().default(`{{name}}@{{version}}`).describe(`GitHub release title with placeholders.`),releaseLatest:e.coerce.boolean().default(!0).describe(`Mark as latest release.`),releasePreRelease:e.coerce.boolean().default(!1).describe(`Mark as pre-release.`),releaseDraft:e.coerce.boolean().default(!1).describe(`Release as draft version.`)}).check(e=>{let t=[`releaseLatest`,`releasePreRelease`,`releaseDraft`];t.filter(t=>!!e.value[t]).length>1&&e.issues.push({code:`custom`,message:`Only one of ${t.join(`, `)} can be set to true.`,input:e.value,path:[`releaseLatest`]}),e.value.skipGit&&e.value.skipPush&&e.issues.push({code:`custom`,message:`skipPush should not be set when skipGit is true.`,input:e.value}),e.value.bumpStrategy===`auto`&&e.value.releaseType!==void 0&&e.value.releaseType!==`prerelease`&&e.issues.push({code:`custom`,message:`When bumpStrategy is 'auto', releaseType can only be 'prerelease' if specified.`,input:e.value})})};var b=class e{static schemas=ce;static base(){return _}static get(t){if(t){let n=e.schemas[t];return _.extend({...n.shape})}let n={};for(let t of Object.values(e.schemas))Object.assign(n,t.shape);return _.extend(n)}static getEffect(t){return t?_.and(e.schemas[t]):Object.values(e.schemas).reduce((e,t)=>e.and(t),_)}};const x={};function le(e){return x[e]}x.release=e.object({command:e.literal(`release`),currentVersion:e.string().optional(),basePath:e.string().default(process.cwd()),nextVersion:e.string().optional(),changelogContent:e.string().optional(),config:b.get(`release`).optional()});const ue={date:!1,compact:!0,columns:0},de=te({formatOptions:ue}),S=te({formatOptions:ue,reporters:[{log(e){e.type===`verbose`?console.log(p.gray(e.args.join(` `))):de.log(e)}}]}),fe=n.enum([`VALIDATION`,`NOT_FOUND`,`CONFLICT`,`IO`,`TIMEOUT`,`UNEXPECTED`,`FAILED`,`INVALID`]),pe=n.object({code:fe,message:n.string(),details:n.unknown().optional(),cause:n.unknown().optional(),retryable:n.boolean().optional(),source:n.string().optional()});function C(e){let t=Error(e.message);return Object.freeze({...e,stack:t.stack})}function w(e,t=`UNEXPECTED`,n){let r={code:t,message:e instanceof Error?e.message:String(e),cause:e,source:n};return C(pe.parse(r))}const me=new Set([`repo`,`pr`,`issue`,`gist`,`release`,`workflow`,`run`,`secret`,`variable`,`auth`,`alias`,`config`,`extension`,`ssh-key`,`gpg-key`,`api`,`codespace`,`project`,`label`,`milestone`]),he=new Set([`repo`,`pr`,`issue`,`gist`,`release`,`workflow`,`run`,`api`,`search`,`browse`,`status`]),ge=n.array(n.string().min(1));function _e(e){if(e.length===0)return!1;let t=e.map(e=>e.toLowerCase());return t.some((e,n)=>{if(me.has(e)){let e=t[n+1];if(e)return`create.delete.edit.merge.close.reopen.comment.review.approve.request-changes.upload.download.clone.fork.sync.enable.disable.cancel.rerun.set.add.remove.login.logout.install.upgrade.remove.publish`.split(`.`).includes(e)}return!1})}function ve(e){if(e.length===0)return!1;let t=e.map(e=>e.toLowerCase());return t.some((e,n)=>{if(he.has(e)){let e=t[n+1];if(e)return[`list`,`view`,`status`,`diff`,`log`,`search`].includes(e)}return!1})}function ye(e){let t=!!process.env.FIREFLY_DEBUG_DONT_TRUNCATE_RELEASE_NOTES;if(e[0]===`release`&&e[1]===`create`&&!t){let t=e.indexOf(`--notes`);if(t!==-1){let n=e.slice(t+2).filter(e=>e.startsWith(`--`));return[...e.slice(0,t+1),`NOTES_TRUNCATED`,...n].join(` `)}}return e.join(` `)}function be(e,t={}){t.verbose=t.verbose??!0;let n=ge.safeParse(e);if(!n.success)return o(C({code:`FAILED`,message:`Invalid gh arguments`,details:n.error}));let r=n.data,i=`gh ${ye(r)}`,a=ve(r)&&!t.forceBuffered,s=a?`streaming`:`buffered`;if(t.verbose&&S.verbose(`GhCommandExecutor: Executing gh command (${s}): ${i}`),t.dryRun&&_e(r)){let e=`Dry run: Skipping ${i}`;return t.verbose&&S.verbose(e),c(e)}let l={cwd:t.cwd??process.cwd(),stdout:`pipe`,stderr:`pipe`,env:{...process.env,GH_NO_UPDATE_NOTIFIER:`1`}};return a?Se(r,l,r.join(` `)):xe(r,l,r.join(` `))}function xe(e,t,n){let r=Bun.spawn([`gh`,...e],t),a=new Response(r.stdout).text(),o=r.exited;return i.fromPromise(Promise.all([a,o]).then(([e])=>r.exitCode===0?e:new Response(r.stderr).text().then(e=>{let t=`GitHub CLI process exited with code ${r.exitCode}: ${e}`;return Promise.reject(Error(t))})),e=>C({code:`FAILED`,message:`GitHub CLI command failed: ${n}`,details:e}))}function Se(e,t,n){return i.fromPromise(Ce(e,t),e=>C({code:`FAILED`,message:`GitHub CLI command failed: ${n}`,details:e}))}function Ce(e,t){return new Promise((n,r)=>{let i=Bun.spawn([`gh`,...e],t),a=[],o=i.stdout.getReader(),s=new TextDecoder,c=()=>{o.read().then(e=>{if(e.done){let e=s.decode();e&&a.push(e),i.exited.then(()=>{i.exitCode===0?n(a.join(``)):new Response(i.stderr).text().then(e=>{let t=`GitHub CLI process exited with code ${i.exitCode}: ${e}`;r(Error(t))})})}else{let t=s.decode(e.value,{stream:!0});a.push(t),c()}})};c()})}var we=class{async createRelease(e){let t=[`release`,`create`,e.tag,`--title`,e.title,e.latest?`--latest`:``,e.draft?`--draft`:``,e.prerelease?`--prerelease`:``];e.content.trim()&&t.push(`--notes`,e.content);let n=await be(t.filter(Boolean),{dryRun:e.dryRun});return n.isErr()?a(n.error):s()}},Te=class{async getToken(){let e=process.env.GITHUB_TOKEN??process.env.GH_TOKEN;if(e)return S.verbose(`GitHubTokenService: Using token from environment variable.`),s(e);S.verbose(`GitHubTokenService: No token found in environment variables, attempting to retrieve via GitHub CLI.`);let t=await be([`auth`,`token`]);return t.isErr()?t:(e=t.value.trim(),S.verbose(`GitHubTokenService: Successfully retrieved token via GitHub CLI.`),s(e))}},Ee=class e{static _instance;_token;_release;constructor(){}static getInstance(){return e._instance||=new e,e._instance}get token(){return this._token||=new Te,this._token}get release(){return this._release||=new we,this._release}},De=class{async generate(e){let t=this.createGitCliffOptions(e);if(t.isErr())return a(t.error);S.verbose(`GitCliffAdapter: GitCliff options created successfully.`);let n=t.value,r=await this.executeGitCliff(n);return r.isErr()?a(r.error):(S.verbose(`GitCliffAdapter: GitCliff executed successfully.`),s(r.value))}createGitCliffOptions(e){if(!e.tagName?.trim())return a(C({message:`GitCliffAdapter: Tag name is required but was provided in options.`,code:`INVALID`}));let t={tag:e.tagName,unreleased:!0,config:`./cliff.toml`,output:`-`};return e.releaseNotes&&(t.withTagMessage=e.releaseNotes.replace(/\\n/g,`
|
|
3
|
+
`),S.verbose(`GitCliffAdapter: Release notes set.`)),e.dryRun?S.verbose(`GitCliffAdapter: Prepend option will not be set for dry run.`):(t.prepend=e.changelogPath,S.verbose(`GitCliffAdapter: Prepend option set for changelog path.`)),e.hasRootDirection&&(t.repository=e.rootDirection,t.includePath=e.includePath,S.verbose(`GitCliffAdapter: Include path set to ${e.includePath}`)),e.repository&&(t.githubRepo=e.repository,S.verbose(`GitCliffAdapter: Repository set to ${e.repository}`)),S.verbose(`GitCliffAdapter: GitCliffOptions constructed.`),s(t)}executeGitCliff(e){return i.fromPromise(this.addGitHubToken(e),w).andThen(e=>{if(e.isErr())return a(e.error);let t={...e.value},n=!!t.githubToken;return S.verbose(`GitCliffAdapter: Executing git-cliff with tag: ${t.tag}`),i.fromPromise(ee(t,{stdio:`pipe`}),w).andThen(e=>{if(e.exitCode!==0)return a(C({code:`FAILED`,message:`GitCliffAdapter: git-cliff failed with exit code ${e.exitCode}`}));let r=e.escapedCommand;if(r&&S.verbose(`GitCliffAdapter: Executing ${this.redactTokenFromCommand(r)}`),!e.stdout)return a(C({code:`FAILED`,message:`GitCliffAdapter: git-cliff returned no stdout content`}));let i=String(e.stdout);return n&&(t.githubToken=``),s(i)})})}async addGitHubToken(e){let t=await Ee.getInstance().token.getToken();return t.isErr()?a(t.error):(S.verbose(`GitCliffAdapter: GitHub token retrieved successfully.`),s({...e,githubToken:t.value}))}redactTokenFromCommand(e){return e.replace(/--github-token\s+([^\s]+)/g,`--github-token REDACTED_FOR_SECURITY`)}};const Oe=new Set([`add`,`am`,`apply`,`branch`,`checkout`,`cherry-pick`,`clean`,`commit`,`fetch`,`merge`,`mv`,`pull`,`push`,`rebase`,`reset`,`restore`,`revert`,`rm`,`stash`,`switch`,`tag`,`worktree`]),ke=new Set([`rev-list`,`log`,`show`,`diff`,`blame`,`cat-file`]),Ae=n.array(n.string().min(1));function je(e){return e.length===0?!1:e.map(e=>e.toLowerCase()).some(e=>Oe.has(e))}function Me(e){return e.length===0?!1:e.map(e=>e.toLowerCase()).some(e=>ke.has(e))}function T(e,t={}){t.verbose=t.verbose??!0;let n=Ae.safeParse(e);if(!n.success)return o(C({code:`FAILED`,message:`Invalid git arguments`,details:n.error}));let r=n.data,i=`git ${r.join(` `)}`,a=Me(r)&&!t.forceBuffered,s=a?`streaming`:`buffered`;if(t.verbose&&S.verbose(`GitCommandExecutor: Executing git command (${s}): ${i}`),t.dryRun&&je(r)){let e=`Dry run: Skipping ${i}`;return t.verbose&&S.verbose(e),c(e)}let l={cwd:t.cwd??process.cwd(),stdout:`pipe`,stderr:`pipe`};return a?Pe(r,l,i):Ne(r,l,i)}function Ne(e,t,n){let r=Bun.spawn([`git`,...e],t),a=new Response(r.stdout).text(),o=r.exited;return i.fromPromise(Promise.all([a,o]).then(([e])=>r.exitCode===0?e:new Response(r.stderr).text().then(e=>{let t=`Git process exited with code ${r.exitCode}: ${e}`;return Promise.reject(Error(t))})),e=>C({code:`FAILED`,message:`Git command failed: ${n}`,details:e}))}function Pe(e,t,n){return i.fromPromise(Fe(e,t),e=>C({code:`FAILED`,message:`Git command failed: ${n}`,details:e}))}function Fe(e,t){return new Promise((n,r)=>{let i=Bun.spawn([`git`,...e],t),a=[],o=i.stdout.getReader(),s=new TextDecoder,c=()=>{o.read().then(e=>{if(e.done){let e=s.decode();e&&a.push(e),i.exited.then(()=>{i.exitCode===0?n(a.join(``)):new Response(i.stderr).text().then(e=>{let t=`Git process exited with code ${i.exitCode}: ${e}`;r(Error(t))})})}else{let t=s.decode(e.value,{stream:!0});a.push(t),c()}})};c()})}const Ie=/^\*\s*/,Le=/^remotes\//;var Re=class{async currentBranch(){S.verbose(`GitBranchService: Getting current branch...`);let e=await T([`branch`,`--show-current`]);if(e.isErr())return a(e.error);let t=e.value.trim();return t?(S.verbose(`GitBranchService: Current branch is "${t}"`),s(t)):a(C({code:`NOT_FOUND`,message:`No current branch found. You may be in a detached HEAD state.`,source:`git/git-branch-service`}))}async listBranches(e=!1){S.verbose(`GitBranchService: Listing ${e?`all`:`local`} branches...`);let t=[`branch`];e&&t.push(`-a`);let n=await T(t);if(n.isErr())return a(n.error);let r=n.value.trim().split(`
|
|
4
|
+
`).map(e=>e.trim()).filter(e=>e.length>0).map(e=>this.parseBranchLine(e));return S.verbose(`GitBranchService: Found ${r.length} ${e?`total`:`local`} branches.`),s(r)}async isProvidedBranchValid(e){S.verbose(`GitBranchService: Checking if branch "${e}" is valid...`);let t=await this.listBranches(!1);if(t.isErr())return a(t.error);if(t.value.some(t=>t.name===e&&!t.isRemote))return s(!0);let n=await this.listBranches(!0);if(n.isErr())return a(n.error);let r=n.value.some(t=>t.name===e||t.isRemote&&t.name.endsWith(`/${e}`));return S.verbose(`GitBranchService: Branch "${e}" is ${r?`valid`:`invalid`}.`),s(r)}async isCurrentBranch(e){let t=await this.currentBranch();if(t.isErr())return a(t.error);let n=t.value===e;return s(n)}async createBranch(e,t,n){let r=[`branch`,e];t&&r.push(t);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):s()}async deleteBranch(e,t=!1,n){let r=[`branch`];r.push(t?`-D`:`-d`),r.push(e);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):s()}async switchToBranch(e,t=!1,n){let r=[`switch`];t&&r.push(`-c`),r.push(e);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):s()}async getUpstreamBranch(e){let t=await T([`rev-parse`,`--abbrev-ref`,`--symbolic-full-name`,`${e||`HEAD`}@{u}`]);if(t.isErr())return s(null);let n=t.value.trim();return s(n||null)}async hasUpstream(e){let t=await this.getUpstreamBranch(e);return t.isErr()?a(t.error):s(t.value!==null)}parseBranchLine(e){let t=e.startsWith(`*`),n=e.includes(`remotes/`),r=e.replace(Ie,``).trim();return n&&(r=r.replace(Le,``)),{name:r,isCurrent:t,isRemote:n}}},ze=class{constructor(e){this.config=e}async create(e,t){S.verbose(`GitCommitService: Creating commit with message: "${e}"${t?` (dry run)`:``}...`);let n=await this.config.canSign();if(n.isErr())return a(n.error);let r=n.value,i=[`commit`,`-m`,e];r&&i.push(`-S`);let o=await T(i,{dryRun:t});return o.isErr()?a(o.error):(S.verbose(`GitCommitService: Commit created successfully.`),s())}async resetLast(e=!1,t){S.verbose(`GitCommitService: Resetting last commit${e?` (hard)`:` (soft)`}${t?` (dry run)`:``}...`);let n=[`reset`,`--soft`,`HEAD~1`];e&&(n[1]=`--hard`);let r=await T(n,{dryRun:t});return r.isErr()?a(r.error):(S.verbose(`GitCommitService: Last commit reset successfully.`),s())}async restoreFileToHead(e,t){S.verbose(`GitCommitService: Restoring file "${e}" to HEAD state${t?` (dry run)`:``}...`);let n=await T([`restore`,`--source`,`HEAD`,`--`,e],{dryRun:t});return n.isErr()?a(n.error):(S.verbose(`GitCommitService: File "${e}" restored to HEAD state successfully.`),s())}},Be=class{async get(e){let t=await T([`config`,`--get`,e]);if(t.isErr())return a(t.error);let n=t.value.trim();return s(n)}async getGlobal(e){let t=await T([`config`,`--global`,`--get`,e]);if(t.isErr())return a(t.error);let n=t.value.trim();return s(n)}async getWithFallback(e){let t=await this.get(e);if(t.isOk())return t;let n=await this.getGlobal(e);return n.isOk()?n:a(C({code:`NOT_FOUND`,message:`Config key "${e}" not found in local or global config.`}))}async canSign(){S.verbose(`GitConfigService: Checking if Git is configured for signing...`);let e=await this.getWithFallback(`commit.gpgSign`);if(e.isErr())return e.error.code===`NOT_FOUND`?s(!1):a(e.error);let t=await this.getWithFallback(`user.signingKey`);if(t.isErr())return t.error.code===`NOT_FOUND`?s(!1):a(t.error);let n=e.value.toLowerCase(),r=t.value,i=(n===`true`||n===`1`)&&r.length>0;return S.verbose(`GitConfigService: Git signing configured: ${i}`),s(i)}async canSignTag(){let e=await this.getWithFallback(`tag.gpgSign`);if(e.isOk()){let t=e.value.toLowerCase();return t===`true`||t===`1`?this.canSign():s(!1)}return this.canSign()}},Ve=class{async lastTagOrNull(){S.verbose(`GitHistoryService: Fetching last tag (or null if none exist)`);let e=await T([`describe`,`--tags`,`--abbrev=0`]);if(e.isErr())return e.error.message.includes(`No names found`)?s(null):a(e.error);let t=e.value.trim();return S.verbose(`GitHistoryService: Last tag found - ${t}`),s(t||null)}async commitsSince(e){S.verbose(`GitHistoryService: Fetching commits since ${e||`the beginning`}`);let t;t=e?[`rev-list`,`${e}..HEAD`]:[`rev-list`,`HEAD`];let n=await T(t);if(n.isErr())return a(n.error);let r=n.value.trim().split(`
|
|
5
5
|
`).map(e=>e.trim()).filter(e=>e.length>0);return S.verbose(`GitHistoryService: Found ${r.length} commits since ${e||`the beginning`}`),s(r)}async commitDetails(e,t=!1){let n=await this.commitExists(e,t);if(n.isErr())return a(n.error);if(!n.value)return a(C({code:`NOT_FOUND`,message:`Commit "${e}" does not exist.`,source:`git/git-history-service`}));let r=[`hash:%H`,`date:%ci`,`author:%an <%ae>`,`subject:%s`,`body:%b`,`notes:%N`].join(`%n`),i=await T([`show`,`--no-patch`,`--format=${r}`,e],{verbose:t});return i.isErr()?a(i.error):s(i.value.trim())}async commitExists(e,t=!1){return(await T([`cat-file`,`-e`,e],{verbose:t})).isErr()?s(!1):s(!0)}async getCommitsBetween(e,t){S.verbose(`GitHistoryService: Fetching commits between ${e} and ${t}`);let n=await T([`rev-list`,`${e}..${t}`]);if(n.isErr())return a(n.error);let r=n.value.trim().split(`
|
|
6
6
|
`).map(e=>e.trim()).filter(e=>e.length>0);return S.verbose(`GitHistoryService: Found ${r.length} commits between ${e} and ${t}`),s(r)}async getTagsContainingCommit(e){S.verbose(`GitHistoryService: Fetching tags containing commit ${e}`);let t=await T([`tag`,`--contains`,e]);if(t.isErr())return a(t.error);let n=t.value.trim().split(`
|
|
7
7
|
`).map(e=>e.trim()).filter(e=>e.length>0);return S.verbose(`GitHistoryService: Found ${n.length} tags containing commit ${e}`),s(n)}async getCommitCount(e){S.verbose(`GitHistoryService: Fetching commit count since ${e||`the beginning`}`);let t;t=e?[`rev-list`,`--count`,`${e}..HEAD`]:[`rev-list`,`--count`,`HEAD`];let n=await T(t);if(n.isErr())return a(n.error);let r=Number.parseInt(n.value.trim(),10);return Number.isNaN(r)?a(C({code:`UNEXPECTED`,message:`Failed to parse commit count.`,source:`git/git-history-service`})):(S.verbose(`GitHistoryService: Commit count since ${e||`the beginning`} is ${r}`),s(r))}async isAncestor(e,t){return S.verbose(`GitHistoryService: Checking if ${e} is an ancestor of ${t}`),(await T([`merge-base`,`--is-ancestor`,e,t])).isErr()?s(!1):(S.verbose(`GitHistoryService: ${e} is an ancestor of ${t}`),s(!0))}async getLatestCommitIfMessageMatches(e){S.verbose(`GitHistoryService: Checking if latest commit message matches "${e}"`);let t=await T([`log`,`-1`,`--pretty=format:%H%n%s`]);if(t.isErr())return a(t.error);let[n,r]=t.value.trim().split(`
|
|
8
|
-
`);if(!(n&&r))return a(C({code:`UNEXPECTED`,message:`Failed to parse latest commit information.`,source:`git/git-history-service`}));let i=r.trim()===e.trim();return S.verbose(i?`GitHistoryService: Latest commit matches expected message. Hash: ${n}`:`GitHistoryService: Latest commit does not match expected message.`),s(i?n:null)}},
|
|
9
|
-
`).map(e=>e.trim()).filter(e=>e.length>0);return S.verbose(`GitPushService: Available remotes: ${n.join(`, `)}`),s(n.includes(e))}},
|
|
10
|
-
`).map(e=>e.trim()).filter(e=>e.length>0&&(e.startsWith(`<`)||e.startsWith(`>`))).some(e=>e.startsWith(`>`)):!1}},
|
|
8
|
+
`);if(!(n&&r))return a(C({code:`UNEXPECTED`,message:`Failed to parse latest commit information.`,source:`git/git-history-service`}));let i=r.trim()===e.trim();return S.verbose(i?`GitHistoryService: Latest commit matches expected message. Hash: ${n}`:`GitHistoryService: Latest commit does not match expected message.`),s(i?n:null)}},He=class{async push(e=`origin`,t,n){S.verbose(`GitPushService: Pushing to remote "${e}"${t?` branch "${t}"`:``}${n?` (dry run)`:``}...`);let r=[`push`,e];t&&r.push(t);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):(S.verbose(`GitPushService: Push completed successfully.`),s())}async pushTags(e=`origin`,t){S.verbose(`GitPushService: Pushing tags to remote "${e}"${t?` (dry run)`:``}...`);let n=await T([`push`,e,`--tags`],{dryRun:t});return n.isErr()?a(n.error):(S.verbose(`GitPushService: Tags push completed successfully.`),s())}async pushFollowTags(e=`origin`,t,n){S.verbose(`GitPushService: Pushing with --follow-tags to remote "${e}"${t?` branch "${t}"`:``}${n?` (dry run)`:``}...`);let r=[`push`,`--follow-tags`,e];t&&r.push(t);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):(S.verbose(`GitPushService: Push with --follow-tags completed successfully.`),s())}async pushTag(e,t=`origin`,n){S.verbose(`GitPushService: Pushing tag "${e}" to remote "${t}"${n?` (dry run)`:``}...`);let r=await T([`push`,t,e],{dryRun:n});return r.isErr()?a(r.error):(S.verbose(`GitPushService: Tag push completed successfully.`),s())}async pushDeleteRemoteTag(e,t=`origin`,n){S.verbose(`GitPushService: Deleting remote tag "${e}" from remote "${t}"${n?` (dry run)`:``}...`);let r=await T([`push`,t,`--delete`,e],{dryRun:n});return r.isErr()?a(r.error):(S.verbose(`GitPushService: Remote tag deleted successfully.`),s())}async pushForce(e=`origin`,t,n){S.verbose(`GitPushService: Force pushing to remote "${e}"${t?` branch "${t}"`:``}${n?` (dry run)`:``}...`);let r=[`push`,`--force-with-lease`,e];t&&r.push(t);let i=await T(r,{dryRun:n});return i.isErr()?a(i.error):(S.verbose(`GitPushService: Push completed successfully.`),s())}async getRemoteUrl(e=`origin`){S.verbose(`GitPushService: Getting URL for remote "${e}"`);let t=await T([`remote`,`get-url`,e]);return t.isErr()?t.error.message.includes(`No such remote`)?a(C({code:`NOT_FOUND`,message:`Remote "${e}" does not exist.`,source:`git/git-push-service`})):a(t.error):(S.verbose(`GitPushService: URL for remote "${e}": ${t.value.trim()}`),s(t.value.trim()))}async hasRemote(e=`origin`){S.verbose(`GitPushService: Checking if remote "${e}" exists...`);let t=await T([`remote`]);if(t.isErr())return a(t.error);let n=t.value.trim().split(`
|
|
9
|
+
`).map(e=>e.trim()).filter(e=>e.length>0);return S.verbose(`GitPushService: Available remotes: ${n.join(`, `)}`),s(n.includes(e))}},Ue=class{async getCurrentRemote(){S.verbose(`GitRemoteService: Getting current remote...`);let e=await T([`rev-parse`,`--abbrev-ref`,`--symbolic-full-name`,`@{u}`]);if(e.isErr())return a(C({code:`NOT_FOUND`,message:`No upstream branch found to determine current remote.`,source:`git/git-remote-service`}));let t=e.value.trim();if(!t)return a(C({code:`NOT_FOUND`,message:`No upstream branch found.`,source:`git/git-remote-service`}));let n=t.split(`/`)[0];return n?(S.verbose(`GitRemoteService: Current remote is "${n}"`),s(n)):a(C({code:`INVALID`,message:`Invalid upstream branch format: ${t}`,source:`git/git-remote-service`}))}async hasUnpushedCommits(){S.verbose(`GitRemoteService: Checking for unpushed commits...`);let e=await T([`rev-parse`,`--abbrev-ref`,`--symbolic-full-name`,`@{u}`]);if(e.isErr())return a(e.error);let t=e.value.trim();if(!t)return a(C({code:`NOT_FOUND`,message:`No upstream branch found.`,source:`git/git-remote-service`}));let n=await T([`rev-list`,`--left-right`,`${t}...HEAD`]);if(n.isErr())return a(n.error);let r=this.hasUnpushedFromOutput(n.value);return S.verbose(`GitRemoteService: Unpushed commits present: ${r}`),s(r)}hasUnpushedFromOutput(e){return e?e.trim().split(`
|
|
10
|
+
`).map(e=>e.trim()).filter(e=>e.length>0&&(e.startsWith(`<`)||e.startsWith(`>`))).some(e=>e.startsWith(`>`)):!1}},We=class{async isInsideWorkTree(){S.verbose(`GitRepositoryService: Checking if inside a Git work tree`);let e=await T([`rev-parse`,`--is-inside-work-tree`]);if(e.isErr())return s(!1);let t=e.value.trim()===`true`;return S.verbose(`GitRepositoryService: Inside Git work tree: ${t}`),s(t)}async getRootDirection(){S.verbose(`GitRepositoryService: Getting root directory`);let e=await T([`rev-parse`,`--show-toplevel`]);if(e.isErr())return a(e.error);let t=e.value.trim(),n=process.cwd(),r=l.relative(n,t);return r===``?s(`.`):(S.verbose(`GitRepositoryService: Relative path to root directory: ${r}`),s(r))}async getRepositoryUrl(e=`origin`){S.verbose(`GitRepositoryService: Getting URL for remote "${e}"`);let t=await T([`remote`,`get-url`,e]);return t.isErr()?t.error.message.includes(`No such remote`)?a(C({code:`NOT_FOUND`,message:`Remote "${e}" does not exist.`,source:`git/git-repository-service`})):a(t.error):(S.verbose(`GitRepositoryService: URL for remote "${e}": ${t.value.trim()}`),s(t.value.trim()))}async getRepositoryName(){S.verbose(`GitRepositoryService: Getting repository name`);let e=await T([`rev-parse`,`--show-toplevel`]);if(e.isErr())return a(e.error);let t=e.value.trim(),n=l.basename(t);return S.verbose(`GitRepositoryService: Repository name: ${n}`),s(n)}async isShallow(){S.verbose(`GitRepositoryService: Checking if repository is shallow`);let e=await T([`rev-parse`,`--is-shallow-repository`]);if(e.isErr())return s(!1);let t=e.value.trim()===`true`;return S.verbose(`GitRepositoryService: Repository is shallow: ${t}`),s(t)}async isBare(){S.verbose(`GitRepositoryService: Checking if repository is bare`);let e=await T([`rev-parse`,`--is-bare-repository`]);if(e.isErr())return s(!1);let t=e.value.trim()===`true`;return S.verbose(`GitRepositoryService: Repository is bare: ${t}`),s(t)}async getGitDirectory(){S.verbose(`GitRepositoryService: Getting .git directory path`);let e=await T([`rev-parse`,`--git-dir`]);return e.isErr()?a(e.error):(S.verbose(`GitRepositoryService: .git directory path: ${e.value.trim()}`),s(e.value.trim()))}async getWorkingDirectory(){S.verbose(`GitRepositoryService: Getting working directory path`);let e=await T([`rev-parse`,`--show-toplevel`]);return e.isErr()?a(e.error):(S.verbose(`GitRepositoryService: Working directory path: ${e.value.trim()}`),s(e.value.trim()))}},Ge=class{constructor(e,t,n){this.pushService=e,this.tagService=t,this.historyService=n}async rollbackPushedTags(e,t=`origin`,n){S.verbose(`GitRollbackService: Rolling back pushed tags: ${e.join(`, `)}`);for(let t of e){let e=await this.tagService.exists(t);if(e.isErr())return a(e.error);if(!e.value)return a(C({code:`NOT_FOUND`,message:`Tag "${t}" does not exist locally. Cannot rollback.`,source:`git/git-rollback-service`}))}for(let r of e){let e=await this.pushService.pushDeleteRemoteTag(r,t,n);if(e.isErr())return a(C({code:`FAILED`,message:`Failed to delete remote tag "${r}": ${e.error.message}`,source:`git/git-rollback-service`,cause:e.error}))}for(let t of e){let e=await this.tagService.deleteLocal(t,n);if(e.isErr())return a(C({code:`FAILED`,message:`Failed to delete local tag "${t}": ${e.error.message}`,source:`git/git-rollback-service`,cause:e.error}))}return S.verbose(`GitRollbackService: Successfully rolled back tags: ${e.join(`, `)}`),s()}async rollbackPushedCommit(e,t,n=`origin`,r){S.verbose(`GitRollbackService: Rolling back to commit ${t} on branch ${e}`);let i=await this.verifyCommitExists(t);if(i.isErr())return a(i.error);if(!i.value)return a(C({code:`NOT_FOUND`,message:`Commit "${t}" does not exist.`,source:`git/git-rollback-service`}));let o=await T([`revert`,`--no-edit`,t],{dryRun:r});if(o.isErr())return a(C({code:`FAILED`,message:`Failed to revert commit "${t}": ${o.error.message}`,source:`git/git-rollback-service`,cause:o.error}));let c=await this.pushService.push(n,e,r);return c.isErr()?a(C({code:`FAILED`,message:`Failed to push revert commit: ${c.error.message}`,source:`git/git-rollback-service`,cause:c.error})):(S.verbose(`GitRollbackService: Rollback to commit ${t} on branch ${e} successful`),s())}async rollbackToCommit(e,t,n=`origin`,r=!1,i){S.verbose(`GitRollbackService: Rolling back to commit ${e} on branch ${t}`);let o=await this.verifyCommitExists(e);if(o.isErr())return a(o.error);if(!o.value)return a(C({code:`NOT_FOUND`,message:`Commit "${e}" does not exist.`,source:`git/git-rollback-service`}));let c=await T([`reset`,`--hard`,e],{dryRun:i});if(c.isErr())return a(C({code:`FAILED`,message:`Failed to reset to commit "${e}": ${c.error.message}`,source:`git/git-rollback-service`,cause:c.error}));if(r){let e=await this.pushService.pushForce(n,t,i);if(e.isErr())return a(C({code:`FAILED`,message:`Failed to force push rollback: ${e.error.message}`,source:`git/git-rollback-service`,cause:e.error}))}else{let e=await this.pushService.push(n,t,i);if(e.isErr())return a(C({code:`FAILED`,message:`Failed to push rollback: ${e.error.message}`,source:`git/git-rollback-service`,cause:e.error}))}return S.verbose(`GitRollbackService: Rollback to commit ${e} on branch ${t} successful`),s()}async verifyCommitExists(e){return S.verbose(`GitRollbackService: Verifying commit exists: ${e}`),(await T([`cat-file`,`-e`,e])).isErr()?s(!1):(S.verbose(`GitRollbackService: Commit exists: ${e}`),s(!0))}async rollbackLatestCommitIfMessageMatches(e,t,n=`origin`,r=!1,i){S.verbose(`GitRollbackService: Attempting safe rollback if latest commit matches "${e}"`);let o=await this.historyService.getLatestCommitIfMessageMatches(e);if(o.isErr())return a(o.error);let s=o.value;return s?(S.verbose(`GitRollbackService: Latest commit matches. Proceeding with rollback to ${s}`),this.rollbackToCommit(`${s}^`,t,n,r,i)):a(C({code:`NOT_FOUND`,message:`Latest commit does not match expected message "${e}". Rollback aborted.`,source:`git/git-rollback-service`}))}},Ke=class{async stageAll(){S.verbose(`GitStagingService: Staging all changes`);let e=await T([`add`,`.`]);return e.isErr()?a(e.error):(S.verbose(`GitStagingService: All changes staged successfully`),s())}async stageFile(e,t){S.verbose(`GitStagingService: Staging file ${e}`);let n=await T([`add`,e],{dryRun:t});return n.isErr()?a(n.error):(S.verbose(`GitStagingService: File ${e} staged successfully`),s())}async stageFiles(e,t){S.verbose(`GitStagingService: Staging files: ${e.join(`, `)}`);let n=await T([`add`,...e],{dryRun:t});return n.isErr()?a(n.error):(S.verbose(`GitStagingService: Files staged successfully`),s())}async unstageAll(){S.verbose(`GitStagingService: Unstaging all changes`);let e=await T([`reset`]);return e.isErr()?a(e.error):(S.verbose(`GitStagingService: All changes unstaged successfully`),s())}async unstageFile(e){S.verbose(`GitStagingService: Unstaging file ${e}`);let t=await T([`reset`,`HEAD`,`--`,e]);return t.isErr()?a(t.error):(S.verbose(`GitStagingService: File ${e} unstaged successfully`),s())}async unstageFiles(e,t){S.verbose(`GitStagingService: Unstaging files: ${e.join(`, `)}`);let n=await T([`reset`,`HEAD`,`--`,...e],{dryRun:t});return n.isErr()?a(n.error):(S.verbose(`GitStagingService: Files unstaged successfully`),s())}},qe=class{async isWorkingDirectoryClean(){S.verbose(`GitStatusService: Checking if working directory is clean`);let e=await T([`status`,`--porcelain`]);if(e.isErr())return a(e.error);let t=e.value.trim().length===0;return S.verbose(`GitStatusService: Working directory ${t?`clean`:`not clean`}`),s(t)}async getModifiedFiles(e){S.verbose(`GitStatusService: Retrieving modified files`);let t=await T([`status`,`--porcelain`],{dryRun:e});if(t.isErr())return a(t.error);let n=t.value.trim();if(n.length===0)return S.verbose(`GitStatusService: No modified files found`),s([]);let r=n.split(`
|
|
11
11
|
`).map(e=>e.slice(2).trim());return S.verbose(`GitStatusService: Found modified files: ${r.join(`, `)}`),s(r)}async getUnstagedFiles(e){S.verbose(`GitStatusService: Retrieving unstaged files`);let t=await T([`status`,`--porcelain`],{dryRun:e});if(t.isErr())return a(t.error);let n=t.value;if(n.length===0)return S.verbose(`GitStatusService: No unstaged files found`),s([]);let r=n.split(`
|
|
12
12
|
`).filter(e=>e.charAt(1)!==` `).map(e=>e.slice(2).trim());return S.verbose(`GitStatusService: Found unstaged files: ${r.join(`, `)}`),s(r)}async getModifiedFilesByNames(e,t){let n=await this.getModifiedFiles(t);if(n.isErr())return a(n.error);let r=n.value.filter(t=>e.some(e=>t===e||u(t)===u(e)));return S.verbose(`GitStatusService: Filtered modified files: ${r.join(`, `)}`),s(r)}async getUnstagedFilesByNames(e,t){let n=await this.getUnstagedFiles(t);if(n.isErr())return a(n.error);let r=n.value.filter(t=>e.some(e=>t===e||u(t)===u(e)));return S.verbose(`GitStatusService: Filtered unstaged files: ${r.join(`, `)}`),s(r)}async getStagedFiles(e){S.verbose(`GitStatusService: Retrieving staged files`);let t=await T([`status`,`--porcelain`],{dryRun:e});if(t.isErr())return a(t.error);let n=t.value;if(n.length===0)return S.verbose(`GitStatusService: No staged files found`),s([]);let r=n.split(`
|
|
13
|
-
`).filter(e=>e.charAt(0)!==` `).map(e=>e.slice(2).trim());return S.verbose(`GitStatusService: Found staged files: ${r.join(`, `)}`),s(r)}async getStagedFilesByNames(e,t){let n=await this.getStagedFiles(t);if(n.isErr())return a(n.error);let r=n.value.filter(t=>e.some(e=>t===e||u(t)===u(e)));return S.verbose(`GitStatusService: Filtered staged files: ${r.join(`, `)}`),s(r)}},
|
|
14
|
-
`).map(e=>e.trim()).filter(e=>e.length>0);return S.verbose(`GitTagService: Found ${t.length} tags`),s(t)}async getTagMessage(e){S.verbose(`GitTagService: Getting message for tag ${e}`);let t=await this.exists(e);if(t.isErr())return a(t.error);if(!t.value)return a(C({code:`NOT_FOUND`,message:`Tag "${e}" does not exist.`,source:`git/git-tag-service`}));let n=await T([`tag`,`-l`,`--format=%(contents)`,e]);return n.isErr()?a(n.error):(S.verbose(`GitTagService: Retrieved message for tag ${e}`),s(n.value.trim()))}};const E={GITHUB_HTTPS:/^https:\/\/github\.com\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/,GITHUB_SSH:/^git@github\.com:([^/]+)\/([^/]+?)(?:\.git)?$/,GITLAB_HTTPS:/^https:\/\/gitlab\.com\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/,GITLAB_SSH:/^git@gitlab\.com:([^/]+)\/([^/]+?)(?:\.git)?$/,BITBUCKET_HTTPS:/^https:\/\/bitbucket\.org\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/,BITBUCKET_SSH:/^git@bitbucket\.org:([^/]+)\/([^/]+?)(?:\.git)?$/,GENERIC_HTTPS:/^https:\/\/([^/]+)\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/,GENERIC_SSH:/^git@([^:]+):([^/]+)\/([^/]+?)(?:\.git)?$/};var
|
|
15
|
-
`),S.verbose(`ChangelogGeneratorService: Release notes added to changelog options.`));let i=await this.gitProvider.repository.getRootDirection();return i.isErr()?a(i.error):(i.value&&i.value!==`.`&&(r.hasRootDirection=!0,r.rootDirection=i.value,r.includePath=`${e.base}/*`,S.verbose(`ChangelogGeneratorService: Include path set to ${r.includePath}`)),S.verbose(`ChangelogGeneratorService: Changelog options built successfully.`),s(r))}},O=class e{static TEMPLATE_PATTERNS={VERSION:/\{\{version\}\}/g,NAME:/\{\{name\}\}/g,UNSCOPED_NAME:/\{\{unscopedName\}\}/g};withContext(e){let t={version:e.version,name:this.getFullPackageName(e.config),unscopedName:e.config.name||``};return{commitMessage:e=>this.resolveTemplate(e,t),tagName:e=>this.resolveTemplate(e,t),releaseTitle:e=>this.resolveTemplate(e,t)}}getFullPackageName(e){return e.name?e.scope?`@${e.scope}/${e.name}`:e.name:``}resolveTemplate(t,n){if(!t?.trim())return t;let r=t;return n.version&&(r=r.replace(e.TEMPLATE_PATTERNS.VERSION,n.version)),r=r.replace(e.TEMPLATE_PATTERNS.NAME,n.name),r=r.replace(e.TEMPLATE_PATTERNS.UNSCOPED_NAME,n.unscopedName),r}},k=class e{static read(t){return e.exec(Bun.file(t).text(),`Failed to read file`).andTee(()=>{S.verbose(`FileSystemService: Read file at ${t}`)})}static write(t,n,r){return r?(S.verbose(`FileSystemService: Dry run mode enabled, not writing file.`),c(void 0)):e.exec(Bun.write(t,n),`Failed to write file`).map(()=>{}).andTee(()=>S.verbose(`FileSystemService: Wrote file at ${t}`))}static exists(t){return e.exec(Bun.file(t).exists(),`Failed to check if file exists`).andTee(()=>S.verbose(`FileSystemService: Checked existence of file at ${t}`))}static exec(e,t){return i.fromPromise(e,e=>C({code:`INVALID`,message:t,source:`filesystem/file-system-service`,cause:e}))}};function A(e){return`id`in e&&typeof e.id==`string`?e.id:new e().id}function j(e){return i.fromPromise(e,e=>C(w(e)))}function Qe(...t){return t.slice(1).reduce((t,n)=>e.intersection(t,n),t[0])}function $e(e,...t){let n={};for(let e of t)Object.assign(n,e);return e.extend(n)}function et(e){if(e?._def!==void 0)return e;let t=e;return t.mode===`effect`?Qe(...t.schemas):$e(t.base,...t.shapes)}function M(e,t){let n=et(e).safeParse(t);return n.success?s(n.data):a(C(w(n.error)))}function tt(e,t){let n=et(e);return i.fromPromise(n.parseAsync(t),e=>C(w(e)))}var N=class{id=`push-tag`;description=`Pushes the tag to the remote repository.`;getDependencies(){return[A(P)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipGit)}getNextTasks(e){return s([])}execute(e){let t=D.getInstance(),n=e.getConfig(),r=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).tagName(e.getConfig().tagName);return j(t.remote.getCurrentRemote()).andThen(e=>e.isErr()?o(e.error):j(t.push.pushTag(r,e.value,n.dryRun))).orElse(()=>j(t.push.pushTag(r,`origin`,n.dryRun))).map(()=>{S.success(`Pushed tag to remote repository`)})}canUndo(){return!0}undo(e){let t=D.getInstance(),n=e.getConfig(),r=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).tagName(n.tagName);return j(t.remote.getCurrentRemote()).andThen(e=>e.isErr()?o(e.error):j(t.push.pushDeleteRemoteTag(r,e.value,n.dryRun))).orElse(()=>j(t.push.pushDeleteRemoteTag(r,`origin`,n.dryRun))).map(()=>{S.success(`Rolled back tag '${r}' from remote and local`)})}},P=class e{id=`push-commit`;description=`Pushes the commit to the remote repository.`;getDependencies(){return[A(F)]}shouldExecute(e){let t=e.getConfig();return t.skipPush?s(!1):s(!t.skipGit)}getNextTasks(e){return e.getConfig().skipGit?s([]):s([A(N)])}getSkipThroughTasks(t){let n=t?.getConfig();return n?.skipPush?s([A(R)]):n?.skipGit?s([]):s([A(e)])}execute(e){let t=D.getInstance(),n=e.getConfig();return j(t.remote.getCurrentRemote()).andThen(e=>e.isErr()?o(e.error):j(t.push.push(e.value,n.branch,n.dryRun))).orElse(()=>j(t.push.push(`origin`,n.branch,n.dryRun))).map(()=>{S.success(`Pushed commit to remote repository.`)})}canUndo(){return!0}undo(e){let t=D.getInstance(),n=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).commitMessage(e.getConfig().commitMessage),r=e.getConfig();return j(t.remote.getCurrentRemote()).andThen(e=>e.isErr()?o(e.error):j(t.rollback.rollbackLatestCommitIfMessageMatches(n,r.branch,e.value,!1,r.dryRun))).orElse(()=>j(t.rollback.rollbackLatestCommitIfMessageMatches(n,r.branch,`origin`,!1,r.dryRun))).map(()=>{S.success(`Undid push commit to remote repository.`)})}},F=class{id=`create-tag`;description=`Creates a new tag for the release.`;getDependencies(){return[A(L)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipGit)}getNextTasks(e){return e.getConfig().skipGit?s([]):s([A(P)])}execute(e){let t=D.getInstance(),n=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}),r=n.tagName(e.getConfig().tagName),i=n.commitMessage(e.getConfig().releaseTitle);return j(t.tag.createTag(r,i,e.getConfig().dryRun)).map(()=>{S.info(`Created tag: ${p.gray(r)}`)})}canUndo(){return!0}undo(e){let t=D.getInstance(),n=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).tagName(e.getConfig().tagName);return j(t.tag.deleteLocal(n,e.getConfig().dryRun)).map(()=>{S.info(`Deleted tag: ${p.gray(n)}`)})}},I=class{id=`stage-changes`;description=`Stages the changes for the release.`;getDependencies(e){return e?.getConfig().skipChangelog?[A(z)]:[A(X)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipGit)}getNextTasks(e){return e.getConfig().skipGit?s([]):s([A(L)])}execute(e){let t=e.getConfig(),n=t.changelogPath||`CHANGELOG.md`,r=f(e.getBasePath(),`package.json`),a=f(e.getBasePath(),n),s=D.getInstance();return S.info(`Staging changes for ${p.underline(u(r))} and ${p.underline(u(a))}`),j(s.status.getUnstagedFilesByNames([a,r],t.dryRun)).andThen(e=>{if(e.isErr())return o(e.error);let n=e.value;return S.verbose(`StageChangesTask: Found ${n.length} files to stage: ${n.join(`, `)}`),n.length===0?(S.verbose(`StageChangesTask: No changes detected to stage, continuing...`),i.fromSafePromise(Promise.resolve())):j(s.staging.stageFiles(n,t.dryRun)).andTee(e=>{e.isErr()?S.error(`Failed to stage files: ${n.join(`, `)}. Error: ${e.error.message}`):S.verbose(`StageChangesTask: Staged files: ${n.join(`, `)}`)}).map(()=>{})})}canUndo(){return!0}undo(e){let t=e.getConfig(),n=t.changelogPath||`CHANGELOG.md`,r=f(e.getBasePath(),`package.json`),i=f(e.getBasePath(),n),a=D.getInstance();return j(a.staging.unstageFiles([i,r],t.dryRun)).andTee(e=>{e.isErr()?S.error(`Failed to unstage files: ${[i,r].join(`, `)}. Error: ${e.error.message}`):S.verbose(`StageChangesTask: Unstaged files: ${[i,r].join(`, `)}`)}).map(()=>{})}},L=class{id=`commit-changes`;description=`Commits the changes for the release.`;getDependencies(){return[A(I)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipGit)}getNextTasks(e){return e.getConfig().skipGit?s([]):s([A(F)])}execute(e){let t=D.getInstance(),n=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).commitMessage(e.getConfig().commitMessage);return j(t.commit.create(n,e.getConfig().dryRun)).map(()=>{S.info(`Committed changes with message: ${p.gray(n)}`)})}canUndo(){return!0}undo(e){let t=D.getInstance(),n=e.getConfig();return j(t.commit.resetLast(!1,n.dryRun)).andTee(e=>{e.isErr()?S.error(`Failed to reset last commit: ${e.error.message}`):S.verbose(`CommitChangesTask: Last commit reset successfully.`)}).map(()=>{})}},nt=class{constructor(e){this.cliffTomlService=e}async process(e){let t=await this.cliffTomlService.parse();if(t.isErr())return a(t.error);S.verbose(`ChangelogPostProcessor: Cliff TOML config parsed successfully, processing changelog...`);let n=t.value,r=this.extractChangesSection(e,n);if(r.isErr())return r;let i=r.value.trim();return i.includes(`###`)?s(i):(S.verbose(`ChangelogPostProcessorService: No commit entries found, returning empty changelog.`),s(``))}extractChangesSection(e,t){let n=t.changelog?.header,r=t.changelog?.body;if(!(n&&r))return S.verbose(`ChangelogPostProcessorService: No header/body template found in cliff.toml, returning raw changelog.`),s(e);let i=this.findChangesStartIndex(e);if(i===-1)return S.verbose(`ChangelogPostProcessorService: No changes section found, returning raw changelog.`),s(e);let a=e.slice(i).trimStart();return S.verbose(`ChangelogPostProcessorService: Extracted changes section from changelog.`),s(a)}findChangesStartIndex(e){return e.indexOf(`###`)}},rt=class e{static instance=null;pathToCliffToml;constructor(e){this.pathToCliffToml=e}static getInstance(t){return e.instance||=new e(d(t,`cliff.toml`)),e.instance}async parse(){let e=await k.read(this.pathToCliffToml);return e.isErr()?a(e.error):(S.verbose(`CliffTomlService: TOML file content successfully read, parsing...`),this.parseContent(e.value))}parseContent(t){let n=ne(t);return e.isCliffToml(n)?(S.verbose(`CliffTomlService: TOML parsed and validated as CliffToml`),s(n)):a(C({message:`CliffTomlService: Parsed TOML is not a valid CliffToml`,code:`INVALID`}))}static isCliffToml(t){return e.isObject(t)}static isObject(e,t){return typeof e==`object`&&e?e.constructor===(t??Object):!1}},it=class{id=`publish-github-release`;description=`Publishes the release on GitHub.`;getDependencies(){return[A(R)]}shouldExecute(e){return e.getConfig().skipGitHubRelease?s(!1):s(!0)}execute(e){let t=e.getConfig(),n=e.get(`changelogContent`),r=``;n.isErr()?S.warn(`Changelog content is not available. Proceeding with an empty changelog.`):r=n.value;let i=De.getInstance(),a=rt.getInstance(e.getBasePath()),s=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}),c=s.releaseTitle(e.getConfig().releaseTitle),l=s.tagName(e.getConfig().tagName),u=new nt(a),d=[t.releaseDraft?`draft`:null,t.releasePreRelease?`pre-release`:null,t.releaseLatest?`latest`:null].filter(e=>e!==null).join(`, `)||`normal`;S.info(`Publishing a ${p.gray(d)} GitHub release.`);let f=e=>j(i.release.createRelease({title:c,tag:l,content:e,latest:t.releaseLatest,draft:t.releaseDraft,prerelease:t.releasePreRelease,dryRun:t.dryRun}));return r.trim()?j(u.process(r)).andThen(e=>{if(e.isErr())return o(e.error);process.env.FIREFLY_DEBUG_SHOW_CHANGELOG_CONTENT&&S.verbose(`PublishGitHubReleaseTask: Postprocessed changelog content:\n${e.value}\n`);let t=e.value;return e.value.trim()===``&&(S.warn(`Changelog post-processing resulted in an empty changelog. Proceeding with an empty changelog.`),t=``),f(t)}).map(()=>{S.success(`Pushed GitHub release to remote repository.`)}):f(``).map(()=>{S.success(`Pushed GitHub release to remote repository.`)})}},R=class{id=`platform-publish-controller`;description=`Controls the flow for platform publish based on configuration.`;getDependencies(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit?[A(Y)]:t?.skipGitHubRelease?[]:t?.skipGit?[A(X)]:t?.skipPush?[A(F)]:[A(N)]}shouldExecute(e){return(e?.getConfig()).skipGitHubRelease?s(!1):s(!0)}getNextTasks(e){return e.getConfig().skipGitHubRelease?s([]):s([A(it)])}execute(e){return c()}},z=class{id=`git-flow-controller`;description=`Controls the flow for git operations based on configuration.`;getDependencies(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit||t?.skipChangelog?[A(Y)]:[A(X)]}shouldExecute(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit?s(!1):s(!0)}getNextTasks(e){return e.getConfig().skipGit?s([A(R)]):s([A(I)])}getSkipThroughTasks(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit?s([A(R)]):s([])}execute(e){return c()}},at=class e{static COMMIT_MESSAGE_PATTERNS={BREAKING:/^(\w*)(?:\((.*)\))?!: (.*)$/,CONVENTIONAL:/^(\w*)(?:\((.*)\))?: (.*)$/,REVERT:/^Revert "(.+)"\s*\[([a-f0-9]+)\]$/};static EXTRACTION_PATTERNS={BREAKING_CHANGE:/BREAKING CHANGE:\s*(.+?)(?=\n\n|\n[A-Z]|$)/gs,MENTION:/@([a-zA-Z0-9_-]+)/g,REFERENCE:/(fixes?|closes?|resolves?)\s+#(\d+)|#(\d+)/gi};gitProvider;constructor(e){this.gitProvider=e??D.getInstance()}async getCommitsSinceLastTag(){S.verbose(`CommitHistoryService: Retrieving commits since last tag...`);let e=await this.gitProvider.history.lastTagOrNull();if(e.isErr())return a(e.error);let t=e.value;S.verbose(`CommitHistoryService: Last tag is: ${t||`none`}`);let n=await this.gitProvider.history.commitsSince(t);if(n.isErr())return a(n.error);let r=n.value;if(S.verbose(`CommitHistoryService: Found ${r.length} commits since last tag.`),r.length===0)return S.verbose(`CommitHistoryService: No new commits found since last tag.`),s([]);let i=await this.parseCommitDetails(r);return i.isErr()?a(i.error):(S.verbose(`CommitHistoryService: Successfully parsed ${i.value.length} commits`),s(i.value))}async getAllCommits(){S.verbose(`CommitHistoryService: Retrieving all commits...`);let e=await this.gitProvider.history.commitsSince(null);if(e.isErr())return a(e.error);let t=e.value;if(S.verbose(`CommitHistoryService: Found ${t.length} total commits.`),t.length===0)return S.verbose(`CommitHistoryService: No commits found in repository.`),s([]);let n=await this.parseCommitDetails(t);return n.isErr()?a(n.error):(S.verbose(`CommitHistoryService: Successfully parsed ${n.value.length} commits`),s(n.value))}async parseCommitDetails(e){let t=[],n=e.map(async e=>{let t=await this.gitProvider.history.commitDetails(e,!1);return{hash:e,result:t}}),r=await Promise.all(n);for(let{hash:e,result:n}of r){if(n.isErr())return a(n.error);let r=this.parseCommitFromRaw(n.value,e);if(r.isErr())return a(r.error);t.push(r.value)}return s(t)}parseCommitFromRaw(e,t){if(!e||typeof e!=`string`)return a(C({code:`INVALID`,message:`Invalid commit details for ${t}`,source:`CommitHistoryService.parseCommitFromRaw`}));let n=this.extractCommitFields(e),r=this.analyzeCommitMessage(n.subject),i=this.extractRevertInfo(n.subject),o=this.extractBreakingChangeNotes(n.body,n.notes),c=this.extractMentions(n.body),l=this.extractReferences(n.body),u={hash:t,date:n.date||null,author:n.author||null,header:n.subject||null,body:n.body||null,footer:null,type:r.type,scope:r.scope,subject:r.subject,merge:null,revert:i,notes:o,mentions:c,references:l};return s(u)}extractCommitFields(e){let t=e.trim().split(`
|
|
16
|
-
`),n={};for(let e of t){let t=e.indexOf(`:`);if(t===-1)continue;let r=e.substring(0,t);n[r]=e.substring(t+1)}return{subject:n.subject||``,body:n.body||``,author:n.author||``,date:n.date||``,notes:n.notes||``}}analyzeCommitMessage(t){let n=t.match(e.COMMIT_MESSAGE_PATTERNS.BREAKING);if(n)return{type:n[1]||null,scope:n[2]||null,subject:n[3]||null};let r=t.match(e.COMMIT_MESSAGE_PATTERNS.CONVENTIONAL);return r?{type:r[1]||null,scope:r[2]||null,subject:r[3]||null}:{type:null,scope:null,subject:t||null}}extractRevertInfo(t){let n=t.match(e.COMMIT_MESSAGE_PATTERNS.REVERT);return n?{header:n[1]||null,hash:n[2]||null}:null}extractBreakingChangeNotes(t,n){let r=[],i=`${t}\n${n}`,a=e.EXTRACTION_PATTERNS.BREAKING_CHANGE.exec(i);for(;a!==null;){let t=a[1];t&&r.push({title:`BREAKING CHANGE`,text:t.trim()}),a=e.EXTRACTION_PATTERNS.BREAKING_CHANGE.exec(i)}return r}extractMentions(t){let n=[],r=e.EXTRACTION_PATTERNS.MENTION.exec(t);for(;r!==null;){let i=r[1];i&&n.push(i),r=e.EXTRACTION_PATTERNS.MENTION.exec(t)}return n}extractReferences(t){let n=[],r=e.EXTRACTION_PATTERNS.REFERENCE.exec(t);for(;r!==null;){let i=r[1]||null,a=r[2]||r[3];a&&n.push({raw:r[0],action:i?.toLowerCase()||null,owner:null,repository:null,issue:a,prefix:`#`}),r=e.EXTRACTION_PATTERNS.REFERENCE.exec(t)}return n}},ot=class e{static VERSION_LEVELS={MAJOR:0,MINOR:1,PATCH:2};static RELEASE_TYPES={[e.VERSION_LEVELS.MAJOR]:`major`,[e.VERSION_LEVELS.MINOR]:`minor`,[e.VERSION_LEVELS.PATCH]:`patch`};static DEFAULT_CONFIGURATION={major:[`revert`],minor:[`feat`,`feature`],patch:[`fix`,`perf`,`refactor`,`style`,`test`,`build`,`ci`,`chore`,`docs`,`security`],scopeRules:{deps:`patch`,dependencies:`patch`,security:`patch`,api:`minor`,breaking:`major`,"breaking-change":`major`}};static TRANSITION_KEYWORDS=[`general availability`,`promote to stable`,`move to stable`];static PATTERN_MATCHERS={BREAKING_HEADER:/^[a-zA-Z]+(?:\([^)]*\))?!:/,SCOPE_HEADER:/^[a-zA-Z]+\(([^)]+)\)[:!]/};configuration;constructor(e={}){this.configuration=this.mergeConfiguration(e)}analyzeCommits(e){S.verbose(`SemanticVersionAnalyzer: Starting commit analysis for version recommendation...`);let t=Date.now(),n=this.validateCommitsInput(e);if(n.isErr())return a(n.error);if(e.length===0)return S.verbose(`SemanticVersionAnalyzer: No commits provided, returning patch recommendation.`),s(this.createDefaultPatchRecommendation([]));let r=this.performDetailedAnalysis(e),i=this.determineVersionLevel(r),o=this.buildVersionRecommendation(i,e,r),c=Date.now()-t;return S.verbose(`SemanticVersionAnalyzer: Analysis completed in ${c}ms. Recommendation: ${o.releaseType}`),s(o)}mergeConfiguration(t){return{major:[...e.DEFAULT_CONFIGURATION.major,...t.major??[]],minor:[...e.DEFAULT_CONFIGURATION.minor,...t.minor??[]],patch:[...e.DEFAULT_CONFIGURATION.patch,...t.patch??[]],scopeRules:{...e.DEFAULT_CONFIGURATION.scopeRules,...t.scopeRules}}}validateCommitsInput(e){return Array.isArray(e)?s(void 0):a(C({code:`INVALID`,message:`Commits input must be an array`,source:`SemanticVersionAnalyzer.validateCommitsInput`}))}performDetailedAnalysis(e){S.verbose(`SemanticVersionAnalyzer: Performing detailed commit analysis...`);let t=e.reduce((e,t)=>{let n=t.type?.toLowerCase()||`unknown`;return e.commitsByType[n]||(e.commitsByType[n]=[]),e.commitsByType[n].push(t),{breakingChanges:e.breakingChanges+this.countBreakingChanges(t),features:e.features+(this.isFeatureCommit(t)?1:0),patches:e.patches+(this.isPatchCommit(t)?1:0),scopedBreaking:[...e.scopedBreaking,...this.analyzeScopeBreaking(t)],hasPreReleaseTransition:e.hasPreReleaseTransition||this.detectPreReleaseTransition(t),commitsByType:e.commitsByType}},{breakingChanges:0,features:0,patches:0,scopedBreaking:[],hasPreReleaseTransition:!1,commitsByType:{}});return S.verbose(`SemanticVersionAnalyzer: Analysis results - Breaking: ${t.breakingChanges}, Features: ${t.features}, Patches: ${t.patches}`),t}countBreakingChanges(e){let t=0;return t+=e.notes?.length??0,this.hasBreakingHeader(e)&&(t+=1),t}hasBreakingHeader(t){return t.header?e.PATTERN_MATCHERS.BREAKING_HEADER.test(t.header):!1}isFeatureCommit(e){let t=e.type?.toLowerCase()??``;return this.configuration.minor.includes(t)}isPatchCommit(e){let t=e.type?.toLowerCase()??``;return this.configuration.patch.includes(t)}analyzeScopeBreaking(e){let t=this.extractCommitScope(e);return t&&this.configuration.scopeRules[t.toLowerCase()]===`major`?[t]:[]}extractCommitScope(t){return t.scope?t.scope:t.header?t.header.match(e.PATTERN_MATCHERS.SCOPE_HEADER)?.[1]??null:null}detectPreReleaseTransition(t){let n=t.header?.toLowerCase()??``,r=t.body?.toLowerCase()??``;return e.TRANSITION_KEYWORDS.some(e=>n.includes(e)||r.includes(e))}determineVersionLevel(t){return S.verbose(`SemanticVersionAnalyzer: Determining version level from analysis...`),t.breakingChanges>0||t.scopedBreaking.length>0?(S.verbose(`SemanticVersionAnalyzer: Breaking changes detected, recommending MAJOR version bump.`),e.VERSION_LEVELS.MAJOR):t.features>0?(S.verbose(`SemanticVersionAnalyzer: New features detected, recommending MINOR version bump.`),e.VERSION_LEVELS.MINOR):t.patches>0?(S.verbose(`SemanticVersionAnalyzer: Patch-level changes detected, recommending PATCH version bump.`),e.VERSION_LEVELS.PATCH):(S.verbose(`SemanticVersionAnalyzer: No significant changes detected, defaulting to PATCH version bump.`),e.VERSION_LEVELS.PATCH)}buildVersionRecommendation(t,n,r){return S.verbose(`SemanticVersionAnalyzer: Building version recommendation...`),{level:t,releaseType:e.RELEASE_TYPES[t],commits:[...n],reason:this.generateRecommendationReason(r),analysis:r}}createDefaultPatchRecommendation(t){let n={breakingChanges:0,features:0,patches:0,scopedBreaking:[],hasPreReleaseTransition:!1,commitsByType:{}};return{level:e.VERSION_LEVELS.PATCH,releaseType:`patch`,commits:[...t],reason:`No commits provided, defaulting to patch increment for safety`,analysis:n}}generateRecommendationReason(e){let t=[];if(e.breakingChanges>0){let n=e.breakingChanges===1?`change`:`changes`;t.push(`${e.breakingChanges} breaking ${n}`)}if(e.scopedBreaking.length>0){let n=e.scopedBreaking.join(`, `);t.push(`breaking scope(s): ${n}`)}if(e.features>0){let n=e.features===1?`feature`:`features`;t.push(`${e.features} new ${n}`)}if(e.patches>0){let n=e.patches===1?`fix`:`fixes`;t.push(`${e.patches} ${n}`)}return e.hasPreReleaseTransition&&t.push(`pre-release transition detected`),t.length===0?`No significant changes detected, defaulting to patch increment`:`Analysis found: ${t.join(`, `)}`}},st=class{gitProvider;commitHistoryService;versionAnalyzer;configuration;constructor(e={}){this.gitProvider=D.getInstance(),this.commitHistoryService=new at(this.gitProvider),this.versionAnalyzer=new ot({major:e.additionalCommitTypes?.major,minor:e.additionalCommitTypes?.minor,patch:e.additionalCommitTypes?.patch,scopeRules:e.scopeRules}),this.configuration={includeAllCommitsWhenNoTags:!1,...e}}async recommendVersion(){S.verbose(`SemanticVersionService: Starting version recommendation process...`);let e=Date.now(),t=await this.getRelevantCommits();if(t.isErr())return a(t.error);let n=t.value;if(S.verbose(`SemanticVersionService: Analyzing ${n.length} commits for version recommendation`),n.length===0)return S.verbose(`SemanticVersionService: No commits found, returning default patch recommendation`),s(this.createDefaultRecommendation());let r=this.versionAnalyzer.analyzeCommits(n);if(r.isErr())return a(r.error);let i=r.value,o=Date.now()-e;return S.verbose(`SemanticVersionService: Version recommendation completed in ${o}ms. Recommendation: ${i.releaseType} (level ${i.level})`),s(i)}async getCommitsSinceLastTag(){return S.verbose(`SemanticVersionService: Retrieving commits since last tag...`),this.commitHistoryService.getCommitsSinceLastTag()}async getAllCommits(){return S.verbose(`SemanticVersionService: Retrieving all commits...`),this.commitHistoryService.getAllCommits()}async getLastTag(){return S.verbose(`SemanticVersionService: Getting last git tag...`),this.gitProvider.history.lastTagOrNull()}async hasAnyTags(){S.verbose(`SemanticVersionService: Checking if repository has any tags...`);let e=await this.getLastTag();return e.isErr()?a(e.error):s(e.value!==null)}analyzeCommitsOnly(e){return S.verbose(`SemanticVersionService: Analyzing provided ${e.length} commits without fetching from git`),this.versionAnalyzer.analyzeCommits(e)}async getRelevantCommits(){let e=await this.hasAnyTags();return e.isErr()?a(e.error):e.value?(S.verbose(`SemanticVersionService: Retrieving commits since last tag`),this.commitHistoryService.getCommitsSinceLastTag()):(S.verbose(`SemanticVersionService: No tags found in repository`),this.configuration.includeAllCommitsWhenNoTags?(S.verbose(`SemanticVersionService: Configuration set to include all commits when no tags exist`),this.commitHistoryService.getAllCommits()):(S.verbose(`SemanticVersionService: Configuration set to return empty commits when no tags exist`),s([])))}createDefaultRecommendation(){return{level:2,releaseType:`patch`,commits:[],reason:`No commits available for analysis, defaulting to patch increment`,analysis:{breakingChanges:0,features:0,patches:0,scopedBreaking:[],hasPreReleaseTransition:!1,commitsByType:{}}}}},B=class e{_raw;_parsed;constructor(e,t){this._raw=e,this._parsed=t}static from(t){let n=h.clean(t);if(!n)return a(C({code:`INVALID`,message:`"${t}" is not a valid semantic version.`}));let r=h.parse(n);return r?s(new e(n,r)):a(C({code:`INVALID`,message:`Failed to parse semantic version "${n}".`}))}static fromClean(t){let n=h.parse(t);return n?s(new e(t,n)):a(C({code:`INVALID`,message:`Expected clean version but got invalid: ${t}`}))}get raw(){return this._raw}get major(){return this._parsed.major}get minor(){return this._parsed.minor}get patch(){return this._parsed.patch}get isPrerelease(){return this._parsed.prerelease.length>0}get prerelease(){return this._parsed.prerelease}get prereleaseIdentifier(){if(!this.isPrerelease)return null;let e=this._parsed.prerelease[0];return typeof e==`string`?e:null}get prereleaseNumber(){if(!this.isPrerelease)return null;let e=this._parsed.prerelease.at(-1);return typeof e==`number`?e:null}get build(){return this._parsed.build}toString(){return this._raw}equals(e){return h.eq(this._raw,e._raw)}compare(e){return h.compare(this._raw,e._raw)}isGreaterThan(e){return h.gt(this._raw,e._raw)}isLessThan(e){return h.lt(this._raw,e._raw)}satisfies(e){return h.satisfies(this._raw,e)}toStable(){let t=`${this.major}.${this.minor}.${this.patch}`;return e.fromClean(t)}},V=class e{static bumpVersion(t){let{currentVersion:n,releaseType:r,prereleaseIdentifier:i,prereleaseBase:o}=t;return r===`major`||r===`minor`||r===`patch`?e.bumpStandard(n,r):r===`premajor`||r===`preminor`||r===`prepatch`?e.bumpPreStandard(n,r,i,o):r===`prerelease`?e.bumpPrerelease(n,i,o):r===`graduate`?e.graduatePrerelease(n):a(C({code:`INVALID`,message:`Unsupported release type: ${r}`}))}static bumpStandard(e,t){let n=e.raw;if(e.isPrerelease){let t=e.toStable();if(t.isErr())return a(t.error);n=t.value.raw}let r=h.inc(n,t);return r?B.fromClean(r):a(C({code:`INVALID`,message:`Failed to bump ${t} version from '${n}'.`}))}static bumpPreStandard(t,n,r,i){let o=e.normalizeBase(i);if(o.isErr())return a(o.error);let s=o.value,c=null;return c=s===void 0?r?h.inc(t.raw,n,r):h.inc(t.raw,n):r?h.inc(t.raw,n,r,s):h.inc(t.raw,n,void 0,s),c?B.fromClean(c):a(C({code:`INVALID`,message:`Failed to bump ${n} version from '${t.raw}' with identifier '${r}' and base '${i}'.`}))}static bumpPrerelease(t,n,r){let i=null;if(e.isComplexIdentifier(n))i=e.bumpWithComplexIdentifier(t,n);else if(r!=null){let o=e.normalizeBase(r);if(o.isErr())return a(o.error);let s=o.value;i=n?h.inc(t.raw,`prerelease`,n,s):h.inc(t.raw,`prerelease`,void 0,s)}else if(t.isPrerelease)i=e.bumpExistingPrerelease(t,n);else{let e=n||`alpha`;i=h.inc(t.raw,`prerelease`,e)}return i?B.fromClean(i):a(C({code:`INVALID`,message:`Failed to bump prerelease version from '${t.raw}' with identifier '${n}' and base '${r}'.`}))}static graduatePrerelease(e){if(!e.isPrerelease)return a(C({code:`INVALID`,message:`Cannot graduate non-prerelease version '${e.raw}'. Only prerelease versions can be graduated.`}));let t=e.toStable();if(t.isErr())return a(t.error);let n=t.value;return s(n)}static normalizeBase(e){return e==null?s(void 0):e===`0`||e===`1`?s(e):typeof e==`number`&&(e===0||e===1)?s(e.toString()):a(C({code:`INVALID`,message:`Invalid prerelease base '${e}'. Must be "0", "1", 0, or 1.`}))}static isComplexIdentifier(e){return typeof e==`string`&&e.includes(`.`)}static bumpWithComplexIdentifier(e,t){return t?h.inc(e.raw,`prerelease`,t,!1):h.inc(e.raw,`prerelease`,void 0,`0`)}static bumpExistingPrerelease(e,t){return t?h.inc(e.raw,`prerelease`,t):h.inc(e.raw,`prerelease`)}},ct=class e{static TRANSITION_KEYWORDS=[`stable`,`release`,`production`,`final`,`ga`,`general availability`,`promote to stable`,`move to stable`,`release candidate`,`rc`];static LEVEL_TO_RELEASE_TYPE={0:`major`,1:`minor`,2:`patch`};static decideNextVersion(t,n){S.verbose(`VersionResolverService: Deciding next version...`);let r=e.analyzePreReleaseContext(t.currentVersion,n);return t.releaseType===`prerelease`?(S.verbose(`VersionResolverService: Handling prerelease request...`),e.handlePreReleaseRequest(t,r)):r.isCurrentPreRelease&&r.hasStableTransition?(S.verbose(`VersionResolverService: Handling pre-release to stable transition...`),e.handlePreReleaseToStableTransition(t,n)):n?(S.verbose(`VersionResolverService: Handling recommendation-based versioning...`),e.createRecommendationBasedVersion(t,n,r)):(S.verbose(`VersionResolverService: Handling standard version bump...`),e.bumpVersion(t))}static analyzePreReleaseContext(t,n){let r=t.isPrerelease,i=t.prereleaseIdentifier,a=e.detectStableTransition(n);return{isCurrentPreRelease:r,prereleaseIdentifier:i,hasStableTransition:a}}static detectStableTransition(t){if(!t)return!1;let n=t.reason.toLowerCase();return e.TRANSITION_KEYWORDS.some(e=>n.includes(e))}static handlePreReleaseRequest(e,t){let n={currentVersion:e.currentVersion,releaseType:`prerelease`,prereleaseIdentifier:e.prereleaseIdentifier||t.prereleaseIdentifier||`alpha`,prereleaseBase:e.prereleaseBase};return S.verbose(`VersionResolverService: Bumping to prerelease version...`),V.bumpVersion(n)}static handlePreReleaseToStableTransition(t,n){if(!n)return a(C({code:`INVALID`,message:`Cannot transition to stable version without recommendation`}));let r=V.bumpVersion({currentVersion:t.currentVersion,releaseType:`graduate`});if(r.isErr())return a(r.error);let i=r.value;if(n.level<2){S.verbose(`VersionResolverService: Further bumping after graduation...`);let t=e.LEVEL_TO_RELEASE_TYPE[n.level];return V.bumpVersion({currentVersion:i,releaseType:t})}return S.verbose(`VersionResolverService: Graduated to stable version:`,i.raw),s(i)}static createRecommendationBasedVersion(t,n,r){let i=e.LEVEL_TO_RELEASE_TYPE[n.level];if(r.isCurrentPreRelease&&!r.hasStableTransition){S.verbose(`VersionResolverService: Continuing prerelease versioning...`);let e={currentVersion:t.currentVersion,releaseType:`prerelease`,prereleaseIdentifier:t.prereleaseIdentifier||r.prereleaseIdentifier||`alpha`,prereleaseBase:t.prereleaseBase};return V.bumpVersion(e)}return S.verbose(`VersionResolverService: Bumping version based on recommendation...`),e.bumpVersion({...t,releaseType:i})}static bumpVersion(e){if(!e.releaseType)return a(C({code:`INVALID`,message:`Release type is required for version bump`}));let t={currentVersion:e.currentVersion,releaseType:e.releaseType,prereleaseIdentifier:e.prereleaseIdentifier,prereleaseBase:e.prereleaseBase};return V.bumpVersion(t)}};const lt=r.fromThrowable(JSON.parse,e=>C(w(e))),ut=e.object({name:e.string().optional(),version:e.string().optional()}).catchall(e.unknown());var H=class e{static instance=null;static VERSION_REGEX=/^(\s*"version"\s*:\s*)"[^"]*"(.*)$/m;pathToPackageJson;constructor(e){this.pathToPackageJson=e}static getInstance(t){return e.instance||=new e(d(t,`package.json`)),e.instance}async read(){let e=await k.read(this.pathToPackageJson);return e.isErr()?o(e.error):this.parseAndValidatePackageJson(e.value)}async updateVersion(e,t){let n=await k.read(this.pathToPackageJson);if(n.isErr())return o(n.error);let r=this.replaceVersionInContent(n.value,e),i=await k.write(this.pathToPackageJson,r,t);return i.isErr()?o(i.error):(S.verbose(`PackageJsonService: Updated version to ${e} in ${this.pathToPackageJson}`),this.verifyVersionUpdate(e,t))}parseAndValidatePackageJson(e){let t=lt(e);if(t.isErr())return o(t.error);let n=M(ut,t.value);return n.isErr()?o(n.error):c(n.value)}replaceVersionInContent(t,n){return t.replace(e.VERSION_REGEX,`$1"${n}"$2`)}async verifyVersionUpdate(e,t){let n=await this.read();return n.isErr()?o(n.error):t?(S.verbose(`PackageJsonService: Dry run mode enabled, not verifying version update.`),c()):n.value.version===e?c():o(C({code:`INVALID`,message:`Version verification failed. Expected version: ${e}, but found: ${n.value.version}`,source:`filesystem/package-json-service`}))}},U=class{id=`bump-version`;description=`Writes the new version to package.json.`;previousVersion=``;isEntryPoint(){return!1}getDependents(){return[]}getDependencies(){return[]}shouldExecute(e){let t=e.getConfig();return s(!t.skipBump)}getNextTasks(){return s([A(Y)])}execute(e){this.previousVersion=e.getCurrentVersion();let t=e.getBasePath(),n=e.getNextVersion(),r=e.getConfig().dryRun,a=H.getInstance(t).updateVersion(n,r);return S.info(`Updating version...`),i.fromPromise(a,w).andThen(()=>c()).andTee(()=>[S.success(`Version updated to ${p.cyanBright(n)}`)])}canUndo(){return!0}undo(e){if(!this.previousVersion)return o(C({code:`NOT_FOUND`,message:`Previous version not found, cannot undo version bump.`}));let t=e.getBasePath(),n=e.getConfig().dryRun,r=H.getInstance(t).updateVersion(this.previousVersion,n);return i.fromPromise(r,w).andThen(()=>c())}},W=class{id=`initialize-current-version`;description=`Loads the current version from package.json or initializes it to 0.0.0.`;getDependencies(){return[]}shouldExecute(){return s(!0)}getSkipThroughTasks(){return s([A(J)])}canUndo(){return!1}execute(e){S.verbose(`InitializeCurrentVersionTask: Initializing current version...`);let t=e.getBasePath(),n=H.getInstance(t);return i.fromPromise(n.read(),w).andThen(t=>{let n=t.isErr()||!t.value.version?`0.0.0`:t.value.version;return S.verbose(`InitializeCurrentVersionTask: Current version is "${n}"`),S.info(`Current version is ${p.cyanBright(n)}`),e.set(`currentVersion`,n),c()})}},dt=class{constructor(e){this.versionChoicesService=e}async run(e){if(!e.currentVersion)return a(C({code:`INVALID`,message:`Current version is required to generate version choices`,source:`semver/version-choice-prompter`}));S.verbose(`VersionChoicePrompter: Generating version choices...`);let t=this.versionChoicesService.createVersionChoices(e);if(t.isErr())return a(t.error);let n=t.value;if(n.length===0)return a(C({code:`NOT_FOUND`,message:`No version choices available`,source:`semver/version-choice-prompter`}));S.verbose(`VersionChoicePrompter: Prompting user for version selection.`);let r=await this.prompt(n);if(r.isErr())return a(r.error);S.level!==m.verbose&&S.log(``);let i=r.value;return!i||i===``?a(C({code:`INVALID`,message:`No version selected`,source:`semver/version-choice-prompter`})):(S.verbose(`VersionChoicePrompter: User selected version: '${i}'`),s(i))}async prompt(e){let t=e[0];if(!t)return a(C({code:`NOT_FOUND`,message:`No default version choice found`,source:`semver/version-choice-prompter`}));let n=await this.createPrompter(e,t.value);return n.isErr()?a(n.error):(S.level===m.verbose&&n.andTee(()=>S.log(``)),n.andThen(t=>this.validateVersion(t,e)))}createPrompter(e,t){let n=S.prompt(`Select version bump`,{type:`select`,options:e,initial:t,cancel:`reject`});return i.fromPromise(n,e=>C(w(e)))}validateVersion(e,t){let n=t.map(e=>e.value);return n.includes(e)?s(e):a(C({code:`INVALID`,message:`Invalid version selected: ${e}. Valid options: ${n.join(`, `)}`,source:`semver/version-choice-prompter`}))}},ft=class e{static VERSION_TYPES={RELEASE:[`patch`,`minor`,`major`],PRERELEASE:[`prepatch`,`preminor`,`premajor`],CONTINUATION:[`prerelease`],GRADUATION:[`graduate`]};static VERSION_CHOICES={latestIsPreRelease:[...e.VERSION_TYPES.CONTINUATION,...e.VERSION_TYPES.GRADUATION,...e.VERSION_TYPES.RELEASE],preRelease:e.VERSION_TYPES.PRERELEASE,default:[...e.VERSION_TYPES.RELEASE,...e.VERSION_TYPES.PRERELEASE]};static VERSION_DESCRIPTIONS={patch:`Fixes and minor enhancements without breaking compatibility. Suitable for bug fixes and small improvements.`,minor:`New, backward-compatible functionality. Adds features that do not break existing APIs.`,major:`Incompatible API changes. Introduces breaking changes or removes deprecated features.`,prepatch:`Unstable patch release candidate. Used for testing patch changes before a stable release.`,preminor:`Unstable minor release candidate. Used for previewing new features before a minor release.`,premajor:`Unstable major release candidate. Used for testing breaking changes before a major release.`,prerelease:`Unstable pre-release continuation. Increments the pre-release number or changes identifier.`,graduate:`Promote pre-release to stable. Removes pre-release identifiers to create a stable version.`};createVersionChoices(e){S.verbose(`VersionChoicesService: Creating version choices for '${e.currentVersion.raw}'...`);let t=this.determineAvailableVersionTypes(e.currentVersion,e.releaseType).map(t=>this.createVersionChoice({currentVersion:e.currentVersion,releaseType:t,prereleaseIdentifier:e.prereleaseIdentifier,prereleaseBase:e.prereleaseBase})),n=r.combine(t);return n.isErr()?a(n.error):(S.verbose(`VersionChoicesService: Created ${n.value.length} version choices.`),s(n.value))}determineAvailableVersionTypes(t,n){return n===void 0?t.isPrerelease?e.VERSION_CHOICES.latestIsPreRelease:e.VERSION_CHOICES.default:this.getVersionTypesForReleaseType(n)}getVersionTypesForReleaseType(t){return t===`prerelease`?e.VERSION_CHOICES.preRelease:e.VERSION_CHOICES.default}createVersionChoice(e){let t=this.computeNewVersion(e);if(t.isErr())return a(t.error);let n=t.value,r=e.releaseType||`patch`,i={label:`${r} (${n.raw})`,hint:this.getVersionDescription(r),value:n.raw};return s(i)}computeNewVersion(e){if(!e.releaseType)return a(C({code:`INVALID`,message:`Release type is required to compute new version`}));let t={currentVersion:e.currentVersion,releaseType:e.releaseType,prereleaseIdentifier:e.prereleaseIdentifier,prereleaseBase:e.prereleaseBase};return V.bumpVersion(t)}getVersionDescription(t){return e.VERSION_DESCRIPTIONS[t]??``}},G=class{id=`prompt-manual-version`;description=`Prompts the user to manually enter the desired version`;getDependencies(){return[A(K)]}shouldExecute(e){let t=e.getConfig();return s(t.bumpStrategy===y)}getNextTasks(){return s([A(U)])}execute(e){let t=e.get(`currentVersion`);if(t.isErr())return o(t.error);let n=B.from(t.value||``);if(n.isErr())return o(n.error);let r=new dt(new ft),a=e.getConfig(),s={currentVersion:n.value,releaseType:a.releaseType,prereleaseIdentifier:a.preReleaseId,prereleaseBase:a.preReleaseBase};return i.fromPromise(r.run(s),e=>w(e)).andThen(t=>t.isErr()?o(t.error):(e.setNextVersion(t.value),S.verbose(`PromptManualVersionTask: From '${n.value.raw}' to '${t.value}'`),c()))}},K=class{id=`execute-bump-strategy`;description=`Executes the selected bump strategy to determine the new version.`;getDependencies(){return[A(W)]}shouldExecute(e){let t=e.getConfig(),n=!t.releaseType&&!!t.bumpStrategy;return s(n)}getNextTasks(e){let t=e.getConfig().bumpStrategy;return s(t===y?[A(G)]:t===v?[A(q)]:[])}getSkipThroughTasks(e){let t=e.getConfig().bumpStrategy;return s(t===y?[A(G)]:t===v?[A(q)]:[A(U)])}execute(){return c()}},q=class{id=`automatic-bump`;description=`Uses semantic analysis to determine the next version bump`;getDependencies(){return[A(K)]}shouldExecute(e){let t=e.getConfig();return s(t.bumpStrategy===v)}getNextTasks(){return s([A(U)])}execute(e){let t=B.from(e.getCurrentVersion());if(t.isErr())return o(t.error);let n={currentVersion:t.value,releaseType:e.getConfig().releaseType,prereleaseIdentifier:e.getConfig().preReleaseId,prereleaseBase:e.getConfig().preReleaseBase},r=new st;return i.fromPromise(r.recommendVersion(),w).andThen(r=>{if(r.isErr())return o(r.error);let{reason:i}=r.value;if(i)if(i.startsWith(`Analysis found:`)){let e=i.slice(15).trim();S.info(`Analysis found: ${p.bold(e)}`)}else S.info(i);let a=ct.decideNextVersion(n,r.value);return a.isErr()?o(a.error):(e.setNextVersion(a.value.raw),S.verbose(`AutomaticBumpTask: From '${t.value.raw}' to '${a.value.raw}'`),c())})}},pt=class e{static STRATEGIES=[{label:`Automatic Bump`,value:v,hint:`Determines the next version based on conventional commits history`},{label:`Manual Bump`,value:y,hint:`Manually specify the next version`}];async run(){let t=e.STRATEGIES[1];if(!t)return a(C({code:`NOT_FOUND`,message:`No default version bump strategy found`,source:`semver/version-strategy-prompter-service`}));S.verbose(`BumpStrategyPrompter: Prompting user for version bump strategy.`);let n=await this.prompt(t.value);if(n.isErr())return a(n.error);S.level!==m.verbose&&S.log(``);let r=n.value;return!r||r===``?a(C({code:`INVALID`,message:`No version bump strategy selected`,source:`semver/version-strategy-prompter-service`})):(S.verbose(`BumpStrategyPrompter: User selected version bump strategy: '${r}'`),s(r))}async prompt(e){let t=await this.createPrompter(e);return t.isErr()?a(t.error):(S.level===m.verbose&&t.andTee(()=>S.log(``)),t.andThen(e=>this.validateStrategy(e)))}createPrompter(t){let n=S.prompt(`Select version bump strategy`,{type:`select`,options:e.STRATEGIES,initial:t,cancel:`reject`});return i.fromPromise(n,e=>C(w(e)))}validateStrategy(t){return e.STRATEGIES.map(e=>e.value).includes(t)?s(t):a(C({code:`INVALID`,message:`Invalid version bump strategy: ${t}`,source:`semver/version-strategy-prompter-service`}))}},mt=class{id=`prompt-bump-strategy`;description=`Prompts the user to select a bump strategy (manual or automatic) if none is specified.`;getDependencies(){return[A(W)]}shouldExecute(e){let t=e.getConfig();return s(!(t.bumpStrategy||t.releaseType))}getNextTasks(){return s([A(K)])}getSkipThroughTasks(){return s([A(K)])}execute(e){let t=new pt;return i.fromPromise(t.run(),e=>w(e)).andThen(t=>{let n=e.getConfig();return t.isErr()?o(t.error):(n.bumpStrategy=t.value,c())})}},ht=class{id=`straight-bump`;description=`Handles version bump from provided release type.`;getDependencies(){return[A(W)]}shouldExecute(e){return e.getConfig().releaseType===void 0?s(!1):s(!0)}getNextTasks(){return s([A(U)])}getSkipThroughTasks(e){return e.getConfig().skipBump?s([A(Y)]):s([A(J)])}execute(e){let t=B.from(e.getCurrentVersion());if(t.isErr())return o(t.error);let n={currentVersion:t.value,releaseType:e.getConfig().releaseType,prereleaseIdentifier:e.getConfig().preReleaseId,prereleaseBase:e.getConfig().preReleaseBase},r=ct.decideNextVersion(n);return r.isErr()?o(r.error):(e.setNextVersion(r.value.raw),S.verbose(`StraightBumpTask: From '${t.value.raw}' to '${r.value.raw}'`),c())}canUndo(){return!1}},J=class{id=`version-flow-controller`;description=`Controls the flow between version bump and subsequent tasks based on configuration.`;getDependencies(){return[A(W)]}shouldExecute(){return s(!0)}getNextTasks(e){let t=e.getConfig(),n=[];return t.releaseType===void 0?t.bumpStrategy||n.push(A(mt)):n.push(A(ht)),s(n)}canUndo(){return!1}execute(){return c()}},Y=class{id=`changelog-flow-controller`;description=`Controls the flow for changelog generation based on configuration.`;getDependencies(e){return e?.getConfig().skipBump?[A(J)]:[A(U)]}shouldExecute(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit&&t?.skipGitHubRelease?s(!1):s(!0)}getNextTasks(e){return e.getConfig().skipChangelog?s([A(z)]):s([A(X)])}execute(e){return c()}},X=class{id=`generate-changelog`;description=`Generates the changelog based on the current release context.`;getDependencies(){return[A(Y)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipChangelog)}getNextTasks(){return s([A(z)])}execute(e){let t=d(process.cwd(),e.getConfig().changelogPath||`CHANGELOG.md`),n=i.fromPromise(k.exists(t),w),r=Date.now(),a=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}),s=new Ze(a);return n.andThen(n=>n.isErr()?o(n.error):n.value?(S.info(`Generating changelog...`),i.fromPromise(s.generateChangelog(e.getConfig()),w).andThen(t=>{if(t.isErr())return o(t.error);let n=Date.now()-r;return S.success(`Generation complete in ${p.greenBright(`${n}ms`)}`),process.env.FIREFLY_DEBUG_SHOW_CHANGELOG_CONTENT&&S.verbose(`GenerateChangelogTask: Generated changelog content:\n${t.value}\n`),e.set(`changelogContent`,t.value),c()})):k.write(t,``))}canUndo(){return!0}undo(e){let t=d(process.cwd(),e.getConfig().changelogPath||`CHANGELOG.md`);return e.get(`changelogContent`)?i.fromPromise(D.getInstance().commit.restoreFileToHead(t),w).andThen(()=>c()):o(w({code:`NOT_FOUND`,message:`Changelog content not found in context, cannot undo changelog generation.`}))}},gt=class e{static SCOPED_PACKAGE_REGEX=/^@[^/]+\//;gitProvider;packageJsonService;constructor(e){this.gitProvider=D.getInstance(),this.packageJsonService=H.getInstance(e)}async hydrateConfig(e){let t={...e},n=await this.hydrateFromGitRepository(t);if(n.isErr())return a(n.error);t=n.value;let r=await this.hydrateBranchFromGit(t);if(r.isErr())return a(r.error);t=r.value;let i=await this.hydrateFromPackageJson(t);return i.isErr()?a(i.error):(t=i.value,s(t))}async hydrateFromPackageJson(e){if(!this.packageJsonService)return a(C({code:`NOT_FOUND`,message:`packageJsonService is not available for hydration.`}));let t=await this.packageJsonService.read();if(t.isErr())return a(C({code:`NOT_FOUND`,message:`Could not find a valid package.json file in the current directory.`}));S.verbose(`ConfigHydratorService: package.json found, hydrating configuration...`);let n=t.value;if(!n)return a(C({code:`NOT_FOUND`,message:`package.json is empty or invalid`}));let r=this.hydrateFromPackageData(e,n);return r.isErr()?a(r.error):s(r.value)}async hydrateFromGitRepository(e){let t=await this.gitProvider.repository.isInsideWorkTree();return t.isErr()?a(t.error):t.value?(S.verbose(`ConfigHydratorService: Inside a Git repository, hydrating configuration...`),this.hydrateRepositoryFromGit(e)):a(C({code:`NOT_FOUND`,message:`Not inside a Git repository. Please run Firefly from within a valid Git project.`}))}async hydrateRepositoryFromGit(e){if(!this.gitProvider||e.repository&&e.repository.trim()!==``)return s(e);let t=await this.gitProvider.repository.getRepositoryUrl();if(t.isErr())return a(t.error);let n=this.gitProvider.repositoryParse.extractRepository(t.value);if(n.isErr())return a(n.error);let r=n.value,i=`${r.owner}/${r.repo}`;return S.verbose(`ConfigHydratorService: Auto-detected repository: ${i}`),s({...e,repository:i})}async hydrateBranchFromGit(e){if(!this.gitProvider)return s(e);if(e.branch&&e.branch.trim()!==``){let t=await this.gitProvider.branch.isProvidedBranchValid(e.branch);return t.isErr()?a(t.error):t.value?(S.verbose(`ConfigHydratorService: Using provided branch: ${e.branch}`),s(e)):a(C({code:`NOT_FOUND`,message:`The provided branch "${e.branch}" does not exist in the repository.`}))}let t=await this.gitProvider.branch.currentBranch();if(t.isErr())return a(t.error);let n=t.value;return S.verbose(`ConfigHydratorService: Auto-detected branch: ${n}`),s({...e,branch:n})}hydrateFromPackageData(e,t){let n={...e},r=this.hydrateNameFromPackageJson(n,t);if(r.isErr())return a(r.error);Object.assign(n,r.value);let i=this.hydrateScopeFromPackageJson(e,t);if(i.isErr())return a(i.error);Object.assign(n,i.value);let o=this.hydratePreReleaseIdFromPackageJson(e,t);return o.isErr()?a(o.error):(Object.assign(n,o.value),s(n))}hydratePreReleaseIdFromPackageJson(e,t){if(e.preReleaseId!==void 0&&e.preReleaseId.trim()!==``)return s({});if(t.version){let e=h.parse(t.version);if(!e)return a(C({code:`INVALID`,message:`Invalid version in package.json: ${t.version}`}));if(e.prerelease.length>0){let n=typeof e.prerelease[0]==`string`?e.prerelease[0]:``;return n?(S.verbose(`ConfigHydratorService: Auto-detected preReleaseId from package.json: ${n}`),s({preReleaseId:n})):a(C({code:`INVALID`,message:`package.json version "${t.version}" is a prerelease but has no valid identifier`}))}}return s({preReleaseId:`alpha`})}hydrateNameFromPackageJson(e,t){if(e.name===void 0&&!t.name)return a(C({code:`NOT_FOUND`,message:`Could not find a valid package name in package.json`}));if(e.name===void 0&&t.name){S.verbose(`ConfigHydratorService: hydrating name from package.json...`);let e=this.extractPackageName(t.name);return e.isErr()?a(e.error):(S.verbose(`ConfigHydratorService: hydrating name from package.json: ${t.name} -> ${e.value}`),s({name:e.value}))}return S.verbose(`ConfigHydratorService: name explicitly provided in config: "${e.name}"`),s({})}hydrateScopeFromPackageJson(e,t){if(Object.hasOwn(e,`scope`)&&e.scope!==void 0)return S.verbose(`ConfigHydratorService: Scope explicitly provided in config: "${e.scope}" - not hydrating from package.json`),s({});if(t.name&&this.isScopedPackage(t.name)){let e=this.extractScope(t.name);return e.isErr()?a(e.error):(S.verbose(`ConfigHydratorService: Auto-detected scope from package.json: ${e.value}`),s({scope:e.value}))}return s({})}extractPackageName(t){if(!t?.trim())return a(C({code:`INVALID`,message:`Package name cannot be empty`}));let n=t.replace(e.SCOPED_PACKAGE_REGEX,``);return n?s(n):a(C({code:`INVALID`,message:`Malformed package name: "${t}"`}))}extractScope(e){if(!this.isScopedPackage(e))return s(``);let t=e.split(`/`)[0];return!t||t.length<=1?a(C({code:`INVALID`,message:`Malformed scoped package name: "${e}"`})):s(t.substring(1))}isScopedPackage(e){return e.startsWith(`@`)}},_t=class{id=`prepare-release-config`;description=`Hydrates and prepares the release configuration.`;getDependencies(){return[]}shouldExecute(){return s(!0)}canUndo(){return!1}execute(e){S.verbose(`PrepareReleaseConfigTask: Preparing and hydrating release configuration...`);let t=e.getBasePath(),n=new gt(t),r=e.getConfig();return i.fromPromise(n.hydrateConfig(r),w).andThen(t=>{if(t.isErr())return o(t.error);let n=e.set(`config`,t.value);return n.isErr()?o(n.error):c()}).andTee(()=>S.verbose(`PrepareReleaseConfigTask: Release configuration prepared.`))}},vt=class{id=`release-preflight-check`;description=`Perform preflight checks before starting the release command.`;shouldExecute(e){return e?.getConfig().skipPreflightCheck?s(!1):s(!0)}getSkipThroughTasks(e){return e?.getConfig().skipPreflightCheck?s([A(W)]):s([])}canUndo(){return!1}execute(e){S.verbose(`ReleasePreflightCheckTask: Starting preflight checks...`);let t=e.getBasePath();return this.checkGitCliffConfig(t).andThen(this.cleanWorkingDirectory).andThen(this.ensureNoUnpushedCommits).map(()=>S.verbose(`ReleasePreflightCheckTask: All preflight checks passed.`))}checkGitCliffConfig(e){S.verbose(`ReleasePreflightCheckTask: Checking for git-cliff configuration...`);let t=k.exists(d(e,`cliff.toml`));return i.fromPromise(t,w).andThen(e=>e.isErr()?o(e.error):e.value?c(D.getInstance()):o(C({code:`NOT_FOUND`,message:`No git-cliff configuration found!`})))}cleanWorkingDirectory(e){return S.verbose(`ReleasePreflightCheckTask: Checking if working directory is clean...`),i.fromPromise(e.status.isWorkingDirectoryClean(),w).andThen(t=>t.isErr()?a(t.error):t.value?(S.verbose(`ReleasePreflightCheckTask: Working directory is clean`),s(e)):a(C({code:`FAILED`,message:`Working directory is not clean, clean working directory before proceeding!`})))}ensureNoUnpushedCommits(e){return S.verbose(`ReleasePreflightCheckTask: Checking for unpushed commits...`),i.fromPromise(e.remote.hasUnpushedCommits(),w).andThen(e=>e.isErr()?a(e.error):e.value?(S.verbose(`ReleasePreflightCheckTask: There are unpushed commits`),a(C({code:`FAILED`,message:`There are unpushed commits, push them before proceeding!`}))):(S.verbose(`ReleasePreflightCheckTask: No unpushed commits found`),s(void 0)))}};function yt(){return{id:`release-workflow`,name:`Release Workflow`,description:`Bump a new version, generate a changelog, and publish the release.`,command:`release`,buildTasks(){let e=[new vt,new _t,new W,new J,new ht,new mt,new K,new q,new G,new U,new Y,new X,new z,new I,new L,new F,new P,new N,new R,new it];return s(e)}}}var bt=class{constructor(e={}){this.options=e}load(){let{cwd:e=process.cwd(),configFile:t,overrides:n={}}=this.options;return i.fromPromise(re({name:`firefly`,cwd:e,configFile:t,packageJson:!1}),e=>C(w(e))).andThen(e=>this.handleConfigLoad(e,n)).andThen(e=>this.validateConfig(e))}handleConfigLoad(e,t){e.configFile!==`firefly.config`&&S.info(`Using firefly config: ${p.underline(e.configFile??`unknown`)}`);let n=this.mergeConfig(e.config??{},t);return s(this.normalizeFields(n))}validateConfig(e){return this.options.commandName?tt(b.getEffect(this.options.commandName),e):tt(b.getEffect(),e)}normalizeFields(e){return{...e,name:e.name??void 0,scope:e.scope??void 0}}mergeConfig(e,t){return this.deepMerge(e,t)}deepMerge(e,t){let n={...e};for(let r of Object.keys(t)){let i=e[r],a=t[r];i&&a&&typeof i==`object`&&typeof a==`object`&&!Array.isArray(i)&&!Array.isArray(a)?n[r]=this.deepMerge(i,a):a!==void 0&&(n[r]=a)}return n}},xt=class e{executionId;startTime;command;state;schema;constructor(e,t,n,r){this.command=e,this.executionId=r??Bun.randomUUIDv7(),this.startTime=new Date,this.state=t,this.schema=n}static create(t,n,r){if(!e.hasContextSchema(t))return a(C({message:`No context schema found for command "${t}".`,code:`NOT_FOUND`,source:`orchestration/scoped-context-service`}));let i=ue(t);if(!i)return a(C({message:`No context schema found for command "${t}".`,code:`NOT_FOUND`,source:`orchestration/scoped-context-service`}));let o=M(i,n);return o.isErr()?a(o.error):s(new e(t,o.value,i,r))}static hasContextSchema(e){return e in x}getConfig(){return this.state.config}setConfig(e){return this.set(`config`,e)}get(e){return e in this.state?s(this.state[e]):a(C({message:`Key "${String(e)}" does not exist in the context state.`,code:`NOT_FOUND`,source:`orchestration/scoped-context-service`}))}set(e,t){let n={...this.state,[e]:t},r=M(this.schema,n);return r.isErr()?a(r.error):(this.state=r.value,s())}update(e,t){let n=t(this.state[e]);return this.set(e,n)}has(e){return e in this.state&&this.state[e]!==void 0}snapshot(){return Object.freeze({...this.state})}clear(){let e={command:this.command,executionId:this.executionId,startTime:this.startTime},t=M(this.schema,e);return t.isErr()?a(t.error):(this.state=t.value,s())}getBasePath(){let e=this.state.basePath;return typeof e==`string`?e:process.cwd()}getCurrentVersion(){let e=this.state.currentVersion;return typeof e==`string`?e:`0.0.0`}getNextVersion(){let e=this.state.nextVersion;return typeof e==`string`?e:`0.0.0`}setCurrentVersion(e){return this.set(`currentVersion`,e)}setNextVersion(e){return this.set(`nextVersion`,e)}};const St=e.enum([`reverse`,`compensation`,`custom`,`none`]);e.object({taskId:e.string().min(1),task:e.custom(),executionTime:e.date(),compensationId:e.string().optional()});const Ct=e.object({executionId:e.uuid().optional(),name:e.string().min(1).optional(),description:e.string().optional(),dryRun:e.boolean().default(!1),featureFlags:e.map(e.string(),e.boolean()).optional(),rollbackStrategy:St.default(`reverse`)}),Z=e.string().min(1,`Feature name must be at least 1 character long`).max(100,`Feature name must be at most 100 characters long`).regex(/^[a-zA-Z0-9-_]+$/,`Feature name can only contain alphanumeric characters, hyphens, and underscores`),wt=e.boolean(),Tt=e.record(Z,wt);var Et=class e{features;metadata;constructor(e,t){this.features=e?new Map(e):new Map,this.metadata=t?new Map(t):new Map}static empty(){return new e}static fromMaps(t,n){return new e(t,n)}static fromConfig(t){let n=M(Tt,t);if(n.isErr())return a(C({code:`VALIDATION`,message:`Invalid feature configuration: ${n.error.message}`,source:`orchestration/feature-manager-service`}));let r=new Map(Object.entries(n.value));return s(e.fromMaps(r,new Map))}static create(t){if(!t.featureFlags)return s(new e);let n=t.featureFlags instanceof Map?Object.fromEntries(t.featureFlags):t.featureFlags;return e.fromConfig(n)}isEnabled(e){let t=M(Z,e);return t.isErr()?(S.warn(`FeatureManagerService: Invalid feature name checked - ${t.error.message}`),!1):this.features.get(e)??!1}areAllEnabled(e){return e.every(e=>this.isEnabled(e))}isAnyEnabled(e){return e.some(e=>this.isEnabled(e))}enable(t){let n=M(Z,t);if(n.isErr())return a(n.error);let r=this.metadata.get(t);if(r){let e=this.validateDependencies(t,r);if(e.isErr())return a(e.error);let n=this.validateConflicts(t,r);if(n.isErr())return a(n.error)}let i=new Map(this.features),o=new Map(this.metadata);return i.set(t,!0),o.set(t,{...r||{name:t,createdAt:new Date},updatedAt:new Date}),s(e.fromMaps(i,o))}disable(t){let n=M(Z,t);if(n.isErr())return S.warn(`FeatureManagerService: Invalid feature name checked - ${n.error.message}`),a(n.error);let r=this.findDependents(t);if(r.length>0)return a(C({code:`VALIDATION`,message:`Cannot disable feature "${t}" because the following features depend on it: ${r.join(`, `)}`,source:`orchestration/feature-manager-service`}));let i=this.metadata.get(t),o=new Map(this.features),c=new Map(this.metadata);return o.set(t,!1),c.set(t,{...i||{name:t,createdAt:new Date},updatedAt:new Date}),s(e.fromMaps(o,c))}findDependents(e){let t=[];for(let[n,r]of this.metadata.entries())r.dependencies?.includes(e)&&this.isEnabled(n)&&t.push(n);return t}validateDependencies(e,t){if(!t.dependencies)return s();let n=t.dependencies.filter(e=>!this.isEnabled(e));return n.length>0?a(C({code:`VALIDATION`,message:`Cannot enable feature "${e}" due to missing dependencies: ${n.join(`, `)}`,source:`orchestration/feature-manager-service`})):s()}validateConflicts(e,t){if(!t.conflictsWith)return s();let n=t.conflictsWith.filter(e=>this.isEnabled(e));return n.length>0?a(C({code:`VALIDATION`,message:`Cannot enable feature "${e}" due to conflicts with enabled features: ${n.join(`, `)}`,source:`orchestration/feature-manager-service`})):s()}toggle(e){return this.isEnabled(e)?this.disable(e):this.enable(e)}getEnabledFeatures(){return new Set(Array.from(this.features.entries()).filter(([,e])=>e).map(([e])=>e))}getDisabledFeatures(){return new Set(Array.from(this.features.entries()).filter(([,e])=>!e).map(([e])=>e))}getAllFeatures(){return new Map(this.features)}setFeatures(t){let n=new Map(this.features),r=new Map(this.metadata),i=new Date,o=[];for(let[e,a]of t.entries()){let t=M(Z,e);if(t.isErr()){o.push(`Invalid feature name "${e}": ${t.error.message}`);continue}let s=M(wt,a);if(s.isErr()){o.push(`Invalid flag for feature "${e}": ${s.error.message}`);continue}let c=this.metadata.get(e);n.set(e,a),r.set(e,{...c||{name:e,createdAt:i},updatedAt:i})}return o.length>0?a(C({code:`VALIDATION`,message:`Errors setting features: ${o.join(`; `)}`,source:`orchestration/feature-manager-service`})):s(e.fromMaps(n,r))}getMetadata(e){let t=M(Z,e);if(t.isErr()){S.warn(`FeatureManagerService: Invalid feature name checked - ${t.error.message}`);return}return this.metadata.get(e)}getMetadataWithEnabled(e){let t=M(Z,e);if(t.isErr()){S.warn(`FeatureManagerService: Invalid feature name checked - ${t.error.message}`);return}let n=this.metadata.get(e);if(n)return{...n,enabled:this.features.get(e)??!1}}setMetadata(t,n){let r=M(Z,t);if(r.isErr())return S.warn(`FeatureManagerService: Invalid feature name checked - ${r.error.message}`),a(r.error);let i=new Map(this.metadata),o=i.get(t);return i.set(t,{name:t,createdAt:o?.createdAt??new Date,updatedAt:new Date,...n}),s(e.fromMaps(this.features,i))}checkCompatibility(e){let t=[];for(let n of e){let e=M(Z,n);e.isErr()&&t.push(`Invalid feature name "${n}": ${e.error.message}`)}for(let n of e){if(M(Z,n).isErr())continue;let r=this.getMetadata(n);if(r?.dependencies){let i=r.dependencies.filter(t=>!e.includes(t));i.length>0&&t.push(`Feature "${n}" is missing dependencies: ${i.map(e=>`"${e}"`).join(`, `)}`)}if(r?.conflictsWith){let i=r.conflictsWith.filter(t=>e.includes(t));i.length>0&&t.push(`Feature "${n}" conflicts with: ${i.map(e=>`"${e}"`).join(`, `)}`)}}return t.length>0?a(C({code:`VALIDATION`,message:`Feature compatibility check failed: ${t.join(`; `)}`,details:{errors:t},source:`orchestration/feature-manager-service`})):s()}};function Q(e){return`shouldExecute`in e&&typeof e.shouldExecute==`function`}var Dt=class t{rollbackStack=[];compensationTasks=new Map;config;constructor(e){this.config={strategy:e?.strategy??`reverse`,maxRetries:e?.maxRetries??1,continueOnError:e?.continueOnError??!1,parallel:e?.parallel??!1}}static create(n){return M(e.object({strategy:e.enum([`reverse`,`compensation`,`custom`,`none`]).default(`reverse`),maxRetries:e.number().min(0).optional(),continueOnError:e.boolean().optional(),parallel:e.boolean().optional()}),n??{}).map(e=>new t(e))}addTask(e){return this.validateTask(e).andThen(()=>{let t={taskId:e.id,task:e,executionTime:new Date,compensationId:void 0};return e.canUndo?.()?(this.rollbackStack.push(t),S.verbose(`RollbackManagerService: Added task to rollback stack: '${e.id}'`),s()):s()})}registerCompensation(t,n){let r=M(e.string().min(1),t).andThen(()=>this.validateCompensationTask(n));if(r.isErr())return r;this.compensationTasks.set(t,n);let i=this.rollbackStack.slice().reverse().find(e=>e.taskId===t);return i&&(i.compensationId=n.id),s()}executeRollback(e,t){let n=e??this.config.strategy,r=Date.now();return this.rollbackStack.length===0?(S.verbose(`RollbackManagerService: No tasks to rollback`),c({success:!0,rolledBackTasks:[],failedTasks:[],errors:[],duration:0})):(S.info(`RollbackManagerService: Starting rollback with strategy: ${n}`),this.executeStrategyRollback(n,t).map(e=>({...e,duration:Date.now()-r})).mapErr(e=>(S.error(`RollbackManagerService: Rollback failed`,e),e)))}executeStrategyRollback(e,t){let n={reverse:e=>this.executeReverseRollback(e),compensation:e=>this.executeCompensationRollback(e),custom:e=>this.executeCustomRollback(e),none:()=>c(this.createEmptyResult())}[e];return n?n(t):o(C({code:`VALIDATION`,message:`Unknown rollback strategy: ${String(e)}`,source:`application`}))}createEmptyResult(){return{success:!0,rolledBackTasks:[],failedTasks:[],errors:[],duration:0}}handleRollbackError(e,t,n){e.failedTasks.push(t.taskId),e.errors.push(n),e.success=!1}executeRollbackSequence(e,t,n){let r=this.createEmptyResult(),i=[...e].reverse(),a=e=>{if(e>=i.length)return c(r);let o=i[e];return o?this.executeWithRetries(()=>t(o,n),this.config.maxRetries??1).andThen(()=>(r.rolledBackTasks.push(o.taskId),a(e+1))).orElse(t=>(this.handleRollbackError(r,o,t),this.config.continueOnError?a(e+1):c(r))):a(e+1)};return a(0)}executeWithRetries(e,t){let n=r=>e().orElse(e=>r<t?(S.verbose(`RollbackManagerService: Retry attempt ${r+1}/${t}`),n(r+1)):o(e));return n(0)}executeReverseRollback(e){return this.executeRollbackSequence(this.rollbackStack,(e,t)=>this.executeTaskRollback(e,t),e)}executeCompensationRollback(e){return this.executeRollbackSequence(this.rollbackStack,(e,t)=>e.compensationId&&this.compensationTasks.has(e.compensationId)?this.executeCompensation(e.compensationId,t):this.executeTaskRollback(e,t),e)}executeCustomRollback(e){return this.executeRollbackSequence(this.rollbackStack,(e,t)=>t?(e.task.beforeRollback?.(t)??c()).andThen(()=>this.executeTaskRollback(e,t)).andThen(()=>e.task.afterRollback?.(t)??c()).orElse(n=>(e.task.onRollbackError?.(n,t)??c()).andThen(()=>o(n))):this.executeTaskRollback(e,t),e)}executeTaskRollback(e,t){let{task:n}=e;return n.canUndo?.()?(S.verbose(`RollbackManagerService: Executing rollback for task '${n.id}'`),n.undo?t?n.undo(t):n.undo({}):(S.warn(`RollbackManagerService: Task '${n.id}' does not have an undo method. Skipping rollback.`),c())):(S.verbose(`RollbackManagerService: Task '${n.id}' cannot be undone. Skipping rollback.`),c())}executeCompensation(e,t){let n=this.compensationTasks.get(e);return n?(S.verbose(`RollbackManagerService: Executing compensation task: ${n.name}`),n.execute(t)):o(C({message:`Compensation task with id '${e}' not found.`,code:`NOT_FOUND`,source:`orchestration/rollback-manager-service`}))}validateTask(e){return!e.id||typeof e.id!=`string`?a(C({message:`Task must have a valid 'id' of type string.`,code:`VALIDATION`,source:`orchestration/rollback-manager-service`})):s()}validateCompensationTask(e){return!e.id||typeof e.id!=`string`?a(C({message:`Compensation task must have a valid 'id' of type string.`,code:`VALIDATION`,source:`orchestration/rollback-manager-service`})):s()}getRollbackStack(){return[...this.rollbackStack]}clear(){this.rollbackStack.length=0,this.compensationTasks.clear()}getTaskCount(){return this.rollbackStack.length}hasTasks(){return this.rollbackStack.length>0}getConfig(){return{...this.config}}};const Ot=process.env.FIREFLY_DEBUG_TASK_LIFECYCLE===`true`;var kt=class{executeTask(e,t){let n=`TaskExecutorService: Executing task '${e.id}'`;return S.verbose(Ot?p.redBright(n):n),this.executeWithLifecycle(e,t).andThen(()=>{let t=`TaskExecutorService: Successfully executed task '${e.id}'`;return S.verbose(Ot?p.redBright(t):t),c()}).mapErr(t=>(S.verbose(`TaskExecutorService: Failed to execute task '${e.id}'`),S.verbose(`TaskExecutorService: Reason: ${t.message}`),t))}undoTask(e,t){return S.verbose(`TaskExecutorService: Undoing task '${e.id}'`),e.canUndo?.()?this.undoWithLifecycle(e,t).andThen(()=>(S.verbose(`TaskExecutorService: Successfully undone task '${e.id}'`),c())).mapErr(t=>(S.verbose(`TaskExecutorService: Failed to undo task '${e.id}': ${t.message}`),t)):o(C({message:`Task '${e.id}' cannot be undone.`,code:`INVALID`,source:`orchestration/task-executor-service`}))}compensateTask(e,t){return S.verbose(`TaskExecutorService: Compensating task '${e.id}'`),e.compensate?(t?e.compensate?.(t):e.compensate?.({})).andThen(()=>(S.verbose(`TaskExecutorService: Successfully compensated task '${e.id}'`),c())).mapErr(t=>(S.verbose(`TaskExecutorService: Failed to compensate task '${e.id}': ${t.message}`),t)):o(C({message:`Task '${e.id}' does not have a compensate operation defined.`,code:`INVALID`,source:`orchestration/task-executor-service`}))}executeWithLifecycle(e,t){return t&&e.beforeExecute?e.beforeExecute(t).andThen(()=>this.performExecution(e,t)).andThen(()=>e.afterExecute?e.afterExecute(t):c()).orElse(n=>e.onExecuteError&&t?e.onExecuteError(n,t).andThen(()=>o(n)):o(n)):this.performExecution(e,t)}performExecution(e,t){if(t&&e.validate){let n=e.validate?.(t);if(n.isErr())return o(n.error)}return t?e.execute?.(t):e.execute?.({})}undoWithLifecycle(e,t){return t&&e.beforeRollback?e.beforeRollback(t).andThen(()=>this.performUndo(e,t)).andThen(()=>e.afterRollback?e.afterRollback(t):c()).orElse(n=>e.onRollbackError&&t?e.onRollbackError(n,t).andThen(()=>o(n)):o(n)):this.performUndo(e,t)}performUndo(e,t){return(t?e.undo?.(t):e.undo?.({}))||o(C({message:`Task '${e.id}' does not have an undo operation defined.`,code:`INVALID`,source:`orchestration/task-executor-service`}))}},At=class{options;startTime;taskExecutor;featureManager;rollbackManager;taskMap;constructor(e){this.options=e,this.startTime=new Date,this.taskMap=new Map;let t={strategy:e.rollbackStrategy,continueOnError:!1,parallel:!1};this.taskExecutor=new kt;let n=Dt.create(t);n.isOk()&&(this.rollbackManager=n.value);let r=Et.create(e);r.isOk()&&(this.featureManager=r.value)}execute(e,t){this.initializeTaskMap(e);let n=[],r=[],i=[],a=!1,s=!1,c=this.getInitialExecutionQueue(e,t),l=()=>{let e=this.getNextExecutableTask(c,t);if(!e)return this.createResult(!0,n,r,i,{rollbackExecuted:a,compensationExecuted:s});let u=this.taskMap.get(e);if(!u)return o(C({code:`VALIDATION`,message:`Task node not found for ID: ${e}`,source:`orchestration/sequential-execution-strategy`}));let d=u.task;return u.visited=!0,this.shouldExecuteTask(d,t).asyncAndThen(o=>{if(!o){if(i.push(d.id),this.removeFromQueue(c,e),Q(d)&&d.getSkipThroughTasks){let e=d.getSkipThroughTasks(t);if(e.isOk())for(let t of e.value)this.taskMap.has(t)&&!c.includes(t)&&(c.push(t),S.verbose(`SequentialExecutionStrategy: Added skip-through task '${t}' from skipped task '${d.id}'`))}return l()}return this.taskExecutor.executeTask(d,t).andThen(()=>{let r=this.rollbackManager.addTask(d);r.isErr()&&S.warn(`Failed to add task '${d.id}' to rollback stack`,r.error),n.push(d.id),this.removeFromQueue(c,e);let i=this.addDynamicNextTasks(d,c,t);return i.isErr()&&S.warn(`Failed to resolve next tasks for '${d.id}'`,i.error),l()}).orElse(e=>(r.push(d.id),this.options.rollbackStrategy===`none`?this.createResult(!1,n,r,i,{error:e,rollbackExecuted:!1,compensationExecuted:!1}):(S.verbose(`SequentialExecutionStrategy: Executing rollback with strategy: ${this.options.rollbackStrategy}`),this.rollbackManager.executeRollback(this.options.rollbackStrategy,t).andThen(t=>(a=t.success,s=this.options.rollbackStrategy===`compensation`&&t.success,t.success?S.verbose(`SequentialExecutionStrategy: Rollback completed successfully`):S.error(`SequentialExecutionStrategy: Rollback failed`,t.errors),this.createResult(!1,n,r,i,{error:e,rollbackExecuted:a,compensationExecuted:s}))).orElse(t=>(S.error(`SequentialExecutionStrategy: Rollback execution failed`,t),this.createResult(!1,n,r,i,{error:e,rollbackExecuted:!1,compensationExecuted:!1}))))))})};return l()}initializeTaskMap(e){this.taskMap.clear();for(let t of e)this.taskMap.set(t.id,{task:t,visited:!1})}getInitialExecutionQueue(e,t){let n=e.filter(e=>(e.getDependencies?.(t)??[]).length===0&&(e.isEntryPoint?.()??!0));if(n.length===0){let t=e.find(e=>e.isEntryPoint?.()??!0);return t?[t.id]:[]}return n.map(e=>e.id)}getNextExecutableTask(e,t){for(let n of e){let e=this.taskMap.get(n);if(!(!e||e.visited)&&(e.task.getDependencies?.(t)??[]).every(e=>this.taskMap.get(e)?.visited===!0))return n}return null}removeFromQueue(e,t){let n=e.indexOf(t);n>-1&&e.splice(n,1)}addDynamicNextTasks(e,t,n){let r=!1;if(Q(e)){let i=e.getNextTasks?.(n);if(i?.isOk()){let n=i.value;r=n.length>0;for(let r of n)this.taskMap.has(r)&&!t.includes(r)&&(t.push(r),S.verbose(`SequentialExecutionStrategy: Added dynamic next task '${r}' from '${e.id}'`))}else i?.isErr()&&S.warn(`Failed to get next tasks from '${e.id}'`,i.error)}if(!r){for(let[n,r]of this.taskMap)(r.task.getDependencies?.()??[]).includes(e.id)&&!t.includes(n)&&!r.visited&&(t.push(n),S.verbose(`SequentialExecutionStrategy: Added dependent task '${n}' from '${e.id}'`));let n=e.getDependents?.()??[];for(let r of n)this.taskMap.has(r)&&!t.includes(r)&&(t.push(r),S.verbose(`SequentialExecutionStrategy: Added dependent task '${r}' from '${e.id}'`))}return s()}shouldExecuteTask(e,t){if(!e||typeof e.id!=`string`)return S.warn(`SequentialExecutionStrategy: Invalid task structure for task ${e?.id||`unknown`}`),s(!1);let n=e.getRequiredFeatures?.()??[];if(n.length>0){let t=this.featureManager.getEnabledFeatures();if(!(typeof e.isEnabled!=`function`||e.isEnabled(t)))return S.verbose(`SequentialExecutionStrategy: Task '${e.id}' disabled due to missing required features: ${n.join(`, `)}`),s(!1)}if(Q(e)){let n=e.shouldExecute(t);if(n.isErr())return S.warn(`SequentialExecutionStrategy: Error evaluating conditions for task '${e.id}'`,n.error),s(!1);if(!n.value)return S.verbose(`SequentialExecutionStrategy: Skipping task '${e.id}' due to runtime conditions`),s(!1)}return s(!0)}createResult(e,t,n,r,i){let a=new Date,o={success:e,executionId:this.options.executionId??`unknown`,workflowId:this.options.name??`sequential-workflow`,executedTasks:t,failedTasks:n,skippedTasks:r,error:i?.error,rollbackExecuted:i?.rollbackExecuted??!1,compensationExecuted:i?.compensationExecuted??!1,startTime:this.startTime,endTime:a,executionTime:a.getTime()-this.startTime.getTime()};return c(o)}};function jt(e){return new At(e)}var Mt=class e{tasks;context;options;executionStrategy;executionId;featureManager;constructor(e,t,n){this.tasks=e,this.options=t,this.context=n,this.executionId=t.executionId??Bun.randomUUIDv7();let r=Et.create(t);r.isOk()&&(this.featureManager=r.value),this.executionStrategy=jt(this.options)}static fromTasks(t,n,r={}){let i=e.validateOptions(r);if(i.isErr())return a(i.error);let o=e.validateTaskConfiguration(t,n);return o.isErr()?a(o.error):(S.verbose(`TaskOrchestratorService: Initialized with ${t.length} tasks.`),s(new e(t,i.value,n)))}static fromWorkflow(t,n,r={}){S.verbose(`TaskOrchestratorService: Building tasks from workflow '${t.id}'.`);let i=e.validateOptions(r);if(i.isErr())return a(i.error);let o=t.buildTasks(n);if(o.isErr())return a(o.error);let c=e.validateTaskConfiguration(o.value,n);return c.isErr()?a(c.error):s(new e(o.value,i.value,n))}run(){let e=this.filterTasksByFeatures(Array.from(this.tasks));return e.isErr()?o(e.error):this.executionStrategy.execute(e.value,this.context).map(e=>(S.verbose(`TaskOrchestratorService: Workflow execution completed.`),e)).mapErr(e=>e)}static validateOptions(e){let t=M(Ct,e);return t.isErr()?a(C({code:`VALIDATION`,message:`Invalid orchestrator options: ${t.error.message}`,source:`orchestration/task-orchestrator-service`})):s(t.value)}getExecutionId(){return this.executionId}static validateTaskConfiguration(e,t){let n=new Set(e.map(e=>e.id)),r=[];for(let i of e){for(let e of i.getDependencies?.(t)??[])n.has(e)||r.push(`Task ${i.id} has a missing dependency: ${e}`);for(let e of i.getDependents?.()??[])n.has(e)||r.push(`Task ${i.id} has a missing dependent: ${e}`)}let i=new Set,o=new Set,c=n=>{if(o.has(n))return!0;if(i.has(n))return!1;i.add(n),o.add(n);let r=e.find(e=>e.id===n);if(r){for(let e of r.getDependencies?.(t)??[])if(c(e))return!0}return o.delete(n),!1};for(let t of e)c(t.id)&&r.push(`Task ${t.id} is part of a circular dependency in static dependencies`);return r.length>0?a(C({code:`VALIDATION`,message:`Task configuration errors:\n${r.join(`
|
|
17
|
-
`)}`,source:`orchestration/task-orchestrator-service`})):s()}filterTasksByFeatures(e){let t=this.featureManager.getEnabledFeatures(),n=[];for(let r of e){let e=r.getRequiredFeatures?.()??[];e.length===0||r.isEnabled?.(t)?n.push(r):S.verbose(`TaskOrchestratorService: Task ${r.id} disabled due to missing features: ${e.join(`, `)}`)}return s(n)}},
|
|
13
|
+
`).filter(e=>e.charAt(0)!==` `).map(e=>e.slice(2).trim());return S.verbose(`GitStatusService: Found staged files: ${r.join(`, `)}`),s(r)}async getStagedFilesByNames(e,t){let n=await this.getStagedFiles(t);if(n.isErr())return a(n.error);let r=n.value.filter(t=>e.some(e=>t===e||u(t)===u(e)));return S.verbose(`GitStatusService: Filtered staged files: ${r.join(`, `)}`),s(r)}},Je=class{constructor(e){this.config=e}async createTag(e,t,n){S.verbose(`GitTagService: Creating tag ${e} with message: ${t?`yes`:`no`}`);let r=await this.config.canSignTag();if(r.isErr())return a(r.error);let i=r.value,o=[`tag`,`-a`];i&&o.push(`-s`),o.push(e),t&&o.push(`-m`,t);let c=await T(o,{dryRun:n});return c.isErr()?a(c.error):(S.verbose(`GitTagService: Tag ${e} created successfully`),s())}async deleteLocal(e,t){S.verbose(`GitTagService: Deleting local tag ${e}`);let n=await T([`tag`,`-d`,e],{dryRun:t});return n.isErr()?a(n.error):(S.verbose(`GitTagService: Tag ${e} deleted successfully`),s())}async pushDeleteRemoteTag(e,t,n){S.verbose(`GitPushService: Deleting remote tag ${e} from ${t}`);let r=await T([`push`,t,`--delete`,`refs/tags/${e}`],{dryRun:n});return r.isErr()?a(r.error):(S.verbose(`GitPushService: Remote tag ${e} deleted successfully from ${t}`),s())}async exists(e){S.verbose(`GitTagService: Checking if tag ${e} exists`);let t=await T([`tag`,`-l`,e]);if(t.isErr())return s(!1);let n=t.value.trim()===e;return S.verbose(`GitTagService: Tag ${e} exists: ${n}`),s(n)}async listTags(){S.verbose(`GitTagService: Listing all tags`);let e=await T([`tag`,`-l`]);if(e.isErr())return a(e.error);let t=e.value.trim().split(`
|
|
14
|
+
`).map(e=>e.trim()).filter(e=>e.length>0);return S.verbose(`GitTagService: Found ${t.length} tags`),s(t)}async getTagMessage(e){S.verbose(`GitTagService: Getting message for tag ${e}`);let t=await this.exists(e);if(t.isErr())return a(t.error);if(!t.value)return a(C({code:`NOT_FOUND`,message:`Tag "${e}" does not exist.`,source:`git/git-tag-service`}));let n=await T([`tag`,`-l`,`--format=%(contents)`,e]);return n.isErr()?a(n.error):(S.verbose(`GitTagService: Retrieved message for tag ${e}`),s(n.value.trim()))}};const E={GITHUB_HTTPS:/^https:\/\/github\.com\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/,GITHUB_SSH:/^git@github\.com:([^/]+)\/([^/]+?)(?:\.git)?$/,GITLAB_HTTPS:/^https:\/\/gitlab\.com\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/,GITLAB_SSH:/^git@gitlab\.com:([^/]+)\/([^/]+?)(?:\.git)?$/,BITBUCKET_HTTPS:/^https:\/\/bitbucket\.org\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/,BITBUCKET_SSH:/^git@bitbucket\.org:([^/]+)\/([^/]+?)(?:\.git)?$/,GENERIC_HTTPS:/^https:\/\/([^/]+)\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/,GENERIC_SSH:/^git@([^:]+):([^/]+)\/([^/]+?)(?:\.git)?$/};var Ye=class{extractRepository(e){let t=e.trim();if(!t)return a(C({code:`INVALID`,message:`Repository URL cannot be empty.`,source:`git/repository-parse-service`}));let n=t.match(E.GITHUB_HTTPS);if(n){let e=n[1],t=n[2];return e&&t?this.createRepositoryInfo(e,t,`github.com`,`https`):a(C({code:`INVALID`,message:`Failed to extract owner and repository name from GitHub HTTPS URL.`,source:`git/repository-parse-service`}))}let r=t.match(E.GITHUB_SSH);if(r){let e=r[1],t=r[2];return e&&t?this.createRepositoryInfo(e,t,`github.com`,`ssh`):a(C({code:`INVALID`,message:`Failed to extract owner and repository name from GitHub SSH URL.`,source:`git/repository-parse-service`}))}let i=t.match(E.GITLAB_HTTPS);if(i){let e=i[1],t=i[2];return e&&t?this.createRepositoryInfo(e,t,`gitlab.com`,`https`):a(C({code:`INVALID`,message:`Failed to extract owner and repository name from GitLab HTTPS URL.`,source:`git/repository-parse-service`}))}let o=t.match(E.GITLAB_SSH);if(o){let e=o[1],t=o[2];return e&&t?this.createRepositoryInfo(e,t,`gitlab.com`,`ssh`):a(C({code:`INVALID`,message:`Failed to extract owner and repository name from GitLab SSH URL.`,source:`git/repository-parse-service`}))}let s=t.match(E.BITBUCKET_HTTPS);if(s){let e=s[1],t=s[2];return e&&t?this.createRepositoryInfo(e,t,`bitbucket.org`,`https`):a(C({code:`INVALID`,message:`Failed to extract owner and repository name from Bitbucket HTTPS URL.`,source:`git/repository-parse-service`}))}let c=t.match(E.BITBUCKET_SSH);if(c){let e=c[1],t=c[2];return e&&t?this.createRepositoryInfo(e,t,`bitbucket.org`,`ssh`):a(C({code:`INVALID`,message:`Failed to extract owner and repository name from Bitbucket SSH URL.`,source:`git/repository-parse-service`}))}let l=t.match(E.GENERIC_HTTPS);if(l){let e=l[1],t=l[2],n=l[3];return e&&t&&n?this.createRepositoryInfo(t,n,e,`https`):a(C({code:`INVALID`,message:`Failed to extract repository information from generic HTTPS URL.`,source:`git/repository-parse-service`}))}let u=t.match(E.GENERIC_SSH);if(u){let e=u[1],t=u[2],n=u[3];return e&&t&&n?this.createRepositoryInfo(t,n,e,`ssh`):a(C({code:`INVALID`,message:`Failed to extract repository information from generic SSH URL.`,source:`git/repository-parse-service`}))}return a(C({code:`INVALID`,message:`Unable to parse repository URL: "${e}". Supported formats include GitHub, GitLab, and Bitbucket URLs.`,source:`git/repository-parse-service`}))}validateRepositoryString(e){let t=re.safeParse(e);return t.success?s(!0):a(C({code:`VALIDATION`,message:`Invalid repository format: "${e}". Expected format: "owner/repo".`,source:`git/repository-parse-service`,details:t.error.issues}))}parseRepositoryString(e){let t=this.validateRepositoryString(e);if(t.isErr())return a(t.error);if(e===``)return a(C({code:`INVALID`,message:`Repository string cannot be empty.`,source:`git/repository-parse-service`}));let n=e.split(`/`);if(n.length!==2)return a(C({code:`INVALID`,message:`Invalid repository format: "${e}". Expected format: "owner/repo".`,source:`git/repository-parse-service`}));let r=n[0]||``,i=n[1]||``;return r===``||i===``?a(C({code:`INVALID`,message:`Repository owner and name cannot be empty.`,source:`git/repository-parse-service`})):s({owner:r,repo:i})}createRepositoryInfo(e,t,n,r){if(e===``||t===``)return a(C({code:`INVALID`,message:`Repository owner and name cannot be empty.`,source:`git/repository-parse-service`}));let i=`${e}/${t}`,o=this.validateRepositoryString(i);return o.isErr()?a(o.error):s({owner:e,repo:t,host:n,protocol:r,fullName:i})}},D=class e{static _instance;_config;_remote;_status;_staging;_commit;_tag;_push;_rollback;_repository;_branch;_history;_repositoryParse;constructor(){}static getInstance(){return e._instance||=new e,e._instance}get config(){return this._config||=new Be,this._config}get remote(){return this._remote||=new Ue,this._remote}get status(){return this._status||=new qe,this._status}get staging(){return this._staging||=new Ke,this._staging}get commit(){return this._commit||=new ze(this.config),this._commit}get tag(){return this._tag||=new Je(this.config),this._tag}get push(){return this._push||=new He,this._push}get rollback(){return this._rollback||=new Ge(this.push,this.tag,this.history),this._rollback}get repository(){return this._repository||=new We,this._repository}get branch(){return this._branch||=new Re,this._branch}get history(){return this._history||=new Ve,this._history}get repositoryParse(){return this._repositoryParse||=new Ye,this._repositoryParse}},Xe=class{templateResolver;gitCliffAdapter;gitProvider;constructor(e){this.templateResolver=e,this.gitCliffAdapter=new De,this.gitProvider=D.getInstance()}async generateChangelog(e){S.verbose(`ChangelogHandlerService: Next version resolved for changelog generation.`);let t=await this.resolveRepository(e.repository);if(t.isErr())return a(t.error);S.verbose(`ChangelogHandlerService: Repository resolved: ${t.value}`);let n=this.templateResolver.tagName(e.tagName||``);S.verbose(`ChangelogHandlerService: Tag name resolved: ${n}`);let r=await this.buildChangelogOptions(e,n,t.value);if(r.isErr())return a(r.error);let i=await this.gitCliffAdapter.generate(r.value);return i.isErr()?(S.error(`ChangelogHandlerService: Failed to generate changelog`,i.error),a(i.error)):(S.verbose(`ChangelogHandlerService: Changelog generated successfully.`),s(i.value))}async resolveRepository(e){if(e?.trim()&&e!==``)return S.verbose(`ChangelogGeneratorService: Using repository from config: ${e}`),s(e);let t=await this.gitProvider.repository.getRepositoryUrl();if(t.isErr())return a(t.error);S.verbose(`ChangelogGeneratorService: Repository URL retrieved from git provider: ${t.value}`);let n=this.gitProvider.repositoryParse.extractRepository(t.value);if(n.isErr())return a(n.error);let{owner:r,repo:i}=n.value;return S.verbose(`ChangelogGeneratorService: Extracted repository owner: ${r}, name: ${i}`),s(`${r}/${i}`)}async buildChangelogOptions(e,t,n){let r={dryRun:e.dryRun,changelogPath:e.changelogPath||`CHANGELOG.md`,tagName:t,repository:n};e.changelogPath&&(r.changelogPath=e.changelogPath,S.verbose(`ChangelogGeneratorService: Changelog path set to ${e.changelogPath}`)),e.releaseNotes?.trim()&&(r.releaseNotes=e.releaseNotes.replace(/\\n/g,`
|
|
15
|
+
`),S.verbose(`ChangelogGeneratorService: Release notes added to changelog options.`));let i=await this.gitProvider.repository.getRootDirection();return i.isErr()?a(i.error):(i.value&&i.value!==`.`&&(r.hasRootDirection=!0,r.rootDirection=i.value,r.includePath=`${e.base}/*`,S.verbose(`ChangelogGeneratorService: Include path set to ${r.includePath}`)),S.verbose(`ChangelogGeneratorService: Changelog options built successfully.`),s(r))}},O=class e{static TEMPLATE_PATTERNS={VERSION:/\{\{version\}\}/g,NAME:/\{\{name\}\}/g,UNSCOPED_NAME:/\{\{unscopedName\}\}/g};withContext(e){let t={version:e.version,name:this.getFullPackageName(e.config),unscopedName:e.config.name||``};return{commitMessage:e=>this.resolveTemplate(e,t),tagName:e=>this.resolveTemplate(e,t),releaseTitle:e=>this.resolveTemplate(e,t)}}getFullPackageName(e){return e.name?e.scope?`@${e.scope}/${e.name}`:e.name:``}resolveTemplate(t,n){if(!t?.trim())return t;let r=t;return n.version&&(r=r.replace(e.TEMPLATE_PATTERNS.VERSION,n.version)),r=r.replace(e.TEMPLATE_PATTERNS.NAME,n.name),r=r.replace(e.TEMPLATE_PATTERNS.UNSCOPED_NAME,n.unscopedName),r}},k=class e{static read(t){return e.exec(Bun.file(t).text(),`Failed to read file`).andTee(()=>{S.verbose(`FileSystemService: Read file at ${t}`)})}static write(t,n,r){return r?(S.verbose(`FileSystemService: Dry run mode enabled, not writing file.`),c(void 0)):e.exec(Bun.write(t,n),`Failed to write file`).map(()=>{}).andTee(()=>S.verbose(`FileSystemService: Wrote file at ${t}`))}static exists(t){return e.exec(Bun.file(t).exists(),`Failed to check if file exists`).andTee(()=>S.verbose(`FileSystemService: Checked existence of file at ${t}`))}static exec(e,t){return i.fromPromise(e,e=>C({code:`INVALID`,message:t,source:`filesystem/file-system-service`,cause:e}))}};function A(e){return`id`in e&&typeof e.id==`string`?e.id:new e().id}function j(e){return i.fromPromise(e,e=>C(w(e)))}function Ze(...t){return t.slice(1).reduce((t,n)=>e.intersection(t,n),t[0])}function Qe(e,...t){let n={};for(let e of t)Object.assign(n,e);return e.extend(n)}function $e(e){if(e?._def!==void 0)return e;let t=e;return t.mode===`effect`?Ze(...t.schemas):Qe(t.base,...t.shapes)}function M(e,t){let n=$e(e).safeParse(t);return n.success?s(n.data):a(C(w(n.error)))}function et(e,t){let n=$e(e);return i.fromPromise(n.parseAsync(t),e=>C(w(e)))}var N=class{id=`push-tag`;description=`Pushes the tag to the remote repository.`;getDependencies(){return[A(P)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipGit)}getNextTasks(e){return s([])}execute(e){let t=D.getInstance(),n=e.getConfig(),r=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).tagName(e.getConfig().tagName);return j(t.remote.getCurrentRemote()).andThen(e=>e.isErr()?o(e.error):j(t.push.pushTag(r,e.value,n.dryRun))).orElse(()=>j(t.push.pushTag(r,`origin`,n.dryRun))).map(()=>{S.success(`Pushed tag to remote repository`)})}canUndo(){return!0}undo(e){let t=D.getInstance(),n=e.getConfig(),r=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).tagName(n.tagName);return j(t.remote.getCurrentRemote()).andThen(e=>e.isErr()?o(e.error):j(t.push.pushDeleteRemoteTag(r,e.value,n.dryRun))).orElse(()=>j(t.push.pushDeleteRemoteTag(r,`origin`,n.dryRun))).map(()=>{S.success(`Rolled back tag '${r}' from remote and local`)})}},P=class e{id=`push-commit`;description=`Pushes the commit to the remote repository.`;getDependencies(){return[A(F)]}shouldExecute(e){let t=e.getConfig();return t.skipPush?s(!1):s(!t.skipGit)}getNextTasks(e){return e.getConfig().skipGit?s([]):s([A(N)])}getSkipThroughTasks(t){let n=t?.getConfig();return n?.skipPush?s([A(R)]):n?.skipGit?s([]):s([A(e)])}execute(e){let t=D.getInstance(),n=e.getConfig();return j(t.remote.getCurrentRemote()).andThen(e=>e.isErr()?o(e.error):j(t.push.push(e.value,n.branch,n.dryRun))).orElse(()=>j(t.push.push(`origin`,n.branch,n.dryRun))).map(()=>{S.success(`Pushed commit to remote repository.`)})}canUndo(){return!0}undo(e){let t=D.getInstance(),n=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).commitMessage(e.getConfig().commitMessage),r=e.getConfig();return j(t.remote.getCurrentRemote()).andThen(e=>e.isErr()?o(e.error):j(t.rollback.rollbackLatestCommitIfMessageMatches(n,r.branch,e.value,!1,r.dryRun))).orElse(()=>j(t.rollback.rollbackLatestCommitIfMessageMatches(n,r.branch,`origin`,!1,r.dryRun))).map(()=>{S.success(`Undid push commit to remote repository.`)})}},F=class{id=`create-tag`;description=`Creates a new tag for the release.`;getDependencies(){return[A(L)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipGit)}getNextTasks(e){return e.getConfig().skipGit?s([]):s([A(P)])}execute(e){let t=D.getInstance(),n=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}),r=n.tagName(e.getConfig().tagName),i=n.commitMessage(e.getConfig().releaseTitle);return j(t.tag.createTag(r,i,e.getConfig().dryRun)).map(()=>{S.info(`Created tag: ${p.gray(r)}`)})}canUndo(){return!0}undo(e){let t=D.getInstance(),n=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).tagName(e.getConfig().tagName);return j(t.tag.deleteLocal(n,e.getConfig().dryRun)).map(()=>{S.info(`Deleted tag: ${p.gray(n)}`)})}},I=class{id=`stage-changes`;description=`Stages the changes for the release.`;getDependencies(e){return e?.getConfig().skipChangelog?[A(z)]:[A(X)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipGit)}getNextTasks(e){return e.getConfig().skipGit?s([]):s([A(L)])}execute(e){let t=e.getConfig(),n=t.changelogPath||`CHANGELOG.md`,r=f(e.getBasePath(),`package.json`),a=f(e.getBasePath(),n),s=D.getInstance();return S.info(`Staging changes for ${p.underline(u(r))} and ${p.underline(u(a))}`),j(s.status.getUnstagedFilesByNames([a,r],t.dryRun)).andThen(e=>{if(e.isErr())return o(e.error);let n=e.value;return S.verbose(`StageChangesTask: Found ${n.length} files to stage: ${n.join(`, `)}`),n.length===0?(S.verbose(`StageChangesTask: No changes detected to stage, continuing...`),i.fromSafePromise(Promise.resolve())):j(s.staging.stageFiles(n,t.dryRun)).andTee(e=>{e.isErr()?S.error(`Failed to stage files: ${n.join(`, `)}. Error: ${e.error.message}`):S.verbose(`StageChangesTask: Staged files: ${n.join(`, `)}`)}).map(()=>{})})}canUndo(){return!0}undo(e){let t=e.getConfig(),n=t.changelogPath||`CHANGELOG.md`,r=f(e.getBasePath(),`package.json`),i=f(e.getBasePath(),n),a=D.getInstance();return j(a.staging.unstageFiles([i,r],t.dryRun)).andTee(e=>{e.isErr()?S.error(`Failed to unstage files: ${[i,r].join(`, `)}. Error: ${e.error.message}`):S.verbose(`StageChangesTask: Unstaged files: ${[i,r].join(`, `)}`)}).map(()=>{})}},L=class{id=`commit-changes`;description=`Commits the changes for the release.`;getDependencies(){return[A(I)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipGit)}getNextTasks(e){return e.getConfig().skipGit?s([]):s([A(F)])}execute(e){let t=D.getInstance(),n=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}).commitMessage(e.getConfig().commitMessage);return j(t.commit.create(n,e.getConfig().dryRun)).map(()=>{S.info(`Committed changes with message: ${p.gray(n)}`)})}canUndo(){return!0}undo(e){let t=D.getInstance(),n=e.getConfig();return j(t.commit.resetLast(!1,n.dryRun)).andTee(e=>{e.isErr()?S.error(`Failed to reset last commit: ${e.error.message}`):S.verbose(`CommitChangesTask: Last commit reset successfully.`)}).map(()=>{})}},tt=class{constructor(e){this.cliffTomlService=e}async process(e){let t=await this.cliffTomlService.parse();if(t.isErr())return a(t.error);S.verbose(`ChangelogPostProcessor: Cliff TOML config parsed successfully, processing changelog...`);let n=t.value,r=this.extractChangesSection(e,n);if(r.isErr())return r;let i=r.value.trim();return i.includes(`###`)?s(i):(S.verbose(`ChangelogPostProcessorService: No commit entries found, returning empty changelog.`),s(``))}extractChangesSection(e,t){let n=t.changelog?.header,r=t.changelog?.body;if(!(n&&r))return S.verbose(`ChangelogPostProcessorService: No header/body template found in cliff.toml, returning raw changelog.`),s(e);let i=this.findChangesStartIndex(e);if(i===-1)return S.verbose(`ChangelogPostProcessorService: No changes section found, returning raw changelog.`),s(e);let a=e.slice(i).trimStart();return S.verbose(`ChangelogPostProcessorService: Extracted changes section from changelog.`),s(a)}findChangesStartIndex(e){return e.indexOf(`###`)}},nt=class e{static instance=null;pathToCliffToml;constructor(e){this.pathToCliffToml=e}static getInstance(t){return e.instance||=new e(d(t,`cliff.toml`)),e.instance}async parse(){let e=await k.read(this.pathToCliffToml);return e.isErr()?a(e.error):(S.verbose(`CliffTomlService: TOML file content successfully read, parsing...`),this.parseContent(e.value))}parseContent(t){let n=Bun.TOML.parse(t);return e.isCliffToml(n)?(S.verbose(`CliffTomlService: TOML parsed and validated as CliffToml`),s(n)):a(C({message:`CliffTomlService: Parsed TOML is not a valid CliffToml`,code:`INVALID`}))}static isCliffToml(t){return e.isObject(t)}static isObject(e,t){return typeof e==`object`&&e?e.constructor===(t??Object):!1}},rt=class{id=`publish-github-release`;description=`Publishes the release on GitHub.`;getDependencies(){return[A(R)]}shouldExecute(e){return e.getConfig().skipGitHubRelease?s(!1):s(!0)}execute(e){let t=e.getConfig(),n=e.get(`changelogContent`),r=``;n.isErr()?S.warn(`Changelog content is not available. Proceeding with an empty changelog.`):r=n.value;let i=Ee.getInstance(),a=nt.getInstance(e.getBasePath()),s=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}),c=s.releaseTitle(e.getConfig().releaseTitle),l=s.tagName(e.getConfig().tagName),u=new tt(a),d=[t.releaseDraft?`draft`:null,t.releasePreRelease?`pre-release`:null,t.releaseLatest?`latest`:null].filter(e=>e!==null).join(`, `)||`normal`;S.info(`Publishing a ${p.gray(d)} GitHub release.`);let f=e=>j(i.release.createRelease({title:c,tag:l,content:e,latest:t.releaseLatest,draft:t.releaseDraft,prerelease:t.releasePreRelease,dryRun:t.dryRun}));return r.trim()?j(u.process(r)).andThen(e=>{if(e.isErr())return o(e.error);process.env.FIREFLY_DEBUG_SHOW_CHANGELOG_CONTENT&&S.verbose(`PublishGitHubReleaseTask: Postprocessed changelog content:\n${e.value}\n`);let t=e.value;return e.value.trim()===``&&(S.warn(`Changelog post-processing resulted in an empty changelog. Proceeding with an empty changelog.`),t=``),f(t)}).map(()=>{S.success(`Pushed GitHub release to remote repository.`)}):f(``).map(()=>{S.success(`Pushed GitHub release to remote repository.`)})}},R=class{id=`platform-publish-controller`;description=`Controls the flow for platform publish based on configuration.`;getDependencies(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit?[A(Y)]:t?.skipGitHubRelease?[]:t?.skipGit?[A(X)]:t?.skipPush?[A(F)]:[A(N)]}shouldExecute(e){return(e?.getConfig()).skipGitHubRelease?s(!1):s(!0)}getNextTasks(e){return e.getConfig().skipGitHubRelease?s([]):s([A(rt)])}execute(e){return c()}},z=class{id=`git-flow-controller`;description=`Controls the flow for git operations based on configuration.`;getDependencies(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit||t?.skipChangelog?[A(Y)]:[A(X)]}shouldExecute(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit?s(!1):s(!0)}getNextTasks(e){return e.getConfig().skipGit?s([A(R)]):s([A(I)])}getSkipThroughTasks(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit?s([A(R)]):s([])}execute(e){return c()}},it=class e{static COMMIT_MESSAGE_PATTERNS={BREAKING:/^(\w*)(?:\((.*)\))?!: (.*)$/,CONVENTIONAL:/^(\w*)(?:\((.*)\))?: (.*)$/,REVERT:/^Revert "(.+)"\s*\[([a-f0-9]+)\]$/};static EXTRACTION_PATTERNS={BREAKING_CHANGE:/BREAKING CHANGE:\s*(.+?)(?=\n\n|\n[A-Z]|$)/gs,MENTION:/@([a-zA-Z0-9_-]+)/g,REFERENCE:/(fixes?|closes?|resolves?)\s+#(\d+)|#(\d+)/gi};gitProvider;constructor(e){this.gitProvider=e??D.getInstance()}async getCommitsSinceLastTag(){S.verbose(`CommitHistoryService: Retrieving commits since last tag...`);let e=await this.gitProvider.history.lastTagOrNull();if(e.isErr())return a(e.error);let t=e.value;S.verbose(`CommitHistoryService: Last tag is: ${t||`none`}`);let n=await this.gitProvider.history.commitsSince(t);if(n.isErr())return a(n.error);let r=n.value;if(S.verbose(`CommitHistoryService: Found ${r.length} commits since last tag.`),r.length===0)return S.verbose(`CommitHistoryService: No new commits found since last tag.`),s([]);let i=await this.parseCommitDetails(r);return i.isErr()?a(i.error):(S.verbose(`CommitHistoryService: Successfully parsed ${i.value.length} commits`),s(i.value))}async getAllCommits(){S.verbose(`CommitHistoryService: Retrieving all commits...`);let e=await this.gitProvider.history.commitsSince(null);if(e.isErr())return a(e.error);let t=e.value;if(S.verbose(`CommitHistoryService: Found ${t.length} total commits.`),t.length===0)return S.verbose(`CommitHistoryService: No commits found in repository.`),s([]);let n=await this.parseCommitDetails(t);return n.isErr()?a(n.error):(S.verbose(`CommitHistoryService: Successfully parsed ${n.value.length} commits`),s(n.value))}async parseCommitDetails(e){let t=[],n=e.map(async e=>{let t=await this.gitProvider.history.commitDetails(e,!1);return{hash:e,result:t}}),r=await Promise.all(n);for(let{hash:e,result:n}of r){if(n.isErr())return a(n.error);let r=this.parseCommitFromRaw(n.value,e);if(r.isErr())return a(r.error);t.push(r.value)}return s(t)}parseCommitFromRaw(e,t){if(!e||typeof e!=`string`)return a(C({code:`INVALID`,message:`Invalid commit details for ${t}`,source:`CommitHistoryService.parseCommitFromRaw`}));let n=this.extractCommitFields(e),r=this.analyzeCommitMessage(n.subject),i=this.extractRevertInfo(n.subject),o=this.extractBreakingChangeNotes(n.body,n.notes),c=this.extractMentions(n.body),l=this.extractReferences(n.body),u={hash:t,date:n.date||null,author:n.author||null,header:n.subject||null,body:n.body||null,footer:null,type:r.type,scope:r.scope,subject:r.subject,merge:null,revert:i,notes:o,mentions:c,references:l};return s(u)}extractCommitFields(e){let t=e.trim().split(`
|
|
16
|
+
`),n={};for(let e of t){let t=e.indexOf(`:`);if(t===-1)continue;let r=e.substring(0,t);n[r]=e.substring(t+1)}return{subject:n.subject||``,body:n.body||``,author:n.author||``,date:n.date||``,notes:n.notes||``}}analyzeCommitMessage(t){let n=t.match(e.COMMIT_MESSAGE_PATTERNS.BREAKING);if(n)return{type:n[1]||null,scope:n[2]||null,subject:n[3]||null};let r=t.match(e.COMMIT_MESSAGE_PATTERNS.CONVENTIONAL);return r?{type:r[1]||null,scope:r[2]||null,subject:r[3]||null}:{type:null,scope:null,subject:t||null}}extractRevertInfo(t){let n=t.match(e.COMMIT_MESSAGE_PATTERNS.REVERT);return n?{header:n[1]||null,hash:n[2]||null}:null}extractBreakingChangeNotes(t,n){let r=[],i=`${t}\n${n}`,a=e.EXTRACTION_PATTERNS.BREAKING_CHANGE.exec(i);for(;a!==null;){let t=a[1];t&&r.push({title:`BREAKING CHANGE`,text:t.trim()}),a=e.EXTRACTION_PATTERNS.BREAKING_CHANGE.exec(i)}return r}extractMentions(t){let n=[],r=e.EXTRACTION_PATTERNS.MENTION.exec(t);for(;r!==null;){let i=r[1];i&&n.push(i),r=e.EXTRACTION_PATTERNS.MENTION.exec(t)}return n}extractReferences(t){let n=[],r=e.EXTRACTION_PATTERNS.REFERENCE.exec(t);for(;r!==null;){let i=r[1]||null,a=r[2]||r[3];a&&n.push({raw:r[0],action:i?.toLowerCase()||null,owner:null,repository:null,issue:a,prefix:`#`}),r=e.EXTRACTION_PATTERNS.REFERENCE.exec(t)}return n}},at=class e{static VERSION_LEVELS={MAJOR:0,MINOR:1,PATCH:2};static RELEASE_TYPES={[e.VERSION_LEVELS.MAJOR]:`major`,[e.VERSION_LEVELS.MINOR]:`minor`,[e.VERSION_LEVELS.PATCH]:`patch`};static DEFAULT_CONFIGURATION={major:[`revert`],minor:[`feat`,`feature`],patch:[`fix`,`perf`,`refactor`,`style`,`test`,`build`,`ci`,`chore`,`docs`,`security`],scopeRules:{deps:`patch`,dependencies:`patch`,security:`patch`,api:`minor`,breaking:`major`,"breaking-change":`major`}};static TRANSITION_KEYWORDS=[`general availability`,`promote to stable`,`move to stable`];static PATTERN_MATCHERS={BREAKING_HEADER:/^[a-zA-Z]+(?:\([^)]*\))?!:/,SCOPE_HEADER:/^[a-zA-Z]+\(([^)]+)\)[:!]/};configuration;constructor(e={}){this.configuration=this.mergeConfiguration(e)}analyzeCommits(e){S.verbose(`SemanticVersionAnalyzer: Starting commit analysis for version recommendation...`);let t=Date.now(),n=this.validateCommitsInput(e);if(n.isErr())return a(n.error);if(e.length===0)return S.verbose(`SemanticVersionAnalyzer: No commits provided, returning patch recommendation.`),s(this.createDefaultPatchRecommendation([]));let r=this.performDetailedAnalysis(e),i=this.determineVersionLevel(r),o=this.buildVersionRecommendation(i,e,r),c=Date.now()-t;return S.verbose(`SemanticVersionAnalyzer: Analysis completed in ${c}ms. Recommendation: ${o.releaseType}`),s(o)}mergeConfiguration(t){return{major:[...e.DEFAULT_CONFIGURATION.major,...t.major??[]],minor:[...e.DEFAULT_CONFIGURATION.minor,...t.minor??[]],patch:[...e.DEFAULT_CONFIGURATION.patch,...t.patch??[]],scopeRules:{...e.DEFAULT_CONFIGURATION.scopeRules,...t.scopeRules}}}validateCommitsInput(e){return Array.isArray(e)?s(void 0):a(C({code:`INVALID`,message:`Commits input must be an array`,source:`SemanticVersionAnalyzer.validateCommitsInput`}))}performDetailedAnalysis(e){S.verbose(`SemanticVersionAnalyzer: Performing detailed commit analysis...`);let t=e.reduce((e,t)=>{let n=t.type?.toLowerCase()||`unknown`;return e.commitsByType[n]||(e.commitsByType[n]=[]),e.commitsByType[n].push(t),{breakingChanges:e.breakingChanges+this.countBreakingChanges(t),features:e.features+(this.isFeatureCommit(t)?1:0),patches:e.patches+(this.isPatchCommit(t)?1:0),scopedBreaking:[...e.scopedBreaking,...this.analyzeScopeBreaking(t)],hasPreReleaseTransition:e.hasPreReleaseTransition||this.detectPreReleaseTransition(t),commitsByType:e.commitsByType}},{breakingChanges:0,features:0,patches:0,scopedBreaking:[],hasPreReleaseTransition:!1,commitsByType:{}});return S.verbose(`SemanticVersionAnalyzer: Analysis results - Breaking: ${t.breakingChanges}, Features: ${t.features}, Patches: ${t.patches}`),t}countBreakingChanges(e){let t=0;return t+=e.notes?.length??0,this.hasBreakingHeader(e)&&(t+=1),t}hasBreakingHeader(t){return t.header?e.PATTERN_MATCHERS.BREAKING_HEADER.test(t.header):!1}isFeatureCommit(e){let t=e.type?.toLowerCase()??``;return this.configuration.minor.includes(t)}isPatchCommit(e){let t=e.type?.toLowerCase()??``;return this.configuration.patch.includes(t)}analyzeScopeBreaking(e){let t=this.extractCommitScope(e);return t&&this.configuration.scopeRules[t.toLowerCase()]===`major`?[t]:[]}extractCommitScope(t){return t.scope?t.scope:t.header?t.header.match(e.PATTERN_MATCHERS.SCOPE_HEADER)?.[1]??null:null}detectPreReleaseTransition(t){let n=t.header?.toLowerCase()??``,r=t.body?.toLowerCase()??``;return e.TRANSITION_KEYWORDS.some(e=>n.includes(e)||r.includes(e))}determineVersionLevel(t){return S.verbose(`SemanticVersionAnalyzer: Determining version level from analysis...`),t.breakingChanges>0||t.scopedBreaking.length>0?(S.verbose(`SemanticVersionAnalyzer: Breaking changes detected, recommending MAJOR version bump.`),e.VERSION_LEVELS.MAJOR):t.features>0?(S.verbose(`SemanticVersionAnalyzer: New features detected, recommending MINOR version bump.`),e.VERSION_LEVELS.MINOR):t.patches>0?(S.verbose(`SemanticVersionAnalyzer: Patch-level changes detected, recommending PATCH version bump.`),e.VERSION_LEVELS.PATCH):(S.verbose(`SemanticVersionAnalyzer: No significant changes detected, defaulting to PATCH version bump.`),e.VERSION_LEVELS.PATCH)}buildVersionRecommendation(t,n,r){return S.verbose(`SemanticVersionAnalyzer: Building version recommendation...`),{level:t,releaseType:e.RELEASE_TYPES[t],commits:[...n],reason:this.generateRecommendationReason(r),analysis:r}}createDefaultPatchRecommendation(t){let n={breakingChanges:0,features:0,patches:0,scopedBreaking:[],hasPreReleaseTransition:!1,commitsByType:{}};return{level:e.VERSION_LEVELS.PATCH,releaseType:`patch`,commits:[...t],reason:`No commits provided, defaulting to patch increment for safety`,analysis:n}}generateRecommendationReason(e){let t=[];if(e.breakingChanges>0){let n=e.breakingChanges===1?`change`:`changes`;t.push(`${e.breakingChanges} breaking ${n}`)}if(e.scopedBreaking.length>0){let n=e.scopedBreaking.join(`, `);t.push(`breaking scope(s): ${n}`)}if(e.features>0){let n=e.features===1?`feature`:`features`;t.push(`${e.features} new ${n}`)}if(e.patches>0){let n=e.patches===1?`fix`:`fixes`;t.push(`${e.patches} ${n}`)}return e.hasPreReleaseTransition&&t.push(`pre-release transition detected`),t.length===0?`No significant changes detected, defaulting to patch increment`:`Analysis found: ${t.join(`, `)}`}},ot=class{gitProvider;commitHistoryService;versionAnalyzer;configuration;constructor(e={}){this.gitProvider=D.getInstance(),this.commitHistoryService=new it(this.gitProvider),this.versionAnalyzer=new at({major:e.additionalCommitTypes?.major,minor:e.additionalCommitTypes?.minor,patch:e.additionalCommitTypes?.patch,scopeRules:e.scopeRules}),this.configuration={includeAllCommitsWhenNoTags:!1,...e}}async recommendVersion(){S.verbose(`SemanticVersionService: Starting version recommendation process...`);let e=Date.now(),t=await this.getRelevantCommits();if(t.isErr())return a(t.error);let n=t.value;if(S.verbose(`SemanticVersionService: Analyzing ${n.length} commits for version recommendation`),n.length===0)return S.verbose(`SemanticVersionService: No commits found, returning default patch recommendation`),s(this.createDefaultRecommendation());let r=this.versionAnalyzer.analyzeCommits(n);if(r.isErr())return a(r.error);let i=r.value,o=Date.now()-e;return S.verbose(`SemanticVersionService: Version recommendation completed in ${o}ms. Recommendation: ${i.releaseType} (level ${i.level})`),s(i)}async getCommitsSinceLastTag(){return S.verbose(`SemanticVersionService: Retrieving commits since last tag...`),this.commitHistoryService.getCommitsSinceLastTag()}async getAllCommits(){return S.verbose(`SemanticVersionService: Retrieving all commits...`),this.commitHistoryService.getAllCommits()}async getLastTag(){return S.verbose(`SemanticVersionService: Getting last git tag...`),this.gitProvider.history.lastTagOrNull()}async hasAnyTags(){S.verbose(`SemanticVersionService: Checking if repository has any tags...`);let e=await this.getLastTag();return e.isErr()?a(e.error):s(e.value!==null)}analyzeCommitsOnly(e){return S.verbose(`SemanticVersionService: Analyzing provided ${e.length} commits without fetching from git`),this.versionAnalyzer.analyzeCommits(e)}async getRelevantCommits(){let e=await this.hasAnyTags();return e.isErr()?a(e.error):e.value?(S.verbose(`SemanticVersionService: Retrieving commits since last tag`),this.commitHistoryService.getCommitsSinceLastTag()):(S.verbose(`SemanticVersionService: No tags found in repository`),this.configuration.includeAllCommitsWhenNoTags?(S.verbose(`SemanticVersionService: Configuration set to include all commits when no tags exist`),this.commitHistoryService.getAllCommits()):(S.verbose(`SemanticVersionService: Configuration set to return empty commits when no tags exist`),s([])))}createDefaultRecommendation(){return{level:2,releaseType:`patch`,commits:[],reason:`No commits available for analysis, defaulting to patch increment`,analysis:{breakingChanges:0,features:0,patches:0,scopedBreaking:[],hasPreReleaseTransition:!1,commitsByType:{}}}}},B=class e{_raw;_parsed;constructor(e,t){this._raw=e,this._parsed=t}static from(t){let n=h.clean(t);if(!n)return a(C({code:`INVALID`,message:`"${t}" is not a valid semantic version.`}));let r=h.parse(n);return r?s(new e(n,r)):a(C({code:`INVALID`,message:`Failed to parse semantic version "${n}".`}))}static fromClean(t){let n=h.parse(t);return n?s(new e(t,n)):a(C({code:`INVALID`,message:`Expected clean version but got invalid: ${t}`}))}get raw(){return this._raw}get major(){return this._parsed.major}get minor(){return this._parsed.minor}get patch(){return this._parsed.patch}get isPrerelease(){return this._parsed.prerelease.length>0}get prerelease(){return this._parsed.prerelease}get prereleaseIdentifier(){if(!this.isPrerelease)return null;let e=this._parsed.prerelease[0];return typeof e==`string`?e:null}get prereleaseNumber(){if(!this.isPrerelease)return null;let e=this._parsed.prerelease.at(-1);return typeof e==`number`?e:null}get build(){return this._parsed.build}toString(){return this._raw}equals(e){return h.eq(this._raw,e._raw)}compare(e){return h.compare(this._raw,e._raw)}isGreaterThan(e){return h.gt(this._raw,e._raw)}isLessThan(e){return h.lt(this._raw,e._raw)}satisfies(e){return h.satisfies(this._raw,e)}toStable(){let t=`${this.major}.${this.minor}.${this.patch}`;return e.fromClean(t)}},V=class e{static bumpVersion(t){let{currentVersion:n,releaseType:r,prereleaseIdentifier:i,prereleaseBase:o}=t;return r===`major`||r===`minor`||r===`patch`?e.bumpStandard(n,r):r===`premajor`||r===`preminor`||r===`prepatch`?e.bumpPreStandard(n,r,i,o):r===`prerelease`?e.bumpPrerelease(n,i,o):r===`graduate`?e.graduatePrerelease(n):a(C({code:`INVALID`,message:`Unsupported release type: ${r}`}))}static bumpStandard(e,t){let n=e.raw;if(e.isPrerelease){let t=e.toStable();if(t.isErr())return a(t.error);n=t.value.raw}let r=h.inc(n,t);return r?B.fromClean(r):a(C({code:`INVALID`,message:`Failed to bump ${t} version from '${n}'.`}))}static bumpPreStandard(t,n,r,i){let o=e.normalizeBase(i);if(o.isErr())return a(o.error);let s=o.value,c=null;return c=s===void 0?r?h.inc(t.raw,n,r):h.inc(t.raw,n):r?h.inc(t.raw,n,r,s):h.inc(t.raw,n,void 0,s),c?B.fromClean(c):a(C({code:`INVALID`,message:`Failed to bump ${n} version from '${t.raw}' with identifier '${r}' and base '${i}'.`}))}static bumpPrerelease(t,n,r){let i=null;if(e.isComplexIdentifier(n))i=e.bumpWithComplexIdentifier(t,n);else if(r!=null){let o=e.normalizeBase(r);if(o.isErr())return a(o.error);let s=o.value;i=n?h.inc(t.raw,`prerelease`,n,s):h.inc(t.raw,`prerelease`,void 0,s)}else if(t.isPrerelease)i=e.bumpExistingPrerelease(t,n);else{let e=n||`alpha`;i=h.inc(t.raw,`prerelease`,e)}return i?B.fromClean(i):a(C({code:`INVALID`,message:`Failed to bump prerelease version from '${t.raw}' with identifier '${n}' and base '${r}'.`}))}static graduatePrerelease(e){if(!e.isPrerelease)return a(C({code:`INVALID`,message:`Cannot graduate non-prerelease version '${e.raw}'. Only prerelease versions can be graduated.`}));let t=e.toStable();if(t.isErr())return a(t.error);let n=t.value;return s(n)}static normalizeBase(e){return e==null?s(void 0):e===`0`||e===`1`?s(e):typeof e==`number`&&(e===0||e===1)?s(e.toString()):a(C({code:`INVALID`,message:`Invalid prerelease base '${e}'. Must be "0", "1", 0, or 1.`}))}static isComplexIdentifier(e){return typeof e==`string`&&e.includes(`.`)}static bumpWithComplexIdentifier(e,t){return t?h.inc(e.raw,`prerelease`,t,!1):h.inc(e.raw,`prerelease`,void 0,`0`)}static bumpExistingPrerelease(e,t){return t?h.inc(e.raw,`prerelease`,t):h.inc(e.raw,`prerelease`)}},st=class e{static TRANSITION_KEYWORDS=[`stable`,`release`,`production`,`final`,`ga`,`general availability`,`promote to stable`,`move to stable`,`release candidate`,`rc`];static LEVEL_TO_RELEASE_TYPE={0:`major`,1:`minor`,2:`patch`};static decideNextVersion(t,n){S.verbose(`VersionResolverService: Deciding next version...`);let r=e.analyzePreReleaseContext(t.currentVersion,n);return t.releaseType===`prerelease`?(S.verbose(`VersionResolverService: Handling prerelease request...`),e.handlePreReleaseRequest(t,r)):r.isCurrentPreRelease&&r.hasStableTransition?(S.verbose(`VersionResolverService: Handling pre-release to stable transition...`),e.handlePreReleaseToStableTransition(t,n)):n?(S.verbose(`VersionResolverService: Handling recommendation-based versioning...`),e.createRecommendationBasedVersion(t,n,r)):(S.verbose(`VersionResolverService: Handling standard version bump...`),e.bumpVersion(t))}static analyzePreReleaseContext(t,n){let r=t.isPrerelease,i=t.prereleaseIdentifier,a=e.detectStableTransition(n);return{isCurrentPreRelease:r,prereleaseIdentifier:i,hasStableTransition:a}}static detectStableTransition(t){if(!t)return!1;let n=t.reason.toLowerCase();return e.TRANSITION_KEYWORDS.some(e=>n.includes(e))}static handlePreReleaseRequest(e,t){let n={currentVersion:e.currentVersion,releaseType:`prerelease`,prereleaseIdentifier:e.prereleaseIdentifier||t.prereleaseIdentifier||`alpha`,prereleaseBase:e.prereleaseBase};return S.verbose(`VersionResolverService: Bumping to prerelease version...`),V.bumpVersion(n)}static handlePreReleaseToStableTransition(t,n){if(!n)return a(C({code:`INVALID`,message:`Cannot transition to stable version without recommendation`}));let r=V.bumpVersion({currentVersion:t.currentVersion,releaseType:`graduate`});if(r.isErr())return a(r.error);let i=r.value;if(n.level<2){S.verbose(`VersionResolverService: Further bumping after graduation...`);let t=e.LEVEL_TO_RELEASE_TYPE[n.level];return V.bumpVersion({currentVersion:i,releaseType:t})}return S.verbose(`VersionResolverService: Graduated to stable version:`,i.raw),s(i)}static createRecommendationBasedVersion(t,n,r){let i=e.LEVEL_TO_RELEASE_TYPE[n.level];if(r.isCurrentPreRelease&&!r.hasStableTransition){S.verbose(`VersionResolverService: Continuing prerelease versioning...`);let e={currentVersion:t.currentVersion,releaseType:`prerelease`,prereleaseIdentifier:t.prereleaseIdentifier||r.prereleaseIdentifier||`alpha`,prereleaseBase:t.prereleaseBase};return V.bumpVersion(e)}return S.verbose(`VersionResolverService: Bumping version based on recommendation...`),e.bumpVersion({...t,releaseType:i})}static bumpVersion(e){if(!e.releaseType)return a(C({code:`INVALID`,message:`Release type is required for version bump`}));let t={currentVersion:e.currentVersion,releaseType:e.releaseType,prereleaseIdentifier:e.prereleaseIdentifier,prereleaseBase:e.prereleaseBase};return V.bumpVersion(t)}};const ct=r.fromThrowable(JSON.parse,e=>C(w(e))),lt=e.object({name:e.string().optional(),version:e.string().optional()}).catchall(e.unknown());var H=class e{static instance=null;static VERSION_REGEX=/^(\s*"version"\s*:\s*)"[^"]*"(.*)$/m;pathToPackageJson;constructor(e){this.pathToPackageJson=e}static getInstance(t){return e.instance||=new e(d(t,`package.json`)),e.instance}async read(){let e=await k.read(this.pathToPackageJson);return e.isErr()?o(e.error):this.parseAndValidatePackageJson(e.value)}async updateVersion(e,t){let n=await k.read(this.pathToPackageJson);if(n.isErr())return o(n.error);let r=this.replaceVersionInContent(n.value,e),i=await k.write(this.pathToPackageJson,r,t);return i.isErr()?o(i.error):(S.verbose(`PackageJsonService: Updated version to ${e} in ${this.pathToPackageJson}`),this.verifyVersionUpdate(e,t))}parseAndValidatePackageJson(e){let t=ct(e);if(t.isErr())return o(t.error);let n=M(lt,t.value);return n.isErr()?o(n.error):c(n.value)}replaceVersionInContent(t,n){return t.replace(e.VERSION_REGEX,`$1"${n}"$2`)}async verifyVersionUpdate(e,t){let n=await this.read();return n.isErr()?o(n.error):t?(S.verbose(`PackageJsonService: Dry run mode enabled, not verifying version update.`),c()):n.value.version===e?c():o(C({code:`INVALID`,message:`Version verification failed. Expected version: ${e}, but found: ${n.value.version}`,source:`filesystem/package-json-service`}))}},U=class{id=`bump-version`;description=`Writes the new version to package.json.`;previousVersion=``;isEntryPoint(){return!1}getDependents(){return[]}getDependencies(){return[]}shouldExecute(e){let t=e.getConfig();return s(!t.skipBump)}getNextTasks(){return s([A(Y)])}execute(e){this.previousVersion=e.getCurrentVersion();let t=e.getBasePath(),n=e.getNextVersion(),r=e.getConfig().dryRun,a=H.getInstance(t).updateVersion(n,r);return S.info(`Updating version...`),i.fromPromise(a,w).andThen(()=>c()).andTee(()=>[S.success(`Version updated to ${p.cyanBright(n)}`)])}canUndo(){return!0}undo(e){if(!this.previousVersion)return o(C({code:`NOT_FOUND`,message:`Previous version not found, cannot undo version bump.`}));let t=e.getBasePath(),n=e.getConfig().dryRun,r=H.getInstance(t).updateVersion(this.previousVersion,n);return i.fromPromise(r,w).andThen(()=>c())}},W=class{id=`initialize-current-version`;description=`Loads the current version from package.json or initializes it to 0.0.0.`;getDependencies(){return[]}shouldExecute(){return s(!0)}getSkipThroughTasks(){return s([A(J)])}canUndo(){return!1}execute(e){S.verbose(`InitializeCurrentVersionTask: Initializing current version...`);let t=e.getBasePath(),n=H.getInstance(t);return i.fromPromise(n.read(),w).andThen(t=>{let n=t.isErr()||!t.value.version?`0.0.0`:t.value.version;return S.verbose(`InitializeCurrentVersionTask: Current version is "${n}"`),S.info(`Current version is ${p.cyanBright(n)}`),e.set(`currentVersion`,n),c()})}},ut=class{constructor(e){this.versionChoicesService=e}async run(e){if(!e.currentVersion)return a(C({code:`INVALID`,message:`Current version is required to generate version choices`,source:`semver/version-choice-prompter`}));S.verbose(`VersionChoicePrompter: Generating version choices...`);let t=this.versionChoicesService.createVersionChoices(e);if(t.isErr())return a(t.error);let n=t.value;if(n.length===0)return a(C({code:`NOT_FOUND`,message:`No version choices available`,source:`semver/version-choice-prompter`}));S.verbose(`VersionChoicePrompter: Prompting user for version selection.`);let r=await this.prompt(n);if(r.isErr())return a(r.error);S.level!==m.verbose&&S.log(``);let i=r.value;return!i||i===``?a(C({code:`INVALID`,message:`No version selected`,source:`semver/version-choice-prompter`})):(S.verbose(`VersionChoicePrompter: User selected version: '${i}'`),s(i))}async prompt(e){let t=e[0];if(!t)return a(C({code:`NOT_FOUND`,message:`No default version choice found`,source:`semver/version-choice-prompter`}));let n=await this.createPrompter(e,t.value);return n.isErr()?a(n.error):(S.level===m.verbose&&n.andTee(()=>S.log(``)),n.andThen(t=>this.validateVersion(t,e)))}createPrompter(e,t){let n=S.prompt(`Select version bump`,{type:`select`,options:e,initial:t,cancel:`reject`});return i.fromPromise(n,e=>C(w(e)))}validateVersion(e,t){let n=t.map(e=>e.value);return n.includes(e)?s(e):a(C({code:`INVALID`,message:`Invalid version selected: ${e}. Valid options: ${n.join(`, `)}`,source:`semver/version-choice-prompter`}))}},dt=class e{static VERSION_TYPES={RELEASE:[`patch`,`minor`,`major`],PRERELEASE:[`prepatch`,`preminor`,`premajor`],CONTINUATION:[`prerelease`],GRADUATION:[`graduate`]};static VERSION_CHOICES={latestIsPreRelease:[...e.VERSION_TYPES.CONTINUATION,...e.VERSION_TYPES.GRADUATION,...e.VERSION_TYPES.RELEASE],preRelease:e.VERSION_TYPES.PRERELEASE,default:[...e.VERSION_TYPES.RELEASE,...e.VERSION_TYPES.PRERELEASE]};static VERSION_DESCRIPTIONS={patch:`Fixes and minor enhancements without breaking compatibility. Suitable for bug fixes and small improvements.`,minor:`New, backward-compatible functionality. Adds features that do not break existing APIs.`,major:`Incompatible API changes. Introduces breaking changes or removes deprecated features.`,prepatch:`Unstable patch release candidate. Used for testing patch changes before a stable release.`,preminor:`Unstable minor release candidate. Used for previewing new features before a minor release.`,premajor:`Unstable major release candidate. Used for testing breaking changes before a major release.`,prerelease:`Unstable pre-release continuation. Increments the pre-release number or changes identifier.`,graduate:`Promote pre-release to stable. Removes pre-release identifiers to create a stable version.`};createVersionChoices(e){S.verbose(`VersionChoicesService: Creating version choices for '${e.currentVersion.raw}'...`);let t=this.determineAvailableVersionTypes(e.currentVersion,e.releaseType).map(t=>this.createVersionChoice({currentVersion:e.currentVersion,releaseType:t,prereleaseIdentifier:e.prereleaseIdentifier,prereleaseBase:e.prereleaseBase})),n=r.combine(t);return n.isErr()?a(n.error):(S.verbose(`VersionChoicesService: Created ${n.value.length} version choices.`),s(n.value))}determineAvailableVersionTypes(t,n){return n===void 0?t.isPrerelease?e.VERSION_CHOICES.latestIsPreRelease:e.VERSION_CHOICES.default:this.getVersionTypesForReleaseType(n)}getVersionTypesForReleaseType(t){return t===`prerelease`?e.VERSION_CHOICES.preRelease:e.VERSION_CHOICES.default}createVersionChoice(e){let t=this.computeNewVersion(e);if(t.isErr())return a(t.error);let n=t.value,r=e.releaseType||`patch`,i={label:`${r} (${n.raw})`,hint:this.getVersionDescription(r),value:n.raw};return s(i)}computeNewVersion(e){if(!e.releaseType)return a(C({code:`INVALID`,message:`Release type is required to compute new version`}));let t={currentVersion:e.currentVersion,releaseType:e.releaseType,prereleaseIdentifier:e.prereleaseIdentifier,prereleaseBase:e.prereleaseBase};return V.bumpVersion(t)}getVersionDescription(t){return e.VERSION_DESCRIPTIONS[t]??``}},G=class{id=`prompt-manual-version`;description=`Prompts the user to manually enter the desired version`;getDependencies(){return[A(K)]}shouldExecute(e){let t=e.getConfig();return s(t.bumpStrategy===y)}getNextTasks(){return s([A(U)])}execute(e){let t=e.get(`currentVersion`);if(t.isErr())return o(t.error);let n=B.from(t.value||``);if(n.isErr())return o(n.error);let r=new ut(new dt),a=e.getConfig(),s={currentVersion:n.value,releaseType:a.releaseType,prereleaseIdentifier:a.preReleaseId,prereleaseBase:a.preReleaseBase};return i.fromPromise(r.run(s),e=>w(e)).andThen(t=>t.isErr()?o(t.error):(e.setNextVersion(t.value),S.verbose(`PromptManualVersionTask: From '${n.value.raw}' to '${t.value}'`),c()))}},K=class{id=`execute-bump-strategy`;description=`Executes the selected bump strategy to determine the new version.`;getDependencies(){return[A(W)]}shouldExecute(e){let t=e.getConfig(),n=!t.releaseType&&!!t.bumpStrategy;return s(n)}getNextTasks(e){let t=e.getConfig().bumpStrategy;return s(t===y?[A(G)]:t===v?[A(q)]:[])}getSkipThroughTasks(e){let t=e.getConfig().bumpStrategy;return s(t===y?[A(G)]:t===v?[A(q)]:[A(U)])}execute(){return c()}},q=class{id=`automatic-bump`;description=`Uses semantic analysis to determine the next version bump`;getDependencies(){return[A(K)]}shouldExecute(e){let t=e.getConfig();return s(t.bumpStrategy===v)}getNextTasks(){return s([A(U)])}execute(e){let t=B.from(e.getCurrentVersion());if(t.isErr())return o(t.error);let n={currentVersion:t.value,releaseType:e.getConfig().releaseType,prereleaseIdentifier:e.getConfig().preReleaseId,prereleaseBase:e.getConfig().preReleaseBase},r=new ot;return i.fromPromise(r.recommendVersion(),w).andThen(r=>{if(r.isErr())return o(r.error);let{reason:i}=r.value;if(i)if(i.startsWith(`Analysis found:`)){let e=i.slice(15).trim();S.info(`Analysis found: ${p.bold(e)}`)}else S.info(i);let a=st.decideNextVersion(n,r.value);return a.isErr()?o(a.error):(e.setNextVersion(a.value.raw),S.verbose(`AutomaticBumpTask: From '${t.value.raw}' to '${a.value.raw}'`),c())})}},ft=class e{static STRATEGIES=[{label:`Automatic Bump`,value:v,hint:`Determines the next version based on conventional commits history`},{label:`Manual Bump`,value:y,hint:`Manually specify the next version`}];async run(){let t=e.STRATEGIES[1];if(!t)return a(C({code:`NOT_FOUND`,message:`No default version bump strategy found`,source:`semver/version-strategy-prompter-service`}));S.verbose(`BumpStrategyPrompter: Prompting user for version bump strategy.`);let n=await this.prompt(t.value);if(n.isErr())return a(n.error);S.level!==m.verbose&&S.log(``);let r=n.value;return!r||r===``?a(C({code:`INVALID`,message:`No version bump strategy selected`,source:`semver/version-strategy-prompter-service`})):(S.verbose(`BumpStrategyPrompter: User selected version bump strategy: '${r}'`),s(r))}async prompt(e){let t=await this.createPrompter(e);return t.isErr()?a(t.error):(S.level===m.verbose&&t.andTee(()=>S.log(``)),t.andThen(e=>this.validateStrategy(e)))}createPrompter(t){let n=S.prompt(`Select version bump strategy`,{type:`select`,options:e.STRATEGIES,initial:t,cancel:`reject`});return i.fromPromise(n,e=>C(w(e)))}validateStrategy(t){return e.STRATEGIES.map(e=>e.value).includes(t)?s(t):a(C({code:`INVALID`,message:`Invalid version bump strategy: ${t}`,source:`semver/version-strategy-prompter-service`}))}},pt=class{id=`prompt-bump-strategy`;description=`Prompts the user to select a bump strategy (manual or automatic) if none is specified.`;getDependencies(){return[A(W)]}shouldExecute(e){let t=e.getConfig();return s(!(t.bumpStrategy||t.releaseType))}getNextTasks(){return s([A(K)])}getSkipThroughTasks(){return s([A(K)])}execute(e){let t=new ft;return i.fromPromise(t.run(),e=>w(e)).andThen(t=>{let n=e.getConfig();return t.isErr()?o(t.error):(n.bumpStrategy=t.value,c())})}},mt=class{id=`straight-bump`;description=`Handles version bump from provided release type.`;getDependencies(){return[A(W)]}shouldExecute(e){return e.getConfig().releaseType===void 0?s(!1):s(!0)}getNextTasks(){return s([A(U)])}getSkipThroughTasks(e){return e.getConfig().skipBump?s([A(Y)]):s([A(J)])}execute(e){let t=B.from(e.getCurrentVersion());if(t.isErr())return o(t.error);let n={currentVersion:t.value,releaseType:e.getConfig().releaseType,prereleaseIdentifier:e.getConfig().preReleaseId,prereleaseBase:e.getConfig().preReleaseBase},r=st.decideNextVersion(n);return r.isErr()?o(r.error):(e.setNextVersion(r.value.raw),S.verbose(`StraightBumpTask: From '${t.value.raw}' to '${r.value.raw}'`),c())}canUndo(){return!1}},J=class{id=`version-flow-controller`;description=`Controls the flow between version bump and subsequent tasks based on configuration.`;getDependencies(){return[A(W)]}shouldExecute(){return s(!0)}getNextTasks(e){let t=e.getConfig(),n=[];return t.releaseType===void 0?t.bumpStrategy||n.push(A(pt)):n.push(A(mt)),s(n)}canUndo(){return!1}execute(){return c()}},Y=class{id=`changelog-flow-controller`;description=`Controls the flow for changelog generation based on configuration.`;getDependencies(e){return e?.getConfig().skipBump?[A(J)]:[A(U)]}shouldExecute(e){let t=e?.getConfig();return t?.skipBump&&t?.skipChangelog&&t?.skipGit&&t?.skipGitHubRelease?s(!1):s(!0)}getNextTasks(e){return e.getConfig().skipChangelog?s([A(z)]):s([A(X)])}execute(e){return c()}},X=class{id=`generate-changelog`;description=`Generates the changelog based on the current release context.`;getDependencies(){return[A(Y)]}shouldExecute(e){let t=e.getConfig();return s(!t.skipChangelog)}getNextTasks(){return s([A(z)])}execute(e){let t=d(process.cwd(),e.getConfig().changelogPath||`CHANGELOG.md`),n=i.fromPromise(k.exists(t),w),r=Date.now(),a=new O().withContext({version:e.getNextVersion(),config:e.getConfig()}),s=new Xe(a);return n.andThen(n=>n.isErr()?o(n.error):n.value?(S.info(`Generating changelog...`),i.fromPromise(s.generateChangelog(e.getConfig()),w).andThen(t=>{if(t.isErr())return o(t.error);let n=Date.now()-r;return S.success(`Generation complete in ${p.greenBright(`${n}ms`)}`),process.env.FIREFLY_DEBUG_SHOW_CHANGELOG_CONTENT&&S.verbose(`GenerateChangelogTask: Generated changelog content:\n${t.value}\n`),e.set(`changelogContent`,t.value),c()})):k.write(t,``))}canUndo(){return!0}undo(e){let t=d(process.cwd(),e.getConfig().changelogPath||`CHANGELOG.md`);return e.get(`changelogContent`)?i.fromPromise(D.getInstance().commit.restoreFileToHead(t),w).andThen(()=>c()):o(w({code:`NOT_FOUND`,message:`Changelog content not found in context, cannot undo changelog generation.`}))}},ht=class e{static SCOPED_PACKAGE_REGEX=/^@[^/]+\//;gitProvider;packageJsonService;constructor(e){this.gitProvider=D.getInstance(),this.packageJsonService=H.getInstance(e)}async hydrateConfig(e){let t={...e},n=await this.hydrateFromGitRepository(t);if(n.isErr())return a(n.error);t=n.value;let r=await this.hydrateBranchFromGit(t);if(r.isErr())return a(r.error);t=r.value;let i=await this.hydrateFromPackageJson(t);return i.isErr()?a(i.error):(t=i.value,s(t))}async hydrateFromPackageJson(e){if(!this.packageJsonService)return a(C({code:`NOT_FOUND`,message:`packageJsonService is not available for hydration.`}));let t=await this.packageJsonService.read();if(t.isErr())return a(C({code:`NOT_FOUND`,message:`Could not find a valid package.json file in the current directory.`}));S.verbose(`ConfigHydratorService: package.json found, hydrating configuration...`);let n=t.value;if(!n)return a(C({code:`NOT_FOUND`,message:`package.json is empty or invalid`}));let r=this.hydrateFromPackageData(e,n);return r.isErr()?a(r.error):s(r.value)}async hydrateFromGitRepository(e){let t=await this.gitProvider.repository.isInsideWorkTree();return t.isErr()?a(t.error):t.value?(S.verbose(`ConfigHydratorService: Inside a Git repository, hydrating configuration...`),this.hydrateRepositoryFromGit(e)):a(C({code:`NOT_FOUND`,message:`Not inside a Git repository. Please run Firefly from within a valid Git project.`}))}async hydrateRepositoryFromGit(e){if(!this.gitProvider||e.repository&&e.repository.trim()!==``)return s(e);let t=await this.gitProvider.repository.getRepositoryUrl();if(t.isErr())return a(t.error);let n=this.gitProvider.repositoryParse.extractRepository(t.value);if(n.isErr())return a(n.error);let r=n.value,i=`${r.owner}/${r.repo}`;return S.verbose(`ConfigHydratorService: Auto-detected repository: ${i}`),s({...e,repository:i})}async hydrateBranchFromGit(e){if(!this.gitProvider)return s(e);if(e.branch&&e.branch.trim()!==``){let t=await this.gitProvider.branch.isProvidedBranchValid(e.branch);return t.isErr()?a(t.error):t.value?(S.verbose(`ConfigHydratorService: Using provided branch: ${e.branch}`),s(e)):a(C({code:`NOT_FOUND`,message:`The provided branch "${e.branch}" does not exist in the repository.`}))}let t=await this.gitProvider.branch.currentBranch();if(t.isErr())return a(t.error);let n=t.value;return S.verbose(`ConfigHydratorService: Auto-detected branch: ${n}`),s({...e,branch:n})}hydrateFromPackageData(e,t){let n={...e},r=this.hydrateNameFromPackageJson(n,t);if(r.isErr())return a(r.error);Object.assign(n,r.value);let i=this.hydrateScopeFromPackageJson(e,t);if(i.isErr())return a(i.error);Object.assign(n,i.value);let o=this.hydratePreReleaseIdFromPackageJson(e,t);return o.isErr()?a(o.error):(Object.assign(n,o.value),s(n))}hydratePreReleaseIdFromPackageJson(e,t){if(e.preReleaseId!==void 0&&e.preReleaseId.trim()!==``)return s({});if(t.version){let e=h.parse(t.version);if(!e)return a(C({code:`INVALID`,message:`Invalid version in package.json: ${t.version}`}));if(e.prerelease.length>0){let n=typeof e.prerelease[0]==`string`?e.prerelease[0]:``;return n?(S.verbose(`ConfigHydratorService: Auto-detected preReleaseId from package.json: ${n}`),s({preReleaseId:n})):a(C({code:`INVALID`,message:`package.json version "${t.version}" is a prerelease but has no valid identifier`}))}}return s({preReleaseId:`alpha`})}hydrateNameFromPackageJson(e,t){if(e.name===void 0&&!t.name)return a(C({code:`NOT_FOUND`,message:`Could not find a valid package name in package.json`}));if(e.name===void 0&&t.name){S.verbose(`ConfigHydratorService: hydrating name from package.json...`);let e=this.extractPackageName(t.name);return e.isErr()?a(e.error):(S.verbose(`ConfigHydratorService: hydrating name from package.json: ${t.name} -> ${e.value}`),s({name:e.value}))}return S.verbose(`ConfigHydratorService: name explicitly provided in config: "${e.name}"`),s({})}hydrateScopeFromPackageJson(e,t){if(Object.hasOwn(e,`scope`)&&e.scope!==void 0)return S.verbose(`ConfigHydratorService: Scope explicitly provided in config: "${e.scope}" - not hydrating from package.json`),s({});if(t.name&&this.isScopedPackage(t.name)){let e=this.extractScope(t.name);return e.isErr()?a(e.error):(S.verbose(`ConfigHydratorService: Auto-detected scope from package.json: ${e.value}`),s({scope:e.value}))}return s({})}extractPackageName(t){if(!t?.trim())return a(C({code:`INVALID`,message:`Package name cannot be empty`}));let n=t.replace(e.SCOPED_PACKAGE_REGEX,``);return n?s(n):a(C({code:`INVALID`,message:`Malformed package name: "${t}"`}))}extractScope(e){if(!this.isScopedPackage(e))return s(``);let t=e.split(`/`)[0];return!t||t.length<=1?a(C({code:`INVALID`,message:`Malformed scoped package name: "${e}"`})):s(t.substring(1))}isScopedPackage(e){return e.startsWith(`@`)}},gt=class{id=`prepare-release-config`;description=`Hydrates and prepares the release configuration.`;getDependencies(){return[]}shouldExecute(){return s(!0)}canUndo(){return!1}execute(e){S.verbose(`PrepareReleaseConfigTask: Preparing and hydrating release configuration...`);let t=e.getBasePath(),n=new ht(t),r=e.getConfig();return i.fromPromise(n.hydrateConfig(r),w).andThen(t=>{if(t.isErr())return o(t.error);let n=e.set(`config`,t.value);return n.isErr()?o(n.error):c()}).andTee(()=>S.verbose(`PrepareReleaseConfigTask: Release configuration prepared.`))}},_t=class{id=`release-preflight-check`;description=`Perform preflight checks before starting the release command.`;shouldExecute(e){return e?.getConfig().skipPreflightCheck?s(!1):s(!0)}getSkipThroughTasks(e){return e?.getConfig().skipPreflightCheck?s([A(W)]):s([])}canUndo(){return!1}execute(e){S.verbose(`ReleasePreflightCheckTask: Starting preflight checks...`);let t=e.getBasePath();return this.checkGitCliffConfig(t).andThen(this.cleanWorkingDirectory).andThen(this.ensureNoUnpushedCommits).map(()=>S.verbose(`ReleasePreflightCheckTask: All preflight checks passed.`))}checkGitCliffConfig(e){S.verbose(`ReleasePreflightCheckTask: Checking for git-cliff configuration...`);let t=k.exists(d(e,`cliff.toml`));return i.fromPromise(t,w).andThen(e=>e.isErr()?o(e.error):e.value?c(D.getInstance()):o(C({code:`NOT_FOUND`,message:`No git-cliff configuration found!`})))}cleanWorkingDirectory(e){return S.verbose(`ReleasePreflightCheckTask: Checking if working directory is clean...`),i.fromPromise(e.status.isWorkingDirectoryClean(),w).andThen(t=>t.isErr()?a(t.error):t.value?(S.verbose(`ReleasePreflightCheckTask: Working directory is clean`),s(e)):a(C({code:`FAILED`,message:`Working directory is not clean, clean working directory before proceeding!`})))}ensureNoUnpushedCommits(e){return S.verbose(`ReleasePreflightCheckTask: Checking for unpushed commits...`),i.fromPromise(e.remote.hasUnpushedCommits(),w).andThen(e=>e.isErr()?a(e.error):e.value?(S.verbose(`ReleasePreflightCheckTask: There are unpushed commits`),a(C({code:`FAILED`,message:`There are unpushed commits, push them before proceeding!`}))):(S.verbose(`ReleasePreflightCheckTask: No unpushed commits found`),s(void 0)))}};function vt(){return{id:`release-workflow`,name:`Release Workflow`,description:`Bump a new version, generate a changelog, and publish the release.`,command:`release`,buildTasks(){let e=[new _t,new gt,new W,new J,new mt,new pt,new K,new q,new G,new U,new Y,new X,new z,new I,new L,new F,new P,new N,new R,new rt];return s(e)}}}var yt=class{constructor(e={}){this.options=e}load(){let{cwd:e=process.cwd(),configFile:t,overrides:n={}}=this.options;return i.fromPromise(ne({name:`firefly`,cwd:e,configFile:t,packageJson:!1}),e=>C(w(e))).andThen(e=>this.handleConfigLoad(e,n)).andThen(e=>this.validateConfig(e))}handleConfigLoad(e,t){e.configFile!==`firefly.config`&&S.info(`Using firefly config: ${p.underline(e.configFile??`unknown`)}`);let n=this.mergeConfig(e.config??{},t);return s(this.normalizeFields(n))}validateConfig(e){return this.options.commandName?et(b.getEffect(this.options.commandName),e):et(b.getEffect(),e)}normalizeFields(e){return{...e,name:e.name??void 0,scope:e.scope??void 0}}mergeConfig(e,t){return this.deepMerge(e,t)}deepMerge(e,t){let n={...e};for(let r of Object.keys(t)){let i=e[r],a=t[r];i&&a&&typeof i==`object`&&typeof a==`object`&&!Array.isArray(i)&&!Array.isArray(a)?n[r]=this.deepMerge(i,a):a!==void 0&&(n[r]=a)}return n}},bt=class e{executionId;startTime;command;state;schema;constructor(e,t,n,r){this.command=e,this.executionId=r??Bun.randomUUIDv7(),this.startTime=new Date,this.state=t,this.schema=n}static create(t,n,r){if(!e.hasContextSchema(t))return a(C({message:`No context schema found for command "${t}".`,code:`NOT_FOUND`,source:`orchestration/scoped-context-service`}));let i=le(t);if(!i)return a(C({message:`No context schema found for command "${t}".`,code:`NOT_FOUND`,source:`orchestration/scoped-context-service`}));let o=M(i,n);return o.isErr()?a(o.error):s(new e(t,o.value,i,r))}static hasContextSchema(e){return e in x}getConfig(){return this.state.config}setConfig(e){return this.set(`config`,e)}get(e){return e in this.state?s(this.state[e]):a(C({message:`Key "${String(e)}" does not exist in the context state.`,code:`NOT_FOUND`,source:`orchestration/scoped-context-service`}))}set(e,t){let n={...this.state,[e]:t},r=M(this.schema,n);return r.isErr()?a(r.error):(this.state=r.value,s())}update(e,t){let n=t(this.state[e]);return this.set(e,n)}has(e){return e in this.state&&this.state[e]!==void 0}snapshot(){return Object.freeze({...this.state})}clear(){let e={command:this.command,executionId:this.executionId,startTime:this.startTime},t=M(this.schema,e);return t.isErr()?a(t.error):(this.state=t.value,s())}getBasePath(){let e=this.state.basePath;return typeof e==`string`?e:process.cwd()}getCurrentVersion(){let e=this.state.currentVersion;return typeof e==`string`?e:`0.0.0`}getNextVersion(){let e=this.state.nextVersion;return typeof e==`string`?e:`0.0.0`}setCurrentVersion(e){return this.set(`currentVersion`,e)}setNextVersion(e){return this.set(`nextVersion`,e)}};const xt=e.enum([`reverse`,`compensation`,`custom`,`none`]);e.object({taskId:e.string().min(1),task:e.custom(),executionTime:e.date(),compensationId:e.string().optional()});const St=e.object({executionId:e.uuid().optional(),name:e.string().min(1).optional(),description:e.string().optional(),dryRun:e.boolean().default(!1),featureFlags:e.map(e.string(),e.boolean()).optional(),rollbackStrategy:xt.default(`reverse`)}),Z=e.string().min(1,`Feature name must be at least 1 character long`).max(100,`Feature name must be at most 100 characters long`).regex(/^[a-zA-Z0-9-_]+$/,`Feature name can only contain alphanumeric characters, hyphens, and underscores`),Ct=e.boolean(),wt=e.record(Z,Ct);var Tt=class e{features;metadata;constructor(e,t){this.features=e?new Map(e):new Map,this.metadata=t?new Map(t):new Map}static empty(){return new e}static fromMaps(t,n){return new e(t,n)}static fromConfig(t){let n=M(wt,t);if(n.isErr())return a(C({code:`VALIDATION`,message:`Invalid feature configuration: ${n.error.message}`,source:`orchestration/feature-manager-service`}));let r=new Map(Object.entries(n.value));return s(e.fromMaps(r,new Map))}static create(t){if(!t.featureFlags)return s(new e);let n=t.featureFlags instanceof Map?Object.fromEntries(t.featureFlags):t.featureFlags;return e.fromConfig(n)}isEnabled(e){let t=M(Z,e);return t.isErr()?(S.warn(`FeatureManagerService: Invalid feature name checked - ${t.error.message}`),!1):this.features.get(e)??!1}areAllEnabled(e){return e.every(e=>this.isEnabled(e))}isAnyEnabled(e){return e.some(e=>this.isEnabled(e))}enable(t){let n=M(Z,t);if(n.isErr())return a(n.error);let r=this.metadata.get(t);if(r){let e=this.validateDependencies(t,r);if(e.isErr())return a(e.error);let n=this.validateConflicts(t,r);if(n.isErr())return a(n.error)}let i=new Map(this.features),o=new Map(this.metadata);return i.set(t,!0),o.set(t,{...r||{name:t,createdAt:new Date},updatedAt:new Date}),s(e.fromMaps(i,o))}disable(t){let n=M(Z,t);if(n.isErr())return S.warn(`FeatureManagerService: Invalid feature name checked - ${n.error.message}`),a(n.error);let r=this.findDependents(t);if(r.length>0)return a(C({code:`VALIDATION`,message:`Cannot disable feature "${t}" because the following features depend on it: ${r.join(`, `)}`,source:`orchestration/feature-manager-service`}));let i=this.metadata.get(t),o=new Map(this.features),c=new Map(this.metadata);return o.set(t,!1),c.set(t,{...i||{name:t,createdAt:new Date},updatedAt:new Date}),s(e.fromMaps(o,c))}findDependents(e){let t=[];for(let[n,r]of this.metadata.entries())r.dependencies?.includes(e)&&this.isEnabled(n)&&t.push(n);return t}validateDependencies(e,t){if(!t.dependencies)return s();let n=t.dependencies.filter(e=>!this.isEnabled(e));return n.length>0?a(C({code:`VALIDATION`,message:`Cannot enable feature "${e}" due to missing dependencies: ${n.join(`, `)}`,source:`orchestration/feature-manager-service`})):s()}validateConflicts(e,t){if(!t.conflictsWith)return s();let n=t.conflictsWith.filter(e=>this.isEnabled(e));return n.length>0?a(C({code:`VALIDATION`,message:`Cannot enable feature "${e}" due to conflicts with enabled features: ${n.join(`, `)}`,source:`orchestration/feature-manager-service`})):s()}toggle(e){return this.isEnabled(e)?this.disable(e):this.enable(e)}getEnabledFeatures(){return new Set(Array.from(this.features.entries()).filter(([,e])=>e).map(([e])=>e))}getDisabledFeatures(){return new Set(Array.from(this.features.entries()).filter(([,e])=>!e).map(([e])=>e))}getAllFeatures(){return new Map(this.features)}setFeatures(t){let n=new Map(this.features),r=new Map(this.metadata),i=new Date,o=[];for(let[e,a]of t.entries()){let t=M(Z,e);if(t.isErr()){o.push(`Invalid feature name "${e}": ${t.error.message}`);continue}let s=M(Ct,a);if(s.isErr()){o.push(`Invalid flag for feature "${e}": ${s.error.message}`);continue}let c=this.metadata.get(e);n.set(e,a),r.set(e,{...c||{name:e,createdAt:i},updatedAt:i})}return o.length>0?a(C({code:`VALIDATION`,message:`Errors setting features: ${o.join(`; `)}`,source:`orchestration/feature-manager-service`})):s(e.fromMaps(n,r))}getMetadata(e){let t=M(Z,e);if(t.isErr()){S.warn(`FeatureManagerService: Invalid feature name checked - ${t.error.message}`);return}return this.metadata.get(e)}getMetadataWithEnabled(e){let t=M(Z,e);if(t.isErr()){S.warn(`FeatureManagerService: Invalid feature name checked - ${t.error.message}`);return}let n=this.metadata.get(e);if(n)return{...n,enabled:this.features.get(e)??!1}}setMetadata(t,n){let r=M(Z,t);if(r.isErr())return S.warn(`FeatureManagerService: Invalid feature name checked - ${r.error.message}`),a(r.error);let i=new Map(this.metadata),o=i.get(t);return i.set(t,{name:t,createdAt:o?.createdAt??new Date,updatedAt:new Date,...n}),s(e.fromMaps(this.features,i))}checkCompatibility(e){let t=[];for(let n of e){let e=M(Z,n);e.isErr()&&t.push(`Invalid feature name "${n}": ${e.error.message}`)}for(let n of e){if(M(Z,n).isErr())continue;let r=this.getMetadata(n);if(r?.dependencies){let i=r.dependencies.filter(t=>!e.includes(t));i.length>0&&t.push(`Feature "${n}" is missing dependencies: ${i.map(e=>`"${e}"`).join(`, `)}`)}if(r?.conflictsWith){let i=r.conflictsWith.filter(t=>e.includes(t));i.length>0&&t.push(`Feature "${n}" conflicts with: ${i.map(e=>`"${e}"`).join(`, `)}`)}}return t.length>0?a(C({code:`VALIDATION`,message:`Feature compatibility check failed: ${t.join(`; `)}`,details:{errors:t},source:`orchestration/feature-manager-service`})):s()}};function Q(e){return`shouldExecute`in e&&typeof e.shouldExecute==`function`}var Et=class t{rollbackStack=[];compensationTasks=new Map;config;constructor(e){this.config={strategy:e?.strategy??`reverse`,maxRetries:e?.maxRetries??1,continueOnError:e?.continueOnError??!1,parallel:e?.parallel??!1}}static create(n){return M(e.object({strategy:e.enum([`reverse`,`compensation`,`custom`,`none`]).default(`reverse`),maxRetries:e.number().min(0).optional(),continueOnError:e.boolean().optional(),parallel:e.boolean().optional()}),n??{}).map(e=>new t(e))}addTask(e){return this.validateTask(e).andThen(()=>{let t={taskId:e.id,task:e,executionTime:new Date,compensationId:void 0};return e.canUndo?.()?(this.rollbackStack.push(t),S.verbose(`RollbackManagerService: Added task to rollback stack: '${e.id}'`),s()):s()})}registerCompensation(t,n){let r=M(e.string().min(1),t).andThen(()=>this.validateCompensationTask(n));if(r.isErr())return r;this.compensationTasks.set(t,n);let i=this.rollbackStack.slice().reverse().find(e=>e.taskId===t);return i&&(i.compensationId=n.id),s()}executeRollback(e,t){let n=e??this.config.strategy,r=Date.now();return this.rollbackStack.length===0?(S.verbose(`RollbackManagerService: No tasks to rollback`),c({success:!0,rolledBackTasks:[],failedTasks:[],errors:[],duration:0})):(S.info(`RollbackManagerService: Starting rollback with strategy: ${n}`),this.executeStrategyRollback(n,t).map(e=>({...e,duration:Date.now()-r})).mapErr(e=>(S.error(`RollbackManagerService: Rollback failed`,e),e)))}executeStrategyRollback(e,t){let n={reverse:e=>this.executeReverseRollback(e),compensation:e=>this.executeCompensationRollback(e),custom:e=>this.executeCustomRollback(e),none:()=>c(this.createEmptyResult())}[e];return n?n(t):o(C({code:`VALIDATION`,message:`Unknown rollback strategy: ${String(e)}`,source:`application`}))}createEmptyResult(){return{success:!0,rolledBackTasks:[],failedTasks:[],errors:[],duration:0}}handleRollbackError(e,t,n){e.failedTasks.push(t.taskId),e.errors.push(n),e.success=!1}executeRollbackSequence(e,t,n){let r=this.createEmptyResult(),i=[...e].reverse(),a=e=>{if(e>=i.length)return c(r);let o=i[e];return o?this.executeWithRetries(()=>t(o,n),this.config.maxRetries??1).andThen(()=>(r.rolledBackTasks.push(o.taskId),a(e+1))).orElse(t=>(this.handleRollbackError(r,o,t),this.config.continueOnError?a(e+1):c(r))):a(e+1)};return a(0)}executeWithRetries(e,t){let n=r=>e().orElse(e=>r<t?(S.verbose(`RollbackManagerService: Retry attempt ${r+1}/${t}`),n(r+1)):o(e));return n(0)}executeReverseRollback(e){return this.executeRollbackSequence(this.rollbackStack,(e,t)=>this.executeTaskRollback(e,t),e)}executeCompensationRollback(e){return this.executeRollbackSequence(this.rollbackStack,(e,t)=>e.compensationId&&this.compensationTasks.has(e.compensationId)?this.executeCompensation(e.compensationId,t):this.executeTaskRollback(e,t),e)}executeCustomRollback(e){return this.executeRollbackSequence(this.rollbackStack,(e,t)=>t?(e.task.beforeRollback?.(t)??c()).andThen(()=>this.executeTaskRollback(e,t)).andThen(()=>e.task.afterRollback?.(t)??c()).orElse(n=>(e.task.onRollbackError?.(n,t)??c()).andThen(()=>o(n))):this.executeTaskRollback(e,t),e)}executeTaskRollback(e,t){let{task:n}=e;return n.canUndo?.()?(S.verbose(`RollbackManagerService: Executing rollback for task '${n.id}'`),n.undo?t?n.undo(t):n.undo({}):(S.warn(`RollbackManagerService: Task '${n.id}' does not have an undo method. Skipping rollback.`),c())):(S.verbose(`RollbackManagerService: Task '${n.id}' cannot be undone. Skipping rollback.`),c())}executeCompensation(e,t){let n=this.compensationTasks.get(e);return n?(S.verbose(`RollbackManagerService: Executing compensation task: ${n.name}`),n.execute(t)):o(C({message:`Compensation task with id '${e}' not found.`,code:`NOT_FOUND`,source:`orchestration/rollback-manager-service`}))}validateTask(e){return!e.id||typeof e.id!=`string`?a(C({message:`Task must have a valid 'id' of type string.`,code:`VALIDATION`,source:`orchestration/rollback-manager-service`})):s()}validateCompensationTask(e){return!e.id||typeof e.id!=`string`?a(C({message:`Compensation task must have a valid 'id' of type string.`,code:`VALIDATION`,source:`orchestration/rollback-manager-service`})):s()}getRollbackStack(){return[...this.rollbackStack]}clear(){this.rollbackStack.length=0,this.compensationTasks.clear()}getTaskCount(){return this.rollbackStack.length}hasTasks(){return this.rollbackStack.length>0}getConfig(){return{...this.config}}};const Dt=process.env.FIREFLY_DEBUG_TASK_LIFECYCLE===`true`;var Ot=class{executeTask(e,t){let n=`TaskExecutorService: Executing task '${e.id}'`;return S.verbose(Dt?p.redBright(n):n),this.executeWithLifecycle(e,t).andThen(()=>{let t=`TaskExecutorService: Successfully executed task '${e.id}'`;return S.verbose(Dt?p.redBright(t):t),c()}).mapErr(t=>(S.verbose(`TaskExecutorService: Failed to execute task '${e.id}'`),S.verbose(`TaskExecutorService: Reason: ${t.message}`),t))}undoTask(e,t){return S.verbose(`TaskExecutorService: Undoing task '${e.id}'`),e.canUndo?.()?this.undoWithLifecycle(e,t).andThen(()=>(S.verbose(`TaskExecutorService: Successfully undone task '${e.id}'`),c())).mapErr(t=>(S.verbose(`TaskExecutorService: Failed to undo task '${e.id}': ${t.message}`),t)):o(C({message:`Task '${e.id}' cannot be undone.`,code:`INVALID`,source:`orchestration/task-executor-service`}))}compensateTask(e,t){return S.verbose(`TaskExecutorService: Compensating task '${e.id}'`),e.compensate?(t?e.compensate?.(t):e.compensate?.({})).andThen(()=>(S.verbose(`TaskExecutorService: Successfully compensated task '${e.id}'`),c())).mapErr(t=>(S.verbose(`TaskExecutorService: Failed to compensate task '${e.id}': ${t.message}`),t)):o(C({message:`Task '${e.id}' does not have a compensate operation defined.`,code:`INVALID`,source:`orchestration/task-executor-service`}))}executeWithLifecycle(e,t){return t&&e.beforeExecute?e.beforeExecute(t).andThen(()=>this.performExecution(e,t)).andThen(()=>e.afterExecute?e.afterExecute(t):c()).orElse(n=>e.onExecuteError&&t?e.onExecuteError(n,t).andThen(()=>o(n)):o(n)):this.performExecution(e,t)}performExecution(e,t){if(t&&e.validate){let n=e.validate?.(t);if(n.isErr())return o(n.error)}return t?e.execute?.(t):e.execute?.({})}undoWithLifecycle(e,t){return t&&e.beforeRollback?e.beforeRollback(t).andThen(()=>this.performUndo(e,t)).andThen(()=>e.afterRollback?e.afterRollback(t):c()).orElse(n=>e.onRollbackError&&t?e.onRollbackError(n,t).andThen(()=>o(n)):o(n)):this.performUndo(e,t)}performUndo(e,t){return(t?e.undo?.(t):e.undo?.({}))||o(C({message:`Task '${e.id}' does not have an undo operation defined.`,code:`INVALID`,source:`orchestration/task-executor-service`}))}},kt=class{options;startTime;taskExecutor;featureManager;rollbackManager;taskMap;constructor(e){this.options=e,this.startTime=new Date,this.taskMap=new Map;let t={strategy:e.rollbackStrategy,continueOnError:!1,parallel:!1};this.taskExecutor=new Ot;let n=Et.create(t);n.isOk()&&(this.rollbackManager=n.value);let r=Tt.create(e);r.isOk()&&(this.featureManager=r.value)}execute(e,t){this.initializeTaskMap(e);let n=[],r=[],i=[],a=!1,s=!1,c=this.getInitialExecutionQueue(e,t),l=()=>{let e=this.getNextExecutableTask(c,t);if(!e)return this.createResult(!0,n,r,i,{rollbackExecuted:a,compensationExecuted:s});let u=this.taskMap.get(e);if(!u)return o(C({code:`VALIDATION`,message:`Task node not found for ID: ${e}`,source:`orchestration/sequential-execution-strategy`}));let d=u.task;return u.visited=!0,this.shouldExecuteTask(d,t).asyncAndThen(o=>{if(!o){if(i.push(d.id),this.removeFromQueue(c,e),Q(d)&&d.getSkipThroughTasks){let e=d.getSkipThroughTasks(t);if(e.isOk())for(let t of e.value)this.taskMap.has(t)&&!c.includes(t)&&(c.push(t),S.verbose(`SequentialExecutionStrategy: Added skip-through task '${t}' from skipped task '${d.id}'`))}return l()}return this.taskExecutor.executeTask(d,t).andThen(()=>{let r=this.rollbackManager.addTask(d);r.isErr()&&S.warn(`Failed to add task '${d.id}' to rollback stack`,r.error),n.push(d.id),this.removeFromQueue(c,e);let i=this.addDynamicNextTasks(d,c,t);return i.isErr()&&S.warn(`Failed to resolve next tasks for '${d.id}'`,i.error),l()}).orElse(e=>(r.push(d.id),this.options.rollbackStrategy===`none`?this.createResult(!1,n,r,i,{error:e,rollbackExecuted:!1,compensationExecuted:!1}):(S.verbose(`SequentialExecutionStrategy: Executing rollback with strategy: ${this.options.rollbackStrategy}`),this.rollbackManager.executeRollback(this.options.rollbackStrategy,t).andThen(t=>(a=t.success,s=this.options.rollbackStrategy===`compensation`&&t.success,t.success?S.verbose(`SequentialExecutionStrategy: Rollback completed successfully`):S.error(`SequentialExecutionStrategy: Rollback failed`,t.errors),this.createResult(!1,n,r,i,{error:e,rollbackExecuted:a,compensationExecuted:s}))).orElse(t=>(S.error(`SequentialExecutionStrategy: Rollback execution failed`,t),this.createResult(!1,n,r,i,{error:e,rollbackExecuted:!1,compensationExecuted:!1}))))))})};return l()}initializeTaskMap(e){this.taskMap.clear();for(let t of e)this.taskMap.set(t.id,{task:t,visited:!1})}getInitialExecutionQueue(e,t){let n=e.filter(e=>(e.getDependencies?.(t)??[]).length===0&&(e.isEntryPoint?.()??!0));if(n.length===0){let t=e.find(e=>e.isEntryPoint?.()??!0);return t?[t.id]:[]}return n.map(e=>e.id)}getNextExecutableTask(e,t){for(let n of e){let e=this.taskMap.get(n);if(!(!e||e.visited)&&(e.task.getDependencies?.(t)??[]).every(e=>this.taskMap.get(e)?.visited===!0))return n}return null}removeFromQueue(e,t){let n=e.indexOf(t);n>-1&&e.splice(n,1)}addDynamicNextTasks(e,t,n){let r=!1;if(Q(e)){let i=e.getNextTasks?.(n);if(i?.isOk()){let n=i.value;r=n.length>0;for(let r of n)this.taskMap.has(r)&&!t.includes(r)&&(t.push(r),S.verbose(`SequentialExecutionStrategy: Added dynamic next task '${r}' from '${e.id}'`))}else i?.isErr()&&S.warn(`Failed to get next tasks from '${e.id}'`,i.error)}if(!r){for(let[n,r]of this.taskMap)(r.task.getDependencies?.()??[]).includes(e.id)&&!t.includes(n)&&!r.visited&&(t.push(n),S.verbose(`SequentialExecutionStrategy: Added dependent task '${n}' from '${e.id}'`));let n=e.getDependents?.()??[];for(let r of n)this.taskMap.has(r)&&!t.includes(r)&&(t.push(r),S.verbose(`SequentialExecutionStrategy: Added dependent task '${r}' from '${e.id}'`))}return s()}shouldExecuteTask(e,t){if(!e||typeof e.id!=`string`)return S.warn(`SequentialExecutionStrategy: Invalid task structure for task ${e?.id||`unknown`}`),s(!1);let n=e.getRequiredFeatures?.()??[];if(n.length>0){let t=this.featureManager.getEnabledFeatures();if(!(typeof e.isEnabled!=`function`||e.isEnabled(t)))return S.verbose(`SequentialExecutionStrategy: Task '${e.id}' disabled due to missing required features: ${n.join(`, `)}`),s(!1)}if(Q(e)){let n=e.shouldExecute(t);if(n.isErr())return S.warn(`SequentialExecutionStrategy: Error evaluating conditions for task '${e.id}'`,n.error),s(!1);if(!n.value)return S.verbose(`SequentialExecutionStrategy: Skipping task '${e.id}' due to runtime conditions`),s(!1)}return s(!0)}createResult(e,t,n,r,i){let a=new Date,o={success:e,executionId:this.options.executionId??`unknown`,workflowId:this.options.name??`sequential-workflow`,executedTasks:t,failedTasks:n,skippedTasks:r,error:i?.error,rollbackExecuted:i?.rollbackExecuted??!1,compensationExecuted:i?.compensationExecuted??!1,startTime:this.startTime,endTime:a,executionTime:a.getTime()-this.startTime.getTime()};return c(o)}};function At(e){return new kt(e)}var jt=class e{tasks;context;options;executionStrategy;executionId;featureManager;constructor(e,t,n){this.tasks=e,this.options=t,this.context=n,this.executionId=t.executionId??Bun.randomUUIDv7();let r=Tt.create(t);r.isOk()&&(this.featureManager=r.value),this.executionStrategy=At(this.options)}static fromTasks(t,n,r={}){let i=e.validateOptions(r);if(i.isErr())return a(i.error);let o=e.validateTaskConfiguration(t,n);return o.isErr()?a(o.error):(S.verbose(`TaskOrchestratorService: Initialized with ${t.length} tasks.`),s(new e(t,i.value,n)))}static fromWorkflow(t,n,r={}){S.verbose(`TaskOrchestratorService: Building tasks from workflow '${t.id}'.`);let i=e.validateOptions(r);if(i.isErr())return a(i.error);let o=t.buildTasks(n);if(o.isErr())return a(o.error);let c=e.validateTaskConfiguration(o.value,n);return c.isErr()?a(c.error):s(new e(o.value,i.value,n))}run(){let e=this.filterTasksByFeatures(Array.from(this.tasks));return e.isErr()?o(e.error):this.executionStrategy.execute(e.value,this.context).map(e=>(S.verbose(`TaskOrchestratorService: Workflow execution completed.`),e)).mapErr(e=>e)}static validateOptions(e){let t=M(St,e);return t.isErr()?a(C({code:`VALIDATION`,message:`Invalid orchestrator options: ${t.error.message}`,source:`orchestration/task-orchestrator-service`})):s(t.value)}getExecutionId(){return this.executionId}static validateTaskConfiguration(e,t){let n=new Set(e.map(e=>e.id)),r=[];for(let i of e){for(let e of i.getDependencies?.(t)??[])n.has(e)||r.push(`Task ${i.id} has a missing dependency: ${e}`);for(let e of i.getDependents?.()??[])n.has(e)||r.push(`Task ${i.id} has a missing dependent: ${e}`)}let i=new Set,o=new Set,c=n=>{if(o.has(n))return!0;if(i.has(n))return!1;i.add(n),o.add(n);let r=e.find(e=>e.id===n);if(r){for(let e of r.getDependencies?.(t)??[])if(c(e))return!0}return o.delete(n),!1};for(let t of e)c(t.id)&&r.push(`Task ${t.id} is part of a circular dependency in static dependencies`);return r.length>0?a(C({code:`VALIDATION`,message:`Task configuration errors:\n${r.join(`
|
|
17
|
+
`)}`,source:`orchestration/task-orchestrator-service`})):s()}filterTasksByFeatures(e){let t=this.featureManager.getEnabledFeatures(),n=[];for(let r of e){let e=r.getRequiredFeatures?.()??[];e.length===0||r.isEnabled?.(t)?n.push(r):S.verbose(`TaskOrchestratorService: Task ${r.id} disabled due to missing features: ${e.join(`, `)}`)}return s(n)}},Mt=class{orchestrator;logSuccess(e){let t={executionId:e.executionId,executionTime:e.executionTime,executedTasks:e.executedTasks,skippedTasks:e.skippedTasks};S.verbose(``),S.verbose(JSON.stringify(t,null,2))}async run(e,t,n){let r=Bun.randomUUIDv7(),i=new Date,a=bt.create(e,{command:e,executionId:r,startTime:i,config:t.config,...t});if(a.isErr()){S.error(`Failed to create application context`,a.error);return}let o=a.value;S.verbose(`WorkflowRunnerService: Workflow runner started with execution ID: ${o.executionId}`),t.verbose&&(S.level=m.verbose);let s=n();if(s.command!==e){S.error(`Workflow command '${s.command}' does not match expected command '${e}'`);return}t.dryRun&&S.warn(`Running in dry-run mode. No actual changes will be made.`);let c={name:s.name,dryRun:t.dryRun??!1,executionId:o.executionId,rollbackStrategy:t.rollbackStrategy??`reverse`,featureFlags:t.enabledFeatures?new Map(t.enabledFeatures.map(e=>[e,!0])):void 0};if(s.beforeExecute){let e=await s.beforeExecute(o);if(e.isErr()){S.error(`Workflow beforeExecute hook failed`,e.error);return}}let l=jt.fromWorkflow(s,o,c);if(l.isErr()){S.error(`Failed to initialize the task orchestrator`,l.error);return}this.orchestrator=l.value;let u=await this.orchestrator.run();if(u.isErr()){await this.handleWorkflowError(s,u.error,o);return}let d=u.value;if(s.afterExecute){let e=await s.afterExecute(d,o);e.isErr()&&S.warn(`Workflow afterExecute hook failed`,e.error)}if(d.success){this.logSuccess(d);return}let f=process.env.FIREFLY_DEBUG_ERROR===`true`?d.error:d.error?.message;S.error(f)}async handleWorkflowError(e,t,n){if(t&&e.onError&&n){S.verbose(`Executing workflow error handler...`);let r=await e.onError(t,n);r.isErr()&&S.warn(`Workflow error handler failed`,r.error)}}},Nt=class e{normalize(e,t){let n=t?b.get(t):b.get(),r=this.buildMappingFromSchema(n),i={...e};for(let[e,t]of r)e in i&&!(t in i)&&(i[t]=i[e],delete i[e]);return i}buildMappingFromSchema(t){let n=new Map,r=t.shape;for(let t of Object.keys(r)){let r=e.toKebab(t);if(r!==t){let e=r.replace(/-([a-z])/g,(e,t)=>t.toUpperCase());n.set(e,t)}}return n}static toKebab(e){return e.replace(/GitHub/g,`Github`).replace(/([a-z])([A-Z])/g,`$1-$2`).toLowerCase().replace(/_/g,`-`)}},Pt=class{shorthandMap=new Map([[`bumpStrategy`,`bs`],[`releaseType`,`rt`]]);registerOptions(t,n){let r=n.shape;for(let[n,i]of Object.entries(r)){if(!i)continue;let r=this.unwrapSchema(i),a=Nt.toKebab(n),o=this.shorthandMap.get(n),s=o?`--${o}, --${a}`:`--${a}`;if(t.options.find(e=>e.long===`--${a}`||o&&e.short===`-${o}`))continue;let c,l=e.object({[n]:i}).partial().safeParse({});l.success&&(c=l.data[n]);let u=i.description??``;if(this.isBooleanField(i)){t.option(s,u);continue}if(r instanceof e.ZodNumber){let e=this.createNumberParser(i,a);t.option(`${s} <${a}>`,u,t=>{let n=e(t);if(n.isErr())throw Error(n.error);return n.value},c);continue}if(r instanceof e.ZodEnum){let e=this.getEnumChoices(r),n=this.createEnumParser(i,a,e);t.option(`${s} <${a}>`,`${u}${e.length?` (choices: ${e.join(`, `)})`:``}`,e=>{let t=n(e);if(t.isErr())throw Error(t.error);return t.value},c);continue}if(r instanceof e.ZodString){let e=this.createStringParser(i);t.option(`${s} <${a}>`,u,t=>{let n=e(t);if(n.isErr())throw Error(n.error);return n.value},c);continue}let d=this.createGenericParser(i);t.option(`${s} <${a}>`,u,e=>{let t=d(e);if(t.isErr())throw Error(t.error);return t.value},c)}}createNumberParser(e,t){return n=>{let r=Number(n);if(Number.isNaN(r))return a(`Invalid number for --${t}: ${n}`);let i=M(e,r);return i.isErr()?a(i.error.message):s(i.value)}}createEnumParser(e,t,n){return r=>{let i=M(e,r);return i.isErr()?a(`Invalid value for --${t}: ${r}. Allowed: ${n.join(`, `)}`):s(i.value)}}createStringParser(e){return t=>{let n=M(e,t);return n.isErr()?a(n.error.message):s(n.value)}}createGenericParser(e){return t=>{let n=M(e,t);return n.isErr()?a(n.error.message):s(n.value)}}getInternalDef(e){let t=e._zod;return t?.def?t.def:e._def??{}}unwrapSchema(t){if(t instanceof e.ZodDefault){let e=this.getInternalDef(t).innerType;return e?this.unwrapSchema(e):t}if(t instanceof e.ZodOptional){let e=this.getInternalDef(t).innerType;return e?this.unwrapSchema(e):t}if(t instanceof e.ZodUnknown){let e=this.getInternalDef(t).schema;return e?this.unwrapSchema(e):t}return t}isBooleanField(t){let n=this.getInternalDef(t);return(n.innerType??n.schema)instanceof e.ZodBoolean}getEnumChoices(e){return this.getInternalDef(e).values??[]}},Ft=class{normalizer=new Nt;registrar=new Pt;create(e){return g.name(`firefly`),g.description(String(process.env.FIREFLY_DESCRIPTION)).version(String(process.env.FIREFLY_VERSION)),g.helpOption(`-h, --help`,`Display help information`).helpCommand(`help`,`Display help for command`),this.registrar.registerOptions(g,e),g}register(e,t){let{command:n,description:r}=t(),i=g.command(n).description(r);this.registrar.registerOptions(i,e),i.action(e=>(this.logVersionInfo(n),this.runCommand(n,e,t)))}logVersionInfo(e){S.info(this.formatVersionInfo(e))}formatVersionInfo(e){let t=p.dim(`v${String(process.env.FIREFLY_VERSION)}`),n=`${p.magenta(`firefly`)} ${t}`;if(e===`release`){let e=p.dim(`v${String(process.env.FIREFLY_GIT_CLIFF_VERSION)}`);return`${n} powered by git-cliff ${e}`}return n}async runCommand(e,t,n){let r=this.mergeAndNormalizeOptions(t,e),i=await this.loadConfig(e,r);if(i.isErr()){this.handleConfigError(i.error);return}let a={...i.value,...r},o=this.buildExecutorOptions(a);await new Mt().run(e,o,n)}mergeAndNormalizeOptions(e,t){let n={...g.opts(),...e},r=this.normalizer.normalize(n,t),{releaseLatest:i,releasePreRelease:a,releaseDraft:o}=r;return(a===!0||o===!0)&&(r.releaseLatest=!1),i===!0&&(r.releasePreRelease=!1,r.releaseDraft=!1),r}buildExecutorOptions(e){return{dryRun:e.dryRun??!1,verbose:e.verbose??!1,rollbackStrategy:`reverse`,continueOnError:!1,config:e}}loadConfig(e,t){return new yt({configFile:t.config,overrides:t,commandName:e}).load()}handleConfigError(e){e.cause instanceof t&&S.error(e.cause.issues.map(e=>e.message).join(`; `))}};function It(){let e=new Ft;return e.register(b.get(`release`),vt),e.create(b.base())}var $={name:`fireflyy`,version:`3.0.3`,description:`CLI orchestrator for semantic versioning, changelog generation, and creating releases.`,type:`module`,license:`MIT`,author:`Yehezkiel Dio Sinolungan <yehezkieldio@proton.me>`,files:[`dist/**/*.js`,`assets`],main:`./dist/index.js`,module:`./dist/index.js`,types:`./dist/index.d.ts`,exports:{"./config":{types:`./dist/index.d.ts`,import:`./dist/index.js`}},typesVersions:{"*":{"*":[`./dist/*`,`./*`]}},bin:{firefly:`./dist/main.js`,ff:`./dist/main.js`},publishConfig:{access:`public`},scripts:{postbuild:`bun scripts/generate-json-schema.ts assets/firefly.schema.json`,build:`tsdown`,dev:`bun run src/platform/cli/main.ts`,check:`biome check .`,"check:unsafe":`biome check --write --unsafe .`,"check:write":`biome check --write .`,typecheck:`tsc --noEmit`,format:`biome format . --write`,lint:`biome lint .`,"lint:fix":`biome lint . --fix --unsafe`},dependencies:{c12:`^3.3.0`,commander:`^14.0.1`,consola:`^3.4.2`,"git-cliff":`^2.10.1`,neverthrow:`^8.2.0`,semver:`^7.7.2`,zod:`^4.1.11`},devDependencies:{"@biomejs/biome":`^2.2.4`,"@types/bun":`^1.2.23`,"@types/node":`^24.6.1`,"@types/semver":`^7.7.1`,tsdown:`^0.15.6`,typescript:`^5.9.3`},homepage:`https://github.com/yehezkieldio/firefly#readme`,bugs:{url:`https://github.com/yehezkieldio/firefly/issues`},repository:{type:`git`,url:`git+https://github.com/yehezkieldio/firefly.git`}};process.versions.bun||(console.error(`Firefly is designed to run with Bun. Please install Bun if you haven't already and run the command again.`),process.exit(1));async function Lt(){process.argv.length===2&&process.argv.push(`-h`),process.env.FIREFLY_VERSION=$.version,process.env.FIREFLY_DESCRIPTION=$.description,process.env.FIREFLY_GIT_CLIFF_VERSION=$.dependencies[`git-cliff`].replace(`^`,``),await It().parseAsync(process.argv)}Lt();
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "fireflyy",
|
|
3
|
-
"version": "3.0.
|
|
3
|
+
"version": "3.0.3",
|
|
4
4
|
"description": "CLI orchestrator for semantic versioning, changelog generation, and creating releases.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
@@ -52,7 +52,6 @@
|
|
|
52
52
|
"git-cliff": "^2.10.1",
|
|
53
53
|
"neverthrow": "^8.2.0",
|
|
54
54
|
"semver": "^7.7.2",
|
|
55
|
-
"smol-toml": "^1.4.2",
|
|
56
55
|
"zod": "^4.1.11"
|
|
57
56
|
},
|
|
58
57
|
"devDependencies": {
|