flu-cli 0.0.1 → 0.0.4

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.
package/README.md CHANGED
@@ -1,29 +1,35 @@
1
- # Flutter CLI 工具
1
+ # Flu CLI 工具
2
2
 
3
3
  火之夜工作室 Flutter 项目创建工具,基于 Node.js 实现的命令行工具,用于快速创建和配置 Flutter 项目。
4
4
 
5
5
  ## 功能特点
6
6
 
7
- - 交互式命令行界面,简化项目创建流程
8
- - 支持创建应用(app)和模块(module)两种项目类型
9
- - 提供基础版和增强版两种项目模板
10
- - 自动配置项目包名和显示名称
11
- - 支持从 Git 仓库获取最新模板代码
12
- - 自动打开 IDE(支持 VS Code、Android Studio 等)
13
- - 跨平台支持(Windows、macOS、Linux)
7
+ - **交互式命令行界面**:简化项目创建流程,引导用户完成各项配置
8
+ - **多项目类型支持**:可创建应用(app)、模块(module)、包(package)和插件(plugin)四种项目类型
9
+ - **丰富的模板选择**:提供四种模板类型,满足不同开发需求
10
+ - **仅基础项目(only)**:仅包含Flutter官方基础项目结构
11
+ - **最小模板(min)**:基础结构+路由管理+主题管理
12
+ - **标准模板(normal)**:最小模板+状态管理+工具集+UI组件库
13
+ - **高级模板(pro)**:标准模板+网络请求+数据缓存+示例模块
14
+ - **灵活的状态管理**:支持原生setState、GetX等多种状态管理方案
15
+ - **自动化配置**:自动处理包名替换、项目命名和依赖管理
16
+ - **开发环境集成**:自动配置VSCode开发环境(代码风格、调试配置、扩展推荐)
17
+ - **依赖包管理**:支持通过Git仓库自动集成常用工具库和网络请求库
18
+ - **IDE自动打开**:创建完成后可自动在VSCode或Android Studio中打开项目
19
+ - **跨平台支持**:兼容Windows、macOS和Linux操作系统
14
20
 
15
21
  ## 安装
16
22
 
17
23
  ### 全局安装
18
24
 
19
25
  ```bash
20
- npm install -g flutter-cli
26
+ npm install -g flu-cli
21
27
  ```
22
28
 
23
29
  ### 本地安装
24
30
 
25
31
  ```bash
26
- npm install flutter-cli
32
+ npm install flu-cli
27
33
  ```
28
34
 
29
35
  ## 使用方法
@@ -32,25 +38,108 @@ npm install flutter-cli
32
38
 
33
39
  ```bash
34
40
  # 如果全局安装
35
- flutter-cli
41
+ flu-cli
36
42
 
37
43
  # 或者使用 npx
38
- npx flutter-cli
44
+ npx flu-cli
39
45
  ```
40
46
 
41
47
  ### 创建新项目
42
48
 
43
49
  ```bash
44
- flutter-cli create
50
+ flu-cli create
45
51
  ```
46
52
 
53
+ ### 命令行参数示例
54
+
55
+ 可以直接通过命令行参数指定所有配置,无需交互式输入:
56
+
57
+ ```bash
58
+ # 创建应用项目(高级模板+GetX状态管理+VSCode)
59
+ flu-cli create --project-type app --template-type pro --state-manager GetX --project-name my_flutter_app --package-name com.example.myapp --parent-dir ~/your projects path --ide vscode
60
+
61
+ # 创建模块项目(标准模板+State状态管理 + Android Studio)
62
+ flu-cli create --project-type module --template-type normal --state-manager state --project-name my_flutter_module --package-name com.example.mymodule --parent-dir ~/your projects path --ide android_studio
63
+
64
+ # 最小化模板快速创建
65
+ flu-cli create --project-type app --template-type min --project-name quick_start --package-name com.example.quick --parent-dir ~/your projects path
66
+
67
+ # 仅仅创建一个flutter项目
68
+ flu-cli create --project-type app --template-type only --project-name quick_start --package-name com.example.quick --parent-dir ~/your projects path
69
+ ```
70
+
71
+ #### 参数说明
72
+
73
+ | 参数 | 说明 | 可选值 |
74
+ | --project-type | 项目类型 | app, module, package, plugin |
75
+ | --template-type | 模板类型 | only, min, normal, pro |
76
+ | --state-manager | 状态管理方案 | state, GetX, |
77
+ | --project-name | 项目名称 | 小写字母、数字和下划线组合 |
78
+ | --package-name | 包名 | 类似Java包名格式,如com.example.app |
79
+ | --parent-dir | 存放目录 | 绝对路径或相对路径 |
80
+ | --ide | IDE选择 | vscode, android_studio, open_folder, manual |
81
+ | --flutter-sdk | Flutter SDK路径 | 默认为系统环境变量中的flutter |
82
+
47
83
  按照提示完成以下步骤:
