You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

如何解决SvelteKit开发模式下与Go同源后端的端口及CORS问题?

解决SvelteKit开发模式与Go后端的跨域及API路径问题

我来分享几个在SvelteKit+Go项目里处理这类开发环境问题的实用方案,都是社区里常用的靠谱办法:

方案一:用SvelteKit内置的Vite代理(最推荐)

SvelteKit基于Vite构建,所以可以直接通过配置Vite的代理功能,把前端的API请求转发到Go服务器上。这样既解决了跨域问题,又能让前端继续使用相对路径,完全不用修改业务代码,和生产环境的代码逻辑保持一致。

具体配置步骤:

  1. 打开你的svelte.config.js文件,在kit.vite下添加server.proxy配置:
// svelte.config.js
import adapter from '@sveltejs/adapter-static'; // 根据你实际使用的adapter调整

/** @type {import('@sveltejs/kit').Config} */
const config = {
	kit: {
		adapter: adapter(),
		vite: {
			server: {
				proxy: {
					// 假设你的API接口前缀是/api,根据实际情况修改
					'/api': {
						target: 'http://localhost:8080', // Go服务器的地址和端口
						changeOrigin: true, // 必须开启,否则Go服务器会收到来自Vite服务器的请求origin
						// 如果你的Go服务器用了HTTPS且是自签名证书,需要加上secure: false
						// secure: false
					}
				}
			}
		}
	}
};

export default config;
  1. 重启SvelteKit的开发服务器,现在前端发起的/api/xxx请求会自动转发到http://localhost:8080/api/xxx,既没有跨域问题,相对路径也能正常工作。

这个方案的优势是开发体验流畅,不需要额外的命令,生产构建后直接和Go服务器部署即可,完全兼容。

方案二:让Go服务器托管SvelteKit的监听构建(完全模拟生产环境)

如果你希望开发环境和生产环境的运行方式完全一致,可以让SvelteKit以监听模式构建,然后用Go服务器同时托管静态文件和API。这样不需要启动SvelteKit的开发服务器,所有请求都走Go的端口,从根源上避免跨域和路径问题。

步骤如下:

  1. 启动SvelteKit的监听构建:
svelte-kit build --watch

这个命令会监听srcstatic目录的文件变化,自动重新编译生成最新的静态文件到build目录(默认路径)。
2. 配置Go服务器,把静态文件路由指向SvelteKit的build目录,同时处理API请求:

package main

import (
	"net/http"
)

func main() {
	// 处理API路由示例
	http.HandleFunc("/api/hello", func(w http.ResponseWriter, r *http.Request) {
		w.Write([]byte("Hello from Go API"))
	})

	// 托管SvelteKit的静态构建文件
	staticFS := http.FileServer(http.Dir("./build"))
	http.Handle("/", staticFS)

	// 启动Go服务器,端口根据你的需求调整
	http.ListenAndServe(":8080", nil)
}
  1. 启动Go服务器,访问http://localhost:8080就能看到SvelteKit的前端页面,API请求也会直接同域处理,完全没有跨域问题。

这个方案的好处是开发环境和生产环境的运行逻辑完全一致,适合需要提前验证生产部署效果的场景。

方案三:在Go服务器配置CORS中间件(备用方案)

如果上面两个方案都不适合你,也可以在Go服务器上添加CORS中间件,允许SvelteKit开发服务器的跨域请求。不过这个方案需要区分开发和生产环境的API路径,相对来说不够优雅。

示例代码(用gorilla/handlers实现CORS):

package main

import (
	"net/http"

	"github.com/gorilla/handlers"
)

func main() {
	// 允许SvelteKit开发服务器的源地址(默认端口是5173)
	allowedOrigins := []string{"http://localhost:5173"}
	allowedMethods := []string{"GET", "POST", "PUT", "DELETE", "OPTIONS"}
	allowedHeaders := []string{"Content-Type", "Authorization"}

	// 配置CORS中间件
	corsMiddleware := handlers.CORS(
		handlers.AllowedOrigins(allowedOrigins),
		handlers.AllowedMethods(allowedMethods),
		handlers.AllowedHeaders(allowedHeaders),
	)

	// 处理API路由
	http.HandleFunc("/api/hello", func(w http.ResponseWriter, r *http.Request) {
		w.Write([]byte("Hello from Go API"))
	})

	// 应用CORS中间件到所有路由
	http.ListenAndServe(":8080", corsMiddleware(http.DefaultServeMux))
}

同时,在SvelteKit里需要根据环境切换API地址,比如创建src/lib/api-config.js

// src/lib/api-config.js
export const API_BASE = import.meta.env.MODE === 'development'
	? 'http://localhost:8080/api'
	: '/api';

然后在请求API时使用这个地址:

// 示例请求
const response = await fetch(`${API_BASE}/hello`);
const data = await response.json();

这个方案的缺点是需要维护环境分支的代码,容易出现开发和生产环境的不一致问题,所以只推荐作为前两个方案的备选。


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

火山引擎 最新活动