package.dist.chunks.mermaid.esm.min.gitGraphDiagram-PQENWCQG.mjs.map Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of mermaid Show documentation
Show all versions of mermaid Show documentation
Markdown-ish syntax for generating flowcharts, mindmaps, sequence diagrams, class diagrams, gantt charts, git graphs and more.
{
"version": 3,
"sources": ["../../../src/diagrams/git/gitGraphTypes.ts", "../../../src/diagrams/git/gitGraphAst.ts", "../../../src/diagrams/git/gitGraphParser.ts", "../../../src/diagrams/git/gitGraphRenderer.ts", "../../../src/diagrams/git/styles.js", "../../../src/diagrams/git/gitGraphDiagram.ts"],
"sourcesContent": ["import type { GitGraphDiagramConfig } from '../../config.type.js';\nimport type { DiagramDBBase } from '../../diagram-api/types.js';\n\nexport const commitType = {\n NORMAL: 0,\n REVERSE: 1,\n HIGHLIGHT: 2,\n MERGE: 3,\n CHERRY_PICK: 4,\n} as const;\n\nexport interface CommitDB {\n msg: string;\n id: string;\n type: number;\n tags?: string[];\n}\n\nexport interface BranchDB {\n name: string;\n order: number;\n}\n\nexport interface MergeDB {\n branch: string;\n id: string;\n type?: number;\n tags?: string[];\n}\n\nexport interface CherryPickDB {\n id: string;\n targetId: string;\n parent: string;\n tags?: string[];\n}\n\nexport interface Commit {\n id: string;\n message: string;\n seq: number;\n type: number;\n tags: string[];\n parents: string[];\n branch: string;\n customType?: number;\n customId?: boolean;\n}\n\nexport interface GitGraph {\n statements: Statement[];\n}\n\nexport type Statement = CommitAst | BranchAst | MergeAst | CheckoutAst | CherryPickingAst;\n\nexport interface CommitAst {\n $type: 'Commit';\n id: string;\n message?: string;\n tags?: string[];\n type?: 'NORMAL' | 'REVERSE' | 'HIGHLIGHT';\n}\n\nexport interface BranchAst {\n $type: 'Branch';\n name: string;\n order?: number;\n}\n\nexport interface MergeAst {\n $type: 'Merge';\n branch: string;\n id?: string;\n tags?: string[];\n type?: 'NORMAL' | 'REVERSE' | 'HIGHLIGHT';\n}\n\nexport interface CheckoutAst {\n $type: 'Checkout';\n branch: string;\n}\n\nexport interface CherryPickingAst {\n $type: 'CherryPicking';\n id: string;\n parent: string;\n tags?: string[];\n}\n\nexport interface GitGraphDB extends DiagramDBBase {\n commitType: typeof commitType;\n setDirection: (dir: DiagramOrientation) => void;\n setOptions: (rawOptString: string) => void;\n getOptions: () => any;\n commit: (commitDB: CommitDB) => void;\n branch: (branchDB: BranchDB) => void;\n merge: (mergeDB: MergeDB) => void;\n cherryPick: (cherryPickDB: CherryPickDB) => void;\n checkout: (branch: string) => void;\n prettyPrint: () => void;\n clear: () => void;\n getBranchesAsObjArray: () => { name: string }[];\n getBranches: () => Map;\n getCommits: () => Map;\n getCommitsArray: () => Commit[];\n getCurrentBranch: () => string;\n getDirection: () => DiagramOrientation;\n getHead: () => Commit | null;\n}\n\nexport interface GitGraphDBParseProvider extends Partial {\n commitType: typeof commitType;\n setDirection: (dir: DiagramOrientation) => void;\n commit: (commitDB: CommitDB) => void;\n branch: (branchDB: BranchDB) => void;\n merge: (mergeDB: MergeDB) => void;\n cherryPick: (cherryPickDB: CherryPickDB) => void;\n checkout: (branch: string) => void;\n}\n\nexport interface GitGraphDBRenderProvider extends Partial {\n prettyPrint: () => void;\n clear: () => void;\n getBranchesAsObjArray: () => { name: string }[];\n getBranches: () => Map;\n getCommits: () => Map;\n getCommitsArray: () => Commit[];\n getCurrentBranch: () => string;\n getDirection: () => DiagramOrientation;\n getHead: () => Commit | null;\n getDiagramTitle: () => string;\n}\n\nexport type DiagramOrientation = 'LR' | 'TB' | 'BT';\n", "import { log } from '../../logger.js';\nimport { cleanAndMerge, random } from '../../utils.js';\nimport { getConfig as commonGetConfig } from '../../config.js';\nimport common from '../common/common.js';\nimport {\n setAccTitle,\n getAccTitle,\n getAccDescription,\n setAccDescription,\n clear as commonClear,\n setDiagramTitle,\n getDiagramTitle,\n} from '../common/commonDb.js';\nimport type {\n DiagramOrientation,\n Commit,\n GitGraphDB,\n CommitDB,\n MergeDB,\n BranchDB,\n CherryPickDB,\n} from './gitGraphTypes.js';\nimport { commitType } from './gitGraphTypes.js';\nimport { ImperativeState } from '../../utils/imperativeState.js';\n\nimport DEFAULT_CONFIG from '../../defaultConfig.js';\n\nimport type { GitGraphDiagramConfig } from '../../config.type.js';\ninterface GitGraphState {\n commits: Map;\n head: Commit | null;\n branchConfig: Map;\n branches: Map;\n currBranch: string;\n direction: DiagramOrientation;\n seq: number;\n options: any;\n}\n\nconst DEFAULT_GITGRAPH_CONFIG: Required = DEFAULT_CONFIG.gitGraph;\nconst getConfig = (): Required => {\n const config = cleanAndMerge({\n ...DEFAULT_GITGRAPH_CONFIG,\n ...commonGetConfig().gitGraph,\n });\n return config;\n};\n\nconst state = new ImperativeState(() => {\n const config = getConfig();\n const mainBranchName = config.mainBranchName;\n const mainBranchOrder = config.mainBranchOrder;\n return {\n mainBranchName,\n commits: new Map(),\n head: null,\n branchConfig: new Map([[mainBranchName, { name: mainBranchName, order: mainBranchOrder }]]),\n branches: new Map([[mainBranchName, null]]),\n currBranch: mainBranchName,\n direction: 'LR',\n seq: 0,\n options: {},\n };\n});\n\nfunction getID() {\n return random({ length: 7 });\n}\n\n/**\n * @param list - list of items\n * @param fn - function to get the key\n */\nfunction uniqBy(list: any[], fn: (item: any) => any) {\n const recordMap = Object.create(null);\n return list.reduce((out, item) => {\n const key = fn(item);\n if (!recordMap[key]) {\n recordMap[key] = true;\n out.push(item);\n }\n return out;\n }, []);\n}\n\nexport const setDirection = function (dir: DiagramOrientation) {\n state.records.direction = dir;\n};\n\nexport const setOptions = function (rawOptString: string) {\n log.debug('options str', rawOptString);\n rawOptString = rawOptString?.trim();\n rawOptString = rawOptString || '{}';\n try {\n state.records.options = JSON.parse(rawOptString);\n } catch (e: any) {\n log.error('error while parsing gitGraph options', e.message);\n }\n};\n\nexport const getOptions = function () {\n return state.records.options;\n};\n\nexport const commit = function (commitDB: CommitDB) {\n let msg = commitDB.msg;\n let id = commitDB.id;\n const type = commitDB.type;\n let tags = commitDB.tags;\n\n log.info('commit', msg, id, type, tags);\n log.debug('Entering commit:', msg, id, type, tags);\n const config = getConfig();\n id = common.sanitizeText(id, config);\n msg = common.sanitizeText(msg, config);\n tags = tags?.map((tag) => common.sanitizeText(tag, config));\n const newCommit: Commit = {\n id: id ? id : state.records.seq + '-' + getID(),\n message: msg,\n seq: state.records.seq++,\n type: type ?? commitType.NORMAL,\n tags: tags ?? [],\n parents: state.records.head == null ? [] : [state.records.head.id],\n branch: state.records.currBranch,\n };\n state.records.head = newCommit;\n log.info('main branch', config.mainBranchName);\n state.records.commits.set(newCommit.id, newCommit);\n state.records.branches.set(state.records.currBranch, newCommit.id);\n log.debug('in pushCommit ' + newCommit.id);\n};\n\nexport const branch = function (branchDB: BranchDB) {\n let name = branchDB.name;\n const order = branchDB.order;\n name = common.sanitizeText(name, getConfig());\n if (state.records.branches.has(name)) {\n throw new Error(\n `Trying to create an existing branch. (Help: Either use a new name if you want create a new branch or try using \"checkout ${name}\")`\n );\n }\n\n state.records.branches.set(name, state.records.head != null ? state.records.head.id : null);\n state.records.branchConfig.set(name, { name, order });\n checkout(name);\n log.debug('in createBranch');\n};\n\nexport const merge = (mergeDB: MergeDB): void => {\n let otherBranch = mergeDB.branch;\n let customId = mergeDB.id;\n const overrideType = mergeDB.type;\n const customTags = mergeDB.tags;\n const config = getConfig();\n otherBranch = common.sanitizeText(otherBranch, config);\n if (customId) {\n customId = common.sanitizeText(customId, config);\n }\n const currentBranchCheck = state.records.branches.get(state.records.currBranch);\n const otherBranchCheck = state.records.branches.get(otherBranch);\n const currentCommit = currentBranchCheck\n ? state.records.commits.get(currentBranchCheck)\n : undefined;\n const otherCommit: Commit | undefined = otherBranchCheck\n ? state.records.commits.get(otherBranchCheck)\n : undefined;\n if (currentCommit && otherCommit && currentCommit.branch === otherBranch) {\n throw new Error(`Cannot merge branch '${otherBranch}' into itself.`);\n }\n if (state.records.currBranch === otherBranch) {\n const error: any = new Error('Incorrect usage of \"merge\". Cannot merge a branch to itself');\n error.hash = {\n text: `merge ${otherBranch}`,\n token: `merge ${otherBranch}`,\n expected: ['branch abc'],\n };\n throw error;\n }\n if (currentCommit === undefined || !currentCommit) {\n const error: any = new Error(\n `Incorrect usage of \"merge\". Current branch (${state.records.currBranch})has no commits`\n );\n error.hash = {\n text: `merge ${otherBranch}`,\n token: `merge ${otherBranch}`,\n expected: ['commit'],\n };\n throw error;\n }\n if (!state.records.branches.has(otherBranch)) {\n const error: any = new Error(\n 'Incorrect usage of \"merge\". Branch to be merged (' + otherBranch + ') does not exist'\n );\n error.hash = {\n text: `merge ${otherBranch}`,\n token: `merge ${otherBranch}`,\n expected: [`branch ${otherBranch}`],\n };\n throw error;\n }\n if (otherCommit === undefined || !otherCommit) {\n const error: any = new Error(\n 'Incorrect usage of \"merge\". Branch to be merged (' + otherBranch + ') has no commits'\n );\n error.hash = {\n text: `merge ${otherBranch}`,\n token: `merge ${otherBranch}`,\n expected: ['\"commit\"'],\n };\n throw error;\n }\n if (currentCommit === otherCommit) {\n const error: any = new Error('Incorrect usage of \"merge\". Both branches have same head');\n error.hash = {\n text: `merge ${otherBranch}`,\n token: `merge ${otherBranch}`,\n expected: ['branch abc'],\n };\n throw error;\n }\n if (customId && state.records.commits.has(customId)) {\n const error: any = new Error(\n 'Incorrect usage of \"merge\". Commit with id:' +\n customId +\n ' already exists, use different custom Id'\n );\n error.hash = {\n text: `merge ${otherBranch} ${customId} ${overrideType} ${customTags?.join(' ')}`,\n token: `merge ${otherBranch} ${customId} ${overrideType} ${customTags?.join(' ')}`,\n expected: [\n `merge ${otherBranch} ${customId}_UNIQUE ${overrideType} ${customTags?.join(' ')}`,\n ],\n };\n\n throw error;\n }\n\n const verifiedBranch: string = otherBranchCheck ? otherBranchCheck : ''; //figure out a cleaner way to do this\n\n const commit = {\n id: customId || `${state.records.seq}-${getID()}`,\n message: `merged branch ${otherBranch} into ${state.records.currBranch}`,\n seq: state.records.seq++,\n parents: state.records.head == null ? [] : [state.records.head.id, verifiedBranch],\n branch: state.records.currBranch,\n type: commitType.MERGE,\n customType: overrideType,\n customId: customId ? true : false,\n tags: customTags ?? [],\n } satisfies Commit;\n state.records.head = commit;\n state.records.commits.set(commit.id, commit);\n state.records.branches.set(state.records.currBranch, commit.id);\n log.debug(state.records.branches);\n log.debug('in mergeBranch');\n};\n\nexport const cherryPick = function (cherryPickDB: CherryPickDB) {\n let sourceId = cherryPickDB.id;\n let targetId = cherryPickDB.targetId;\n let tags = cherryPickDB.tags;\n let parentCommitId = cherryPickDB.parent;\n log.debug('Entering cherryPick:', sourceId, targetId, tags);\n const config = getConfig();\n sourceId = common.sanitizeText(sourceId, config);\n targetId = common.sanitizeText(targetId, config);\n\n tags = tags?.map((tag) => common.sanitizeText(tag, config));\n\n parentCommitId = common.sanitizeText(parentCommitId, config);\n\n if (!sourceId || !state.records.commits.has(sourceId)) {\n const error: any = new Error(\n 'Incorrect usage of \"cherryPick\". Source commit id should exist and provided'\n );\n error.hash = {\n text: `cherryPick ${sourceId} ${targetId}`,\n token: `cherryPick ${sourceId} ${targetId}`,\n expected: ['cherry-pick abc'],\n };\n throw error;\n }\n\n const sourceCommit = state.records.commits.get(sourceId);\n if (sourceCommit === undefined || !sourceCommit) {\n throw new Error('Incorrect usage of \"cherryPick\". Source commit id should exist and provided');\n }\n if (\n parentCommitId &&\n !(Array.isArray(sourceCommit.parents) && sourceCommit.parents.includes(parentCommitId))\n ) {\n const error = new Error(\n 'Invalid operation: The specified parent commit is not an immediate parent of the cherry-picked commit.'\n );\n throw error;\n }\n const sourceCommitBranch = sourceCommit.branch;\n if (sourceCommit.type === commitType.MERGE && !parentCommitId) {\n const error = new Error(\n 'Incorrect usage of cherry-pick: If the source commit is a merge commit, an immediate parent commit must be specified.'\n );\n throw error;\n }\n if (!targetId || !state.records.commits.has(targetId)) {\n // cherry-pick source commit to current branch\n\n if (sourceCommitBranch === state.records.currBranch) {\n const error: any = new Error(\n 'Incorrect usage of \"cherryPick\". Source commit is already on current branch'\n );\n error.hash = {\n text: `cherryPick ${sourceId} ${targetId}`,\n token: `cherryPick ${sourceId} ${targetId}`,\n expected: ['cherry-pick abc'],\n };\n throw error;\n }\n const currentCommitId = state.records.branches.get(state.records.currBranch);\n if (currentCommitId === undefined || !currentCommitId) {\n const error: any = new Error(\n `Incorrect usage of \"cherry-pick\". Current branch (${state.records.currBranch})has no commits`\n );\n error.hash = {\n text: `cherryPick ${sourceId} ${targetId}`,\n token: `cherryPick ${sourceId} ${targetId}`,\n expected: ['cherry-pick abc'],\n };\n throw error;\n }\n\n const currentCommit = state.records.commits.get(currentCommitId);\n if (currentCommit === undefined || !currentCommit) {\n const error: any = new Error(\n `Incorrect usage of \"cherry-pick\". Current branch (${state.records.currBranch})has no commits`\n );\n error.hash = {\n text: `cherryPick ${sourceId} ${targetId}`,\n token: `cherryPick ${sourceId} ${targetId}`,\n expected: ['cherry-pick abc'],\n };\n throw error;\n }\n const commit = {\n id: state.records.seq + '-' + getID(),\n message: `cherry-picked ${sourceCommit?.message} into ${state.records.currBranch}`,\n seq: state.records.seq++,\n parents: state.records.head == null ? [] : [state.records.head.id, sourceCommit.id],\n branch: state.records.currBranch,\n type: commitType.CHERRY_PICK,\n tags: tags\n ? tags.filter(Boolean)\n : [\n `cherry-pick:${sourceCommit.id}${\n sourceCommit.type === commitType.MERGE ? `|parent:${parentCommitId}` : ''\n }`,\n ],\n };\n\n state.records.head = commit;\n state.records.commits.set(commit.id, commit);\n state.records.branches.set(state.records.currBranch, commit.id);\n log.debug(state.records.branches);\n log.debug('in cherryPick');\n }\n};\nexport const checkout = function (branch: string) {\n branch = common.sanitizeText(branch, getConfig());\n if (!state.records.branches.has(branch)) {\n const error: any = new Error(\n `Trying to checkout branch which is not yet created. (Help try using \"branch ${branch}\")`\n );\n error.hash = {\n text: `checkout ${branch}`,\n token: `checkout ${branch}`,\n expected: [`branch ${branch}`],\n };\n throw error;\n } else {\n state.records.currBranch = branch;\n const id = state.records.branches.get(state.records.currBranch);\n if (id === undefined || !id) {\n state.records.head = null;\n } else {\n state.records.head = state.records.commits.get(id) ?? null;\n }\n }\n};\n\n/**\n * @param arr - array\n * @param key - key\n * @param newVal - new value\n */\nfunction upsert(arr: any[], key: any, newVal: any) {\n const index = arr.indexOf(key);\n if (index === -1) {\n arr.push(newVal);\n } else {\n arr.splice(index, 1, newVal);\n }\n}\n\nfunction prettyPrintCommitHistory(commitArr: Commit[]) {\n const commit = commitArr.reduce((out, commit) => {\n if (out.seq > commit.seq) {\n return out;\n }\n return commit;\n }, commitArr[0]);\n let line = '';\n commitArr.forEach(function (c) {\n if (c === commit) {\n line += '\\t*';\n } else {\n line += '\\t|';\n }\n });\n const label = [line, commit.id, commit.seq];\n for (const branch in state.records.branches) {\n if (state.records.branches.get(branch) === commit.id) {\n label.push(branch);\n }\n }\n log.debug(label.join(' '));\n if (commit.parents && commit.parents.length == 2 && commit.parents[0] && commit.parents[1]) {\n const newCommit = state.records.commits.get(commit.parents[0]);\n upsert(commitArr, commit, newCommit);\n if (commit.parents[1]) {\n commitArr.push(state.records.commits.get(commit.parents[1])!);\n }\n } else if (commit.parents.length == 0) {\n return;\n } else {\n if (commit.parents[0]) {\n const newCommit = state.records.commits.get(commit.parents[0]);\n upsert(commitArr, commit, newCommit);\n }\n }\n commitArr = uniqBy(commitArr, (c) => c.id);\n prettyPrintCommitHistory(commitArr);\n}\n\nexport const prettyPrint = function () {\n log.debug(state.records.commits);\n const node = getCommitsArray()[0];\n prettyPrintCommitHistory([node]);\n};\n\nexport const clear = function () {\n state.reset();\n commonClear();\n};\n\nexport const getBranchesAsObjArray = function () {\n const branchesArray = [...state.records.branchConfig.values()]\n .map((branchConfig, i) => {\n if (branchConfig.order !== null && branchConfig.order !== undefined) {\n return branchConfig;\n }\n return {\n ...branchConfig,\n order: parseFloat(`0.${i}`),\n };\n })\n .sort((a, b) => (a.order ?? 0) - (b.order ?? 0))\n .map(({ name }) => ({ name }));\n\n return branchesArray;\n};\n\nexport const getBranches = function () {\n return state.records.branches;\n};\nexport const getCommits = function () {\n return state.records.commits;\n};\nexport const getCommitsArray = function () {\n const commitArr = [...state.records.commits.values()];\n commitArr.forEach(function (o) {\n log.debug(o.id);\n });\n commitArr.sort((a, b) => a.seq - b.seq);\n return commitArr;\n};\nexport const getCurrentBranch = function () {\n return state.records.currBranch;\n};\nexport const getDirection = function () {\n return state.records.direction;\n};\nexport const getHead = function () {\n return state.records.head;\n};\n\nexport const db: GitGraphDB = {\n commitType,\n getConfig,\n setDirection,\n setOptions,\n getOptions,\n commit,\n branch,\n merge,\n cherryPick,\n checkout,\n //reset,\n prettyPrint,\n clear,\n getBranchesAsObjArray,\n getBranches,\n getCommits,\n getCommitsArray,\n getCurrentBranch,\n getDirection,\n getHead,\n setAccTitle,\n getAccTitle,\n getAccDescription,\n setAccDescription,\n setDiagramTitle,\n getDiagramTitle,\n};\n", "import type { GitGraph } from '@mermaid-js/parser';\nimport { parse } from '@mermaid-js/parser';\nimport type { ParserDefinition } from '../../diagram-api/types.js';\nimport { log } from '../../logger.js';\nimport { populateCommonDb } from '../common/populateCommonDb.js';\nimport { db } from './gitGraphAst.js';\nimport { commitType } from './gitGraphTypes.js';\nimport type {\n CheckoutAst,\n CherryPickingAst,\n MergeAst,\n CommitAst,\n BranchAst,\n GitGraphDBParseProvider,\n CommitDB,\n BranchDB,\n MergeDB,\n CherryPickDB,\n} from './gitGraphTypes.js';\n\nconst populate = (ast: GitGraph, db: GitGraphDBParseProvider) => {\n populateCommonDb(ast, db);\n // @ts-ignore: this wont exist if the direction is not specified\n if (ast.dir) {\n // @ts-ignore: this wont exist if the direction is not specified\n db.setDirection(ast.dir);\n }\n for (const statement of ast.statements) {\n parseStatement(statement, db);\n }\n};\n\nconst parseStatement = (statement: any, db: GitGraphDBParseProvider) => {\n const parsers: Record void> = {\n Commit: (stmt) => db.commit(parseCommit(stmt)),\n Branch: (stmt) => db.branch(parseBranch(stmt)),\n Merge: (stmt) => db.merge(parseMerge(stmt)),\n Checkout: (stmt) => db.checkout(parseCheckout(stmt)),\n CherryPicking: (stmt) => db.cherryPick(parseCherryPicking(stmt)),\n };\n\n const parser = parsers[statement.$type];\n if (parser) {\n parser(statement);\n } else {\n log.error(`Unknown statement type: ${statement.$type}`);\n }\n};\n\nconst parseCommit = (commit: CommitAst): CommitDB => {\n const commitDB: CommitDB = {\n id: commit.id,\n msg: commit.message ?? '',\n type: commit.type !== undefined ? commitType[commit.type] : commitType.NORMAL,\n tags: commit.tags ?? undefined,\n };\n return commitDB;\n};\n\nconst parseBranch = (branch: BranchAst): BranchDB => {\n const branchDB: BranchDB = {\n name: branch.name,\n order: branch.order ?? 0,\n };\n return branchDB;\n};\n\nconst parseMerge = (merge: MergeAst): MergeDB => {\n const mergeDB: MergeDB = {\n branch: merge.branch,\n id: merge.id ?? '',\n type: merge.type !== undefined ? commitType[merge.type] : undefined,\n tags: merge.tags ?? undefined,\n };\n return mergeDB;\n};\n\nconst parseCheckout = (checkout: CheckoutAst): string => {\n const branch = checkout.branch;\n return branch;\n};\n\nconst parseCherryPicking = (cherryPicking: CherryPickingAst): CherryPickDB => {\n const cherryPickDB: CherryPickDB = {\n id: cherryPicking.id,\n targetId: '',\n tags: cherryPicking.tags?.length === 0 ? undefined : cherryPicking.tags,\n parent: cherryPicking.parent,\n };\n return cherryPickDB;\n};\n\nexport const parser: ParserDefinition = {\n parse: async (input: string): Promise => {\n const ast: GitGraph = await parse('gitGraph', input);\n log.debug(ast);\n populate(ast, db);\n },\n};\n\nif (import.meta.vitest) {\n const { it, expect, describe } = import.meta.vitest;\n\n const mockDB: GitGraphDBParseProvider = {\n commitType: commitType,\n setDirection: vi.fn(),\n commit: vi.fn(),\n branch: vi.fn(),\n merge: vi.fn(),\n cherryPick: vi.fn(),\n checkout: vi.fn(),\n };\n\n describe('GitGraph Parser', () => {\n it('should parse a commit statement', () => {\n const commit = {\n $type: 'Commit',\n id: '1',\n message: 'test',\n tags: ['tag1', 'tag2'],\n type: 'NORMAL',\n };\n parseStatement(commit, mockDB);\n expect(mockDB.commit).toHaveBeenCalledWith({\n id: '1',\n msg: 'test',\n tags: ['tag1', 'tag2'],\n type: 0,\n });\n });\n it('should parse a branch statement', () => {\n const branch = {\n $type: 'Branch',\n name: 'newBranch',\n order: 1,\n };\n parseStatement(branch, mockDB);\n expect(mockDB.branch).toHaveBeenCalledWith({ name: 'newBranch', order: 1 });\n });\n it('should parse a checkout statement', () => {\n const checkout = {\n $type: 'Checkout',\n branch: 'newBranch',\n };\n parseStatement(checkout, mockDB);\n expect(mockDB.checkout).toHaveBeenCalledWith('newBranch');\n });\n it('should parse a merge statement', () => {\n const merge = {\n $type: 'Merge',\n branch: 'newBranch',\n id: '1',\n tags: ['tag1', 'tag2'],\n type: 'NORMAL',\n };\n parseStatement(merge, mockDB);\n expect(mockDB.merge).toHaveBeenCalledWith({\n branch: 'newBranch',\n id: '1',\n tags: ['tag1', 'tag2'],\n type: 0,\n });\n });\n it('should parse a cherry picking statement', () => {\n const cherryPick = {\n $type: 'CherryPicking',\n id: '1',\n tags: ['tag1', 'tag2'],\n parent: '2',\n };\n parseStatement(cherryPick, mockDB);\n expect(mockDB.cherryPick).toHaveBeenCalledWith({\n id: '1',\n targetId: '',\n parent: '2',\n tags: ['tag1', 'tag2'],\n });\n });\n\n it('should parse a langium generated gitGraph ast', () => {\n const dummy: GitGraph = {\n $type: 'GitGraph',\n statements: [],\n };\n const gitGraphAst: GitGraph = {\n $type: 'GitGraph',\n statements: [\n {\n $container: dummy,\n $type: 'Commit',\n id: '1',\n message: 'test',\n tags: ['tag1', 'tag2'],\n type: 'NORMAL',\n },\n {\n $container: dummy,\n $type: 'Branch',\n name: 'newBranch',\n order: 1,\n },\n {\n $container: dummy,\n $type: 'Merge',\n branch: 'newBranch',\n id: '1',\n tags: ['tag1', 'tag2'],\n type: 'NORMAL',\n },\n {\n $container: dummy,\n $type: 'Checkout',\n branch: 'newBranch',\n },\n {\n $container: dummy,\n $type: 'CherryPicking',\n id: '1',\n tags: ['tag1', 'tag2'],\n parent: '2',\n },\n ],\n };\n\n populate(gitGraphAst, mockDB);\n\n expect(mockDB.commit).toHaveBeenCalledWith({\n id: '1',\n msg: 'test',\n tags: ['tag1', 'tag2'],\n type: 0,\n });\n expect(mockDB.branch).toHaveBeenCalledWith({ name: 'newBranch', order: 1 });\n expect(mockDB.merge).toHaveBeenCalledWith({\n branch: 'newBranch',\n id: '1',\n tags: ['tag1', 'tag2'],\n type: 0,\n });\n expect(mockDB.checkout).toHaveBeenCalledWith('newBranch');\n });\n });\n}\n", "import { select } from 'd3';\nimport { getConfig, setupGraphViewbox } from '../../diagram-api/diagramAPI.js';\nimport { log } from '../../logger.js';\nimport utils from '../../utils.js';\nimport type { DrawDefinition } from '../../diagram-api/types.js';\nimport type d3 from 'd3';\nimport type { Commit, GitGraphDBRenderProvider, DiagramOrientation } from './gitGraphTypes.js';\nimport { commitType } from './gitGraphTypes.js';\n\ninterface BranchPosition {\n pos: number;\n index: number;\n}\n\ninterface CommitPosition {\n x: number;\n y: number;\n}\n\ninterface CommitPositionOffset extends CommitPosition {\n posWithOffset: number;\n}\n\nconst DEFAULT_CONFIG = getConfig();\nconst DEFAULT_GITGRAPH_CONFIG = DEFAULT_CONFIG?.gitGraph;\nconst LAYOUT_OFFSET = 10;\nconst COMMIT_STEP = 40;\nconst PX = 4;\nconst PY = 2;\n\nconst THEME_COLOR_LIMIT = 8;\nconst branchPos = new Map();\nconst commitPos = new Map();\nconst defaultPos = 30;\n\nlet allCommitsDict = new Map();\nlet lanes: number[] = [];\nlet maxPos = 0;\nlet dir: DiagramOrientation = 'LR';\n\nconst clear = () => {\n branchPos.clear();\n commitPos.clear();\n allCommitsDict.clear();\n maxPos = 0;\n lanes = [];\n dir = 'LR';\n};\n\nconst drawText = (txt: string | string[]) => {\n const svgLabel = document.createElementNS('http://www.w3.org/2000/svg', 'text');\n const rows = typeof txt === 'string' ? txt.split(/\\\\n|\\n|
/gi) : txt;\n\n rows.forEach((row) => {\n const tspan = document.createElementNS('http://www.w3.org/2000/svg', 'tspan');\n tspan.setAttributeNS('http://www.w3.org/XML/1998/namespace', 'xml:space', 'preserve');\n tspan.setAttribute('dy', '1em');\n tspan.setAttribute('x', '0');\n tspan.setAttribute('class', 'row');\n tspan.textContent = row.trim();\n svgLabel.appendChild(tspan);\n });\n\n return svgLabel;\n};\n\nconst findClosestParent = (parents: string[]): string | undefined => {\n let closestParent: string | undefined;\n let comparisonFunc;\n let targetPosition: number;\n if (dir === 'BT') {\n comparisonFunc = (a: number, b: number) => a <= b;\n targetPosition = Infinity;\n } else {\n comparisonFunc = (a: number, b: number) => a >= b;\n targetPosition = 0;\n }\n\n parents.forEach((parent) => {\n const parentPosition =\n dir === 'TB' || dir == 'BT' ? commitPos.get(parent)?.y : commitPos.get(parent)?.x;\n\n if (parentPosition !== undefined && comparisonFunc(parentPosition, targetPosition)) {\n closestParent = parent;\n targetPosition = parentPosition;\n }\n });\n\n return closestParent;\n};\n\nconst findClosestParentBT = (parents: string[]) => {\n let closestParent = '';\n let maxPosition = Infinity;\n\n parents.forEach((parent) => {\n const parentPosition = commitPos.get(parent)!.y;\n if (parentPosition <= maxPosition) {\n closestParent = parent;\n maxPosition = parentPosition;\n }\n });\n return closestParent || undefined;\n};\n\nconst setParallelBTPos = (\n sortedKeys: string[],\n commits: Map,\n defaultPos: number\n) => {\n let curPos = defaultPos;\n let maxPosition = defaultPos;\n const roots: Commit[] = [];\n\n sortedKeys.forEach((key) => {\n const commit = commits.get(key);\n if (!commit) {\n throw new Error(`Commit not found for key ${key}`);\n }\n\n if (commit.parents.length) {\n curPos = calculateCommitPosition(commit);\n maxPosition = Math.max(curPos, maxPosition);\n } else {\n roots.push(commit);\n }\n setCommitPosition(commit, curPos);\n });\n\n curPos = maxPosition;\n roots.forEach((commit) => {\n setRootPosition(commit, curPos, defaultPos);\n });\n sortedKeys.forEach((key) => {\n const commit = commits.get(key);\n\n if (commit?.parents.length) {\n const closestParent = findClosestParentBT(commit.parents)!;\n curPos = commitPos.get(closestParent)!.y - COMMIT_STEP;\n if (curPos <= maxPosition) {\n maxPosition = curPos;\n }\n const x = branchPos.get(commit.branch)!.pos;\n const y = curPos - LAYOUT_OFFSET;\n commitPos.set(commit.id, { x: x, y: y });\n }\n });\n};\n\nconst findClosestParentPos = (commit: Commit): number => {\n const closestParent = findClosestParent(commit.parents.filter((p) => p !== null));\n if (!closestParent) {\n throw new Error(`Closest parent not found for commit ${commit.id}`);\n }\n\n const closestParentPos = commitPos.get(closestParent)?.y;\n if (closestParentPos === undefined) {\n throw new Error(`Closest parent position not found for commit ${commit.id}`);\n }\n return closestParentPos;\n};\n\nconst calculateCommitPosition = (commit: Commit): number => {\n const closestParentPos = findClosestParentPos(commit);\n return closestParentPos + COMMIT_STEP;\n};\n\nconst setCommitPosition = (commit: Commit, curPos: number): CommitPosition => {\n const branch = branchPos.get(commit.branch);\n\n if (!branch) {\n throw new Error(`Branch not found for commit ${commit.id}`);\n }\n\n const x = branch.pos;\n const y = curPos + LAYOUT_OFFSET;\n commitPos.set(commit.id, { x, y });\n return { x, y };\n};\n\nconst setRootPosition = (commit: Commit, curPos: number, defaultPos: number) => {\n const branch = branchPos.get(commit.branch);\n if (!branch) {\n throw new Error(`Branch not found for commit ${commit.id}`);\n }\n\n const y = curPos + defaultPos;\n const x = branch.pos;\n commitPos.set(commit.id, { x, y });\n};\n\nconst drawCommitBullet = (\n gBullets: d3.Selection,\n commit: Commit,\n commitPosition: CommitPositionOffset,\n typeClass: string,\n branchIndex: number,\n commitSymbolType: number\n) => {\n if (commitSymbolType === commitType.HIGHLIGHT) {\n gBullets\n .append('rect')\n .attr('x', commitPosition.x - 10)\n .attr('y', commitPosition.y - 10)\n .attr('width', 20)\n .attr('height', 20)\n .attr(\n 'class',\n `commit ${commit.id} commit-highlight${branchIndex % THEME_COLOR_LIMIT} ${typeClass}-outer`\n );\n gBullets\n .append('rect')\n .attr('x', commitPosition.x - 6)\n .attr('y', commitPosition.y - 6)\n .attr('width', 12)\n .attr('height', 12)\n .attr(\n 'class',\n `commit ${commit.id} commit${branchIndex % THEME_COLOR_LIMIT} ${typeClass}-inner`\n );\n } else if (commitSymbolType === commitType.CHERRY_PICK) {\n gBullets\n .append('circle')\n .attr('cx', commitPosition.x)\n .attr('cy', commitPosition.y)\n .attr('r', 10)\n .attr('class', `commit ${commit.id} ${typeClass}`);\n gBullets\n .append('circle')\n .attr('cx', commitPosition.x - 3)\n .attr('cy', commitPosition.y + 2)\n .attr('r', 2.75)\n .attr('fill', '#fff')\n .attr('class', `commit ${commit.id} ${typeClass}`);\n gBullets\n .append('circle')\n .attr('cx', commitPosition.x + 3)\n .attr('cy', commitPosition.y + 2)\n .attr('r', 2.75)\n .attr('fill', '#fff')\n .attr('class', `commit ${commit.id} ${typeClass}`);\n gBullets\n .append('line')\n .attr('x1', commitPosition.x + 3)\n .attr('y1', commitPosition.y + 1)\n .attr('x2', commitPosition.x)\n .attr('y2', commitPosition.y - 5)\n .attr('stroke', '#fff')\n .attr('class', `commit ${commit.id} ${typeClass}`);\n gBullets\n .append('line')\n .attr('x1', commitPosition.x - 3)\n .attr('y1', commitPosition.y + 1)\n .attr('x2', commitPosition.x)\n .attr('y2', commitPosition.y - 5)\n .attr('stroke', '#fff')\n .attr('class', `commit ${commit.id} ${typeClass}`);\n } else {\n const circle = gBullets.append('circle');\n circle.attr('cx', commitPosition.x);\n circle.attr('cy', commitPosition.y);\n circle.attr('r', commit.type === commitType.MERGE ? 9 : 10);\n circle.attr('class', `commit ${commit.id} commit${branchIndex % THEME_COLOR_LIMIT}`);\n if (commitSymbolType === commitType.MERGE) {\n const circle2 = gBullets.append('circle');\n circle2.attr('cx', commitPosition.x);\n circle2.attr('cy', commitPosition.y);\n circle2.attr('r', 6);\n circle2.attr(\n 'class',\n `commit ${typeClass} ${commit.id} commit${branchIndex % THEME_COLOR_LIMIT}`\n );\n }\n if (commitSymbolType === commitType.REVERSE) {\n const cross = gBullets.append('path');\n cross\n .attr(\n 'd',\n `M ${commitPosition.x - 5},${commitPosition.y - 5}L${commitPosition.x + 5},${commitPosition.y + 5}M${commitPosition.x - 5},${commitPosition.y + 5}L${commitPosition.x + 5},${commitPosition.y - 5}`\n )\n .attr('class', `commit ${typeClass} ${commit.id} commit${branchIndex % THEME_COLOR_LIMIT}`);\n }\n }\n};\n\nconst drawCommitLabel = (\n gLabels: d3.Selection,\n commit: Commit,\n commitPosition: CommitPositionOffset,\n pos: number\n) => {\n if (\n commit.type !== commitType.CHERRY_PICK &&\n ((commit.customId && commit.type === commitType.MERGE) || commit.type !== commitType.MERGE) &&\n DEFAULT_GITGRAPH_CONFIG?.showCommitLabel\n ) {\n const wrapper = gLabels.append('g');\n const labelBkg = wrapper.insert('rect').attr('class', 'commit-label-bkg');\n const text = wrapper\n .append('text')\n .attr('x', pos)\n .attr('y', commitPosition.y + 25)\n .attr('class', 'commit-label')\n .text(commit.id);\n const bbox = text.node()?.getBBox();\n\n if (bbox) {\n labelBkg\n .attr('x', commitPosition.posWithOffset - bbox.width / 2 - PY)\n .attr('y', commitPosition.y + 13.5)\n .attr('width', bbox.width + 2 * PY)\n .attr('height', bbox.height + 2 * PY);\n\n if (dir === 'TB' || dir === 'BT') {\n labelBkg\n .attr('x', commitPosition.x - (bbox.width + 4 * PX + 5))\n .attr('y', commitPosition.y - 12);\n text\n .attr('x', commitPosition.x - (bbox.width + 4 * PX))\n .attr('y', commitPosition.y + bbox.height - 12);\n } else {\n text.attr('x', commitPosition.posWithOffset - bbox.width / 2);\n }\n\n if (DEFAULT_GITGRAPH_CONFIG.rotateCommitLabel) {\n if (dir === 'TB' || dir === 'BT') {\n text.attr(\n 'transform',\n 'rotate(' + -45 + ', ' + commitPosition.x + ', ' + commitPosition.y + ')'\n );\n labelBkg.attr(\n 'transform',\n 'rotate(' + -45 + ', ' + commitPosition.x + ', ' + commitPosition.y + ')'\n );\n } else {\n const r_x = -7.5 - ((bbox.width + 10) / 25) * 9.5;\n const r_y = 10 + (bbox.width / 25) * 8.5;\n wrapper.attr(\n 'transform',\n 'translate(' +\n r_x +\n ', ' +\n r_y +\n ') rotate(' +\n -45 +\n ', ' +\n pos +\n ', ' +\n commitPosition.y +\n ')'\n );\n }\n }\n }\n }\n};\n\nconst drawCommitTags = (\n gLabels: d3.Selection,\n commit: Commit,\n commitPosition: CommitPositionOffset,\n pos: number\n) => {\n if (commit.tags.length > 0) {\n let yOffset = 0;\n let maxTagBboxWidth = 0;\n let maxTagBboxHeight = 0;\n const tagElements = [];\n\n for (const tagValue of commit.tags.reverse()) {\n const rect = gLabels.insert('polygon');\n const hole = gLabels.append('circle');\n const tag = gLabels\n .append('text')\n .attr('y', commitPosition.y - 16 - yOffset)\n .attr('class', 'tag-label')\n .text(tagValue);\n const tagBbox = tag.node()?.getBBox();\n if (!tagBbox) {\n throw new Error('Tag bbox not found');\n }\n\n maxTagBboxWidth = Math.max(maxTagBboxWidth, tagBbox.width);\n maxTagBboxHeight = Math.max(maxTagBboxHeight, tagBbox.height);\n\n tag.attr('x', commitPosition.posWithOffset - tagBbox.width / 2);\n\n tagElements.push({\n tag,\n hole,\n rect,\n yOffset,\n });\n\n yOffset += 20;\n }\n\n for (const { tag, hole, rect, yOffset } of tagElements) {\n const h2 = maxTagBboxHeight / 2;\n const ly = commitPosition.y - 19.2 - yOffset;\n rect.attr('class', 'tag-label-bkg').attr(\n 'points',\n `\n ${pos - maxTagBboxWidth / 2 - PX / 2},${ly + PY} \n ${pos - maxTagBboxWidth / 2 - PX / 2},${ly - PY}\n ${commitPosition.posWithOffset - maxTagBboxWidth / 2 - PX},${ly - h2 - PY}\n ${commitPosition.posWithOffset + maxTagBboxWidth / 2 + PX},${ly - h2 - PY}\n ${commitPosition.posWithOffset + maxTagBboxWidth / 2 + PX},${ly + h2 + PY}\n ${commitPosition.posWithOffset - maxTagBboxWidth / 2 - PX},${ly + h2 + PY}`\n );\n\n hole\n .attr('cy', ly)\n .attr('cx', pos - maxTagBboxWidth / 2 + PX / 2)\n .attr('r', 1.5)\n .attr('class', 'tag-hole');\n\n if (dir === 'TB' || dir === 'BT') {\n const yOrigin = pos + yOffset;\n\n rect\n .attr('class', 'tag-label-bkg')\n .attr(\n 'points',\n `\n ${commitPosition.x},${yOrigin + 2}\n ${commitPosition.x},${yOrigin - 2}\n ${commitPosition.x + LAYOUT_OFFSET},${yOrigin - h2 - 2}\n ${commitPosition.x + LAYOUT_OFFSET + maxTagBboxWidth + 4},${yOrigin - h2 - 2}\n ${commitPosition.x + LAYOUT_OFFSET + maxTagBboxWidth + 4},${yOrigin + h2 + 2}\n ${commitPosition.x + LAYOUT_OFFSET},${yOrigin + h2 + 2}`\n )\n .attr('transform', 'translate(12,12) rotate(45, ' + commitPosition.x + ',' + pos + ')');\n hole\n .attr('cx', commitPosition.x + PX / 2)\n .attr('cy', yOrigin)\n .attr('transform', 'translate(12,12) rotate(45, ' + commitPosition.x + ',' + pos + ')');\n tag\n .attr('x', commitPosition.x + 5)\n .attr('y', yOrigin + 3)\n .attr('transform', 'translate(14,14) rotate(45, ' + commitPosition.x + ',' + pos + ')');\n }\n }\n }\n};\n\nconst getCommitClassType = (commit: Commit): string => {\n const commitSymbolType = commit.customType ?? commit.type;\n switch (commitSymbolType) {\n case commitType.NORMAL:\n return 'commit-normal';\n case commitType.REVERSE:\n return 'commit-reverse';\n case commitType.HIGHLIGHT:\n return 'commit-highlight';\n case commitType.MERGE:\n return 'commit-merge';\n case commitType.CHERRY_PICK:\n return 'commit-cherry-pick';\n default:\n return 'commit-normal';\n }\n};\n\nconst calculatePosition = (\n commit: Commit,\n dir: string,\n pos: number,\n commitPos: Map\n): number => {\n const defaultCommitPosition = { x: 0, y: 0 }; // Default position if commit is not found\n\n if (commit.parents.length > 0) {\n const closestParent = findClosestParent(commit.parents);\n if (closestParent) {\n const parentPosition = commitPos.get(closestParent) ?? defaultCommitPosition;\n\n if (dir === 'TB') {\n return parentPosition.y + COMMIT_STEP;\n } else if (dir === 'BT') {\n const currentPosition = commitPos.get(commit.id) ?? defaultCommitPosition;\n return currentPosition.y - COMMIT_STEP;\n } else {\n return parentPosition.x + COMMIT_STEP;\n }\n }\n } else {\n if (dir === 'TB') {\n return defaultPos;\n } else if (dir === 'BT') {\n const currentPosition = commitPos.get(commit.id) ?? defaultCommitPosition;\n return currentPosition.y - COMMIT_STEP;\n } else {\n return 0;\n }\n }\n return 0;\n};\n\nconst getCommitPosition = (\n commit: Commit,\n pos: number,\n isParallelCommits: boolean\n): CommitPositionOffset => {\n const posWithOffset = dir === 'BT' && isParallelCommits ? pos : pos + LAYOUT_OFFSET;\n const y = dir === 'TB' || dir === 'BT' ? posWithOffset : branchPos.get(commit.branch)?.pos;\n const x = dir === 'TB' || dir === 'BT' ? branchPos.get(commit.branch)?.pos : posWithOffset;\n if (x === undefined || y === undefined) {\n throw new Error(`Position were undefined for commit ${commit.id}`);\n }\n return { x, y, posWithOffset };\n};\n\nconst drawCommits = (\n svg: d3.Selection,\n commits: Map,\n modifyGraph: boolean\n) => {\n if (!DEFAULT_GITGRAPH_CONFIG) {\n throw new Error('GitGraph config not found');\n }\n const gBullets = svg.append('g').attr('class', 'commit-bullets');\n const gLabels = svg.append('g').attr('class', 'commit-labels');\n let pos = dir === 'TB' || dir === 'BT' ? defaultPos : 0;\n const keys = [...commits.keys()];\n const isParallelCommits = DEFAULT_GITGRAPH_CONFIG?.parallelCommits ?? false;\n\n const sortKeys = (a: string, b: string) => {\n const seqA = commits.get(a)?.seq;\n const seqB = commits.get(b)?.seq;\n return seqA !== undefined && seqB !== undefined ? seqA - seqB : 0;\n };\n\n let sortedKeys = keys.sort(sortKeys);\n if (dir === 'BT') {\n if (isParallelCommits) {\n setParallelBTPos(sortedKeys, commits, pos);\n }\n sortedKeys = sortedKeys.reverse();\n }\n\n sortedKeys.forEach((key) => {\n const commit = commits.get(key);\n if (!commit) {\n throw new Error(`Commit not found for key ${key}`);\n }\n if (isParallelCommits) {\n pos = calculatePosition(commit, dir, pos, commitPos);\n }\n\n const commitPosition = getCommitPosition(commit, pos, isParallelCommits);\n // Don't draw the commits now but calculate the positioning which is used by the branch lines etc.\n if (modifyGraph) {\n const typeClass = getCommitClassType(commit);\n const commitSymbolType = commit.customType ?? commit.type;\n const branchIndex = branchPos.get(commit.branch)?.index ?? 0;\n drawCommitBullet(gBullets, commit, commitPosition, typeClass, branchIndex, commitSymbolType);\n drawCommitLabel(gLabels, commit, commitPosition, pos);\n drawCommitTags(gLabels, commit, commitPosition, pos);\n }\n if (dir === 'TB' || dir === 'BT') {\n commitPos.set(commit.id, { x: commitPosition.x, y: commitPosition.posWithOffset });\n } else {\n commitPos.set(commit.id, { x: commitPosition.posWithOffset, y: commitPosition.y });\n }\n pos = dir === 'BT' && isParallelCommits ? pos + COMMIT_STEP : pos + COMMIT_STEP + LAYOUT_OFFSET;\n if (pos > maxPos) {\n maxPos = pos;\n }\n });\n};\n\nconst shouldRerouteArrow = (\n commitA: Commit,\n commitB: Commit,\n p1: CommitPosition,\n p2: CommitPosition,\n allCommits: Map\n) => {\n const commitBIsFurthest = dir === 'TB' || dir === 'BT' ? p1.x < p2.x : p1.y < p2.y;\n const branchToGetCurve = commitBIsFurthest ? commitB.branch : commitA.branch;\n const isOnBranchToGetCurve = (x: Commit) => x.branch === branchToGetCurve;\n const isBetweenCommits = (x: Commit) => x.seq > commitA.seq && x.seq < commitB.seq;\n return [...allCommits.values()].some((commitX) => {\n return isBetweenCommits(commitX) && isOnBranchToGetCurve(commitX);\n });\n};\n\nconst findLane = (y1: number, y2: number, depth = 0): number => {\n const candidate = y1 + Math.abs(y1 - y2) / 2;\n if (depth > 5) {\n return candidate;\n }\n\n const ok = lanes.every((lane) => Math.abs(lane - candidate) >= 10);\n if (ok) {\n lanes.push(candidate);\n return candidate;\n }\n const diff = Math.abs(y1 - y2);\n return findLane(y1, y2 - diff / 5, depth + 1);\n};\n\nconst drawArrow = (\n svg: d3.Selection,\n commitA: Commit,\n commitB: Commit,\n allCommits: Map\n) => {\n const p1 = commitPos.get(commitA.id); // arrowStart\n const p2 = commitPos.get(commitB.id); // arrowEnd\n if (p1 === undefined || p2 === undefined) {\n throw new Error(`Commit positions not found for commits ${commitA.id} and ${commitB.id}`);\n }\n const arrowNeedsRerouting = shouldRerouteArrow(commitA, commitB, p1, p2, allCommits);\n // log.debug('drawArrow', p1, p2, arrowNeedsRerouting, commitA.id, commitB.id);\n\n // Lower-right quadrant logic; top-left is 0,0\n\n let arc = '';\n let arc2 = '';\n let radius = 0;\n let offset = 0;\n\n let colorClassNum = branchPos.get(commitB.branch)?.index;\n if (commitB.type === commitType.MERGE && commitA.id !== commitB.parents[0]) {\n colorClassNum = branchPos.get(commitA.branch)?.index;\n }\n\n let lineDef;\n if (arrowNeedsRerouting) {\n arc = 'A 10 10, 0, 0, 0,';\n arc2 = 'A 10 10, 0, 0, 1,';\n radius = 10;\n offset = 10;\n\n const lineY = p1.y < p2.y ? findLane(p1.y, p2.y) : findLane(p2.y, p1.y);\n\n const lineX = p1.x < p2.x ? findLane(p1.x, p2.x) : findLane(p2.x, p1.x);\n\n if (dir === 'TB') {\n if (p1.x < p2.x) {\n // Source commit is on branch position left of destination commit\n // so render arrow rightward with colour of destination branch\n\n lineDef = `M ${p1.x} ${p1.y} L ${lineX - radius} ${p1.y} ${arc2} ${lineX} ${\n p1.y + offset\n } L ${lineX} ${p2.y - radius} ${arc} ${lineX + offset} ${p2.y} L ${p2.x} ${p2.y}`;\n } else {\n // Source commit is on branch position right of destination commit\n // so render arrow leftward with colour of source branch\n\n colorClassNum = branchPos.get(commitA.branch)?.index;\n\n lineDef = `M ${p1.x} ${p1.y} L ${lineX + radius} ${p1.y} ${arc} ${lineX} ${p1.y + offset} L ${lineX} ${p2.y - radius} ${arc2} ${lineX - offset} ${p2.y} L ${p2.x} ${p2.y}`;\n }\n } else if (dir === 'BT') {\n if (p1.x < p2.x) {\n // Source commit is on branch position left of destination commit\n // so render arrow rightward with colour of destination branch\n\n lineDef = `M ${p1.x} ${p1.y} L ${lineX - radius} ${p1.y} ${arc} ${lineX} ${p1.y - offset} L ${lineX} ${p2.y + radius} ${arc2} ${lineX + offset} ${p2.y} L ${p2.x} ${p2.y}`;\n } else {\n // Source commit is on branch position right of destination commit\n // so render arrow leftward with colour of source branch\n\n colorClassNum = branchPos.get(commitA.branch)?.index;\n\n lineDef = `M ${p1.x} ${p1.y} L ${lineX + radius} ${p1.y} ${arc2} ${lineX} ${p1.y - offset} L ${lineX} ${p2.y + radius} ${arc} ${lineX - offset} ${p2.y} L ${p2.x} ${p2.y}`;\n }\n } else {\n if (p1.y < p2.y) {\n // Source commit is on branch positioned above destination commit\n // so render arrow downward with colour of destination branch\n\n lineDef = `M ${p1.x} ${p1.y} L ${p1.x} ${lineY - radius} ${arc} ${\n p1.x + offset\n } ${lineY} L ${p2.x - radius} ${lineY} ${arc2} ${p2.x} ${lineY + offset} L ${p2.x} ${p2.y}`;\n } else {\n // Source commit is on branch positioned below destination commit\n // so render arrow upward with colour of source branch\n\n colorClassNum = branchPos.get(commitA.branch)?.index;\n\n lineDef = `M ${p1.x} ${p1.y} L ${p1.x} ${lineY + radius} ${arc2} ${\n p1.x + offset\n } ${lineY} L ${p2.x - radius} ${lineY} ${arc} ${p2.x} ${lineY - offset} L ${p2.x} ${p2.y}`;\n }\n }\n } else {\n arc = 'A 20 20, 0, 0, 0,';\n arc2 = 'A 20 20, 0, 0, 1,';\n radius = 20;\n offset = 20;\n\n if (dir === 'TB') {\n if (p1.x < p2.x) {\n if (commitB.type === commitType.MERGE && commitA.id !== commitB.parents[0]) {\n lineDef = `M ${p1.x} ${p1.y} L ${p1.x} ${p2.y - radius} ${arc} ${p1.x + offset} ${\n p2.y\n } L ${p2.x} ${p2.y}`;\n } else {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x - radius} ${p1.y} ${arc2} ${p2.x} ${\n p1.y + offset\n } L ${p2.x} ${p2.y}`;\n }\n }\n\n if (p1.x > p2.x) {\n arc = 'A 20 20, 0, 0, 0,';\n arc2 = 'A 20 20, 0, 0, 1,';\n radius = 20;\n offset = 20;\n if (commitB.type === commitType.MERGE && commitA.id !== commitB.parents[0]) {\n lineDef = `M ${p1.x} ${p1.y} L ${p1.x} ${p2.y - radius} ${arc2} ${p1.x - offset} ${\n p2.y\n } L ${p2.x} ${p2.y}`;\n } else {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x + radius} ${p1.y} ${arc} ${p2.x} ${\n p1.y + offset\n } L ${p2.x} ${p2.y}`;\n }\n }\n if (p1.x === p2.x) {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x} ${p2.y}`;\n }\n } else if (dir === 'BT') {\n if (p1.x < p2.x) {\n if (commitB.type === commitType.MERGE && commitA.id !== commitB.parents[0]) {\n lineDef = `M ${p1.x} ${p1.y} L ${p1.x} ${p2.y + radius} ${arc2} ${p1.x + offset} ${\n p2.y\n } L ${p2.x} ${p2.y}`;\n } else {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x - radius} ${p1.y} ${arc} ${p2.x} ${\n p1.y - offset\n } L ${p2.x} ${p2.y}`;\n }\n }\n if (p1.x > p2.x) {\n arc = 'A 20 20, 0, 0, 0,';\n arc2 = 'A 20 20, 0, 0, 1,';\n radius = 20;\n offset = 20;\n\n if (commitB.type === commitType.MERGE && commitA.id !== commitB.parents[0]) {\n lineDef = `M ${p1.x} ${p1.y} L ${p1.x} ${p2.y + radius} ${arc} ${p1.x - offset} ${\n p2.y\n } L ${p2.x} ${p2.y}`;\n } else {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x - radius} ${p1.y} ${arc} ${p2.x} ${\n p1.y - offset\n } L ${p2.x} ${p2.y}`;\n }\n }\n\n if (p1.x === p2.x) {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x} ${p2.y}`;\n }\n } else {\n if (p1.y < p2.y) {\n if (commitB.type === commitType.MERGE && commitA.id !== commitB.parents[0]) {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x - radius} ${p1.y} ${arc2} ${p2.x} ${\n p1.y + offset\n } L ${p2.x} ${p2.y}`;\n } else {\n lineDef = `M ${p1.x} ${p1.y} L ${p1.x} ${p2.y - radius} ${arc} ${p1.x + offset} ${\n p2.y\n } L ${p2.x} ${p2.y}`;\n }\n }\n if (p1.y > p2.y) {\n if (commitB.type === commitType.MERGE && commitA.id !== commitB.parents[0]) {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x - radius} ${p1.y} ${arc} ${p2.x} ${\n p1.y - offset\n } L ${p2.x} ${p2.y}`;\n } else {\n lineDef = `M ${p1.x} ${p1.y} L ${p1.x} ${p2.y + radius} ${arc2} ${p1.x + offset} ${\n p2.y\n } L ${p2.x} ${p2.y}`;\n }\n }\n\n if (p1.y === p2.y) {\n lineDef = `M ${p1.x} ${p1.y} L ${p2.x} ${p2.y}`;\n }\n }\n }\n if (lineDef === undefined) {\n throw new Error('Line definition not found');\n }\n svg\n .append('path')\n .attr('d', lineDef)\n .attr('class', 'arrow arrow' + (colorClassNum! % THEME_COLOR_LIMIT));\n};\n\nconst drawArrows = (\n svg: d3.Selection,\n commits: Map\n) => {\n const gArrows = svg.append('g').attr('class', 'commit-arrows');\n [...commits.keys()].forEach((key) => {\n const commit = commits.get(key);\n\n if (commit!.parents && commit!.parents.length > 0) {\n commit!.parents.forEach((parent) => {\n drawArrow(gArrows, commits.get(parent)!, commit!, commits);\n });\n }\n });\n};\n\nconst drawBranches = (\n svg: d3.Selection,\n branches: { name: string }[]\n) => {\n const g = svg.append('g');\n branches.forEach((branch, index) => {\n const adjustIndexForTheme = index % THEME_COLOR_LIMIT;\n\n const pos = branchPos.get(branch.name)?.pos;\n if (pos === undefined) {\n throw new Error(`Position not found for branch ${branch.name}`);\n }\n const line = g.append('line');\n line.attr('x1', 0);\n line.attr('y1', pos);\n line.attr('x2', maxPos);\n line.attr('y2', pos);\n line.attr('class', 'branch branch' + adjustIndexForTheme);\n\n if (dir === 'TB') {\n line.attr('y1', defaultPos);\n line.attr('x1', pos);\n line.attr('y2', maxPos);\n line.attr('x2', pos);\n } else if (dir === 'BT') {\n line.attr('y1', maxPos);\n line.attr('x1', pos);\n line.attr('y2', defaultPos);\n line.attr('x2', pos);\n }\n lanes.push(pos);\n\n const name = branch.name;\n\n // Create the actual text element\n const labelElement = drawText(name);\n // Create outer g, edgeLabel, this will be positioned after graph layout\n const bkg = g.insert('rect');\n const branchLabel = g.insert('g').attr('class', 'branchLabel');\n\n // Create inner g, label, this will be positioned now for centering the text\n const label = branchLabel.insert('g').attr('class', 'label branch-label' + adjustIndexForTheme);\n\n label.node()!.appendChild(labelElement);\n const bbox = labelElement.getBBox();\n bkg\n .attr('class', 'branchLabelBkg label' + adjustIndexForTheme)\n .attr('rx', 4)\n .attr('ry', 4)\n .attr('x', -bbox.width - 4 - (DEFAULT_GITGRAPH_CONFIG?.rotateCommitLabel === true ? 30 : 0))\n .attr('y', -bbox.height / 2 + 8)\n .attr('width', bbox.width + 18)\n .attr('height', bbox.height + 4);\n label.attr(\n 'transform',\n 'translate(' +\n (-bbox.width - 14 - (DEFAULT_GITGRAPH_CONFIG?.rotateCommitLabel === true ? 30 : 0)) +\n ', ' +\n (pos - bbox.height / 2 - 1) +\n ')'\n );\n if (dir === 'TB') {\n bkg.attr('x', pos - bbox.width / 2 - 10).attr('y', 0);\n label.attr('transform', 'translate(' + (pos - bbox.width / 2 - 5) + ', ' + 0 + ')');\n } else if (dir === 'BT') {\n bkg.attr('x', pos - bbox.width / 2 - 10).attr('y', maxPos);\n label.attr('transform', 'translate(' + (pos - bbox.width / 2 - 5) + ', ' + maxPos + ')');\n } else {\n bkg.attr('transform', 'translate(' + -19 + ', ' + (pos - bbox.height / 2) + ')');\n }\n });\n};\n\nconst setBranchPosition = function (\n name: string,\n pos: number,\n index: number,\n bbox: DOMRect,\n rotateCommitLabel: boolean\n): number {\n branchPos.set(name, { pos, index });\n pos += 50 + (rotateCommitLabel ? 40 : 0) + (dir === 'TB' || dir === 'BT' ? bbox.width / 2 : 0);\n return pos;\n};\n\nexport const draw: DrawDefinition = function (txt, id, ver, diagObj) {\n clear();\n\n log.debug('in gitgraph renderer', txt + '\\n', 'id:', id, ver);\n if (!DEFAULT_GITGRAPH_CONFIG) {\n throw new Error('GitGraph config not found');\n }\n const rotateCommitLabel = DEFAULT_GITGRAPH_CONFIG.rotateCommitLabel ?? false;\n const db = diagObj.db as GitGraphDBRenderProvider;\n allCommitsDict = db.getCommits();\n const branches = db.getBranchesAsObjArray();\n dir = db.getDirection();\n const diagram = select(`[id=\"${id}\"]`);\n let pos = 0;\n\n branches.forEach((branch, index) => {\n const labelElement = drawText(branch.name);\n const g = diagram.append('g');\n const branchLabel = g.insert('g').attr('class', 'branchLabel');\n const label = branchLabel.insert('g').attr('class', 'label branch-label');\n label.node()?.appendChild(labelElement);\n const bbox = labelElement.getBBox();\n\n pos = setBranchPosition(branch.name, pos, index, bbox, rotateCommitLabel);\n label.remove();\n branchLabel.remove();\n g.remove();\n });\n\n drawCommits(diagram, allCommitsDict, false);\n if (DEFAULT_GITGRAPH_CONFIG.showBranches) {\n drawBranches(diagram, branches);\n }\n drawArrows(diagram, allCommitsDict);\n drawCommits(diagram, allCommitsDict, true);\n\n utils.insertTitle(\n diagram,\n 'gitTitleText',\n DEFAULT_GITGRAPH_CONFIG.titleTopMargin ?? 0,\n db.getDiagramTitle()\n );\n\n // Setup the view box and size of the svg element\n setupGraphViewbox(\n undefined,\n diagram,\n DEFAULT_GITGRAPH_CONFIG.diagramPadding,\n DEFAULT_GITGRAPH_CONFIG.useMaxWidth\n );\n};\n\nexport default {\n draw,\n};\n\nif (import.meta.vitest) {\n const { it, expect, describe } = import.meta.vitest;\n\n describe('drawText', () => {\n it('should drawText', () => {\n const svgLabel = drawText('main');\n expect(svgLabel).toBeDefined();\n expect(svgLabel.children[0].innerHTML).toBe('main');\n });\n });\n\n describe('branchPosition', () => {\n const bbox: DOMRect = {\n x: 0,\n y: 0,\n width: 10,\n height: 10,\n top: 0,\n right: 0,\n bottom: 0,\n left: 0,\n toJSON: () => '',\n };\n\n it('should setBranchPositions LR with two branches', () => {\n dir = 'LR';\n\n const pos = setBranchPosition('main', 0, 0, bbox, true);\n expect(pos).toBe(90);\n expect(branchPos.get('main')).toEqual({ pos: 0, index: 0 });\n const posNext = setBranchPosition('develop', pos, 1, bbox, true);\n expect(posNext).toBe(180);\n expect(branchPos.get('develop')).toEqual({ pos: pos, index: 1 });\n });\n\n it('should setBranchPositions TB with two branches', () => {\n dir = 'TB';\n bbox.width = 34.9921875;\n\n const pos = setBranchPosition('main', 0, 0, bbox, true);\n expect(pos).toBe(107.49609375);\n expect(branchPos.get('main')).toEqual({ pos: 0, index: 0 });\n\n bbox.width = 56.421875;\n const posNext = setBranchPosition('develop', pos, 1, bbox, true);\n expect(posNext).toBe(225.70703125);\n expect(branchPos.get('develop')).toEqual({ pos: pos, index: 1 });\n });\n });\n\n describe('commitPosition', () => {\n const commits = new Map([\n [\n 'commitZero',\n {\n id: 'ZERO',\n message: '',\n seq: 0,\n type: commitType.NORMAL,\n tags: [],\n parents: [],\n branch: 'main',\n },\n ],\n [\n 'commitA',\n {\n id: 'A',\n message: '',\n seq: 1,\n type: commitType.NORMAL,\n tags: [],\n parents: ['ZERO'],\n branch: 'feature',\n },\n ],\n [\n 'commitB',\n {\n id: 'B',\n message: '',\n seq: 2,\n type: commitType.NORMAL,\n tags: [],\n parents: ['A'],\n branch: 'feature',\n },\n ],\n [\n 'commitM',\n {\n id: 'M',\n message: 'merged branch feature into main',\n seq: 3,\n type: commitType.MERGE,\n tags: [],\n parents: ['ZERO', 'B'],\n branch: 'main',\n customId: true,\n },\n ],\n [\n 'commitC',\n {\n id: 'C',\n message: '',\n seq: 4,\n type: commitType.NORMAL,\n tags: [],\n parents: ['ZERO'],\n branch: 'release',\n },\n ],\n [\n 'commit5_8928ea0',\n {\n id: '5-8928ea0',\n message: 'cherry-picked [object Object] into release',\n seq: 5,\n type: commitType.CHERRY_PICK,\n tags: [],\n parents: ['C', 'M'],\n branch: 'release',\n },\n ],\n [\n 'commitD',\n {\n id: 'D',\n message: '',\n seq: 6,\n type: commitType.NORMAL,\n tags: [],\n parents: ['5-8928ea0'],\n branch: 'release',\n },\n ],\n [\n 'commit7_ed848ba',\n {\n id: '7-ed848ba',\n message: 'cherry-picked [object Object] into release',\n seq: 7,\n type: commitType.CHERRY_PICK,\n tags: [],\n parents: ['D', 'M'],\n branch: 'release',\n },\n ],\n ]);\n let pos = 0;\n branchPos.set('main', { pos: 0, index: 0 });\n branchPos.set('feature', { pos: 107.49609375, index: 1 });\n branchPos.set('release', { pos: 224.03515625, index: 2 });\n\n describe('TB', () => {\n pos = 30;\n dir = 'TB';\n const expectedCommitPositionTB = new Map([\n ['commitZero', { x: 0, y: 40, posWithOffset: 40 }],\n ['commitA', { x: 107.49609375, y: 90, posWithOffset: 90 }],\n ['commitB', { x: 107.49609375, y: 140, posWithOffset: 140 }],\n ['commitM', { x: 0, y: 190, posWithOffset: 190 }],\n ['commitC', { x: 224.03515625, y: 240, posWithOffset: 240 }],\n ['commit5_8928ea0', { x: 224.03515625, y: 290, posWithOffset: 290 }],\n ['commitD', { x: 224.03515625, y: 340, posWithOffset: 340 }],\n ['commit7_ed848ba', { x: 224.03515625, y: 390, posWithOffset: 390 }],\n ]);\n commits.forEach((commit, key) => {\n it(`should give the correct position for commit ${key}`, () => {\n const position = getCommitPosition(commit, pos, false);\n expect(position).toEqual(expectedCommitPositionTB.get(key));\n pos += 50;\n });\n });\n });\n describe('LR', () => {\n let pos = 30;\n dir = 'LR';\n const expectedCommitPositionLR = new Map([\n ['commitZero', { x: 0, y: 40, posWithOffset: 40 }],\n ['commitA', { x: 107.49609375, y: 90, posWithOffset: 90 }],\n ['commitB', { x: 107.49609375, y: 140, posWithOffset: 140 }],\n ['commitM', { x: 0, y: 190, posWithOffset: 190 }],\n ['commitC', { x: 224.03515625, y: 240, posWithOffset: 240 }],\n ['commit5_8928ea0', { x: 224.03515625, y: 290, posWithOffset: 290 }],\n ['commitD', { x: 224.03515625, y: 340, posWithOffset: 340 }],\n ['commit7_ed848ba', { x: 224.03515625, y: 390, posWithOffset: 390 }],\n ]);\n commits.forEach((commit, key) => {\n it(`should give the correct position for commit ${key}`, () => {\n const position = getCommitPosition(commit, pos, false);\n expect(position).toEqual(expectedCommitPositionLR.get(key));\n pos += 50;\n });\n });\n });\n describe('getCommitClassType', () => {\n const expectedCommitClassType = new Map([\n ['commitZero', 'commit-normal'],\n ['commitA', 'commit-normal'],\n ['commitB', 'commit-normal'],\n ['commitM', 'commit-merge'],\n ['commitC', 'commit-normal'],\n ['commit5_8928ea0', 'commit-cherry-pick'],\n ['commitD', 'commit-normal'],\n ['commit7_ed848ba', 'commit-cherry-pick'],\n ]);\n commits.forEach((commit, key) => {\n it(`should give the correct class type for commit ${key}`, () => {\n const classType = getCommitClassType(commit);\n expect(classType).toBe(expectedCommitClassType.get(key));\n });\n });\n });\n });\n describe('building BT parallel commit diagram', () => {\n const commits = new Map([\n [\n '1-abcdefg',\n {\n id: '1-abcdefg',\n message: '',\n seq: 0,\n type: 0,\n tags: [],\n parents: [],\n branch: 'main',\n },\n ],\n [\n '2-abcdefg',\n {\n id: '2-abcdefg',\n message: '',\n seq: 1,\n type: 0,\n tags: [],\n parents: ['1-abcdefg'],\n branch: 'main',\n },\n ],\n [\n '3-abcdefg',\n {\n id: '3-abcdefg',\n message: '',\n seq: 2,\n type: 0,\n tags: [],\n parents: ['2-abcdefg'],\n branch: 'develop',\n },\n ],\n [\n '4-abcdefg',\n {\n id: '4-abcdefg',\n message: '',\n seq: 3,\n type: 0,\n tags: [],\n parents: ['3-abcdefg'],\n branch: 'develop',\n },\n ],\n [\n '5-abcdefg',\n {\n id: '5-abcdefg',\n message: '',\n seq: 4,\n type: 0,\n tags: [],\n parents: ['2-abcdefg'],\n branch: 'feature',\n },\n ],\n [\n '6-abcdefg',\n {\n id: '6-abcdefg',\n message: '',\n seq: 5,\n type: 0,\n tags: [],\n parents: ['5-abcdefg'],\n branch: 'feature',\n },\n ],\n [\n '7-abcdefg',\n {\n id: '7-abcdefg',\n message: '',\n seq: 6,\n type: 0,\n tags: [],\n parents: ['2-abcdefg'],\n branch: 'main',\n },\n ],\n [\n '8-abcdefg',\n {\n id: '8-abcdefg',\n message: '',\n seq: 7,\n type: 0,\n tags: [],\n parents: ['7-abcdefg'],\n branch: 'main',\n },\n ],\n ]);\n const expectedCommitPosition = new Map([\n ['1-abcdefg', { x: 0, y: 40 }],\n ['2-abcdefg', { x: 0, y: 90 }],\n ['3-abcdefg', { x: 107.49609375, y: 140 }],\n ['4-abcdefg', { x: 107.49609375, y: 190 }],\n ['5-abcdefg', { x: 225.70703125, y: 140 }],\n ['6-abcdefg', { x: 225.70703125, y: 190 }],\n ['7-abcdefg', { x: 0, y: 140 }],\n ['8-abcdefg', { x: 0, y: 190 }],\n ]);\n\n const expectedCommitPositionAfterParallel = new Map([\n ['1-abcdefg', { x: 0, y: 210 }],\n ['2-abcdefg', { x: 0, y: 160 }],\n ['3-abcdefg', { x: 107.49609375, y: 110 }],\n ['4-abcdefg', { x: 107.49609375, y: 60 }],\n ['5-abcdefg', { x: 225.70703125, y: 110 }],\n ['6-abcdefg', { x: 225.70703125, y: 60 }],\n ['7-abcdefg', { x: 0, y: 110 }],\n ['8-abcdefg', { x: 0, y: 60 }],\n ]);\n\n const expectedCommitCurrentPosition = new Map([\n ['1-abcdefg', 30],\n ['2-abcdefg', 80],\n ['3-abcdefg', 130],\n ['4-abcdefg', 180],\n ['5-abcdefg', 130],\n ['6-abcdefg', 180],\n ['7-abcdefg', 130],\n ['8-abcdefg', 180],\n ]);\n const sortedKeys = [...expectedCommitPosition.keys()];\n it('should get the correct commit position and current position', () => {\n dir = 'BT';\n let curPos = 30;\n commitPos.clear();\n branchPos.clear();\n branchPos.set('main', { pos: 0, index: 0 });\n branchPos.set('develop', { pos: 107.49609375, index: 1 });\n branchPos.set('feature', { pos: 225.70703125, index: 2 });\n DEFAULT_GITGRAPH_CONFIG!.parallelCommits = true;\n commits.forEach((commit, key) => {\n if (commit.parents.length > 0) {\n curPos = calculateCommitPosition(commit);\n }\n const position = setCommitPosition(commit, curPos);\n expect(position).toEqual(expectedCommitPosition.get(key));\n expect(curPos).toEqual(expectedCommitCurrentPosition.get(key));\n });\n });\n\n it('should get the correct commit position after parallel commits', () => {\n commitPos.clear();\n branchPos.clear();\n dir = 'BT';\n const curPos = 30;\n commitPos.clear();\n branchPos.clear();\n branchPos.set('main', { pos: 0, index: 0 });\n branchPos.set('develop', { pos: 107.49609375, index: 1 });\n branchPos.set('feature', { pos: 225.70703125, index: 2 });\n setParallelBTPos(sortedKeys, commits, curPos);\n sortedKeys.forEach((commit) => {\n const position = commitPos.get(commit);\n expect(position).toEqual(expectedCommitPositionAfterParallel.get(commit));\n });\n });\n });\n DEFAULT_GITGRAPH_CONFIG!.parallelCommits = false;\n it('add', () => {\n commitPos.set('parent1', { x: 1, y: 1 });\n commitPos.set('parent2', { x: 2, y: 2 });\n commitPos.set('parent3', { x: 3, y: 3 });\n dir = 'LR';\n const parents = ['parent1', 'parent2', 'parent3'];\n const closestParent = findClosestParent(parents);\n\n expect(closestParent).toBe('parent3');\n commitPos.clear();\n });\n}\n", "const getStyles = (options) =>\n `\n .commit-id,\n .commit-msg,\n .branch-label {\n fill: lightgrey;\n color: lightgrey;\n font-family: 'trebuchet ms', verdana, arial, sans-serif;\n font-family: var(--mermaid-font-family);\n }\n ${[0, 1, 2, 3, 4, 5, 6, 7]\n .map(\n (i) =>\n `\n .branch-label${i} { fill: ${options['gitBranchLabel' + i]}; }\n .commit${i} { stroke: ${options['git' + i]}; fill: ${options['git' + i]}; }\n .commit-highlight${i} { stroke: ${options['gitInv' + i]}; fill: ${options['gitInv' + i]}; }\n .label${i} { fill: ${options['git' + i]}; }\n .arrow${i} { stroke: ${options['git' + i]}; }\n `\n )\n .join('\\n')}\n\n .branch {\n stroke-width: 1;\n stroke: ${options.lineColor};\n stroke-dasharray: 2;\n }\n .commit-label { font-size: ${options.commitLabelFontSize}; fill: ${options.commitLabelColor};}\n .commit-label-bkg { font-size: ${options.commitLabelFontSize}; fill: ${\n options.commitLabelBackground\n }; opacity: 0.5; }\n .tag-label { font-size: ${options.tagLabelFontSize}; fill: ${options.tagLabelColor};}\n .tag-label-bkg { fill: ${options.tagLabelBackground}; stroke: ${options.tagLabelBorder}; }\n .tag-hole { fill: ${options.textColor}; }\n\n .commit-merge {\n stroke: ${options.primaryColor};\n fill: ${options.primaryColor};\n }\n .commit-reverse {\n stroke: ${options.primaryColor};\n fill: ${options.primaryColor};\n stroke-width: 3;\n }\n .commit-highlight-outer {\n }\n .commit-highlight-inner {\n stroke: ${options.primaryColor};\n fill: ${options.primaryColor};\n }\n\n .arrow { stroke-width: 8; stroke-linecap: round; fill: none}\n .gitTitleText {\n text-anchor: middle;\n font-size: 18px;\n fill: ${options.textColor};\n }\n`;\n\nexport default getStyles;\n", "// @ts-ignore: JISON doesn't support types\nimport { parser } from './gitGraphParser.js';\nimport { db } from './gitGraphAst.js';\nimport gitGraphRenderer from './gitGraphRenderer.js';\nimport gitGraphStyles from './styles.js';\nimport type { DiagramDefinition } from '../../diagram-api/types.js';\n\nexport const diagram: DiagramDefinition = {\n parser,\n db,\n renderer: gitGraphRenderer,\n styles: gitGraphStyles,\n};\n"],
"mappings": "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",
"names": ["commitType", "DEFAULT_GITGRAPH_CONFIG", "defaultConfig_default", "getConfig", "__name", "cleanAndMerge", "state", "ImperativeState", "config", "mainBranchName", "mainBranchOrder", "getID", "random", "uniqBy", "list", "fn", "recordMap", "out", "item", "key", "setDirection", "dir", "setOptions", "rawOptString", "log", "getOptions", "commit", "commitDB", "msg", "id", "type", "tags", "common_default", "tag", "newCommit", "commitType", "branch", "branchDB", "name", "order", "checkout", "merge", "mergeDB", "otherBranch", "customId", "overrideType", "customTags", "currentBranchCheck", "otherBranchCheck", "currentCommit", "otherCommit", "error", "verifiedBranch", "cherryPick", "cherryPickDB", "sourceId", "targetId", "parentCommitId", "sourceCommit", "sourceCommitBranch", "currentCommitId", "upsert", "arr", "newVal", "index", "prettyPrintCommitHistory", "commitArr", "line", "c", "label", "prettyPrint", "node", "getCommitsArray", "clear", "getBranchesAsObjArray", "branchConfig", "i", "a", "b", "getBranches", "getCommits", "o", "getCurrentBranch", "getDirection", "getHead", "db", "setAccTitle", "getAccTitle", "getAccDescription", "setAccDescription", "setDiagramTitle", "getDiagramTitle", "populate", "__name", "ast", "db", "populateCommonDb", "statement", "parseStatement", "parser", "stmt", "parseCommit", "parseBranch", "parseMerge", "parseCheckout", "parseCherryPicking", "log", "commit", "commitType", "branch", "merge", "checkout", "cherryPicking", "input", "parse", "DEFAULT_CONFIG", "getConfig", "DEFAULT_GITGRAPH_CONFIG", "LAYOUT_OFFSET", "COMMIT_STEP", "PX", "PY", "THEME_COLOR_LIMIT", "branchPos", "commitPos", "defaultPos", "allCommitsDict", "lanes", "maxPos", "dir", "clear", "__name", "drawText", "txt", "svgLabel", "row", "tspan", "findClosestParent", "parents", "closestParent", "comparisonFunc", "targetPosition", "a", "b", "parent", "parentPosition", "findClosestParentBT", "maxPosition", "setParallelBTPos", "sortedKeys", "commits", "curPos", "roots", "key", "commit", "calculateCommitPosition", "setCommitPosition", "setRootPosition", "x", "y", "findClosestParentPos", "p", "closestParentPos", "branch", "drawCommitBullet", "gBullets", "commitPosition", "typeClass", "branchIndex", "commitSymbolType", "commitType", "circle", "circle2", "drawCommitLabel", "gLabels", "pos", "wrapper", "labelBkg", "text", "bbox", "r_x", "r_y", "drawCommitTags", "yOffset", "maxTagBboxWidth", "maxTagBboxHeight", "tagElements", "tagValue", "rect", "hole", "tag", "tagBbox", "h2", "ly", "yOrigin", "getCommitClassType", "calculatePosition", "defaultCommitPosition", "getCommitPosition", "isParallelCommits", "posWithOffset", "drawCommits", "svg", "modifyGraph", "keys", "sortKeys", "seqA", "seqB", "shouldRerouteArrow", "commitA", "commitB", "p1", "p2", "allCommits", "branchToGetCurve", "isOnBranchToGetCurve", "isBetweenCommits", "commitX", "findLane", "y1", "y2", "depth", "candidate", "lane", "diff", "drawArrow", "arrowNeedsRerouting", "arc", "arc2", "radius", "offset", "colorClassNum", "lineDef", "lineY", "lineX", "drawArrows", "gArrows", "drawBranches", "branches", "g", "index", "adjustIndexForTheme", "line", "name", "labelElement", "bkg", "label", "setBranchPosition", "rotateCommitLabel", "draw", "id", "ver", "diagObj", "log", "db", "diagram", "select_default", "branchLabel", "utils_default", "setupGraphViewbox", "gitGraphRenderer_default", "getStyles", "__name", "options", "i", "styles_default", "diagram", "parser", "db", "gitGraphRenderer_default", "styles_default"]
}