flu-cli-core 1.0.5 → 1.1.1

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.
Files changed (118) hide show
  1. package/README.md +9 -0
  2. package/dist/chunk-BGYZU6TU.js +466 -0
  3. package/dist/chunk-QGM4M3NI.js +37 -0
  4. package/dist/factory-LM2CTHPW.js +7 -0
  5. package/dist/factory-P6ABQFH3.js +7 -0
  6. package/dist/index.cjs +17766 -3244
  7. package/dist/index.d.cts +783 -99
  8. package/dist/index.d.ts +783 -99
  9. package/dist/index.js +17323 -2942
  10. package/dist/upgrade_snippets-BJ6CQY5Q.js +9 -0
  11. package/package.json +3 -3
  12. package/templates/README.md +12 -0
  13. package/templates/core_files/auth/auth_middleware.dart.template +33 -0
  14. package/templates/core_files/auth/auth_service.dart.template +22 -0
  15. package/templates/core_files/auth/auth_viewmodel_mixin.dart.template +9 -0
  16. package/templates/core_files/auth/index.dart.template +4 -0
  17. package/templates/core_files/base/base_service.dart.template +12 -0
  18. package/templates/core_files/base/index.dart.template +3 -0
  19. package/templates/core_files/config/agreement_document_page.dart.template +220 -0
  20. package/templates/core_files/config/app_agreement.dart.template +297 -0
  21. package/templates/core_files/config/app_config.dart.template +81 -22
  22. package/templates/core_files/config/app_env.dart.template +107 -0
  23. package/templates/core_files/config/app_initializer.dart.template +16 -23
  24. package/templates/core_files/config/index.dart.template +4 -1
  25. package/templates/core_files/config/privacy_dialog.dart.template +158 -0
  26. package/templates/core_files/index.dart.template +3 -0
  27. package/templates/core_files/mixins/page/keep_alive_mixin.dart.template +6 -0
  28. package/templates/core_files/mixins/page/scroll_controller_mixin.dart.template +7 -0
  29. package/templates/core_files/mixins/service/request_guard_mixin.dart.template +18 -0
  30. package/templates/core_files/mixins/viewmodel/debounce_mixin.dart.template +18 -0
  31. package/templates/core_files/network/app_http.dart.template +19 -4
  32. package/templates/core_files/network/index.dart.template +4 -0
  33. package/templates/core_files/network/interceptors/global_params_interceptor.dart.template +77 -0
  34. package/templates/core_files/network/interceptors/index.dart.template +3 -0
  35. package/templates/core_files/network/network_monitor.dart.template +18 -0
  36. package/templates/core_files/network/response_adapter.dart.template +8 -19
  37. package/templates/core_files/router/app_routes.dart.template +3 -6
  38. package/templates/core_files/storage/storage_keys.dart.template +6 -0
  39. package/templates/core_files/theme/app_color_config.dart.template +32 -0
  40. package/templates/core_files/theme/app_text_size_config.dart.template +22 -0
  41. package/templates/core_files/theme/app_text_style_config.dart.template +139 -0
  42. package/templates/core_files/theme/app_theme.dart.template +72 -12
  43. package/templates/core_files/theme/index.dart.template +3 -0
  44. package/templates/core_files/utils/loading_util.dart.template +1 -1
  45. package/templates/examples/eg_list_page.dart.template +1 -2
  46. package/templates/examples/eg_service.dart.template +27 -4
  47. package/templates/examples/home_feed_service.dart.template +37 -0
  48. package/templates/helper_examples/image_picker_example_page.dart.template +289 -0
  49. package/templates/helper_examples/index.dart.template +4 -0
  50. package/templates/helper_examples/payment_shell_example_page.dart.template +67 -0
  51. package/templates/helper_examples/permission_example_page.dart.template +365 -0
  52. package/templates/helper_examples/webview_example_page.dart.template +44 -0
  53. package/templates/helpers/image_picker/README.md.template +30 -0
  54. package/templates/helpers/image_picker/index.dart.template +73 -0
  55. package/templates/helpers/payment/README.md.template +29 -0
  56. package/templates/helpers/payment/index.dart.template +66 -0
  57. package/templates/helpers/permission/README.md.template +30 -0
  58. package/templates/helpers/permission/index.dart.template +67 -0
  59. package/templates/helpers/webview/README.md.template +29 -0
  60. package/templates/helpers/webview/index.dart.template +88 -0
  61. package/templates/starter_project/.env.dev.template +14 -0
  62. package/templates/starter_project/.env.prod.example.template +14 -0
  63. package/templates/starter_project/.env.staging.template +14 -0
  64. package/templates/starter_project/.vscode/launch.json.template +54 -0
  65. package/templates/starter_project/.vscode/settings.json.template +14 -0
  66. package/templates/starter_project/DEVELOPER_GUIDE.md.template +169 -0
  67. package/templates/starter_project/README.md.template +117 -0
  68. package/templates/starter_project/analysis_options.yaml.template +28 -0
  69. package/templates/starter_project/lib/app.dart.template +22 -0
  70. package/templates/starter_project/lib/main.dart.template +34 -0
  71. package/templates/starter_project/lib/pages/splash_page.dart.template +154 -0
  72. package/templates/template_clean/lib/features/home/data/datasources/index.dart +1 -0
  73. package/templates/template_clean/lib/features/home/data/models/index.dart +1 -0
  74. package/templates/template_clean/lib/features/home/domain/index.dart +1 -0
  75. package/templates/template_clean/lib/features/home/presentation/pages/home_page.dart +290 -0
  76. package/templates/template_clean/lib/features/home/presentation/pages/index.dart +2 -0
  77. package/templates/template_clean/lib/features/home/presentation/pages/splash_page.dart +154 -0
  78. package/templates/template_clean/lib/features/home/presentation/viewmodels/home_viewmodel.dart +17 -0
  79. package/templates/template_clean/lib/features/index.dart +2 -0
  80. package/templates/template_clean/lib/features/user/data/datasources/home_feed_service.dart +37 -0
  81. package/templates/template_clean/lib/features/user/data/datasources/index.dart +4 -0
  82. package/templates/template_clean/lib/features/user/data/models/index.dart +3 -0
  83. package/templates/template_clean/lib/features/user/data/models/user.dart +15 -0
  84. package/templates/template_clean/lib/features/user/domain/index.dart +1 -0
  85. package/templates/template_clean/lib/features/user/presentation/pages/index.dart +1 -0
  86. package/templates/template_clean/lib/features/user/presentation/pages/user_list_page.dart +27 -0
  87. package/templates/template_clean/lib/features/user/presentation/viewmodels/user_list_viewmodel.dart +88 -0
  88. package/templates/template_clean/lib/features/user/presentation/widgets/user_item_card.dart +24 -0
  89. package/templates/template_clean/lib/shared/extensions/index.dart +1 -0
  90. package/templates/template_clean/lib/shared/widgets/index.dart +1 -0
  91. package/templates/template_lite/lib/models/index.dart +1 -0
  92. package/templates/template_lite/lib/pages/home_page.dart +290 -0
  93. package/templates/template_lite/lib/pages/index.dart +3 -0
  94. package/templates/template_lite/lib/pages/splash_page.dart +154 -0
  95. package/templates/template_lite/lib/pages/user_list_page.dart +29 -0
  96. package/templates/template_lite/lib/services/home_feed_service.dart +37 -0
  97. package/templates/template_lite/lib/services/index.dart +5 -0
  98. package/templates/template_lite/lib/utils/index.dart +1 -0
  99. package/templates/template_lite/lib/viewmodels/home_viewmodel.dart +34 -0
  100. package/templates/template_lite/lib/viewmodels/index.dart +2 -0
  101. package/templates/template_lite/lib/viewmodels/user_list_viewmodel.dart +103 -0
  102. package/templates/template_lite/lib/widgets/index.dart +1 -0
  103. package/templates/template_lite/lib/widgets/user_item_widget.dart +57 -0
  104. package/templates/template_modular/lib/features/home/index.dart +2 -0
  105. package/templates/template_modular/lib/features/home/models/index.dart +1 -0
  106. package/templates/template_modular/lib/features/home/pages/home_page.dart +290 -0
  107. package/templates/template_modular/lib/features/home/pages/index.dart +2 -0
  108. package/templates/template_modular/lib/features/home/pages/splash_page.dart +154 -0
  109. package/templates/template_modular/lib/features/home/services/index.dart +1 -0
  110. package/templates/template_modular/lib/features/home/viewmodels/home_viewmodel.dart +17 -0
  111. package/templates/template_modular/lib/features/index.dart +2 -0
  112. package/templates/template_modular/lib/features/user/index.dart +6 -0
  113. package/templates/template_modular/lib/features/user/pages/user_list_page.dart +26 -0
  114. package/templates/template_modular/lib/features/user/services/home_feed_service.dart +37 -0
  115. package/templates/template_modular/lib/features/user/viewmodels/user_list_viewmodel.dart +103 -0
  116. package/templates/template_modular/lib/features/user/widgets/user_item_widget.dart +24 -0
  117. package/templates/template_modular/lib/shared/utils/index.dart +1 -0
  118. package/templates/template_modular/lib/shared/widgets/index.dart +1 -0
