diff --git a/.trae/rules/project_rules.md b/.trae/rules/project_rules.md
index fb737ed..e7c996f 100644
--- a/.trae/rules/project_rules.md
+++ b/.trae/rules/project_rules.md
@@ -18,4 +18,4 @@ const possiblePaths = [
```
14. 涉及交互弹窗的,不要使用浏览器的对话框 使用符合面板风格的弹窗组件
15. 如果需要识别操作系统平台有专门的函数,你需要查找不需要单独写
-16. 项目分为前端和后端 浏览器和后端访问的不一定在同一环境和平台,所以请不要使用浏览器侧相关检测等。应当使用后端方法。
\ No newline at end of file
+16. 编写完毕后需要运行npx tsc --noEmit进行检测
\ No newline at end of file
diff --git a/client/src/pages/EnvironmentManagerPage.tsx b/client/src/pages/EnvironmentManagerPage.tsx
index 0942ba8..c91d8f4 100644
--- a/client/src/pages/EnvironmentManagerPage.tsx
+++ b/client/src/pages/EnvironmentManagerPage.tsx
@@ -29,8 +29,9 @@ interface JavaEnvironment {
installStage?: 'download' | 'extract'
}
-interface SystemInfo {
+interface LocalSystemInfo {
platform: string
+ rawPlatform?: string // 原始平台标识 (win32/linux/darwin)
arch: string
}
@@ -83,7 +84,7 @@ interface DirectXEnvironment {
}
const EnvironmentManagerPage: React.FC = () => {
- const [systemInfo, setSystemInfo] = useState(null)
+ const [systemInfo, setSystemInfo] = useState(null)
const [javaEnvironments, setJavaEnvironments] = useState([])
const [vcRedistEnvironments, setVcRedistEnvironments] = useState([])
const [directxEnvironments, setDirectxEnvironments] = useState([])
@@ -165,6 +166,7 @@ const EnvironmentManagerPage: React.FC = () => {
if (response.success && response.data) {
setSystemInfo({
platform: response.data.platform,
+ rawPlatform: response.data.rawPlatform,
arch: response.data.arch
})
}
@@ -1174,7 +1176,11 @@ const EnvironmentManagerPage: React.FC = () => {
// 获取平台图标
const getPlatformIcon = () => {
if (!systemInfo) return
- return systemInfo.platform === 'win32'
+ // 优先使用 rawPlatform,回退到检查 platform 字段
+ const isWindows = systemInfo?.rawPlatform
+ ? systemInfo.rawPlatform === 'win32'
+ : systemInfo.platform?.toLowerCase().includes('windows')
+ return isWindows
?
:
}
@@ -1182,7 +1188,11 @@ const EnvironmentManagerPage: React.FC = () => {
// 获取平台名称
const getPlatformName = () => {
if (!systemInfo) return '未知'
- return systemInfo.platform === 'win32' ? 'Windows' : 'Linux'
+ // 优先使用 rawPlatform,回退到检查 platform 字段
+ const isWindows = systemInfo?.rawPlatform
+ ? systemInfo.rawPlatform === 'win32'
+ : systemInfo.platform?.toLowerCase().includes('windows')
+ return isWindows ? 'Windows' : 'Linux'
}
if (loading) {
diff --git a/client/src/pages/GameDeploymentPage.tsx b/client/src/pages/GameDeploymentPage.tsx
index 02d0aec..dc39e06 100644
--- a/client/src/pages/GameDeploymentPage.tsx
+++ b/client/src/pages/GameDeploymentPage.tsx
@@ -52,7 +52,18 @@ interface Games {
[key: string]: GameInfo
}
-
+// 辅助函数:判断是否为 Windows 平台
+const isWindowsPlatform = (systemInfo: any): boolean => {
+ // 优先使用 rawPlatform(原始平台标识)
+ if (systemInfo?.rawPlatform) {
+ return systemInfo.rawPlatform === 'win32'
+ }
+ // 回退到检查 platform 字段(友好名称)
+ if (systemInfo?.platform) {
+ return systemInfo.platform.toLowerCase().includes('windows')
+ }
+ return false
+}
const GameDeploymentPage: React.FC = () => {
const { addNotification } = useNotificationStore()
@@ -685,8 +696,9 @@ const GameDeploymentPage: React.FC = () => {
setCloudBuildLogs(prev => [...prev, '部署完成!'])
// 使用后端检测到的启动命令
- const startCommand = response.data.startCommand ||
- (systemInfo?.platform === 'win32' ? '.\\start.bat' : 'bash start.sh')
+ // 使用辅助函数判断平台(优先使用 rawPlatform,回退到 platform)
+ const startCommand = response.data.startCommand ||
+ (isWindowsPlatform(systemInfo) ? '.\\start.bat' : 'bash start.sh')
setCloudBuildComplete(true)
setCloudBuildResult({
@@ -724,10 +736,11 @@ const GameDeploymentPage: React.FC = () => {
const instanceName = `${cloudBuildResult.coreName}-${cloudBuildResult.version}`
setCloudInstanceName(instanceName)
setCloudInstanceDescription(`${cloudBuildResult.coreName} ${cloudBuildResult.version} 服务端`)
-
+
// 使用后端检测到的启动命令,如果没有则使用默认值
- const startCommand = cloudBuildResult.startCommand ||
- (systemInfo?.platform === 'win32' ? '.\\start.bat' : 'bash start.sh')
+ // 使用辅助函数判断平台(优先使用 rawPlatform,回退到 platform)
+ const startCommand = cloudBuildResult.startCommand ||
+ (isWindowsPlatform(systemInfo) ? '.\\start.bat' : 'bash start.sh')
setCloudInstanceStartCommand(startCommand)
setShowCreateCloudInstanceModal(true)
@@ -1654,13 +1667,14 @@ const GameDeploymentPage: React.FC = () => {
}
// 根据服务器类型生成启动命令
- const generateStartCommand = (serverType: string, selectedJava: string = 'default', isWindows: boolean = process.platform === 'win32') => {
+ const generateStartCommand = (serverType: string, selectedJava: string = 'default', isWindows: boolean = isWindowsPlatform(systemInfo)) => {
const lowerServerType = serverType.toLowerCase()
const javaExecutable = getSelectedJavaExecutable(selectedJava)
if (lowerServerType.includes('forge') || lowerServerType.includes('neoforge')) {
// Forge/NeoForge 使用启动脚本
- return isWindows ? 'run.bat' : './run.sh'
+ // 使用辅助函数判断平台(优先使用 rawPlatform,回退到 platform)
+ return isWindows ? '.\\run.bat' : 'bash run.sh'
} else if (lowerServerType.includes('fabric') || lowerServerType.includes('quilt')) {
// Fabric/Quilt 重命名为 server.jar
return `${javaExecutable} -jar server.jar`
@@ -1922,11 +1936,12 @@ const GameDeploymentPage: React.FC = () => {
// 监听Java版本选择变化,自动更新启动命令
useEffect(() => {
// 更新Minecraft实例启动命令
- if (selectedServer && selectedVersion && selectedMinecraftJava) {
+ // 只在用户手动选择时更新,不覆盖下载后扫描得到的启动命令
+ if (selectedServer && selectedVersion && selectedMinecraftJava && !downloadResult) {
setInstanceStartCommand(generateStartCommand(selectedServer, selectedMinecraftJava))
setStartCommandEdited(false)
}
- }, [selectedMinecraftJava, selectedServer])
+ }, [selectedMinecraftJava, selectedServer, downloadResult])
useEffect(() => {
// 更新整合包实例启动命令
@@ -1986,7 +2001,8 @@ const GameDeploymentPage: React.FC = () => {
const folderName = `modrinth-${cleanPackId}-${cleanVersion}`
// 根据平台使用正确的路径分隔符
- const isWindows = systemInfo?.platform === 'win32'
+ // 使用辅助函数判断平台(优先使用 rawPlatform,回退到 platform)
+ const isWindows = isWindowsPlatform(systemInfo)
const separator = isWindows ? '\\' : '/'
// 确保基础路径以分隔符结尾
@@ -3494,7 +3510,8 @@ const GameDeploymentPage: React.FC = () => {
const folderName = `modrinth-${cleanPackId}-${cleanVersion}`
// 根据平台使用正确的路径分隔符
- const isWindows = systemInfo?.platform === 'win32'
+ // 使用辅助函数判断平台(优先使用 rawPlatform,回退到 platform)
+ const isWindows = isWindowsPlatform(systemInfo)
const separator = isWindows ? '\\' : '/'
// 确保基础路径以分隔符结尾
@@ -3966,28 +3983,38 @@ const GameDeploymentPage: React.FC = () => {