48
84
 
49
- 1. 选择项目类型(应用或模块)
50
- 2. 选择模板类型(基础版或增强版)
51
- 3. 输入项目名称、包名和显示名称
52
- 4. 选择项目存放路径
53
- 5. 选择要使用的 IDE
85
+ 1. **选择项目类型**:应用(app)、模块(module)、包(package)或插件(plugin)
86
+ 2. **选择模板类型**:基础(only)、最小(min)、标准(normal)或高级(pro)
87
+ 3. **选择状态管理**:根据模板类型选择合适的状态管理方案(高级模板需要)
88
+ 4. **输入项目信息**:项目名称、包名和存放路径
89
+ 5. **确认配置**:确认项目信息和覆盖选项
90
+ 6. **选择IDE**:选择用于打开项目的IDE
91
+
92
+ ## 模板详情
93
+
94
+ ### 仅基础项目(only)
95
+ - 包含Flutter官方创建的基础项目结构
96
+ - 仅保留核心文件:`main.dart`、`pubspec.yaml`和基础目录结构
97
+ - 适用于快速测试或需要完全自定义项目结构的场景
98
+
99
+ ### 最小模板(min)
100
+ - 基于基础项目扩展,增加以下功能:
101
+ - 路由管理:使用`auto_route`实现路由配置和导航
102
+ - 主题管理:支持亮色/暗色主题切换
103
+ - 基础工具类:包含常用字符串、日期处理方法
104
+
105
+ ### 标准模板(normal)
106
+ - 基于最小模板扩展,增加以下功能:
107
+ - 状态管理:根据选择集成对应状态管理库
108
+ - UI组件库:基础按钮、输入框、列表项等常用组件
109
+ - 网络请求:基于`dio`的基础网络请求封装
110
+ - 本地存储:使用`shared_preferences`实现简单数据存储
111
+
112
+ ### 高级模板(pro)
113
+ - 基于标准模板扩展,增加以下功能:
114
+ - 完整网络层:请求拦截、响应处理、错误统一管理
115
+ - 数据缓存:实现网络数据缓存策略
116
+ - 业务模块划分:按功能模块组织代码结构
117
+ - 示例功能:包含登录、列表等示例页面
118
+ - 依赖注入:使用`get_it`实现服务定位
119
+
120
+ ## 项目结构
121
+
122
+ ```
123
+ flutter-cli/
124
+ ├── index.js # 主入口文件
125
+ ├── package.json # 项目配置
126
+ ├── README.md # 项目说明文档
127
+ └── lib/ # 核心功能模块
128
+ ├── createProject.js # 项目创建主流程协调
129
+ ├── userInteraction.js # 用户交互功能(输入、选择、确认)
130
+ ├── flutterProjectCreator.js # Flutter项目创建(执行flutter create命令)
131
+ ├── libCopier.js # 模板文件复制和处理
132
+ ├── utils.js # 工具函数(验证、格式化、IDE打开等)
133
+ └── desktopPath.js # 桌面路径获取
134
+ ```
135
+
136
+ ### 核心模块说明
137
+
138
+ - **createProject.js**:协调整个项目创建流程,包括用户交互、项目初始化、模板复制和环境配置
139
+ - **userInteraction.js**:提供所有交互式功能,包括获取项目类型、模板类型、状态管理、项目信息等
140
+ - **flutterProjectCreator.js**:执行`flutter create`命令创建基础项目,处理不同项目类型参数
141
+ - **libCopier.js**:负责模板文件复制、占位符替换和Git仓库克隆操作
142
+ - **utils.js**:提供各种辅助功能,如名称验证、彩色输出、README生成和IDE自动打开
54
143
 
55
144
  ## 依赖项