package/dist/index.d.cts CHANGED
@@ -25,6 +25,8 @@ declare const logger: ConsoleLogger;
25
25
  /**
26
26
  * 转换为 PascalCase
27
27
  * home_page -> HomePage
28
+ * homePage -> HomePage(保留已有 camelCase 单词边界)
29
+ * refreshToken -> RefreshToken
28
30
  */
29
31
  declare function toPascalCase(str: string): string;
30
32
  /**
@@ -126,6 +128,207 @@ declare function mirrorNestedTargetDir(options: MirrorDirOptions): string;
126
128
  declare function resolveConfiguredImport(options: ResolveImportOptions): string | null;
127
129
  declare function calculateRelativeImport(fromFile: string, toFile: string): string;
128
130
 
131
+ /**
132
+ * 项目配置管理器
133
+ * 职责:读取和管理项目级别的 .flu-cli.json 配置文件
134
+ */
135
+ /**
136
+ * 架构模式
137
+ * - `inherit` / `mixin`:旧值,保留向后兼容,不注入职责约定
138
+ * - `mvvm` / `bloc` / `clean` / `native`:v2 架构模式,可配合 contracts 注入 AI 规则
139
+ */
140
+ type ArchitectureMode = 'inherit' | 'mixin' | 'mvvm' | 'bloc' | 'clean' | 'native';
141
+ interface ArchitectureContracts {
142
+ /** Service 层禁止直接发 HTTP 请求给 ViewModel/Bloc(默认 false) */
143
+ forbidHttpInStateLayer?: boolean;
144
+ /** Service 层禁止返回 dynamic / Map<String,dynamic> 给状态层(默认 false) */
145
+ forbidDynamicReturn?: boolean;
146
+ /** 错误处理约定:result(Result<T>)/ exception(抛异常)/ either(Either/Failure) */
147
+ errorHandling?: 'result' | 'exception' | 'either';
148
+ }
149
+ interface ArchitectureConfig {
150
+ mode?: ArchitectureMode;
151
+ contracts?: ArchitectureContracts;
152
+ }
153
+ type StateManagement = 'provider' | 'riverpod' | 'bloc' | 'getx' | 'mobx' | 'none';
154
+ type RouterPackage = 'go_router' | 'auto_route' | 'getx' | 'navigator' | 'none';
155
+ type DiPackage = 'get_it' | 'injectable' | 'riverpod' | 'getx' | 'none';
156
+ interface NetworkConfig {
157
+ package?: 'dio' | 'http' | string;
158
+ /** 响应包装类型,如 `BaseResponse<T>`;为空则不强制包装 */
159
+ responseWrapper?: string;
160
+ }
161
+ /** 顶层模型生成约定(区别于 generators.model 的生成器路径配置) */
162
+ interface TopLevelModelConfig {
163
+ /** 模型生成方式:手写 / freezed / json_serializable */
164
+ strategy?: 'manual' | 'freezed' | 'json_serializable';
165
+ /** 是否需要 build_runner(strategy 为 freezed/json_serializable 时自动为 true) */
166
+ buildRunner?: boolean;
167
+ /** *.g.dart / *.freezed.dart 是否纳入版本库 */
168
+ commitGeneratedFiles?: boolean;
169
+ }
170
+ interface LintConfig {
171
+ /** minimal:仅 flutter_lints;strict:团队增强规则集 */
172
+ preset?: 'minimal' | 'strict';
173
+ }
174
+ interface UiStyleConfig {
175
+ /** 优先使用增量包裹风格(body = Wrapper(child: body)),而非直接嵌套 */
176
+ incrementalWrap?: boolean;
177
+ /** 单个 build 方法内最大嵌套层数(超出建议拆 Widget) */
178
+ maxNestingDepth?: number;
179
+ }
180
+ interface UiConfig {
181
+ style?: UiStyleConfig;
182
+ }
183
+ interface GeneratorSelectableOption$1 {
184
+ name: string;
185
+ import: string;
186
+ }
187
+ /**
188
+ * 生成器配置接口
189
+ */
190
+ interface GeneratorConfig {
191
+ path?: string;
192
+ allowSubDir?: boolean;
193
+ defaultType?: 'stateful' | 'stateless';
194
+ fileSuffix?: string;
195
+ fileName?: string;
196
+ policy?: GeneratorFieldPolicy;
197
+ baseOptionDirs?: string[];
198
+ mixinOptionDirs?: string[];
199
+ baseOptions?: GeneratorSelectableOption$1[];
200
+ mixinOptions?: GeneratorSelectableOption$1[];
201
+ native?: boolean;
202
+ mixins?: string[];
203
+ mixinImports?: string[];
204
+ withBasePage?: boolean;
205
+ basePageClass?: string;
206
+ baseListPageClass?: string;
207
+ basePageImport?: string;
208
+ withViewModel?: boolean;
209
+ viewModelPath?: string;
210
+ withBaseViewModel?: boolean;
211
+ baseViewModelClass?: string;
212
+ baseListViewModelClass?: string;
213
+ baseViewModelImport?: string;
214
+ withBaseWidget?: boolean;
215
+ baseWidgetClass?: string;
216
+ baseWidgetImport?: string;
217
+ withBaseModel?: boolean;
218
+ baseModelClass?: string;
219
+ baseModelImport?: string;
220
+ template?: 'network' | 'simple' | 'auto' | string;
221
+ snippetKey?: string;
222
+ mockLevel?: 'global' | 'instance';
223
+ baseServiceClass?: string;
224
+ baseServiceImport?: string;
225
+ serviceConstructor?: 'const' | 'normal';
226
+ }
227
+ /**
228
+ * 项目配置接口(`.flu-cli.json` 的完整类型)
229
+ */
230
+ interface ProjectConfig {
231
+ /**
232
+ * 项目最初使用的脚手架类型(lite / modular / clean 等),**仅作文档与元数据**。
233
+ * 不参与 generators 默认值的推断;生效约定以 `generators` 与磁盘上的完整配置为准。
234
+ */
235
+ template?: 'lite' | 'modular' | 'clean' | string;
236
+ architecture?: ArchitectureConfig;
237
+ packageName?: string;
238
+ /** 状态管理框架 */
239
+ stateManagement?: StateManagement;
240
+ /** 路由/导航方案 */
241
+ router?: RouterPackage;
242
+ /** 网络层约定 */
243
+ network?: NetworkConfig;
244
+ /** 依赖注入方案 */
245
+ di?: DiPackage;
246
+ /** 顶层模型生成约定(区别于 generators.model 路径配置) */
247
+ model?: TopLevelModelConfig;
248
+ /** Lint 级别 */
249
+ lint?: LintConfig;
250
+ /** UI 编码风格约定 */
251
+ ui?: UiConfig;
252
+ generators?: {
253
+ page?: GeneratorConfig;
254
+ viewModel?: GeneratorConfig;
255
+ widget?: GeneratorConfig;
256
+ model?: GeneratorConfig;
257
+ component?: GeneratorConfig;
258
+ service?: GeneratorConfig;
259
+ module?: {
260
+ path?: string;
261
+ };
262
+ };
263
+ }
264
+ type ProjectConfigSource = 'disk' | 'inferred' | 'builtin';
265
+ type GeneratorPolicyMode = 'locked' | 'default';
266
+ type GeneratorFieldPolicy = Partial<Record<string, GeneratorPolicyMode>>;
267
+ interface ResolvedProjectConfig {
268
+ source: ProjectConfigSource;
269
+ config: ProjectConfig;
270
+ diagnostics: string[];
271
+ hasDiskConfig: boolean;
272
+ }
273
+ type GeneratorConfigType = 'page' | 'viewModel' | 'widget' | 'model' | 'component' | 'service';
274
+ /**
275
+ * 项目配置管理器
276
+ */
277
+ declare class ProjectConfigManager {
278
+ private static CONFIG_FILE_NAME;
279
+ /**
280
+ * 加载项目配置
281
+ * @param projectDir 项目目录
282
+ * @returns 配置对象,如果不存在则返回 null
283
+ */
284
+ static loadConfig(projectDir: string): ProjectConfig | null;
285
+ /**
286
+ * 检查项目是否有配置文件
287
+ * @param projectDir 项目目录
288
+ * @returns 是否存在配置文件
289
+ */
290
+ static hasConfig(projectDir: string): boolean;
291
+ /**
292
+ * 解析运行时生效配置。
293
+ * 无 `.flu-cli.json` 时使用「custom」最小默认 generators,不再按目录结构套用 lite/modular/clean 全套预设;
294
+ * `template` 字段仅作元数据写入,不驱动合并基准。
295
+ */
296
+ static resolveEffectiveConfig(projectDir: string): ResolvedProjectConfig;
297
+ /**
298
+ * 获取指定生成器的配置
299
+ * @param projectDir 项目目录
300
+ * @param generatorType 生成器类型
301
+ * @returns 生成器配置,如果不存在则返回 null
302
+ */
303
+ static getGeneratorConfig(projectDir: string, generatorType: GeneratorConfigType): GeneratorConfig | null;
304
+ /**
305
+ * 仅根据目录结构推断模板类型。
306
+ */
307
+ static inferTemplateFromStructure(projectDir: string): 'lite' | 'modular' | 'clean' | null;
308
+ /**
309
+ * 获取默认配置模板
310
+ * @param templateType 模板类型
311
+ * @returns 配置模板对象
312
+ */
313
+ static getDefaultConfigTemplate(templateType: 'lite' | 'modular' | 'clean' | 'custom' | string): ProjectConfig;
314
+ private static readPackageName;
315
+ }
316
+ declare function getArchitectureMode(config?: ProjectConfig | null): ArchitectureMode;
317
+ declare function getGeneratorFieldPolicy(config: ProjectConfig | null | undefined, generatorType: GeneratorConfigType, field: string): GeneratorPolicyMode | null;
318
+ declare function isGeneratorFieldLocked(config: ProjectConfig | null | undefined, generatorType: GeneratorConfigType, field: string): boolean;
319
+
320
+ interface GeneratorSelectableOptionsReport {
321
+ ok: boolean;
322
+ projectDir: string;
323
+ target: GeneratorConfigType;
324
+ diagnostics: string[];
325
+ scannedBaseDirs: string[];
326
+ scannedMixinDirs: string[];
327
+ bases: GeneratorSelectableOption$1[];
328
+ mixins: GeneratorSelectableOption$1[];
329
+ }
330
+ declare function listGeneratorSelectableOptions(projectDir: string, target: GeneratorConfigType): GeneratorSelectableOptionsReport;
331
+
129
332
  /**
130
333
  * 模板生成器
131
334
  * 负责生成各种类型的代码内容,供 Generator 和 Snippets 复用
@@ -142,11 +345,16 @@ declare class TemplateGenerator {
142
345
  coreImportPath?: string;
143
346
  baseClass?: string;
144
347
  extraImports?: string[];
348
+ mixins?: string[];
349
+ mixinImports?: string[];
145
350
  }): string;
146
351
  /**
147
352
  * 生成 Simple Stateful Page
148
353
  */
