You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何修复Google Cloud Build中的TypeScript引用错误?

问题描述

我有一个TypeScript monorepo,其中Vue 3应用从私有模块/包(如@myapp/types或@myapp/config)导入自定义类型和配置常量,这些包不在npm registry中。

本地环境下应用的导入、构建和运行都正常,但在Google Cloud Build中构建失败,报错信息如下:
cloud build error typescript config

相关配置文件

依赖消费方(Vue应用)的tsconfig.json

{
  "files": [],
  "compilerOptions": {
    "forceConsistentCasingInFileNames": true,
    "strict": true
  },
  "references": [
    {
      "path": "./tsconfig.vite-config.json"
    },
    {
      "path": "./tsconfig.app.json"
    },
    {
      "path": "./tsconfig.vitest.json"
    },
    {
      "path": "../../packages/types/tsconfig.json"
    },
    {
      "path": "../../packages/config/tsconfig.json"
    }
  ]
}

tsconfig.app.json

{
  "extends": "@vue/tsconfig/tsconfig.web.json",
  "include": ["env.d.ts", "src/**/*", "src/**/*.vue"],
  "exclude": ["src/**/__tests__/*"],
  "compilerOptions": {
    "allowSyntheticDefaultImports": true,
    "composite": true,
    "baseUrl": ".",
    "paths": {
      "@/*": ["./src/*"],
      "@myapp/config": ["../../packages/config"],
      "@myapp/types": ["../../packages/types"]
    }
  }
}

Monorepo目录结构

  • root(包含tsconfig.base.json)
    • apps
      • ui <== 依赖消费方(包含tsconfig.app.json + tsconfig.json)
    • packages
      • types <= 自定义类型模块(包含tsconfig.json)
      • config <= 自定义配置模块

补充配置

types模块的tsconfig.json

{
  "extends": "../../tsconfig.base.json",
  "compilerOptions": {
    "target": "ESNext",
    "module": "ES6",
    "esModuleInterop": true,
    "skipLibCheck": true,
    "moduleResolution": "Node",
    "allowSyntheticDefaultImports": true,
    "emitDeclarationOnly": true
  },
  "files": ["index.ts"],
  "display": "Types"
}

根目录tsconfig.base.json

{
  "$schema": "https://json.schemastore.org/tsconfig",
  "compilerOptions": {
    "baseUrl": ".",
    "forceConsistentCasingInFileNames": true,
    "strict": true,
    "composite": true,
    "declaration": true,
    "declarationMap": true,
    "paths": {
      "@myapp/types": ["./packages/types"],
      "@myapp/config": ["./packages/config"],
      "@myapp/ui": ["./packages/ui"],
      "@myapp/ui-b2b": ["./apps/ui-b2b/src"],
      "@myapp/ui-partners": ["./apps/ui-patners/src"],
      "@myapp/api": ["./apps/api/src"]
    }
  }
}

cloudbuild.yaml

steps:
  - name: node:16
    entrypoint: npm
    args: ["install"]
  - name: node:16
    dir: "apps/ui-b2b"
    entrypoint: npm
    env:
      - "DEPLOYMENT_TARGET=$_DEPLOYMENT_TARGET"
      - "VITE_RECAPTCHA_SITE_KEY=$_VITE_RECAPTCHA_SITE_KEY"
      - "VITE_DYNAMIC_LINKS_DOMAIN=$_VITE_DYNAMIC_LINKS_DOMAIN"
      - "VITE_API_URL=$_VITE_API_URL"
      - "VITE_DISPOSABLE_API_KEY=$_VITE_DISPOSABLE_API_KEY"
      - "VITE_GCP_AUTH_TENANT_ID=$_VITE_GCP_AUTH_TENANT_ID"
      - "VITE_FIREBASE_CONFIG=$_VITE_FIREBASE_CONFIG"
      - "VITE_BASE_DOMAIN=$_VITE_BASE_DOMAIN"
      - "VITE_LOCAL=$_VITE_LOCAL"
      - "VITE_STRIPE_ALLOW_PROMOTION_CODES=$_VITE_STRIPE_ALLOW_PROMOTION_CODES"
      - "VITE_TOAST_DURATION=$_VITE_TOAST_DURATION"
      - "VITE_SEARCH_API_KEY=$_VITE_SEARCH_API_KEY"
      - "VITE_SEARCH_API_HOST=$_VITE_SEARCH_API_HOST"
      - "VITE_SEARCH_API_PORT=$_VITE_SEARCH_API_PORT"
      - "VITE_SEARCH_API_PROTOCOL=$_VITE_SEARCH_API_PROTOCOL"
    args: ["run", "build:development"]
  - name: "gcr.io/google.com/cloudsdktool/cloud-sdk"
    entrypoint: "bash"
    dir: "apps/ui-b2b"
    args:
      [
        "-c",
        "gcloud config set app/cloud_build_timeout 1600 && gcloud app deploy",
      ]
