@rtorcato/repo-tooling 2.59.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (136) hide show
  1. package/AGENTS.md +113 -0
  2. package/LICENSE +21 -0
  3. package/README.md +201 -0
  4. package/dist/cli/commands/doctor.js +336 -0
  5. package/dist/cli/commands/fix-targets.js +192 -0
  6. package/dist/cli/commands/fix.js +440 -0
  7. package/dist/cli/commands/setup-presets.js +281 -0
  8. package/dist/cli/commands/setup.js +501 -0
  9. package/dist/cli/generators/agent-rules.js +103 -0
  10. package/dist/cli/generators/badges.js +88 -0
  11. package/dist/cli/generators/build.js +216 -0
  12. package/dist/cli/generators/bun.js +25 -0
  13. package/dist/cli/generators/community-health.js +145 -0
  14. package/dist/cli/generators/docs-site.js +436 -0
  15. package/dist/cli/generators/git.js +164 -0
  16. package/dist/cli/generators/github-actions.js +35 -0
  17. package/dist/cli/generators/github-workflows.js +24 -0
  18. package/dist/cli/generators/gitlab-ci.js +10 -0
  19. package/dist/cli/generators/index.js +123 -0
  20. package/dist/cli/generators/linting.js +54 -0
  21. package/dist/cli/generators/misc.js +298 -0
  22. package/dist/cli/generators/nx.js +16 -0
  23. package/dist/cli/generators/package-json.js +317 -0
  24. package/dist/cli/generators/pnpm-workspace.js +126 -0
  25. package/dist/cli/generators/postcss.js +24 -0
  26. package/dist/cli/generators/readme.js +268 -0
  27. package/dist/cli/generators/security.js +156 -0
  28. package/dist/cli/generators/skills-install.js +70 -0
  29. package/dist/cli/generators/tailwind.js +34 -0
  30. package/dist/cli/generators/testing.js +88 -0
  31. package/dist/cli/generators/treeshake.js +148 -0
  32. package/dist/cli/generators/tsconfig.js +27 -0
  33. package/dist/cli/generators/turborepo.js +35 -0
  34. package/dist/cli/generators/typedoc.js +40 -0
  35. package/dist/cli/index.js +332 -0
  36. package/dist/cli/utils/copy-preset.js +98 -0
  37. package/dist/cli/utils/detect-language.js +22 -0
  38. package/dist/cli/utils/format.js +32 -0
  39. package/dist/cli/utils/install.js +28 -0
  40. package/dist/cli/utils/lockfile.js +84 -0
  41. package/dist/languages/js/checks.js +949 -0
  42. package/dist/languages/js/ci.js +251 -0
  43. package/dist/languages/js/fixers.js +735 -0
  44. package/dist/languages/registry.js +37 -0
  45. package/dist/languages/swift/checks.js +127 -0
  46. package/dist/languages/swift/ci.js +165 -0
  47. package/dist/languages/swift/fixers.js +102 -0
  48. package/dist/languages/swift/git-hooks.js +63 -0
  49. package/dist/languages/swift/gitignore.js +43 -0
  50. package/dist/languages/swift/scaffold.js +244 -0
  51. package/package.json +461 -0
  52. package/tooling/biome/README.md +90 -0
  53. package/tooling/biome/biome.json +63 -0
  54. package/tooling/bun/bunfig.toml +14 -0
  55. package/tooling/changesets/README.md +35 -0
  56. package/tooling/changesets/config.json +11 -0
  57. package/tooling/claude/repo-tooling.md +87 -0
  58. package/tooling/commitlint/commitlint.d.mts +4 -0
  59. package/tooling/commitlint/commitlint.mjs +40 -0
  60. package/tooling/cypress/cypress.config.d.mts +4 -0
  61. package/tooling/cypress/cypress.config.mjs +11 -0
  62. package/tooling/docusaurus/index.d.mts +17 -0
  63. package/tooling/docusaurus/index.mjs +38 -0
  64. package/tooling/docusaurus/sync-changelog.mjs +42 -0
  65. package/tooling/docusaurus/theme-tokens.css +79 -0
  66. package/tooling/docusaurus/theme.css +378 -0
  67. package/tooling/esbuild/index.d.mts +6 -0
  68. package/tooling/esbuild/index.mjs +102 -0
  69. package/tooling/eslint/base.d.mts +6 -0
  70. package/tooling/eslint/base.mjs +122 -0
  71. package/tooling/eslint/nextjs.d.mts +4 -0
  72. package/tooling/eslint/nextjs.mjs +22 -0
  73. package/tooling/eslint/types.d.ts +58 -0
  74. package/tooling/github-actions/workflows/cloudflare-pages.yml +42 -0
  75. package/tooling/github-actions/workflows/docker-publish.yml +44 -0
  76. package/tooling/github-actions/workflows/preview-deployments.yml +54 -0
  77. package/tooling/github-actions/workflows/vercel-deploy.yml +40 -0
  78. package/tooling/jest-presets/browser/jest-preset.d.mts +4 -0
  79. package/tooling/jest-presets/browser/jest-preset.mjs +14 -0
  80. package/tooling/jest-presets/node/jest-preset.d.mts +4 -0
  81. package/tooling/jest-presets/node/jest-preset.mjs +13 -0
  82. package/tooling/mcp/mcp.json.example +27 -0
  83. package/tooling/nx/nx.json +24 -0
  84. package/tooling/oxlint/README.md +25 -0
  85. package/tooling/oxlint/oxlintrc.json +28 -0
  86. package/tooling/playwright/playwright.config.d.mts +4 -0
  87. package/tooling/playwright/playwright.config.mjs +19 -0
  88. package/tooling/prettier/index.d.mts +4 -0
  89. package/tooling/prettier/index.mjs +36 -0
  90. package/tooling/release-please/.release-please-manifest.json +3 -0
  91. package/tooling/release-please/release-please-config.json +9 -0
  92. package/tooling/rolldown/rolldown.config.d.mts +18 -0
  93. package/tooling/rolldown/rolldown.config.mjs +59 -0
  94. package/tooling/rollup/rollup.config.d.mts +20 -0
  95. package/tooling/rollup/rollup.config.mjs +70 -0
  96. package/tooling/semantic-release/docker.d.mts +4 -0
  97. package/tooling/semantic-release/docker.mjs +59 -0
  98. package/tooling/semantic-release/github.d.mts +4 -0
  99. package/tooling/semantic-release/github.mjs +79 -0
  100. package/tooling/semantic-release/index.d.mts +4 -0
  101. package/tooling/semantic-release/index.mjs +80 -0
  102. package/tooling/swift/periphery.yml +4 -0
  103. package/tooling/swift/swiftlint.yml +23 -0
  104. package/tooling/tests/exports-resolution.d.mts +14 -0
  105. package/tooling/tests/exports-resolution.mjs +68 -0
  106. package/tooling/tests/ssr-safety.d.mts +14 -0
  107. package/tooling/tests/ssr-safety.mjs +53 -0
  108. package/tooling/tsup/index.d.mts +8 -0
  109. package/tooling/tsup/index.mjs +33 -0
  110. package/tooling/typedoc/typedoc.json +7 -0
  111. package/tooling/typescript/README.md +49 -0
  112. package/tooling/typescript/reset.d.ts +9 -0
  113. package/tooling/typescript/tsconfig.base.json +84 -0
  114. package/tooling/typescript/tsconfig.build.json +11 -0
  115. package/tooling/typescript/tsconfig.bun.json +9 -0
  116. package/tooling/typescript/tsconfig.express.json +9 -0
  117. package/tooling/typescript/tsconfig.next.json +20 -0
  118. package/tooling/typescript/tsconfig.node.json +9 -0
  119. package/tooling/typescript/tsconfig.react.json +15 -0
  120. package/tooling/typescript/tsconfig.test.json +8 -0
  121. package/tooling/typescript/v1/tsconfig.base.json +81 -0
  122. package/tooling/typescript/v1/tsconfig.express.json +9 -0
  123. package/tooling/typescript/v1/tsconfig.next.json +19 -0
  124. package/tooling/typescript/v1/tsconfig.node.json +9 -0
  125. package/tooling/typescript/v1/tsconfig.react.json +14 -0
  126. package/tooling/typescript/v1/tsconfig.test.json +8 -0
  127. package/tooling/vite/vite.config.d.mts +4 -0
  128. package/tooling/vite/vite.config.mjs +18 -0
  129. package/tooling/vitest/jsdom-shims.d.mts +1 -0
  130. package/tooling/vitest/jsdom-shims.mjs +58 -0
  131. package/tooling/vitest/vitest.config.d.mts +4 -0
  132. package/tooling/vitest/vitest.config.mjs +25 -0
  133. package/tooling/vitest/vitest.config.react.d.mts +4 -0
  134. package/tooling/vitest/vitest.config.react.mjs +27 -0
  135. package/tooling/vitest/vitest.setup.d.mts +1 -0
  136. package/tooling/vitest/vitest.setup.mjs +3 -0