149
- static generateSimpleStatefulPage(namePascal: string, nameTitle: string): string;
354
+ static generateSimpleStatefulPage(namePascal: string, nameTitle: string, options?: {
355
+ mixins?: string[];
356
+ mixinImports?: string[];
357
+ }): string;
150
358
  /**
151
359
  * 生成 Simple Stateless Page
152
360
  */
@@ -158,12 +366,16 @@ declare class TemplateGenerator {
158
366
  coreImportPath?: string;
159
367
  baseClass?: string;
160
368
  extraImports?: string[];
369
+ mixins?: string[];
370
+ mixinImports?: string[];
161
371
  }): string;
162
372
  static generateListViewModel(namePascal: string, modelName: string, options?: {
163
373
  coreImportPath?: string;
164
374
  modelImportPath?: string;
165
375
  baseClass?: string;
166
376
  extraImports?: string[];
377
+ mixins?: string[];
378
+ mixinImports?: string[];
167
379
  }): string;
168
380
  static generateListPageWithBase(namePascal: string, nameTitle: string, modelName: string, options?: {
169
381
  vmImportPath?: string;
@@ -171,6 +383,8 @@ declare class TemplateGenerator {
171
383
  coreImportPath?: string;
172
384
  baseClass?: string;
173
385
  extraImports?: string[];
386
+ mixins?: string[];
387
+ mixinImports?: string[];
174
388
  }): string;
175
389
  /**
176
390
  * 生成 Service
@@ -196,6 +410,8 @@ declare class TemplateGenerator {
196
410
  * 生成 Model
197
411
  */
198
412
  static generateModel(namePascal: string): string;
413
+ private static sortImports;
414
+ private static getImportSortKey;
199
415
  }
200
416
 
201
417
  /**
@@ -219,12 +435,164 @@ declare function updateNestedIndexExports(rootDir: string, targetDir: string, fi
219
435
  declare function getTemplatesRootDir(): string;
220
436
  declare function getCoreFilesDir(): string;
221
437
  declare function getNetworkDir(): string;
438
+ declare function getHelpersDir(): string;
439
+ declare function getCoreMixinsDir(): string;
440
+ declare function getHelperExamplesDir(): string;
441
+ declare function getStarterProjectDir(): string;
442
+
443
+ type ProjectStructureType = 'lite' | 'modular' | 'clean' | 'native' | string;
444
+ type StateManagerType = 'default' | 'provider' | 'getx' | 'bloc' | 'riverpod' | string;
445
+ type FlutterSdkMode = 'system' | 'fvm' | 'custom';
446
+ type CompositionProfile = 'base' | 'base_mixins' | 'pure_mixins' | 'pure';
447
+ type ProjectArchitectureMode = 'mvvm' | 'native';
448
+ type ProjectExampleId = 'networkGallery' | 'webviewBasic' | 'permissionBasic' | 'imagePickerBasic' | 'paymentShell' | string;
449
+ interface GeneratorSelectableOption {
450
+ name: string;
451
+ import: string;
452
+ }
453
+ interface ProjectCompositionConfig {
454
+ /** 当前真实架构模式:MVVM 标准架构或原生 Flutter。 */
455
+ architectureMode: ProjectArchitectureMode;
456
+ /** 是否准备 mixin 候选目录;不代表默认注入 mixin。 */
457
+ enableMixinOptions: boolean;
458
+ profile: CompositionProfile;
459
+ pageMixins: GeneratorSelectableOption[];
460
+ viewModelMixins: GeneratorSelectableOption[];
461
+ serviceMixins: GeneratorSelectableOption[];
462
+ }
463
+ interface FlutterSdkConfig {
464
+ mode: FlutterSdkMode;
465
+ version?: string;
466
+ flutterBin?: string;
467
+ }
468
+ interface ProjectCoreConfig {
469
+ enabled: boolean;
470
+ modules: {
471
+ boot: boolean;
472
+ config: boolean;
473
+ base: boolean;
474
+ list: boolean;
475
+ router: boolean;
476
+ theme: boolean;
477
+ storage: boolean;
478
+ utils: boolean;
479
+ widgets: boolean;
480
+ };
481
+ }
482
+ interface NetworkCapabilityConfig {
483
+ enabled: boolean;
484
+ client: 'dio' | string;
485
+ monitor: boolean;
486
+ /** 旧 network.examples 兼容字段;正式协议已上移到顶层 examples。 */
487
+ examples: boolean;
488
+ }
489
+ interface StorageCapabilityConfig {
490
+ enabled: boolean;
491
+ package: 'shared_preferences' | string;
492
+ }
493
+ interface SerializationCapabilityConfig {
494
+ enabled: boolean;
495
+ strategy: 'manual' | 'json_serializable' | 'freezed' | string;
496
+ buildRunner: boolean;
497
+ }
498
+ interface AuthCapabilityConfig {
499
+ enabled: boolean;
500
+ mode: 'basic' | string;
501
+ }
502
+ interface ProjectCapabilitiesConfig {
503
+ network: NetworkCapabilityConfig;
504
+ storage: StorageCapabilityConfig;
505
+ serialization: SerializationCapabilityConfig;
506
+ auth: AuthCapabilityConfig;
507
+ }
508
+ interface ProjectHelpersConfig {
509
+ payment: boolean;
510
+ webview: boolean;
511
+ permission: boolean;
512
+ imagePicker: boolean;
513
+ }
514
+ interface ProjectPlatformConfig {
515
+ platforms: string[];
516
+ flutterCreatePlatforms: string[];
517
+ flutterSdk: FlutterSdkConfig;
518
+ }
519
+ interface ProjectStackConfig {
520
+ stateManagement: StateManagerType;
521
+ network: {
522
+ enabled: boolean;
523
+ client: 'dio' | 'http' | 'none' | string;
524
+ };
525
+ serialization: SerializationCapabilityConfig;
526
+ router: 'go_router' | 'auto_route' | 'getx' | 'navigator' | 'none' | string;
527
+ di: 'get_it' | 'injectable' | 'riverpod' | 'getx' | 'none' | string;
528
+ lint: 'strict' | 'minimal' | string;
529
+ }
530
+ interface ProjectCreateConfig {
531
+ version: 2;
532
+ projectName: string;
533
+ packageName?: string;
534
+ templateType: ProjectStructureType;
535
+ stateManager: StateManagerType;
536
+ architectureMode: ProjectArchitectureMode;
537
+ enableMixinOptions: boolean;
538
+ /**
539
+ * 创建期顶层示例协议。
540
+ * 只用于本次创建时决定示例目录、首页演示和示例路由,不写入 .flu-cli.json。
541
+ */
542
+ examples: ProjectExampleId[];
543
+ composition: ProjectCompositionConfig;
544
+ stack: ProjectStackConfig;
545
+ core: ProjectCoreConfig;
546
+ capabilities: ProjectCapabilitiesConfig;
547
+ helpers: ProjectHelpersConfig;
548
+ platform: ProjectPlatformConfig;
549
+ legacy: {
550
+ templateType?: string;
551
+ includeNetworkLayer?: unknown;
552
+ includeNetwork?: unknown;
553
+ };
554
+ }
555
+ type DeepPartial<T> = {
556
+ [K in keyof T]?: T[K] extends Array<unknown> ? T[K] : T[K] extends object ? DeepPartial<T[K]> : T[K];
557
+ };
558
+ type ProjectCreateConfigInput = DeepPartial<ProjectCreateConfig>;
559
+ interface NormalizeProjectCreateConfigOptions {
560
+ projectName?: string;
561
+ packageName?: string;
562
+ templateType?: string;
563
+ template?: string;
564
+ stateManager?: string;
565
+ architectureMode?: string;
566
+ enableMixinOptions?: boolean;
567
+ includeNetworkLayer?: unknown;
568
+ includeNetwork?: unknown;
569
+ examples?: ProjectExampleId[] | string;
570
+ platforms?: string[];
571
+ flutterSdk?: Partial<FlutterSdkConfig>;
572
+ composition?: DeepPartial<ProjectCompositionConfig>;
573
+ stack?: DeepPartial<ProjectStackConfig>;
574
+ projectCreate?: ProjectCreateConfigInput;
575
+ capabilities?: DeepPartial<ProjectCapabilitiesConfig>;
576
+ helpers?: Partial<ProjectHelpersConfig>;
577
+ }
578
+ declare function normalizeProjectCreateConfig(options?: NormalizeProjectCreateConfigOptions): ProjectCreateConfig;
579
+ declare function normalizeTemplateType(templateType: string): ProjectStructureType;
580
+ declare function normalizeNetworkEnabled(value: unknown): boolean;
581
+ declare function normalizePlatforms(platforms?: string[]): string[];
582
+ declare function normalizeFlutterCreatePlatform(platform: string): string;
583
+ declare function normalizeFlutterCreatePlatforms(platforms: string[]): string[];
584
+ declare function normalizeCompositionProfile(value: string): CompositionProfile;
222
585
 