timeout: "1600s"

我尝试过调整路径、移除引用等方法,但都引发了新错误。请问问题原因是什么?如何修复?


问题原因与修复方案

核心原因

  1. 私有包未预构建:本地环境中TypeScript可能缓存了私有包的编译产物,但Cloud Build是全新环境,直接构建应用时,@myapp/types和@myapp/config未提前编译,导致TS无法找到对应类型定义或输出文件。
  2. Vite未同步TS路径映射:TS的paths配置仅对TS编译器生效,Vite默认不识别该配置,构建时会找不到私有包的实际路径。
  3. Cloud Build未处理monorepo依赖顺序:当前流程仅安装依赖后直接构建应用,未先编译私有包,导致应用构建时依赖的包无可用输出。

修复步骤

1. 为私有包添加构建脚本并预编译

在packages/types和packages/config的package.json中添加构建命令:

// packages/types/package.json
{
  "scripts": {
    "build": "tsc"
  }
}
// packages/config/package.json
{
  "scripts": {
    "build": "tsc"
  }
}

修改cloudbuild.yaml,在安装依赖后添加私有包编译步骤:

steps:
  - name: node:16
    entrypoint: npm
    args: ["install"]
  # 编译types私有包
  - name: node:16
    dir: "packages/types"
    entrypoint: npm
    args: ["run", "build"]
  # 编译config私有包
  - name: node:16
    dir: "packages/config"
    entrypoint: npm
    args: ["run", "build"]
  # 原有应用构建步骤
  - name: node:16
    dir: "apps/ui-b2b"
    entrypoint: npm
    env:
      # 保留原有环境变量
    args: ["run", "build:development"]
  # 原有部署步骤

2. 同步Vite路径别名配置

在Vue应用的vite.config.ts中添加resolve.alias,与tsconfig的paths保持一致:

import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import path from 'path'

export default defineConfig({
  plugins: [vue()],
  resolve: {
    alias: {
      '@': path.resolve(__dirname, './src'),
      '@myapp/config': path.resolve(__dirname, '../../packages/config'),
      '@myapp/types': path.resolve(__dirname, '../../packages/types')
    }
  }
})

3. 完善私有包的package.json配置

在packages/types和packages/config的package.json中指定入口字段,让Node和TS能正确识别:

// packages/types/package.json
{
  "name": "@myapp/types",
  "version": "1.0.0",
  "main": "./index.js",
  "types": "./index.d.ts",
  "scripts": {
    "build": "tsc"
  }
}
// packages/config/package.json
{
  "name": "@myapp/config",
  "version": "1.0.0",
  "main": "./index.js",
  "types": "./index.d.ts", // 若有类型定义则添加
  "scripts": {
    "build": "tsc"
  }
}

4. 优化TS项目引用构建(可选)

如果使用TS项目引用(references),确保所有私有包的tsconfig中composite: true,然后在根目录package.json添加全量构建脚本:

// 根目录package.json
{
  "scripts": {
    "build:all": "tsc --build"
  }
}

再修改cloudbuild.yaml的编译步骤为:

- name: node:16
  entrypoint: npm
  args: ["run", "build:all"]

此步骤可替代单独编译每个私有包的操作,一次性构建所有依赖项目。


内容的提问来源于stack exchange,提问作者Stf_F

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.23 15:09:52