56
145
 
@@ -58,27 +147,11 @@ flutter-cli create
58
147
  - chalk: 终端彩色输出
59
148
  - commander: 命令行参数解析
60
149
  - ora: 终端加载动画
61
- - cli-progress: 进度条显示
62
150
  - fs-extra: 文件系统操作增强
151
+ - child_process: 执行系统命令
63
152
 
64
153
  ## 开发
65
154
 
66
- ### 项目结构
67
-
68
- ```
69
- flutter-cli/
70
- ├── index.js # 主入口文件
71
- ├── package.json # 项目配置
72
- ├── README.md # 项目说明
73
- └── lib/ # 核心功能模块
74
- ├── createProject.js # 项目创建主流程
75
- ├── userInteraction.js # 用户交互功能
76
- ├── flutterProjectCreator.js # Flutter项目创建
77
- ├── libCopier.js # 项目模板复制
78
- ├── utils.js # 工具函数
79
- └── desktopPath.js # 桌面路径获取
80
- ```
81
-
82
155
  ### 本地开发
83
156
 
84
157
  ```bash
@@ -93,7 +166,7 @@ npm install
93
166
  npm link
94
167
 
95
168
  # 测试运行
96
- flutter-cli
169
+ flu-cli
97
170
  ```
98
171
 
99
172
  ## 注意事项
@@ -101,6 +174,8 @@ flutter-cli
101
174
  - 确保系统已正确安装 Flutter SDK 并添加到环境变量
102
175
  - 使用前可运行 `flutter doctor` 检查 Flutter 安装状态
103
176
  - 项目创建过程中需要网络连接以从 Git 仓库获取模板
177
+ - 高级模板可能需要较长时间下载依赖,请耐心等待
178
+ - 如遇权限问题,在命令前添加`sudo`(macOS/Linux)或使用管理员权限运行终端(Windows)
104
179
 
105
180
  ## 许可证
106
181
 
package/index.js CHANGED
@@ -6,35 +6,64 @@
6
6
  * 主入口文件,处理命令行参数并调用相应功能
7
7
  */
8
8
 
9
- const { program } = require('commander');
10
- const chalk = require('chalk');
11
- const { createProject } = require('./lib/createProject');
12
- const packageJson = require('./package.json');
9
+
10
+ import { program } from 'commander'
11
+ import chalk from 'chalk';
12
+ import { createProject } from './lib/createProject.js';
13
+ import { readFileSync } from 'fs';
14
+ import { fileURLToPath } from 'url';
15
+ import { dirname, join } from 'path';
16
+
17
+ // 获取package.json内容
18
+ const __dirname = dirname(fileURLToPath(import.meta.url));
19
+ const packageJson = JSON.parse(readFileSync(join(__dirname, 'package.json'), 'utf8'));
13
20
 
14
21
  // 设置版本号和描述
15
22
  program
16
23
  .version(packageJson.version)
17
24
  .description(chalk.cyan('火之夜工作室 Flutter 项目创建工具'));
18
25
 
26
+ //
27
+
19
28
  // 创建项目命令
20
29
  program
21
30
  .command('create')
22
- .description('创建一个新的Flutter项目')
23
- .option('-t, --project-type <type>', '项目类型: app module', 'app')
24
- .option('-m, --template-type <type>', '模板类型: 0 (基础UI), 1 (State), 2 (GetX)', '2')
25
- .option('-d, --demo <boolean>', '是否需要示例代码: true false', true)
26
- .option('-n, --project-name <name>', '项目名称 (小写字母、数字和下划线)')
27
- .option('-p, --package-name <name>', '包名 (例如: com.example.project_name)')
28
- .option('-o, --output-dir <path>', '项目输出目录')
29
- .option('-i, --ide <type>', '使用的IDE: vscode, android_studio, none', 'none')
31
+ .description('创建新的Flutter项目')
32
+ .option('-t, --project-type <type>', '项目类型: app, module, package, plugin', 'app')
33
+ .option('-m, --template-type <type>', '模板类型: only, min, normal, pro', 'normal')
34
+ .option('-s, --state-manager <name>', '状态管理: state, GetX, Provider, MobX, Bloc, Riverpod', 'GetX')
35
+ .option('-n, --project-name <name>', '项目名称')
36
+ .option('-p, --package-name <name>', '包名(com.example.app)')
37
+ .option('-d, --parent-dir <path>', '项目存放目录')
38
+ .option('-i, --ide <type>', '使用的IDE: vscode, android_studio, open_folder , manual', 'vscode')
30
39
  .option('-f, --flutter-sdk <path>', '自定义Flutter SDK路径')