586
+ /**
587
+ * 复制默认 Core 模板。
588
+ * vNext 优先读取 projectConfig;旧 includeNetworkLayer/templateType 继续保留兼容。
589
+ */
223
590
  declare function copyCoreFiles(projectPath: string, options?: {
224
591
  includeNetworkLayer?: boolean;
225
592
  templateType?: 'lite' | 'modular' | 'clean';
226
593
  projectName?: string;
227
594
  stateManager?: string;
595
+ projectConfig?: ProjectCreateConfig;
228
596
  }): Promise<void>;
229
597
  declare function copyNetworkFiles(projectPath: string, options?: {
230
598
  targetDir?: string;
@@ -232,11 +600,33 @@ declare function copyNetworkFiles(projectPath: string, options?: {
232
600
  }): Promise<void>;
233
601
  declare function copyInfrastructure(projectPath: string, includeExamples?: boolean, includeNetworkLayer?: boolean, templateType?: 'lite' | 'modular' | 'clean'): Promise<void>;
234
602
 
603
+ /**
604
+ * 复制 project helpers。
605
+ * helpers 不属于 Core,本函数只负责把启用的 helper 投影到 lib/helpers 下。
606
+ */
607
+ declare function copyHelperFiles(projectPath: string, projectConfig: ProjectCreateConfig): Promise<void>;
608
+
609
+ declare function copyCoreMixins(projectPath: string, options: {
610
+ projectConfig: ProjectCreateConfig;
611
+ renderData: Record<string, any>;
612
+ }): Promise<void>;
613
+
614
+ declare function copyStarterProjectScaffold(projectPath: string, projectConfig: ProjectCreateConfig, renderData: Record<string, any>): Promise<void>;
615
+
235
616
  declare function copyTemplate(templatePath: string, targetPath: string, options?: {
236
617
  excludes?: string[];
237
618
  }): Promise<boolean>;
238
619
  declare function copyCustomTemplate(templatePath: string, targetPath: string): Promise<boolean>;
239
620
  declare function ensurePubspecName(projectDir: string, projectName: string): Promise<void>;
621
+ declare function ensurePubspecDescription(projectDir: string, description: string): Promise<void>;
622
+ /**
623
+ * 清理 flutter create 写入的默认英文说明注释。
624
+ *
625
+ * 这些注释更适合作为 Flutter 官方脚手架提示,不适合作为最终交付给用户的
626
+ * Starter 工程内容。这里仅移除默认英文说明,不会删除我们后续可能新增的
627
+ * 简短中文注释或业务注释。
628
+ */
629
+ declare function sanitizePubspecComments(projectDir: string): Promise<void>;
240
630
  declare function cleanupTemplateFiles(projectDir: string): Promise<void>;
241
631
 
242
632
  declare function injectNetworkExamples(projectPath: string, contextData?: any): Promise<void>;
@@ -309,6 +699,122 @@ declare function generateService(name: string, options?: any, customLogger?: any
309
699
  */
310
700
  declare function generateModule(name: string, options?: any, logger?: Logger): Promise<boolean>;
311
701
 
702
+ /**
703
+ * flu-blueprint.yaml Schema 类型定义
704
+ *
705
+ * 描述"要生成什么结构"——与 .flu-cli.json 描述"怎么生成"相互独立。
706
+ */
707
+ type BlueprintPageType = 'page' | 'list-page';
708
+ interface BlueprintPage {
709
+ /** 页面名称,PascalCase 或 snake_case 均可,内部统一转换 */
710
+ name: string;
711
+ /** 页面类型:普通页面 / 列表页面(默认 page) */
712
+ type?: BlueprintPageType;
713
+ /** 是否生成配套 ViewModel(默认 true) */
714
+ withVM?: boolean;
715
+ /** list-page 专用:关联的 Model 名称(如 "Order") */
716
+ model?: string;
717
+ /** 额外备注(仅供人阅读,不影响生成) */
718
+ note?: string;
719
+ }
720
+ type BlueprintHttpMethod = 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE';
721
+ interface BlueprintEndpoint {
722
+ /** 接口名称,用于生成方法名(如 "fetchOrders") */
723
+ name: string;
724
+ /** HTTP 方法(默认 GET) */
725
+ method?: BlueprintHttpMethod;
726
+ /** 接口路径(如 "/api/orders") */
727
+ path?: string;
728
+ /** 接口响应的 JSON 示例对象,用于自动推断并生成 Model */
729
+ responseExample?: Record<string, unknown>;
730
+ /** 接口响应 data 字段内部的 JSON 示例(优先级高于 responseExample) */
731
+ dataExample?: Record<string, unknown>;
732
+ /** 额外备注 */
733
+ note?: string;
734
+ }
735
+ interface BlueprintFeature {
736
+ /** 功能模块名(snake_case 或 camelCase,内部统一转 snake_case) */
737
+ name: string;
738
+ /** 该模块下的页面列表 */
739
+ pages?: BlueprintPage[];
740
+ /** 需要生成的 Service 名称列表(如 ["OrderService", "UserService"]) */
741
+ services?: string[];
742
+ /** 需要生成的 Model 名称列表(如 ["OrderModel"])—— 不含接口推断的 Model */
743
+ models?: string[];
744
+ /** 接口定义列表:endpoint → 自动生成 Service 方法 + Model */
745
+ endpoints?: BlueprintEndpoint[];
746
+ /** 额外备注 */
747
+ note?: string;
748
+ }
749
+ interface Blueprint {
750
+ /**
751
+ * Schema 版本,当前为 "1"
752
+ * 便于后续平滑升级,解析时可做版本迁移
753
+ */
754
+ version?: string;
755
+ /**
756
+ * 功能模块列表(模块模式)
757
+ * 若不填 features,则允许使用根级 pages/endpoints/services/models(简单 App 模式)
758
+ */
759
+ features?: BlueprintFeature[];
760
+ /**
761
+ * 简单 App 模式(不写 features)
762
+ * 将自动映射为隐式 feature:`name: "app"`
763
+ */
764
+ pages?: BlueprintPage[];
765
+ services?: string[];
766
+ models?: string[];
767
+ endpoints?: BlueprintEndpoint[];
768
+ }
769
+ interface BlueprintGenerateResult {
770
+ ok: boolean;
771
+ /** 生成的文件路径列表 */
772
+ generated: string[];
773
+ /** 跳过的文件(已存在) */
774
+ skipped: string[];
775
+ /** 每步的诊断消息 */
776
+ diagnostics: string[];
777
+ }
778
+
779
+ /**
780
+ * Blueprint 批量生成器
781
+ *
782
+ * 读取 flu-blueprint.yaml,按 features → pages / services / models / endpoints
783
+ * 顺序调用现有各单体 Generator,汇总生成结果。
784
+ *
785
+ * 所有基类 / Mixin / 路径约束来自 .flu-cli.json(generators 配置),
786
+ * Blueprint 只描述"要什么",不重复配置"怎么写"。
787
+ */
788
+
789
+ /**
790
+ * 从指定目录读取 flu-blueprint.yaml,批量生成所有节点。
791
+ *
792
+ * @param projectDir Flutter 项目根目录(含 .flu-cli.json)
793
+ * @param blueprintPath Blueprint 文件路径(默认 <projectDir>/flu-blueprint.yaml)
794
+ */
795
+ declare function generateFromBlueprint(projectDir: string, blueprintPath?: string, logger?: Logger): Promise<BlueprintGenerateResult>;
796
+
797
+ /**
798
+ * OpenAPI 3 → Blueprint 转换器
799
+ *
800
+ * 将 OpenAPI 3 规范(JSON 或 YAML 字符串/对象)解析为 flu-blueprint.yaml 结构。
801
+ *
802
+ * 映射规则:
803
+ * - paths[path][method] → BlueprintEndpoint(按 tag 分组到 feature)
804
+ * - components/schemas → dataExample(内联到 endpoint,供生成器推断 Model)
805
+ * - tags → feature.name(无 tag 归入 "common")
806
+ *
807
+ * 原则:Blueprint 永远独立可用,本工具只是可选的"填充来源"。
808
+ */
809
+
810
+ /**
811
+ * 将 OpenAPI 3 文档转换为 Blueprint 结构。
812
+ *
813
+ * @param input OpenAPI 3 文档(JSON 字符串 / YAML 字符串 / 已解析对象)
814
+ * @returns Blueprint 对象,可直接写入 flu-blueprint.yaml
815
+ */
816
+ declare function parseOpenApiToBlueprint(input: string | object): Blueprint;
817
+
312
818
  /**
313
819
  * 升级项目中的 snippets 文件
314
820
  */
@@ -325,6 +831,70 @@ declare function upgradeSnippets(options?: {
325
831
  */
326
832
  declare function checkSnippetsVersion(projectDir?: string): 'up-to-date' | 'outdated' | 'missing';
327
833
 
834
+ /**
835
+ * sync-rules 命令核心引擎(AI Skill 投影器)
836
+ *
837
+ * 职责:读取 .flu-cli.json,将架构约束投影为 AI 规则文件:
838
+ * - .cursor/rules/flu-project.mdc (Cursor AI)
839
+ * - CLAUDE.md (Claude Code / Antigravity)
840
+ * - AI_RULES.md (人机共读)
841
+ * - .agent/skills/<包名>/SKILL.md (通用 Agent Skill)
842
+ */
843
+
844
+ declare function syncRules(projectDir?: string): Promise<boolean>;
845
+ interface SyncRulesWriteOutput {
846
+ filePath: string;
847
+ changed: boolean;
848
+ }
849
+ interface SyncRulesReport {
850
+ ok: boolean;
851
+ projectDir: string;
852
+ blocked?: boolean;
853
+ error?: string;
854
+ source?: string;
855
+ template?: string;
856
+ diagnostics?: string[];
857
+ outputs?: SyncRulesWriteOutput[];
858
+ }
859
+ declare function syncRulesWithReport(projectDir?: string, options?: {
860
+ logger?: Logger;
861
+ }): Promise<SyncRulesReport>;
862
+
863
+ type InitAiBaseStarter = 'minimal' | 'lite' | 'modular' | 'clean' | 'native' | 'custom';
864
+ declare function validateProjectId(projectId: string): string | null;
865
+ declare function normalizeProjectIdToPackageName(projectId: string): string;
866
+ declare function buildInitAiBaseConfig(starter: InitAiBaseStarter, packageName: string): ProjectConfig;
867
+ declare function parseFluCliJsonFromPath(filePath: string): ProjectConfig | null;
868
+ interface RunInitAiBaseOptions {
869
+ projectDir: string;
870
+ projectId: string;
871
+ /** 仅在项目根不存在 `.flu-cli.json` 时使用 */
872
+ starter: InitAiBaseStarter;
873
+ /** `starter === 'custom'` 时尝试从此路径导入;失败则兜底 minimal */
874
+ customImportPath?: string;
875
+ }
876
+ interface RunInitAiBaseResult {
877
+ ok: boolean;
878
+ diagnostics: string[];
879
+ packageName: string;
880
+ skillSlug: string;
881
+ createdNewConfig: boolean;
882
+ usedStarter: InitAiBaseStarter;
883
+ fellBackToMinimal: boolean;
884
+ }
885
+ declare function runInitAiBase(opts: RunInitAiBaseOptions): Promise<RunInitAiBaseResult>;
886
+ interface RunInitAiBaseReport extends RunInitAiBaseResult {
887
+ syncRules?: SyncRulesReport;
888
+ }
889
+ declare function runInitAiBaseWithReport(opts: RunInitAiBaseOptions, options?: {
890
+ logger?: Logger;
891
+ }): Promise<RunInitAiBaseReport>;
892
+
893
+ /**
894
+ * 与 `sync_rules` 写入 `.agent/skills/<slug>/SKILL.md` 的目录名规则一致。
895
+ */
896
+ declare function slugForAgentSkill(packageName: string): string;
897
+
328
898
  interface CustomTemplate {
329
899
  id: string;
330
900
  name: string;
@@ -341,6 +911,9 @@ interface ProjectPreset {
341
911
  templateType: string;
342
912
  stateManager: string;
343
913
  includeNetworkLayer: boolean;
914
+ /** 创建期顶层示例协议,允许 preset 复用,但不写入 .flu-cli.json。 */
915
+ examples?: string[];
916
+ networkMonitorEnabled?: boolean;
344
917
  platforms: string[];
345
918
  assetStrategy?: 'manual' | 'skip';
346
919
  triggerAssetWizard?: boolean;
@@ -397,6 +970,7 @@ interface ProjectOptions {
397
970
  packageName: string;
398
971
  outputDir: string;
399
972
  includeNetworkLayer?: boolean;
973
+ examples?: string[];
400
974
  createProjectConfig?: boolean;
401
975
  }
402
976
  /**
@@ -404,6 +978,9 @@ interface ProjectOptions {
404
978
  * 采用 Task Pipeline 架构,极简核心,逻辑拆分至各原子 Task。
405
979
  */
406
980
  declare class ProjectGenerator {
981
+ lastError: string;
982
+ lastSdkBindingWarning: string;
983
+ lastBootstrapWarning: string;
407
984
  /**
408
985
  * 生成项目
409
986
  * @param {string} name 项目名称
@@ -411,128 +988,165 @@ declare class ProjectGenerator {
411
988
  * @param {Logger} logger 日志工具
412
989
  */
413
990
  generate(name: string, options?: any, logger?: Logger): Promise<boolean>;
991
+ private runAutomaticPubGetIfNeeded;
414
992
  /**
415
993
  * 检查项目目录是否存在
416
994
  */
417
995
  checkProjectExists(projectPath: string): boolean;
996
+ /**
997
+ * Native 项目在 flutter create 之后按 vNext 配置做后置增强。
998
+ *
999
+ * 与 lite 管线共用 HelperEnrich 等任务,不复制骨架模板、默认不注入 Core。
1000
+ * 示例入口注入依赖 lib/core/router,纯 Native 无路由基座时会由任务自行跳过。
1001
+ */
1002
+ enrichNativeProjectAfterSkeleton(name: string, options: any, projectPath: string, logger?: Logger): Promise<boolean>;
1003
+ private reapplyIosPodfilePermissionMacrosIfNeeded;
1004
+ private generateNativeProject;
418
1005
  }
419
1006
 
420
1007
  /**
421
- * 项目配置管理器
422
- * 职责:读取和管理项目级别的 .flu-cli.json 配置文件
1008
+ * 任务执行上下文
423
1009
  */
424
- type ArchitectureMode = 'inherit' | 'mixin';
425
- interface ArchitectureConfig {
426
- mode?: ArchitectureMode;
1010
+ interface TaskContext {
1011
+ /** 项目根路径 */
1012
+ projectPath: string;
1013
+ /** 项目名称 */
1014
+ projectName: string;
1015
+ /** Dart package 名(合法标识符,用于 pubspec/package import) */
1016
+ dartPackageName: string;
1017
+ /** 模板类型 */
1018
+ templateType: ProjectStructureType;
1019
+ /** 是否包含网络层 */
1020
+ includeNetworkLayer: boolean;
1021
+ /** 状态管理框架 */
1022
+ stateManager: StateManagerType;
1023
+ /** vNext 统一项目创建配置 */
1024
+ projectConfig: ProjectCreateConfig;
1025
+ /** 用户选项 */
1026
+ options: any;
1027
+ /** 全局变量字典(用于模板替换) */
1028
+ variables: Record<string, string>;
1029
+ /** 日志记录器 */
1030
+ logger: Logger;
1031
+ /** 附加元数据 */
1032
+ [key: string]: any;
427
1033
  }
428
1034
  /**
429
- * 生成器配置接口
1035
+ * 项目生成任务接口
430
1036
  */
431
- interface GeneratorConfig {
432
- path?: string;
433
- allowSubDir?: boolean;
434
- defaultType?: 'stateful' | 'stateless';
435
- fileSuffix?: string;
436
- fileName?: string;
437
- policy?: GeneratorFieldPolicy;
438
- withBasePage?: boolean;
439
- basePageClass?: string;
440
- baseListPageClass?: string;
441
- basePageImport?: string;
442
- withViewModel?: boolean;
443
- viewModelPath?: string;
444
- withBaseViewModel?: boolean;
445
- baseViewModelClass?: string;
446
- baseListViewModelClass?: string;
447
- baseViewModelImport?: string;
448
- withBaseWidget?: boolean;
449
- baseWidgetClass?: string;
450
- baseWidgetImport?: string;
451
- withBaseModel?: boolean;
452
- baseModelClass?: string;
453
- baseModelImport?: string;
454
- template?: 'network' | 'simple' | 'auto' | string;
455
- snippetKey?: string;
456
- mockLevel?: 'global' | 'instance';
457
- baseServiceClass?: string;
458
- baseServiceImport?: string;
459
- mixins?: string[];
460
- mixinImports?: string[];
461
- serviceConstructor?: 'const' | 'normal';
1037
+ interface IProjectTask {
1038
+ /** 任务名称 */
1039
+ name: string;
1040
+ /** 执行任务 */
1041
+ run(context: TaskContext): Promise<void>;
462
1042
  }
463
1043
  /**
464
- * 项目配置接口
1044
+ * 创建初始上下文
465
1045
  */
466
- interface ProjectConfig {
467
- template?: 'lite' | 'modular' | 'clean' | string;
468
- architecture?: ArchitectureConfig;
469
- packageName?: string;
470
- generators?: {
471
- page?: GeneratorConfig;
472
- viewModel?: GeneratorConfig;
473
- widget?: GeneratorConfig;
474
- model?: GeneratorConfig;
475
- component?: GeneratorConfig;
476
- service?: GeneratorConfig;
477
- module?: {
478
- path?: string;
479
- };
480
- };
481
- }
482
- type ProjectConfigSource = 'disk' | 'inferred' | 'builtin';
483
- type GeneratorPolicyMode = 'locked' | 'default';
484
- type GeneratorFieldPolicy = Partial<Record<string, GeneratorPolicyMode>>;
485
- interface ResolvedProjectConfig {
486
- source: ProjectConfigSource;
487
- config: ProjectConfig;
488
- diagnostics: string[];
489
- hasDiskConfig: boolean;
1046
+ declare function createDefaultContext(projectPath: string, projectName: string, options?: any, logger?: Logger): TaskContext;
1047
+
1048
+ /**
1049
+ * 变量落地任务
1050
+ * 负责替换项目中的 {{projectName}}, {{packageName}} 等占位符
1051
+ */
1052
+ declare class VariablesReplaceTask implements IProjectTask {
1053
+ name: string;
1054
+ run(context: TaskContext): Promise<void>;
490
1055
  }
491
- type GeneratorConfigType = 'page' | 'viewModel' | 'widget' | 'model' | 'component' | 'service';
1056
+
492
1057
  /**
493
- * 项目配置管理器
1058
+ * 项目清理与修复任务
1059
+ * 负责环境兼容性修复、权限补丁及冗余文件清理
494
1060
  */
495
- declare class ProjectConfigManager {
496
- private static CONFIG_FILE_NAME;
497
- /**
498
- * 加载项目配置
499
- * @param projectDir 项目目录
500
- * @returns 配置对象,如果不存在则返回 null
501
- */
502
- static loadConfig(projectDir: string): ProjectConfig | null;
1061
+ declare class CleanupTask implements IProjectTask {
1062
+ name: string;
1063
+ run(context: TaskContext): Promise<void>;
503
1064
  /**
504
- * 检查项目是否有配置文件
505
- * @param projectDir 项目目录
506
- * @returns 是否存在配置文件
1065
+ * 启用 Dio / network capability 时,自动确保 Android 主 Manifest 具备联网权限。
507
1066
  */
508
- static hasConfig(projectDir: string): boolean;
1067
+ private patchAndroidInternetPermission;
509
1068
  /**
510
- * 解析运行时生效配置。
511
- * 即使项目没有真实 .flu-cli.json,也会基于目录结构和内置默认值得到一份权威配置。
1069
+ * 自动修复 macOS 网络权限 (避免 SocketException)
512
1070
  */
513
- static resolveEffectiveConfig(projectDir: string): ResolvedProjectConfig;
1071
+ private patchMacOSEntitlements;
514
1072
  /**
515
- * 获取指定生成器的配置
516
- * @param projectDir 项目目录
517
- * @param generatorType 生成器类型
518
- * @returns 生成器配置,如果不存在则返回 null
1073
+ * 修复默认测试文件中的导入路径。
1074
+ *
1075
+ * lite/modular/clean 使用 Starter 的 app.dart;native 只有 main.dart + MyApp。
519
1076
  */
520
- static getGeneratorConfig(projectDir: string, generatorType: GeneratorConfigType): GeneratorConfig | null;
1077
+ private fixTestFile;
1078
+ private buildNativeWidgetTest;
1079
+ private buildStarterWidgetTest;
521
1080
  /**
522
- * 仅根据目录结构推断模板类型。
1081
+ * 修复残留的旧路径引用
523
1082
  */
524
- static inferTemplateFromStructure(projectDir: string): 'lite' | 'modular' | 'clean' | null;
1083
+ private fixLegacyImports;
525
1084
  /**
526
- * 获取默认配置模板
527
- * @param templateType 模板类型
528
- * @returns 配置模板对象
1085
+ * 将 index.dart 顶部的 `///` library doc 改为普通注释。
1086
+ * Dart analyzer 会把没有 `library;` 指令的顶层文档注释判成 dangling library doc,
1087
+ * 新项目首次打开时容易出现一串低价值 warning。
529
1088
  */
530
- static getDefaultConfigTemplate(templateType: 'lite' | 'modular' | 'clean' | 'custom' | string): ProjectConfig;
531
- private static readPackageName;
1089
+ private normalizeIndexFileComments;
1090
+ private downgradeTopLevelDocComments;
1091
+ private removeEmptyDartFiles;
1092
+ private removeBaseResidue;
1093
+ private removeLegacyUserListResidue;
1094
+ private removeNetworkGalleryResidue;
1095
+ private getNetworkResidueTargets;
1096
+ private getLegacyUserListTargets;
1097
+ }
1098
+
1099
+ /**
1100
+ * 项目配置任务
1101
+ * 职责:初始化项目的 .flu-cli.json 配置文件,实现模板自描述
1102
+ */
1103
+ declare class ProjectConfigTask implements IProjectTask {
1104
+ name: string;
1105
+ run(context: TaskContext): Promise<void>;
1106
+ }
1107
+
1108
+ /**
1109
+ * Starter Scaffold 任务。
1110
+ * 负责写入项目级入口文件、说明文档、环境样板和 VSCode 调试配置。
1111
+ */
1112
+ declare class StarterScaffoldTask implements IProjectTask {
1113
+ name: string;
1114
+ run(context: TaskContext): Promise<void>;
532
1115
  }
533
- declare function getArchitectureMode(config?: ProjectConfig | null): ArchitectureMode;
534
- declare function getGeneratorFieldPolicy(config: ProjectConfig | null | undefined, generatorType: GeneratorConfigType, field: string): GeneratorPolicyMode | null;
535
- declare function isGeneratorFieldLocked(config: ProjectConfig | null | undefined, generatorType: GeneratorConfigType, field: string): boolean;
1116
+
1117
+ declare function buildProjectRenderData(context: TaskContext): Record<string, any>;
1118
+
1119
+ /**
1120
+ * Helper 依赖策略。
1121
+ *
1122
+ * 这里集中维护 helper 与 pubspec 依赖的关系,避免 HelperEnrichTask 里散落平台判断。
1123
+ */
1124
+ type HelperName = keyof ProjectHelpersConfig;
1125
+ interface HelperDependencyPlan {
1126
+ dependencies: string[];
1127
+ devDependencies: string[];
1128
+ warnings: string[];
1129
+ platformProfile: 'standard' | 'harmony';
1130
+ }
1131
+ /**
1132
+ * 计算 helper 需要注入的 pubspec 依赖。
1133
+ *
1134
+ * 包含 ohos 平台时仍保留普通 Flutter 依赖,保证 Android/iOS/Web 先可用;
1135
+ * Harmony 原生插件源与版本只给提示,不在 CLI 中维护内置矩阵。
1136
+ */
1137
+ declare function resolveHelperDependencyPlan(projectConfig: ProjectCreateConfig): HelperDependencyPlan;
1138
+ /**
1139
+ * 将 schema 中的 imagePicker 映射到模板目录 image_picker。
1140
+ */
1141
+ declare function getEnabledHelperTemplateDirs(projectConfig: ProjectCreateConfig): string[];
1142
+
1143
+ interface CapabilityDependencyPlan {
1144
+ dependencies: string[];
1145
+ devDependencies: string[];
1146
+ warnings: string[];
1147
+ platformProfile: 'standard' | 'harmony';
1148
+ }
1149
+ declare function resolveCapabilityDependencyPlan(projectConfig: ProjectCreateConfig): CapabilityDependencyPlan;
536
1150
 
537
1151
  /**
538
1152
  * 应用资源选择接口
@@ -558,7 +1172,7 @@ declare class AppAssetsManager {
558
1172
  * @param assets 资源配置
559
1173
  * @param logger 日志工具
560
1174
  */
561
- setupAppAssets(projectPath: string, assets: AppAssetConfig, logger: Logger): Promise<boolean>;
1175
+ setupAppAssets(projectPath: string, assets: AppAssetConfig, logger: Logger, flutterSdk?: FlutterSdkConfig): Promise<boolean>;
562
1176
  /**
563
1177
  * 复制文件(当源路径与目标路径相同时跳过)
564
1178
  */
@@ -623,6 +1237,7 @@ declare class TemplateManager {
623
1237
  * @param isCustom 是否为自定义模板
624
1238
  */
625
1239
  getTemplatePath(templateName: string, isCustom?: boolean): string;
1240
+ getBuiltinTemplateIds(): string[];
626
1241
  /**
627
1242
  * 准备模板(确保已缓存且为最新)
628
1243
  *
@@ -632,6 +1247,20 @@ declare class TemplateManager {
632
1247
  * 3. 内置模板 (lite/modular/clean)
633
1248
  */
634
1249
  prepareTemplate(templateId: string, logger?: Logger, forceUpdate?: boolean): Promise<string | undefined>;
1250
+ refreshBuiltinTemplateCache(templateId: string, logger?: Logger): Promise<string | undefined>;
1251
+ refreshAllBuiltinTemplateCaches(logger?: Logger): Promise<string[]>;
1252
+ cleanBuiltinTemplateCache(logger?: Logger): Promise<number>;
1253
+ private ensureBuiltinTemplateCached;
1254
+ private isBuiltinCacheManagedTemplate;
1255
+ private isBuiltinTemplateCacheStale;
1256
+ private writeBuiltinTemplateMeta;
1257
+ private computeDirectorySignature;
1258
+ private resolveBundledBuiltinTemplatePath;
1259
+ private getBundledTemplateRootCandidates;
1260
+ private resolveInstalledCoreTemplatesRoot;
1261
+ private resolveRuntimeEntryTemplatesRoot;
1262
+ private getBuiltinCacheAliasPaths;
1263
+ private removeLegacyBuiltinCacheAliases;
635
1264
  /**
636
1265
  * 通用 Git 仓库缓存逻辑
637
1266
  */
@@ -668,6 +1297,27 @@ declare const t: (key: string, params?: Record<string, any>) => string;
668
1297
  * Flutter 辅助工具
669
1298
  * 职责:封装 flutter create/pub get/版本检测等命令调用
670
1299
  */
1300
+
1301
+ declare const HARMONY_FVM_SETUP_DOC_URL = "http://huozhiye.cn/flu-cli/";
1302
+ interface FlutterCreateResult {
1303
+ success: boolean;
1304
+ reason: 'ok' | 'unsupported_platform' | 'command_failed';
1305
+ command: string;
1306
+ unsupportedPlatforms: string[];
1307
+ missingPlatforms: string[];
1308
+ errorMessage?: string;
1309
+ }
1310
+ interface FlutterCreateExecutionPlan {
1311
+ flutterCommand: string;
1312
+ prepareCommands: string[];
1313
+ optionalPrepareCommands: string[];
1314
+ createCommand: string;
1315
+ createCwd?: string;
1316
+ command: string;
1317
+ usesFvmWorkflow?: boolean;
1318
+ fvmVersionFile?: string;
1319
+ workspaceFvmSdkRoot?: string;
1320
+ }
671
1321
  /**
672
1322
  * 运行 flutter create 命令
673
1323
  * @param {string} projectDir - 项目目录
@@ -684,13 +1334,40 @@ declare const t: (key: string, params?: Record<string, any>) => string;
684
1334
  * @param {string[]} platforms - 目标平台 (ios, android, web, windows, macos, linux, ohos)
685
1335
  * @returns {Promise<boolean>} 是否成功
686
1336
  */
687
- declare function runFlutterCreate(projectDir: string, projectName: string, packageName: string, flutterTemplate?: string, platforms?: string[]): Promise<boolean>;
1337
+ declare function runFlutterCreate(projectDir: string, projectName: string, packageName: string, flutterTemplate?: string, platforms?: string[], flutterSdk?: FlutterSdkConfig): Promise<FlutterCreateResult>;
1338
+ /**
1339
+ * 根据项目创建配置解析真正要调用的 Flutter 命令。
1340
+ * 这里保留最小入口:system / fvm / custom flutterBin。
1341
+ */
1342
+ /** system 模式:使用本机默认 Flutter,创建链路直接执行 flutter create。 */
1343
+ declare function isSystemFlutterSdk(flutterSdk?: FlutterSdkConfig): boolean;
1344
+ declare function resolveFlutterCommand(flutterSdk?: FlutterSdkConfig): string;
1345
+ /**
1346
+ * VSCode Extension Host 不一定继承用户交互终端的 PATH。
1347
+ * system 模式仍代表“使用本机默认 Flutter”,但执行时优先落到可验证的绝对 flutterBin,
1348
+ * 避免插件创建链路在 `/bin/zsh -lc` 中找不到 `flutter`。
1349
+ */
1350
+ declare function resolveSystemFlutterBin(): string | undefined;
1351
+ declare function resolveFlutterCreateExecutionPlan(projectDir: string, projectName: string, packageName: string, flutterTemplate?: string, platforms?: string[], flutterSdk?: FlutterSdkConfig): FlutterCreateExecutionPlan;
1352
+ declare function validateFvmVersionInput(flutterSdk?: FlutterSdkConfig): string | null;
1353
+ declare function parseFlutterCreateSupportedPlatforms(helpText: string): string[];
1354
+ declare function findMissingFlutterPlatformDirs(projectDir: string, platforms: string[]): string[];
1355
+ declare function bindProjectFlutterSdk(projectDir: string, flutterSdk?: FlutterSdkConfig): Promise<{
1356
+ bound: boolean;
1357
+ message?: string;
1358
+ warning?: string;
1359
+ }>;
688
1360
  /**
689
1361
  * 运行 flutter pub get
690
1362
  * @param {string} projectDir - 项目目录
691
1363
  * @returns {Promise<boolean>} 是否成功
692
1364
  */
693
- declare function runFlutterPubGet(projectDir: string): Promise<boolean>;
1365
+ declare function runFlutterPubGet(projectDir: string, flutterSdk?: FlutterSdkConfig, options?: {
1366
+ timeoutMs?: number;
1367
+ }): Promise<boolean>;
1368
+ declare function resolveProjectFlutterCommand(_projectDir: string, flutterSdk?: FlutterSdkConfig): string;
1369
+ declare function resolveProjectFlutterCliCommand(projectDir: string, flutterSdk?: FlutterSdkConfig): string;
1370
+ declare function resolveProjectFlutterCliCommandForAutomation(projectDir: string, flutterSdk?: FlutterSdkConfig): string;
694
1371
  /**
695
1372
  * 检查 Flutter 是否安装
696
1373
  * @returns {Promise<boolean>} 是否已安装
@@ -702,6 +1379,13 @@ declare function checkFlutterInstalled(): Promise<boolean>;
702
1379
  */
703
1380
  declare function getFlutterVersion(): Promise<string | null>;
704
1381
 
1382
+ /**
1383
+ * 规范化 Dart package 名。
1384
+ * 目录名可保留连字符,但 pubspec name、package: import、flutter create --project-name
1385
+ * 都必须使用合法的 Dart package 标识符。
1386
+ */
1387
+ declare function normalizeDartPackageName(projectName: string): string;
1388
+
705
1389
  type BuildPlatform = 'android' | 'ios' | 'harmony';
706
1390
  declare class BuildManager {
707
1391
  static build(platform: BuildPlatform, buildConfig: NonNullable<UploadConfig['build']>, projectDir?: string): Promise<BuildResult>;
@@ -779,4 +1463,4 @@ declare function fixAndroidPackageName(projectDir: string, packageName: string,
779
1463
  */
780
1464
  declare function fixIosBundleIdentifier(projectDir: string, bundleId: string, logger?: Logger): Promise<void>;
781
1465
 
782
- export { AndroidBuilder, type AppAssetConfig, AppAssetsManager, type ArchitectureConfig, type ArchitectureMode, BUILTIN_TEMPLATES, BuildManager, ConfigManager, ConsoleLogger, type CustomTemplate, type FluConfig, type GeneratorConfig, type GeneratorConfigType, type GeneratorFieldPolicy, type GeneratorPolicyMode, type GeneratorType, I18nManager, IOSBuilder, type Logger, type ProjectConfig, ProjectConfigManager, type ProjectConfigSource, ProjectContextService, ProjectGenerator, type ProjectOptions, type ProjectPreset, type ProjectTemplate, type ResolvedProjectConfig, TemplateGenerator, TemplateManager, TemplatePresetService, type TemplateType, calculateRelativeImport, checkFlutterInstalled, checkSnippetsVersion, cleanupTemplateFiles, copyCoreFiles, copyCustomTemplate, copyInfrastructure, copyNetworkFiles, copyTemplate, detectProjectTemplate, ensurePubspecName, fixAndroidPackageName, fixIosBundleIdentifier, generateComponent, generateIndexFile, generateModel, generateModule, generatePage, generateService, generateViewModel, generateWidget, getArchitectureMode, getCoreFilesDir, getFlutterVersion, getGeneratorFieldPolicy, getModelPath, getNetworkDir, getPagePath, getRelativeImportPath, getServicePath, getSnippetContent, getStateManager, getTemplatesRootDir, getViewModelPath, getWidgetPath, injectNetworkExamples, isCustomTemplateProject, isGeneratorFieldLocked, loadProjectSnippets, logger, mirrorNestedTargetDir, removeTemplateSuffix, renderSnippet, replaceVariables, resolveConfiguredImport, resolveGeneratorBaseDir, resolveGeneratorTargetDir, runFlutterCreate, runFlutterPubGet, t, toCamelCase, toKebabCase, toPascalCase, toSnakeCase, toTitleCase, updateIndexFile, updateNestedIndexExports, upgradeSnippets };
1466
+ export { AndroidBuilder, type AppAssetConfig, AppAssetsManager, type ArchitectureConfig, type ArchitectureMode, type AuthCapabilityConfig, BUILTIN_TEMPLATES, type Blueprint, type BlueprintEndpoint, type BlueprintFeature, type BlueprintGenerateResult, type BlueprintHttpMethod, type BlueprintPage, type BlueprintPageType, BuildManager, type CapabilityDependencyPlan, CleanupTask, type CompositionProfile, ConfigManager, ConsoleLogger, type CustomTemplate, type FluConfig, type FlutterCreateExecutionPlan, type FlutterCreateResult, type FlutterSdkConfig, type FlutterSdkMode, type GeneratorConfig, type GeneratorConfigType, type GeneratorFieldPolicy, type GeneratorPolicyMode, type GeneratorSelectableOption, type GeneratorSelectableOptionsReport, type GeneratorType, HARMONY_FVM_SETUP_DOC_URL, type HelperDependencyPlan, type HelperName, I18nManager, IOSBuilder, type InitAiBaseStarter, type Logger, type NetworkCapabilityConfig, type NormalizeProjectCreateConfigOptions, type ProjectCapabilitiesConfig, type ProjectCompositionConfig, type ProjectConfig, ProjectConfigManager, type ProjectConfigSource, ProjectConfigTask, ProjectContextService, type ProjectCoreConfig, type ProjectCreateConfig, ProjectGenerator, type ProjectHelpersConfig, type ProjectOptions, type ProjectPlatformConfig, type ProjectPreset, type ProjectStackConfig, type ProjectStructureType, type ProjectTemplate, type ResolvedProjectConfig, type RunInitAiBaseOptions, type RunInitAiBaseReport, type RunInitAiBaseResult, type SerializationCapabilityConfig, StarterScaffoldTask, type StateManagerType, type StorageCapabilityConfig, TemplateGenerator, TemplateManager, TemplatePresetService, type TemplateType, VariablesReplaceTask, bindProjectFlutterSdk, buildInitAiBaseConfig, buildProjectRenderData, calculateRelativeImport, checkFlutterInstalled, checkSnippetsVersion, cleanupTemplateFiles, copyCoreFiles, copyCoreMixins, copyCustomTemplate, copyHelperFiles, copyInfrastructure, copyNetworkFiles, copyStarterProjectScaffold, copyTemplate, createDefaultContext, detectProjectTemplate, ensurePubspecDescription, ensurePubspecName, findMissingFlutterPlatformDirs, fixAndroidPackageName, fixIosBundleIdentifier, generateComponent, generateFromBlueprint, generateIndexFile, generateModel, generateModule, generatePage, generateService, generateViewModel, generateWidget, getArchitectureMode, getCoreFilesDir, getCoreMixinsDir, getEnabledHelperTemplateDirs, getFlutterVersion, getGeneratorFieldPolicy, getHelperExamplesDir, getHelpersDir, getModelPath, getNetworkDir, getPagePath, getRelativeImportPath, getServicePath, getSnippetContent, getStarterProjectDir, getStateManager, getTemplatesRootDir, getViewModelPath, getWidgetPath, injectNetworkExamples, isCustomTemplateProject, isGeneratorFieldLocked, isSystemFlutterSdk, listGeneratorSelectableOptions, loadProjectSnippets, logger, mirrorNestedTargetDir, normalizeCompositionProfile, normalizeDartPackageName, normalizeFlutterCreatePlatform, normalizeFlutterCreatePlatforms, normalizeNetworkEnabled, normalizePlatforms, normalizeProjectCreateConfig, normalizeProjectIdToPackageName, normalizeTemplateType, parseFluCliJsonFromPath, parseFlutterCreateSupportedPlatforms, parseOpenApiToBlueprint, removeTemplateSuffix, renderSnippet, replaceVariables, resolveCapabilityDependencyPlan, resolveConfiguredImport, resolveFlutterCommand, resolveFlutterCreateExecutionPlan, resolveGeneratorBaseDir, resolveGeneratorTargetDir, resolveHelperDependencyPlan, resolveProjectFlutterCliCommand, resolveProjectFlutterCliCommandForAutomation, resolveProjectFlutterCommand, resolveSystemFlutterBin, runFlutterCreate, runFlutterPubGet, runInitAiBase, runInitAiBaseWithReport, sanitizePubspecComments, slugForAgentSkill, syncRules, syncRulesWithReport, t, toCamelCase, toKebabCase, toPascalCase, toSnakeCase, toTitleCase, updateIndexFile, updateNestedIndexExports, upgradeSnippets, validateFvmVersionInput, validateProjectId };