@@ -0,0 +1,244 @@
1
+ /**
2
+ * Swift project scaffolding (#288) — what `setup --preset swift-library` writes.
3
+ *
4
+ * The JS generators in `src/cli/generators/` are all package.json-rooted, so a
5
+ * Swift repo shares almost none of them: no package.json, no tsconfig, no
6
+ * bundler, no pnpm. What it *does* share is the language-agnostic half —
7
+ * .editorconfig, Dependabot, CodeQL, the AI agent files — which is imported
8
+ * from there rather than re-templated here.
9
+ *
10
+ * The CI workflow comes from ./ci.ts (#287), which derives its jobs from
11
+ * Package.swift. That's why the manifest is written before the workflow: the
12
+ * platform matrix reads the `platforms:` clause we just emitted.
13
+ */
14
+ import path from 'node:path';
15
+ import fs from 'fs-extra';
16
+ import { installAiSetup } from '../../cli/generators/agent-rules.js';
17
+ import { generateEditorConfig } from '../../cli/generators/misc.js';
18
+ import { generateCodeQLWorkflow, generateDependabotConfig } from '../../cli/generators/security.js';
19
+ import { copyPreset } from '../../cli/utils/copy-preset.js';
20
+ import { LANGUAGES } from '../registry.js';
21
+ import { readSwiftPackage, renderSwiftWorkflow } from './ci.js';
22
+ import { SWIFT_HOOKS_DIR, installSwiftGitHooks } from './git-hooks.js';
23
+ import { ensureSwiftGitignore } from './gitignore.js';
24
+ /**
25
+ * Turn a repo name into a Swift module name: `my-swift-lib` → `MySwiftLib`.
26
+ * SwiftPM target names are type identifiers, so hyphens, dots and spaces have
27
+ * to go, and a leading digit has to be prefixed. Falls back to `Package` when
28
+ * nothing usable survives (e.g. a directory named `123`).
29
+ */
30
+ export function swiftModuleName(projectName) {
31
+ const upperCamel = projectName
32
+ .split(/[^A-Za-z0-9]+/)
33
+ .filter(Boolean)
34
+ .map((word) => word.charAt(0).toUpperCase() + word.slice(1))
35
+ .join('');
36
+ if (upperCamel.length === 0)
37
+ return 'Package';
38
+ return /^\d/.test(upperCamel) ? `Package${upperCamel}` : upperCamel;
39
+ }
40
+ /**
41
+ * Deployment targets baked into the manifest. `doctor` requires *some*
42
+ * `platforms:` clause (without one SwiftPM silently assumes its oldest
43
+ * supported target), and these also become the xcodebuild matrix in CI.
44
+ *
45
+ * No trailing commas in the collection literals: the .swiftlint.yml written
46
+ * alongside leaves `trailing_comma` enabled, so a manifest with them fails the
47
+ * `swiftlint lint --strict` job in the CI this same scaffold generates.
48
+ */
49
+ function packageSwift(module) {
50
+ return `// swift-tools-version: 6.0
51
+
52
+ import PackageDescription
53
+
54
+ let package = Package(
55
+ name: "${module}",
56
+ platforms: [
57
+ .iOS(.v17),
58
+ .macOS(.v14)
59
+ ],
60
+ products: [
61
+ .library(name: "${module}", targets: ["${module}"])
62
+ ],
63
+ targets: [
64
+ .target(name: "${module}"),
65
+ .testTarget(name: "${module}Tests", dependencies: ["${module}"])
66
+ ]
67
+ )
68
+ `;
69
+ }
70
+ /**
71
+ * A real (if tiny) source + test pair, not an empty directory. `swift build`
72
+ * fails outright on a package whose target directory doesn't exist, so a
73
+ * scaffold without these produces a repo whose own CI is red on the first push.
74
+ */
75
+ function sourceFile(module) {
76
+ return `/// The public surface of ${module}.
77
+ public enum ${module} {
78
+ /// Current version of the package. Replace this enum with your own API.
79
+ public static let version = "0.1.0"
80
+ }
81
+ `;
82
+ }
83
+ /** XCTest rather than Swift Testing: it works on every toolchain, Linux included. */
84
+ function testFile(module) {
85
+ return `import XCTest
86
+
87
+ @testable import ${module}
88
+
89
+ final class ${module}Tests: XCTestCase {
90
+ func testVersionIsNotEmpty() {
91
+ XCTAssertFalse(${module}.version.isEmpty)
92
+ }
93
+ }
94
+ `;
95
+ }
96
+ /**
97
+ * Swift is 4-space by convention while the shared .editorconfig is tab-first,
98
+ * so the baseline gets a Swift override appended rather than a separate file.
99
+ */
100
+ const SWIFT_EDITORCONFIG_SECTION = `
101
+ [*.swift]
102
+ indent_style = space
103
+ indent_size = 4
104
+ `;
105
+ function readme(config, module) {
106
+ return `# ${config.projectName}
107
+
108
+ > Generated with [@rtorcato/repo-tooling](https://www.npmjs.com/package/@rtorcato/repo-tooling)
109
+
110
+ ## Description
111
+
112
+ Your package description here.
113
+
114
+ ## Installation
115
+
116
+ Add the package to your \`Package.swift\`:
117
+
118
+ \`\`\`swift
119
+ dependencies: [
120
+ .package(url: "https://github.com/OWNER/${config.projectName}.git", from: "0.1.0"),
121
+ ]
122
+ \`\`\`
123
+
124
+ Then add \`${module}\` to your target's dependencies.
125
+
126
+ ## Development
127
+
128
+ \`\`\`bash
129
+ swift build # Build the package
130
+ swift test # Run the test suite
131
+ swiftlint --fix # Format and autocorrect
132
+ swiftlint lint --strict # Lint the way CI does
133
+ periphery scan # Report unused declarations
134
+ \`\`\`
135
+
136
+ SwiftLint is the formatter *and* the linter here — SwiftFormat is deliberately
137
+ not part of the standard, because a second formatter fights the first.
138
+
139
+ ### Git hooks
140
+
141
+ \`.githooks/\` is committed, but git only runs it once each clone points at it:
142
+
143
+ \`\`\`bash
144
+ git config core.hooksPath .githooks
145
+ \`\`\`
146
+
147
+ \`pre-commit\` runs \`swiftlint --fix\`; \`pre-push\` runs \`swift build\`,
148
+ \`swift test\` and \`swiftlint lint --strict\` — the same gate as CI.
149
+
150
+ ## Project Structure
151
+
152
+ \`\`\`
153
+ ${config.projectName}/
154
+ ├── Sources/${module}/ # Library source
155
+ ├── Tests/${module}Tests/ # XCTest suite
156
+ ├── Package.swift # SwiftPM manifest
157
+ ├── .githooks/ # pre-commit + pre-push (see Git hooks above)
158
+ ├── .swiftlint.yml # SwiftLint configuration
159
+ ├── .periphery.yml # Dead-code scan configuration
160
+ └── README.md
161
+ \`\`\`
162
+
163
+ ## Tooling
164
+
165
+ - **SwiftPM** — build, test, and dependency resolution
166
+ - **SwiftLint** — linting and formatting
167
+ - **Periphery** — dead-code detection
168
+ - **GitHub Actions** — \`swift build\`/\`swift test\` on macOS, plus \`xcodebuild\` per declared platform
169
+
170
+ Run \`npx @rtorcato/repo-tooling doctor\` any time to audit this repo against the standard.
171
+
172
+ ## Contributing
173
+
174
+ 1. Fork the repository
175
+ 2. Create your feature branch (\`git checkout -b feature/amazing-feature\`)
176
+ 3. Commit your changes (\`git commit -m 'feat: add amazing feature'\`)
177
+ 4. Push to the branch (\`git push origin feature/amazing-feature\`)
178
+ 5. Open a Pull Request
179
+
180
+ ## License
181
+
182
+ [Add your license here]
183
+ `;
184
+ }
185
+ /**
186
+ * Relative paths `setup --dry-run` reports for a Swift config, in write order.
187
+ * Kept beside the writer so the two can't drift.
188
+ */
189
+ export function swiftFileList(config) {
190
+ const module = swiftModuleName(config.projectName);
191
+ const files = [
192
+ '.repo-tooling.json',
193
+ 'Package.swift',
194
+ `Sources/${module}/${module}.swift`,
195
+ `Tests/${module}Tests/${module}Tests.swift`,
196
+ '.swiftlint.yml',
197
+ '.periphery.yml',
198
+ '.gitignore',
199
+ '.editorconfig',
200
+ '.github/workflows/ci.yml',
201
+ ];
202
+ if (config.gitHooks) {
203
+ files.push(`${SWIFT_HOOKS_DIR}/pre-commit`, `${SWIFT_HOOKS_DIR}/pre-push`);
204
+ }
205
+ if (config.securityAutomation) {
206
+ files.push('.github/dependabot.yml', '.github/workflows/dependabot-automerge.yml', '.github/workflows/codeql.yml');
207
+ }
208
+ if (config.aiSetup) {
209
+ files.push('AGENTS.md', 'CLAUDE.md', '.cursor/rules/repo-tooling.mdc', '.github/copilot-instructions.md', '.claude/skills/repo-tooling.md', '.mcp.json.example');
210
+ }
211
+ files.push('README.md');
212
+ return files;
213
+ }
214
+ /** Scaffold a SwiftPM library. The Swift arm of `generateConfigs`. */
215
+ export async function generateSwiftProject(config, targetDir) {
216
+ const module = swiftModuleName(config.projectName);
217
+ await fs.writeFile(path.join(targetDir, 'Package.swift'), packageSwift(module));
218
+ await fs.outputFile(path.join(targetDir, 'Sources', module, `${module}.swift`), sourceFile(module));
219
+ await fs.outputFile(path.join(targetDir, 'Tests', `${module}Tests`, `${module}Tests.swift`), testFile(module));
220
+ await copyPreset('swiftlint', targetDir);
221
+ await copyPreset('periphery', targetDir);
222
+ await ensureSwiftGitignore(targetDir);
223
+ await generateEditorConfig(targetDir);
224
+ await fs.appendFile(path.join(targetDir, '.editorconfig'), SWIFT_EDITORCONFIG_SECTION);
225
+ // After Package.swift: the workflow's platform matrix is read back off the
226
+ // manifest written above.
227
+ const workflowsDir = path.join(targetDir, '.github', 'workflows');
228
+ await fs.ensureDir(workflowsDir);
229
+ await fs.writeFile(path.join(workflowsDir, 'ci.yml'), renderSwiftWorkflow(await readSwiftPackage(targetDir)));
230
+ // `core.hooksPath` won't stick here — `setup` scaffolds into a directory that
231
+ // isn't a git repo yet — so the hooks land as files and the README tells you
232
+ // the one-line config to run after `git init`.
233
+ if (config.gitHooks) {
234
+ await installSwiftGitHooks(targetDir);
235
+ }
236
+ if (config.securityAutomation) {
237
+ await generateDependabotConfig(targetDir, LANGUAGES.swift.dependabotEcosystem);
238
+ await generateCodeQLWorkflow(targetDir, LANGUAGES.swift.codeqlLanguages);
239
+ }
240
+ if (config.aiSetup) {
241
+ await installAiSetup(targetDir);
242
+ }
243
+ await fs.writeFile(path.join(targetDir, 'README.md'), readme(config, module));
244
+ }