build.ts 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120
  1. #!/usr/bin/env bun
  2. import { $ } from "bun"
  3. import { rm } from "fs/promises"
  4. import path from "path"
  5. import { Script } from "@opencode-ai/script"
  6. import { createSolidTransformPlugin } from "@opentui/solid/bun-plugin"
  7. import pkg from "../package.json"
  8. import { modelsData } from "./generate"
  9. const dir = path.resolve(import.meta.dirname, "..")
  10. const binary = "opencode2"
  11. const outdir = path.resolve(
  12. dir,
  13. process.argv.find((arg) => arg.startsWith("--outdir="))?.slice("--outdir=".length) ?? "dist",
  14. )
  15. if (outdir === dir) throw new Error("--outdir must not be the package directory")
  16. process.chdir(dir)
  17. await rm(outdir, { recursive: true, force: true })
  18. const singleFlag = process.argv.includes("--single")
  19. const baselineFlag = process.argv.includes("--baseline")
  20. const skipInstall = process.argv.includes("--skip-install")
  21. const plugin = createSolidTransformPlugin()
  22. const allTargets: {
  23. os: string
  24. arch: "arm64" | "x64"
  25. abi?: "musl"
  26. avx2?: false
  27. }[] = [
  28. { os: "linux", arch: "arm64" },
  29. { os: "linux", arch: "x64" },
  30. { os: "linux", arch: "x64", avx2: false },
  31. { os: "linux", arch: "arm64", abi: "musl" },
  32. { os: "linux", arch: "x64", abi: "musl" },
  33. { os: "linux", arch: "x64", abi: "musl", avx2: false },
  34. { os: "darwin", arch: "arm64" },
  35. { os: "darwin", arch: "x64" },
  36. { os: "darwin", arch: "x64", avx2: false },
  37. { os: "win32", arch: "arm64" },
  38. { os: "win32", arch: "x64" },
  39. { os: "win32", arch: "x64", avx2: false },
  40. ]
  41. const targets = singleFlag
  42. ? allTargets.filter((item) => {
  43. if (item.os !== process.platform || item.arch !== process.arch) return false
  44. if (item.avx2 === false) return baselineFlag
  45. return item.abi === undefined
  46. })
  47. : allTargets
  48. if (!skipInstall) await $`bun install --os="*" --cpu="*" @opentui/core@${pkg.dependencies["@opentui/core"]}`
  49. for (const item of targets) {
  50. const target = [
  51. binary,
  52. item.os === "win32" ? "windows" : item.os,
  53. item.arch,
  54. item.avx2 === false ? "baseline" : undefined,
  55. item.abi,
  56. ]
  57. .filter(Boolean)
  58. .join("-")
  59. const name = target.replace(binary, "cli")
  60. console.log(`building ${name}`)
  61. const result = await Bun.build({
  62. entrypoints: ["./src/index.ts"],
  63. tsconfig: "./tsconfig.json",
  64. plugins: [plugin],
  65. external: ["node-gyp"],
  66. format: "esm",
  67. minify: true,
  68. sourcemap: "inline",
  69. splitting: true,
  70. compile: {
  71. autoloadBunfig: false,
  72. autoloadDotenv: false,
  73. autoloadTsconfig: true,
  74. autoloadPackageJson: true,
  75. target: target.replace(binary, "bun") as Bun.Build.CompileTarget,
  76. outfile: path.join(outdir, name, "bin", binary),
  77. execArgv: [`--user-agent=${binary}/${Script.version}`, "--use-system-ca", "--"],
  78. windows: {},
  79. },
  80. define: {
  81. OPENCODE_VERSION: `'${Script.version}'`,
  82. OPENCODE_CLI_NAME: `'${binary}'`,
  83. OPENCODE_MODELS_DEV: modelsData,
  84. OPENCODE_CHANNEL: `'${Script.channel}'`,
  85. OPENCODE_LIBC: item.os === "linux" ? `'${item.abi ?? "glibc"}'` : "undefined",
  86. // FFF_LIBC selects the fff native lib variant: "musl" or "gnu".
  87. FFF_LIBC: item.os === "linux" ? `'${item.abi ?? "gnu"}'` : "undefined",
  88. ...(item.os === "linux" ? { "process.env.OPENTUI_LIBC": JSON.stringify(item.abi ?? "glibc") } : {}),
  89. },
  90. })
  91. if (!result.success) {
  92. for (const log of result.logs) console.error(log)
  93. process.exit(1)
  94. }
  95. await Bun.write(
  96. path.join(outdir, name, "package.json"),
  97. JSON.stringify(
  98. {
  99. name: `@opencode-ai/${name}`,
  100. version: Script.version,
  101. license: "MIT",
  102. repository: { type: "git", url: "git+https://github.com/anomalyco/opencode.git" },
  103. os: [item.os],
  104. cpu: [item.arch],
  105. },
  106. null,
  107. 2,
  108. ),
  109. )
  110. }