40
+ .option('-h, --help', '显示创建命令帮助信息')
31
41
  .action((options) => {
32
- console.log(chalk.bold.greenBright('欢迎使用 火之夜工作室 Flutter 项目创建工具\n'));
42
+ if (options.help) {
43
+ console.log(chalk.bold.greenBright('flu-cli create - 创建新的Flutter项目'));
44
+ console.log('用法: flu-cli create [选项]');
45
+ console.log('选项:');
46
+ console.log(' -t, --project-type <type> 项目类型 (app, module, package, plugin) [默认: app]');
47
+ console.log(' -m, --template-type <type> 模板类型 (only, min, normal, pro) [默认: pro]');
48
+ console.log(' -s, --state-manager <name> 状态管理方案 (state, GetX,) [默认: GetX]');
49
+ console.log(' -n, --project-name <name> 项目名称 [默认: hzy_example_${项目类型}]');
50
+ console.log(' -p, --package-name <name> 包名 [默认: com.example.${项目类型}]');
51
+ console.log(' -d, --parent-dir <path> 项目存放目录 [默认: 当前目录]');
52
+ console.log(' -i, --ide <choice> IDE选择 (vscode, android_studio, open_folder, manual) [默认: vscode]');
53
+ console.log(' -f, --flutter-sdk <path> 自定义Flutter SDK路径 [默认: 系统环境变量中的flutter]');
54
+ console.log(' -h, --help 显示本帮助信息');
55
+ process.exit(0);
56
+ }
57
+
58
+ console.log(chalk.bold.greenBright('欢迎使用 火之夜工作室 Flutter 项目创建工具'));
33
59
 
34
60
  // 检查是否提供了命令行参数
35
- const hasCommandLineArgs = options.projectName || options.packageName ||
36
- options.projectType !== 'app' || options.templateType !== '2' ||
37
- options.demo !== true || options.outputDir || options.ide !== 'none' || options.flutterSdk;
61
+ const hasCommandLineArgs = options.projectName ||
62
+ options.packageName ||
63
+ options.projectType !== 'app' ||
64
+ options.templateType !== 'normal' ||
65
+ options.stateManager !== 'GetX' ||
66
+ options.parentDir || options.ide !== 'vscode' || options.flutterSdk;
38
67
 
39
68
  // 如果提供了命令行参数,则直接使用这些参数创建项目
40
69
  // 否则使用交互式方式获取参数
@@ -42,14 +71,34 @@ program
42
71
  useCommandLineArgs: hasCommandLineArgs,
43
72
  projectType: options.projectType,
44
73
  templateType: options.templateType,
45
- isNeedDemo: options.demo === 'false' ? false : Boolean(options.demo),
74
+ stateManager: options.stateManager,
46
75
  projectName: options.projectName,
47
76
  packageName: options.packageName,
48
- parentDir: options.outputDir,
49
- ideChoice: options.ide
77
+ parentDir: options.parentDir,
78
+ ideChoice: options.ide,
79
+ flutterSdkPath: options.flutterSdk,
50
80
  });
51
81
  });
52
82
 
83
+ // 全局帮助处理
84
+ if (process.argv.includes('-h') || process.argv.includes('--help')) {
85
+ if (process.argv.length <= 3) {
86
+ console.log('flu-cli - 火之夜工作室Flutter项目创建工具');
87
+ console.log('版本: ' + packageJson.version);
88
+ console.log('用法: flu-cli [命令] [选项]\n');
89
+ console.log('命令:');
90
+ console.log(' create 创建新的Flutter项目\n');
91
+ console.log('全局选项:');
92
+ console.log(' -V, --version 显示版本号');
93
+ console.log(' -h, --help 显示全局帮助信息\n');
94
+ console.log('使用 "flu-cli [命令] --help" 查看特定命令的详细帮助');
95
+ process.exit(0);
96
+ }
97
+ program.parse(process.argv);
98
+ }
99
+
100
+
101
+
53
102
  // 如果没有提供命令,默认执行创建项目
