Skip to content

Commit 563e1fb

Browse files
added features, components and few changes in specification file.
1 parent f1bbdc3 commit 563e1fb

File tree

6 files changed

+395
-17
lines changed

6 files changed

+395
-17
lines changed

.idea/libraries/Dart_Packages.xml

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

lib/commands/add/add.dart

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import 'dart:io';
22

33
import 'package:cwa_plugin_core/cwa_plugin_core.dart';
4+
import 'package:react_native/commands/add/add_component.dart';
45
import 'package:react_native/commands/add/add_features.dart';
56
import 'package:react_native/commands/add/add_utils.dart';
67

@@ -11,7 +12,7 @@ class ReactNativeAdd extends Command {
1112

1213
@override
1314
String get description =>
14-
"Add features, libraries, or utilities from our main repo.";
15+
"Add features, service, component, or utilities from our main repo.";
1516

1617
@override
1718
Future<void> run() async {
@@ -20,6 +21,7 @@ class ReactNativeAdd extends Command {
2021
'Add a Utility',
2122
'Add a Service',
2223
'Add a Feature',
24+
'Add a Component',
2325
]);
2426

2527
int idx = menu.choose().index;
@@ -31,6 +33,8 @@ class ReactNativeAdd extends Command {
3133
await ReactNativeService(args).run();
3234
case 2:
3335
await ReactNativeFeature(args).run();
36+
case 3:
37+
await ReactNativeComponent(args).run();
3438
default:
3539
exit(2);
3640
}
Lines changed: 147 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,147 @@
1+
import 'dart:convert';
2+
import 'dart:io';
3+
4+
import 'package:cli_spin/cli_spin.dart';
5+
import 'package:cwa_plugin_core/cwa_plugin_core.dart';
6+
import 'package:react_native/config/plugin_config.dart';
7+
8+
import '../../config/runtime_config.dart';
9+
import '../../model/specification.dart';
10+
11+
class ReactNativeComponent extends Command {
12+
ReactNativeComponent(super.args);
13+
14+
@override
15+
String get description => "Manage Components for React Native project.";
16+
17+
@override
18+
Future<void> run() async {
19+
CWLogger.i.progress("Looking for available Components");
20+
21+
List<String>? dirs = await GitService.getGitLabBranches(
22+
ReactNativeConfig.i.archManagerProjectID,
23+
TokenService().accessToken!,
24+
);
25+
26+
if (dirs == null || dirs.isEmpty) {
27+
CWLogger.namedLog(
28+
'No Components found!',
29+
loggerColor: CWLoggerColor.yellow,
30+
);
31+
exit(1);
32+
}
33+
List<String> utilsBranches = dirs
34+
.where((branch) => branch.startsWith('components/'))
35+
.map((branch) => branch.replaceFirst('components/', ''))
36+
.toList();
37+
38+
if (utilsBranches.isEmpty) {
39+
CWLogger.namedLog(
40+
'No Components found in the "components/" directory!',
41+
loggerColor: CWLoggerColor.yellow,
42+
);
43+
exit(1);
44+
}
45+
46+
CWLogger.i.stdout("Please select the Component you want to use :");
47+
Menu featureMenu = Menu(utilsBranches);
48+
int idx = featureMenu.choose().index;
49+
50+
String selectedComponent = 'components/${utilsBranches[idx]}';
51+
52+
await _handleComponentAndSpecification(selectedComponent);
53+
}
54+
55+
Future<void> _handleComponentAndSpecification(String componentName) async {
56+
CliSpin featureLoader =
57+
CliSpin(text: "Adding $componentName to the project").start();
58+
59+
try {
60+
String filePath = 'specification_config.json';
61+
String? specsFileContent = await GitService.getGitLabFileContent(
62+
projectId: ReactNativeConfig.i.pilotRepoProjectID,
63+
filePath: filePath,
64+
branch: componentName,
65+
token: TokenService().accessToken!,
66+
);
67+
68+
if (specsFileContent != null) {
69+
Map<String, dynamic> specificationData = json.decode(specsFileContent);
70+
71+
// Get the filePath and folderPath from the config (with null checks)
72+
List<dynamic> componentFilePaths = specificationData['filePath'] ?? [];
73+
List<dynamic> componentFolderPaths = specificationData['folderPath'] ?? [];
74+
75+
// Handle file paths if available
76+
if (componentFilePaths.isNotEmpty) {
77+
for (String componentFilePath in componentFilePaths) {
78+
await _downloadFile(componentFilePath, componentName);
79+
}
80+
}
81+
82+
// Handle folder paths if available
83+
if (componentFolderPaths.isNotEmpty) {
84+
for (String componentFolderPath in componentFolderPaths) {
85+
await _downloadDirectory(componentFolderPath, componentName);
86+
}
87+
}
88+
89+
await SpecificationUpdater.updateSpecifications(componentName);
90+
91+
featureLoader.success();
92+
} else {
93+
CWLogger.i.trace('Failed to fetch specification_config.json');
94+
}
95+
} catch (e) {
96+
featureLoader.fail();
97+
CWLogger.namedLog(
98+
e.toString(),
99+
loggerColor: CWLoggerColor.red,
100+
);
101+
CWLogger.i.trace(
102+
'Error downloading component $componentName or updating specifications: $e');
103+
}
104+
}
105+
106+
// Method to download individual file
107+
Future<void> _downloadFile(String componentFilePath, String componentName) async {
108+
String? fileContent = await GitService.getGitLabFileContent(
109+
projectId: ReactNativeConfig.i.pilotRepoProjectID,
110+
filePath: componentFilePath,
111+
branch: componentName,
112+
token: TokenService().accessToken!,
113+
);
114+
115+
if (fileContent != null) {
116+
String localFilePath =
117+
'${RuntimeConfig().commandExecutionPath}/$componentFilePath';
118+
File localFile = File(localFilePath);
119+
120+
if (localFile.existsSync()) {
121+
CWLogger.i.trace('$componentFilePath already exists, skipping download.');
122+
} else {
123+
await localFile.create(recursive: true);
124+
await localFile.writeAsString(fileContent);
125+
CWLogger.i.trace('Downloaded $componentFilePath successfully.');
126+
}
127+
} else {
128+
CWLogger.i.trace('Failed to fetch $componentFilePath.');
129+
}
130+
}
131+
132+
// Method to download a directory
133+
Future<void> _downloadDirectory(String componentFolderPath, String componentName) async {
134+
try {
135+
await GitService.downloadDirectoryContents(
136+
projectId: ReactNativeConfig.i.pilotRepoProjectID,
137+
branch: componentName,
138+
directoryPath: componentFolderPath,
139+
downloadPathBase: RuntimeConfig().commandExecutionPath,
140+
accessToken: TokenService().accessToken!,
141+
);
142+
CWLogger.i.trace('Downloaded directory $componentFolderPath successfully.');
143+
} catch (e) {
144+
CWLogger.i.trace('Failed to download directory $componentFolderPath: $e');
145+
}
146+
}
147+
}

lib/commands/add/add_features.dart

Lines changed: 133 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,145 @@
1+
import 'dart:convert';
2+
import 'dart:io';
3+
4+
import 'package:cli_spin/cli_spin.dart';
15
import 'package:cwa_plugin_core/cwa_plugin_core.dart';
6+
import 'package:react_native/config/plugin_config.dart';
7+
8+
import '../../config/runtime_config.dart';
9+
import '../../model/specification.dart';
210

311
class ReactNativeFeature extends Command {
412
ReactNativeFeature(super.args);
513

614
@override
7-
String get description =>
8-
"";
15+
String get description => "";
916

1017
@override
1118
Future<void> run() async {
19+
CWLogger.i.progress("Looking for available Features");
20+
21+
List<String>? dirs = await GitService.getGitLabBranches(
22+
ReactNativeConfig.i.archManagerProjectID,
23+
TokenService().accessToken!,
24+
);
25+
26+
if (dirs == null || dirs.isEmpty) {
27+
CWLogger.namedLog(
28+
'No Features found!',
29+
loggerColor: CWLoggerColor.yellow,
30+
);
31+
exit(1);
32+
}
33+
CWLogger.i.stdout(dirs.toSet().toString());
34+
List<String> featureBranches = dirs
35+
.where((branch) => branch.startsWith('features/'))
36+
.map((branch) => branch.replaceFirst('features/', ''))
37+
.toList();
38+
39+
if (featureBranches.isEmpty) {
40+
CWLogger.namedLog(
41+
'No Features found in the "features/" directory!',
42+
loggerColor: CWLoggerColor.yellow,
43+
);
44+
exit(1);
45+
}
46+
47+
CWLogger.i.stdout("Please select the Feature you want to use :");
48+
CWLogger.i.stdout(featureBranches.toString());
49+
Menu featureMenu = Menu(featureBranches);
50+
int idx = featureMenu.choose().index;
51+
52+
String selectedFeature = 'features/${featureBranches[idx]}';
53+
54+
await _handleFeatureAndSpecification(selectedFeature);
55+
}
56+
57+
Future<void> _handleFeatureAndSpecification(String featureName) async {
58+
CliSpin featureLoader =
59+
CliSpin(text: "Adding $featureName to the project").start();
60+
61+
try {
62+
String filePath = 'specification_config.json';
63+
String? specsFileContent = await GitService.getGitLabFileContent(
64+
projectId: ReactNativeConfig.i.pilotRepoProjectID,
65+
filePath: filePath,
66+
branch: featureName,
67+
token: TokenService().accessToken!,
68+
);
69+
70+
if (specsFileContent != null) {
71+
Map<String, dynamic> specificationData = json.decode(specsFileContent);
72+
73+
// Get the filePath and folderPath from the config
74+
List<dynamic> featuresFilePaths = specificationData['filePath'] ?? [];
75+
List<dynamic> featuresFolderPaths = specificationData['folderPath'] ?? [];
76+
77+
// Handle file paths if available
78+
if (featuresFilePaths.isNotEmpty) {
79+
for (String featureFilePath in featuresFilePaths) {
80+
await _downloadFile(featureFilePath, featureName);
81+
}
82+
}
83+
84+
// Handle folder paths if available
85+
if (featuresFolderPaths.isNotEmpty) {
86+
for (String featureFolderPath in featuresFolderPaths) {
87+
await _downloadDirectory(featureFolderPath, featureName);
88+
}
89+
}
90+
91+
await SpecificationUpdater.updateSpecifications(featureName);
92+
93+
featureLoader.success();
94+
} else {
95+
CWLogger.i.trace('Failed to fetch specification_config.json');
96+
}
97+
} catch (e) {
98+
featureLoader.fail();
99+
CWLogger.i.trace(
100+
'Error downloading Feature $featureName or updating specifications: $e');
101+
}
102+
}
103+
104+
// Method to download individual file
105+
Future<void> _downloadFile(String featureFilePath, String featureName) async {
106+
String? fileContent = await GitService.getGitLabFileContent(
107+
projectId: ReactNativeConfig.i.pilotRepoProjectID,
108+
filePath: featureFilePath,
109+
branch: featureName,
110+
token: TokenService().accessToken!,
111+
);
112+
113+
if (fileContent != null) {
114+
String localFilePath =
115+
'${RuntimeConfig().commandExecutionPath}/$featureFilePath';
116+
File localFile = File(localFilePath);
117+
118+
if (localFile.existsSync()) {
119+
CWLogger.i.trace('$featureFilePath already exists, skipping download.');
120+
} else {
121+
await localFile.create(recursive: true);
122+
await localFile.writeAsString(fileContent);
123+
CWLogger.i.trace('Downloaded $featureFilePath successfully.');
124+
}
125+
} else {
126+
CWLogger.i.trace('Failed to fetch $featureFilePath.');
127+
}
128+
}
12129

130+
// Method to download a directory
131+
Future<void> _downloadDirectory(String featureFilePath, String featureName) async {
132+
try {
133+
await GitService.downloadDirectoryContents(
134+
projectId: ReactNativeConfig.i.pilotRepoProjectID,
135+
branch: featureName,
136+
directoryPath: featureFilePath,
137+
downloadPathBase: RuntimeConfig().commandExecutionPath,
138+
accessToken: TokenService().accessToken!,
139+
);
140+
CWLogger.i.trace('Downloaded directory $featureFilePath successfully.');
141+
} catch (e) {
142+
CWLogger.i.trace('Failed to download directory $featureFilePath: $e');
143+
}
13144
}
14145
}

lib/config/runtime_config.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ class RuntimeConfig extends RTC<PubSpec> {
1717
static final String l10ngeneratedPath = 'lib/core/l10n/generated';
1818
static final String l10nAppStringPath = 'lib/core/l10n/app_strings.dart';
1919
static final String libraryPath = 'lib/libraries';
20-
static final String featureLocation = 'lib/features';
20+
static final String featureLocation = 'features';
2121
static final String utilsLocation = 'utils';
2222

2323
@override

0 commit comments

Comments
 (0)