(args: Args)
| 18040 | } |
| 18041 | |
| 18042 | function applyArtifactsCommand(args: Args): void { |
| 18043 | repoFromArgs(args); |
| 18044 | const artifactDir = resolve(stringArg(args.artifact_dir, "artifacts")); |
| 18045 | const itemsDir = resolve(stringArg(args.items_dir, defaultItemsDir())); |
| 18046 | const closedDir = resolve(stringArg(args.closed_dir, defaultClosedDir())); |
| 18047 | const plansDir = resolve(stringArg(args.plans_dir, defaultPlansDir())); |
| 18048 | const skipReconcile = boolArg(args.skip_reconcile); |
| 18049 | const replayClosedArtifacts = boolArg(args.replay_closed_artifacts); |
| 18050 | const maxPages = numberArg(args.max_pages, 250); |
| 18051 | const openNumbers = skipReconcile ? null : fetchOpenItemNumbers(maxPages).numbers; |
| 18052 | let appliedArtifacts = 0; |
| 18053 | let skippedClosedArtifacts = 0; |
| 18054 | ensureDir(itemsDir); |
| 18055 | ensureDir(closedDir); |
| 18056 | if (existsSync(artifactDir)) { |
| 18057 | for (const entry of readdirSync(artifactDir, { recursive: true })) { |
| 18058 | const name = String(entry); |
| 18059 | if (!name.endsWith(".md")) continue; |
| 18060 | const source = join(artifactDir, name); |
| 18061 | if (!parseReportFileName(basename(source))) continue; |
| 18062 | const number = numberForMarkdownFile(basename(source)); |
| 18063 | const markdown = readFileSync(source, "utf8"); |
| 18064 | if (!isMarkdownForActiveRepo(markdown, basename(source))) continue; |
| 18065 | const destinationFile = reportFileName( |
| 18066 | markdownRepository(markdown, basename(source)), |
| 18067 | number, |
| 18068 | ); |
| 18069 | const action = frontMatterValue(markdown, "action_taken") ?? "unknown"; |
| 18070 | const destination = reviewArtifactDestination( |
| 18071 | action, |
| 18072 | replayClosedArtifacts || artifactTargetIsOpen(number, openNumbers), |
| 18073 | ); |
| 18074 | if (destination === "skip_closed") { |
| 18075 | skippedClosedArtifacts += 1; |
| 18076 | continue; |
| 18077 | } |
| 18078 | const destinationDir = destination === "closed" ? closedDir : itemsDir; |
| 18079 | const stalePath = join(destinationDir === itemsDir ? closedDir : itemsDir, destinationFile); |
| 18080 | if (existsSync(stalePath)) unlinkSync(stalePath); |
| 18081 | const reportPath = join(destinationDir, destinationFile); |
| 18082 | writeFileSync(reportPath, markdown, "utf8"); |
| 18083 | if (destination === "closed") { |
| 18084 | const planPath = workPlanPathForReport(reportPath, plansDir); |
| 18085 | if (existsSync(planPath)) unlinkSync(planPath); |
| 18086 | } else { |
| 18087 | syncWorkPlanFromReport({ markdown, reportPath, plansDir }); |
| 18088 | } |
| 18089 | appliedArtifacts += 1; |
| 18090 | } |
| 18091 | } |
| 18092 | console.error( |
| 18093 | `[apply-artifacts] applied=${appliedArtifacts} skipped_closed=${skippedClosedArtifacts}`, |
| 18094 | ); |
| 18095 | if (!skipReconcile) reconcileFolders({ itemsDir, closedDir, plansDir }); |
| 18096 | } |
| 18097 | |
| 18098 | function artifactTargetIsOpen(number: number, openNumbers: Set<number> | null): boolean { |
| 18099 | if (openNumbers) return openNumbers.has(number); |
no test coverage detected