54
103
  if (process.argv.length === 2) {
55
104
  console.log(chalk.bold.greenBright('欢迎使用 火之夜工作室 Flutter 项目创建工具\n'));
@@ -1,60 +1,102 @@
1
1
  /**
2
2
  * 项目创建模块
3
3
  *
4
- * 负责协调整个项目创建流程
4
+ * 负责协调整个Flutter项目的创建流程,包括用户交互、项目初始化、模板复制和环境配置
5
+ * 支持通过命令行参数或交互式方式创建不同类型和模板的Flutter项目
5
6
  */
6
7
 
8
+ import { execSync } from 'child_process';
9
+ import ora from 'ora';
10
+ import { dirname, join } from 'path';
11
+ import { fileURLToPath } from 'url';
12
+ import fsExtra from 'fs-extra';
13
+ const { existsSync, mkdirSync, accessSync, constants, removeSync } = fsExtra;
14
+ import { getUserInteraction } from './userInteraction.js';
15
+ import { copyLibDirectory, copyVscode } from './libCopier.js';
16
+ import { runFlutterCreate } from './flutterProjectCreator.js';
17
+ import { printColored, updateReadme, openProjectInIde, getTemplateBranch } from './utils.js';
7
18
 
8
- const { execSync } = require('child_process');
9
- const ora = require('ora');
10
- const path = require('path');
11
- const fs = require('fs-extra');
12
- const { getUserInteraction } = require('./userInteraction');
13
- const { copyLibDirectory } = require('./libCopier');
14
- const { runFlutterCreate } = require('./flutterProjectCreator');
15
- const { printColored, updateReadme, openProjectInIde } = require('./utils');
19
+ /**
20
+ * 生成默认项目名称
21
+ *
22
+ * 根据项目类型和当前日期生成唯一的默认项目名称,避免命名冲突
23
+ * 应用类型项目以'flutter_app_'为前缀,模块类型以'flutter_module_'为前缀
24
+ *
25
+ * @param {string} projectType - 项目类型 ('app' 或 'module')
26
+ * @returns {string} 带时间戳的默认项目名称
27
+ */
28
+ function getDefaultProjectName (projectType) {
29
+ const date = new Date();
30
+ const timestamp = `${date.getFullYear()}${String(date.getMonth() + 1).padStart(2, '0')}${String(date.getDate()).padStart(2, '0')}`;
31
+ return projectType === 'app' ? `flutter_app_${timestamp}` : `flutter_module_${timestamp}`;
32
+ }
16
33
 
17
34
  /**
18
35
  * 创建项目的主函数
19
36
  *
20
- * 协调整个项目创建流程,包括获取用户输入、创建项目、复制模板等
21
- * @param {Object} options - 命令行参数选项
22
- * @param {boolean} options.useCommandLineArgs - 是否使用命令行参数
23
- * @param {string} options.projectType - 项目类型 ('app'或'module')
24
- * @param {string} options.templateType - 模板类型 ('0', '1', '2')
25
- * @param {boolean} options.isNeedDemo - 是否需要示例代码
26
- * @param {string} options.projectName - 项目名称
27
- * @param {string} options.packageName - 包名
28
- * @param {string} options.parentDir - 项目存放路径
29
- * @param {string} options.ideChoice - IDE选择
37
+ * 协调整个项目创建流程,包括获取用户输入、验证环境、创建Flutter项目、复制模板文件、
38
+ * 生成README和自动打开IDE等步骤。支持命令行参数和交互式两种模式
39
+ *
40
+ * @param {Object} [options={}] - 命令行参数选项
41
+ * @param {boolean} [options.useCommandLineArgs=false] - 是否使用命令行参数
42
+ * @param {string} [options.projectType] - 项目类型 ('app','module','package','plugin')
43
+ * @param {string} [options.templateType] - 模板类型 ('only', 'min', 'normal', 'pro')
44
+ * @param {string} [options.stateManager] - 状态管理 ('state', 'GetX', 'Provider', etc.)
45
+ * @param {string} [options.projectName] - 项目名称
46
+ * @param {string} [options.packageName] - 包名
47
+ * @param {string} [options.parentDir] - 项目存放路径
48
+ * @param {string} [options.ideChoice] - IDE选择 ('vscode', 'android_studio', etc.)
49
+ * @param {string} [options.flutterSdk] - Flutter SDK路径
50
+ * @example
51
+ * // 交互式创建项目
52
+ * createProject();
53
+ * // 命令行模式创建项目
54
+ * createProject({
55
+ * useCommandLineArgs: true,
56
+ * projectType: 'app',
57
+ * templateType: 'pro',
58
+ * projectName: 'my_app',
59
+ * packageName: 'com.example.myapp',
60
+ * parentDir: '/path/to/projects'
61
+ * });
30
62
  */
31
63
  async function createProject (options = {}) {
32
64
  try {
33
65
  // 获取项目类型 - 从命令行参数或交互式输入
34
66
  const projectType = options.useCommandLineArgs ? options.projectType : await getUserInteraction.getProjectType();
67
+ let templateType = '';
68
+ // 项目类型为app或module时,获取模板类型
69
+ if (projectType == "app" || projectType == "module") {
70
+ // 获取模板类型 - 从命令行参数或交互式输入
71
+ templateType = options.useCommandLineArgs ? options.templateType : await getUserInteraction.getTemplateType();
72
+ } else {
73
+ // 项目类型为package或plugin时,模板类型固定为only
74
+ templateType = 'only';
75
+ }
35
76
 
36
- // 获取模板类型 - 从命令行参数或交互式输入
37
- const templateType = options.useCommandLineArgs ? options.templateType : await getUserInteraction.getTemplateType();
38
77
 
39
- // 获取是否需要demo的确认 - 从命令行参数或交互式输入
40
- const isNeedDemo = options.useCommandLineArgs ? options.isNeedDemo : await getUserInteraction.getIsNeedDemo();
78
+ // 获取状态管理 - 仅在非基础模板时需要
79
+ let stateManager = '';
80
+ if (templateType != 'only' && templateType != 'min') {
81
+ stateManager = options.useCommandLineArgs ? options.stateManager : await getUserInteraction.getStateManager();
82
+ }
41
83
 
42
84
  // 获取当前脚本所在目录作为源目录
43
- const sourceDir = path.dirname(require.main.filename);
85
+ const sourceDir = dirname(fileURLToPath(import.meta.url));
44
86
 
45
87
  // 获取项目信息 - 从命令行参数或交互式输入
46
88
  let projectName, packageName, parentDir, targetDir, flutterSdkPath;
47
89
 
48
- if (options.useCommandLineArgs && options.projectName && options.packageName && options.parentDir) {
90
+ if (options.useCommandLineArgs && options.projectName && options.packageName && options.parentDir && options.flutterSdk) {
49
91
  // 使用命令行参数
50
92
  projectName = options.projectName;
51
93
  packageName = options.packageName;
52
94
  parentDir = options.parentDir;
53
- targetDir = path.join(parentDir, projectName);
95
+ targetDir = join(parentDir, projectName);
54
96
  flutterSdkPath = options.flutterSdk;
55
97
  } else if (options.useCommandLineArgs) {
56
98
  // 命令行参数不完整,使用交互式输入,但预填充已提供的参数
57
- const defaultName = projectType === 'module' ? "hzy_example_module" : "hzy_example_project";
99
+ const defaultName = getDefaultProjectName(projectType);
58
100
  const projectInfo = await getUserInteraction.getProjectInfo(
59
101
  projectType,
60
102
  options.projectName || defaultName,
@@ -69,8 +111,11 @@ async function createProject (options = {}) {
69
111
  } else {
70
112
  // 完全使用交互式输入
71
113
  const projectInfo = await getUserInteraction.getProjectInfo(projectType);
114
+ // 项目名字
72
115
  projectName = projectInfo.projectName;
116
+ // 包名
73
117
  packageName = projectInfo.packageName;
118
+ // 项目存放地址
74
119
  parentDir = projectInfo.parentDir;
75
120
  targetDir = projectInfo.targetDir;
76
121
  flutterSdkPath = projectInfo.flutterSdkPath;
@@ -78,9 +123,9 @@ async function createProject (options = {}) {
78
123
 
79
124
  console.log('flutterSdkPath:', flutterSdkPath);
80
125
  // 验证目标目录是否存在并具有写权限
81
- if (!fs.existsSync(parentDir)) {
126
+ if (!existsSync(parentDir)) {
82
127
  try {
83
- fs.mkdirSync(parentDir, { recursive: true });
128
+ mkdirSync(parentDir, { recursive: true });
84
129
  } catch (e) {
85
130
  printColored(`错误: 无法创建目录 ${parentDir}: ${e.message}`, 'red');
86
131
  return;
@@ -89,14 +134,14 @@ async function createProject (options = {}) {
89
134
 
90
135
  // 检查目标目录是否具有写权限
91
136
  try {
92
- fs.accessSync(parentDir, fs.constants.W_OK);
137
+ accessSync(parentDir, constants.W_OK);
93
138
  } catch (e) {
94
139
  printColored(`错误: 目录 ${parentDir} 没有写权限`, 'red');
95
140
  return;
96
141
  }
97
142
 
98
143
  // 检查目标目录是否已存在
99
- if (fs.existsSync(targetDir)) {
144
+ if (existsSync(targetDir)) {
100
145
  const overwrite = await getUserInteraction.confirmOverwrite(targetDir);
101
146
  if (!overwrite) {
102
147
  printColored("操作已取消", 'yellow');
@@ -104,7 +149,7 @@ async function createProject (options = {}) {
104
149
  }
105
150
 
106
151
  // 删除已存在的目录
107
- fs.removeSync(targetDir);
152
+ removeSync(targetDir);
108
153
  }
109
154
 
110
155
  // 使用flutter create创建新项目
@@ -116,40 +161,25 @@ async function createProject (options = {}) {
116
161
  }
117
162
  flutterCreateSpinner.succeed('Flutter项目创建成功');
118
163
 
119
- // 根据模板类型选择Git分支和是否需要demo分支
120
- let templateBranch = 'master';
121
-
122
- switch (templateType) {
123
- case '0':
124
- // 基础模版
125
- templateBranch = 'master';
126
- break;
127
- case '1':
128
- // State模板
129
- templateBranch = 'depend';
130
- break;
131
- case '2':
132
- // GetX模板
133
- templateBranch = 'depend-get';
134
- break;
135
- default:
136
- break;
137
- }
138
164
 
139
- if (isNeedDemo && templateType != '0') {
140
- templateBranch = templateBranch + '-demo';
141
- }
142
- // 复制项目文件
143
- const copySpinner = ora('正在复制项目模板...').start();
144
- const copyResult = await copyLibDirectory(sourceDir, targetDir, projectName, projectType, templateType, packageName, templateBranch);
145
- if (!copyResult) {
146
- copySpinner.fail('项目模板复制失败');
147
- return;
165
+
166
+ if (templateType != 'only') {
167
+ // 获取模板分支名称
168
+ const templateBranch = getTemplateBranch(templateType, stateManager);
169
+ // 复制项目文件
170
+ const copySpinner = ora('正在复制项目模板...').start();
171
+ const copyResult = await copyLibDirectory(sourceDir, targetDir, projectName, projectType, templateType, packageName, templateBranch);
172
+ if (!copyResult) {
173
+ copySpinner.fail('项目模板复制失败');
174
+ return;
175
+ }
176
+ copySpinner.succeed('项目模板复制成功');
177
+ // 更新README.md
178
+ updateReadme(targetDir, projectName, packageName);
148
179
  }
149
- copySpinner.succeed('项目模板复制成功');
150
180
 
151
- // 更新README.md
152
- updateReadme(targetDir, projectName,);
181
+
182
+
153
183
 
154
184
  // 打印完成信息
155
185
  printColored("\n新项目已创建成功!", 'green');
@@ -161,6 +191,9 @@ async function createProject (options = {}) {
161
191
 
162
192
  // 获取用户选择的IDE类型 - 从命令行参数或交互式输入
163
193
  const ideChoice = options.useCommandLineArgs ? options.ideChoice : await getUserInteraction.getIdeChoice();
194
+ if (ideChoice == 'vscode' && templateType != 'only') {
195
+ await copyVscode(targetDir);
196
+ }
164
197
  if ((ideChoice == 'vscode' || ideChoice == 'android_studio') && flutterSdkPath === 'flutter') {
165
198
  const pubGetSpinner = ora('正在获取Flutter依赖...').start();
166
199
  try {
@@ -184,4 +217,4 @@ async function createProject (options = {}) {
184
217
  }
185
218
  }
186
219
 
187
- module.exports = { createProject };
220
+ export { createProject };