From 8ad6633cd1fe5f59db84b6ca8bf2df42548f5bed Mon Sep 17 00:00:00 2001 From: Patrick Stewart Date: Sun, 20 Oct 2024 18:50:34 -0700 Subject: [PATCH] update: working on melos based config and build system --- .melos/analyze.yaml | 10 ++++ .melos/base.yaml | 20 ++++++++ .melos/ci.yaml | 5 ++ .melos/debug.yaml | 25 ++++++++++ .melos/dependencies.yaml | 13 +++++ .melos/docs.yaml | 20 ++++++++ .melos/generate.yaml | 51 ++++++++++++++++++++ .melos/publish.yaml | 9 ++++ .melos/test.yaml | 10 ++++ .melos/utils.yaml | 5 ++ helpers/combine_melos_config.dart | 53 ++++++++++++++++++++ melos.yaml | 75 +++++++++++++++++++---------- packages/model/test/dummy_test.dart | 31 ++++++------ pubspec.lock | 6 +-- pubspec.yaml | 3 ++ 15 files changed, 291 insertions(+), 45 deletions(-) create mode 100644 .melos/analyze.yaml create mode 100644 .melos/base.yaml create mode 100644 .melos/ci.yaml create mode 100644 .melos/debug.yaml create mode 100644 .melos/dependencies.yaml create mode 100644 .melos/docs.yaml create mode 100644 .melos/generate.yaml create mode 100644 .melos/publish.yaml create mode 100644 .melos/test.yaml create mode 100644 .melos/utils.yaml create mode 100644 helpers/combine_melos_config.dart diff --git a/.melos/analyze.yaml b/.melos/analyze.yaml new file mode 100644 index 0000000..598befc --- /dev/null +++ b/.melos/analyze.yaml @@ -0,0 +1,10 @@ +scripts: + _: &analyze_scripts + analyze: + run: dart analyze . + description: Run static analysis on all packages + + format: + run: dart format . + description: Format all Dart files in the repository + diff --git a/.melos/base.yaml b/.melos/base.yaml new file mode 100644 index 0000000..15d1988 --- /dev/null +++ b/.melos/base.yaml @@ -0,0 +1,20 @@ +name: protevus_platform +repository: https://github.com/protevus/platform +packages: + - packages/** + - examples/** + +command: + version: + linkToCommits: true + message: "chore: Bump version to %v" + branch: main + workspaceChangelog: true + +ide: + intellij: + enabled: false + +scripts: + _: &base_scripts + diff --git a/.melos/ci.yaml b/.melos/ci.yaml new file mode 100644 index 0000000..182f260 --- /dev/null +++ b/.melos/ci.yaml @@ -0,0 +1,5 @@ +scripts: + _: &ci_scripts + ci: + run: melos run analyze && melos run test + description: Run full CI pipeline \ No newline at end of file diff --git a/.melos/debug.yaml b/.melos/debug.yaml new file mode 100644 index 0000000..389b87c --- /dev/null +++ b/.melos/debug.yaml @@ -0,0 +1,25 @@ +scripts: + _: &debug_scripts + debug_pkg_name: + run: melos exec -- echo "Package name is {MELOS_PACKAGE_NAME}" + description: Debug package name resolution + + debug_pkg_path: + run: melos exec -- echo "Package name is {MELOS_PACKAGE_PATH}" + description: Debug package path resolution + + debug:reflectable: + run: > + melos exec --scope="$MELOS_SCOPE" -- " + echo \"Checking for .reflectable.dart files in {MELOS_PACKAGE_NAME}\" && + find lib test example -name '*.reflectable.dart' -print 2>/dev/null + " + description: Debug script to find .reflectable.dart files (use with MELOS_SCOPE env var) + + list:dart:files: + run: > + melos exec --scope="$MELOS_SCOPE" -- " + echo \"Listing all Dart files in {MELOS_PACKAGE_NAME}:\" && + find lib test example -name '*.dart' -print 2>/dev/null + " + description: List all Dart files in specified package(s) (use with MELOS_SCOPE env var) \ No newline at end of file diff --git a/.melos/dependencies.yaml b/.melos/dependencies.yaml new file mode 100644 index 0000000..749d21a --- /dev/null +++ b/.melos/dependencies.yaml @@ -0,0 +1,13 @@ +scripts: + _: &dependencies_scripts + deps:check: + run: melos exec -- "dart pub outdated" + description: Check for outdated dependencies + + deps:upgrade: + run: melos exec -- "dart pub upgrade" + description: Upgrade all dependencies to their latest versions + + deps:upgrade:custom: + run: melos exec --scope="$MELOS_SCOPE" -- "dart pub upgrade" + description: Upgrade dependencies for specified packages (use with MELOS_SCOPE env var) \ No newline at end of file diff --git a/.melos/docs.yaml b/.melos/docs.yaml new file mode 100644 index 0000000..21bc72f --- /dev/null +++ b/.melos/docs.yaml @@ -0,0 +1,20 @@ +scripts: + _: &docs_scripts + docs:generate: + run: melos exec -- "dart doc ." + description: Generate documentation for all packages + + docs:generate:custom: + run: melos exec --scope="$MELOS_SCOPE" -- "dart doc ." + description: Generate documentation for specified packages (use with MELOS_SCOPE env var) + + docs:serve: + run: dhttpd --path doc + description: Serve generated documentation + + docs:serve:custom: + run: > + melos exec --scope="$MELOS_SCOPE" -- + "echo 'Serving docs for {MELOS_PACKAGE_NAME}' && + dhttpd --path doc --port \${DOC_PORT:-8080}" + description: Serve generated documentation for specified packages (use with MELOS_SCOPE and optionally DOC_PORT env vars) \ No newline at end of file diff --git a/.melos/generate.yaml b/.melos/generate.yaml new file mode 100644 index 0000000..6d8098e --- /dev/null +++ b/.melos/generate.yaml @@ -0,0 +1,51 @@ +scripts: + _: &generate_scripts + generate: + run: melos exec -- "dart run build_runner build --delete-conflicting-outputs" + description: Run code generation for all packages + + generate:custom: + run: melos exec --scope="$MELOS_SCOPE" -- "dart run build_runner build --delete-conflicting-outputs" + description: Run code generation for specified packages (use with MELOS_SCOPE env var) + + generate:check: + run: > + melos exec --scope="$MELOS_SCOPE" -- " + if grep -q 'build_runner' pubspec.yaml; then + if [ -n \"$(find lib test example -name '*.g.dart' -o -name '*.freezed.dart' -o -name '*.reflectable.dart' 2>/dev/null)\" ]; then + echo \"Package {MELOS_PACKAGE_NAME} needs code generation.\" + else + echo \"Package {MELOS_PACKAGE_NAME} has build_runner but no generated files found.\" + fi + else + echo \"Package {MELOS_PACKAGE_NAME} does not use build_runner.\" + fi + " + description: Check if code generation is needed (use with MELOS_SCOPE env var) + + generate:dummy:test: + run: > + melos exec --scope="$MELOS_SCOPE" -- " + echo ' + import \"package:test/test.dart\"; + + void main() { + group(\"Dummy Test\", () { + test(\"Always passes\", () { + expect(true, isTrue); + }); + + test(\"Basic arithmetic\", () { + expect(2 + 2, equals(4)); + }); + + test(\"String manipulation\", () { + String testString = \"Protevus Platform\"; + expect(testString.contains(\"Platform\"), isTrue); + expect(testString.toLowerCase(), equals(\"protevus platform\")); + }); + }); + } + ' > test/dummy_test.dart + " + description: Generate a dummy test file in the specified package(s) \ No newline at end of file diff --git a/.melos/publish.yaml b/.melos/publish.yaml new file mode 100644 index 0000000..023e02d --- /dev/null +++ b/.melos/publish.yaml @@ -0,0 +1,9 @@ +scripts: + _: &publish_scripts + publish: + run: melos publish + description: Publish all packages that have changed. + + publish:check: + run: melos publish --dry-run + description: Check which packages would be published \ No newline at end of file diff --git a/.melos/test.yaml b/.melos/test.yaml new file mode 100644 index 0000000..4f8b60b --- /dev/null +++ b/.melos/test.yaml @@ -0,0 +1,10 @@ +scripts: + _: &test_scripts + test: + run: melos exec -c 1 --fail-fast -- "dart test" + description: Run tests for all packages + + test:custom: + run: melos exec --scope="$MELOS_SCOPE" -- dart test + description: Run tests for specified packages (use with MELOS_SCOPE env var) + diff --git a/.melos/utils.yaml b/.melos/utils.yaml new file mode 100644 index 0000000..9a82917 --- /dev/null +++ b/.melos/utils.yaml @@ -0,0 +1,5 @@ +scripts: + _: &utils_scripts + combine_config: + run: dart helpers/combine_melos_config.dart + description: Combine Melos configuration files \ No newline at end of file diff --git a/helpers/combine_melos_config.dart b/helpers/combine_melos_config.dart new file mode 100644 index 0000000..9691959 --- /dev/null +++ b/helpers/combine_melos_config.dart @@ -0,0 +1,53 @@ +import 'dart:io'; +import 'package:yaml/yaml.dart'; +import 'package:yaml_edit/yaml_edit.dart'; +import 'package:args/args.dart'; + +void main(List arguments) { + final parser = ArgParser() + ..addOption('input', + abbr: 'i', defaultsTo: '.melos', help: 'Input directory for YAML files') + ..addOption('output', + abbr: 'o', defaultsTo: 'melos.yaml', help: 'Output file path'); + + final results = parser.parse(arguments); + final inputDir = results['input']; + final outputFile = results['output']; + + try { + final baseContent = File('$inputDir/base.yaml').readAsStringSync(); + + final scriptFiles = Directory(inputDir) + .listSync() + .where((file) => + file.path.endsWith('.yaml') && !file.path.endsWith('base.yaml')) + .map((file) => file.path.split('/').last) + .toList(); + + final combinedScripts = {}; + + for (final file in scriptFiles) { + print('Processing $file'); + final content = File('$inputDir/$file').readAsStringSync(); + final yaml = loadYaml(content); + if (yaml == null || + yaml['scripts'] == null || + yaml['scripts']['_'] == null) { + print( + 'Warning: $file does not contain expected script structure. Skipping.'); + continue; + } + combinedScripts.addAll(yaml['scripts']['_']); + } + + final outputYamlEditor = YamlEditor(baseContent); + outputYamlEditor.update(['scripts'], combinedScripts); + + File(outputFile).writeAsStringSync(outputYamlEditor.toString()); + print('Combined Melos configuration written to $outputFile'); + } catch (e, stackTrace) { + print('Error: $e'); + print('Stack trace: $stackTrace'); + exit(1); + } +} diff --git a/melos.yaml b/melos.yaml index 8a364e8..81ea5ad 100644 --- a/melos.yaml +++ b/melos.yaml @@ -6,10 +6,8 @@ packages: command: version: - # Generate commit links in package changelogs. linkToCommits: true message: "chore: Bump version to %v" - # Only allow versioning to happen on main branch. branch: main workspaceChangelog: true @@ -17,49 +15,74 @@ ide: intellij: enabled: false -# Project scripts - scripts: analyze: run: dart analyze . description: Run static analysis on all packages - - test: - run: melos exec -c 1 --fail-fast -- "dart test" - description: Run tests for all packages - format: run: dart format . description: Format all Dart files in the repository - generate: run: melos exec -- "dart run build_runner build --delete-conflicting-outputs" description: Run code generation for all packages - - ci: - run: melos run analyze && melos run test - description: Run full CI pipeline - + generate:custom: + run: melos exec --scope="$MELOS_SCOPE" -- "dart run build_runner build --delete-conflicting-outputs" + description: Run code generation for specified packages (use with MELOS_SCOPE env var) + generate:check: + run: "melos exec --scope=\"$MELOS_SCOPE\" -- \" if grep -q 'build_runner' pubspec.yaml; then\n if [ -n \\\"$(find lib test example -name '*.g.dart' -o -name '*.freezed.dart' -o -name '*.reflectable.dart' 2>\/dev\/null)\\\" ]; then\n echo \\\"Package {MELOS_PACKAGE_NAME} needs code generation.\\\"\n else\n echo \\\"Package {MELOS_PACKAGE_NAME} has build_runner but no generated files found.\\\"\n fi\nelse\n echo \\\"Package {MELOS_PACKAGE_NAME} does not use build_runner.\\\"\nfi \"\n" + description: Check if code generation is needed (use with MELOS_SCOPE env var) + generate:dummy:test: + run: "melos exec --scope=\"$MELOS_SCOPE\" -- \" echo ' import \\\"package:test\/test.dart\\\";\nvoid main() {\n group(\\\"Dummy Test\\\", () {\n test(\\\"Always passes\\\", () {\n expect(true, isTrue);\n });\n\n test(\\\"Basic arithmetic\\\", () {\n expect(2 + 2, equals(4));\n });\n\n test(\\\"String manipulation\\\", () {\n String testString = \\\"Protevus Platform\\\";\n expect(testString.contains(\\\"Platform\\\"), isTrue);\n expect(testString.toLowerCase(), equals(\\\"protevus platform\\\"));\n });\n });\n} ' > test\/dummy_test.dart \"\n" + description: Generate a dummy test file in the specified package(s) + publish: + run: melos publish + description: Publish all packages that have changed. + publish:check: + run: melos publish --dry-run + description: Check which packages would be published docs:generate: run: melos exec -- "dart doc ." description: Generate documentation for all packages - + docs:generate:custom: + run: melos exec --scope="$MELOS_SCOPE" -- "dart doc ." + description: Generate documentation for specified packages (use with MELOS_SCOPE env var) + docs:serve: + run: dhttpd --path doc + description: Serve generated documentation + docs:serve:custom: + run: "melos exec --scope=\"$MELOS_SCOPE\" -- \"echo 'Serving docs for {MELOS_PACKAGE_NAME}' && dhttpd --path doc --port \\${DOC_PORT:-8080}\"\n" + description: Serve generated documentation for specified packages (use with MELOS_SCOPE and optionally DOC_PORT env vars) + test: + run: melos exec -c 1 --fail-fast -- "dart test" + description: Run tests for all packages + test:custom: + run: melos exec --scope="$MELOS_SCOPE" -- dart test + description: Run tests for specified packages (use with MELOS_SCOPE env var) deps:check: run: melos exec -- "dart pub outdated" description: Check for outdated dependencies - deps:upgrade: run: melos exec -- "dart pub upgrade" description: Upgrade all dependencies to their latest versions - - publish: - run: melos publish - description: Publish all packages that have changed. - + deps:upgrade:custom: + run: melos exec --scope="$MELOS_SCOPE" -- "dart pub upgrade" + description: Upgrade dependencies for specified packages (use with MELOS_SCOPE env var) + ci: + run: melos run analyze && melos run test + description: Run full CI pipeline debug_pkg_name: - run: melos exec -- echo "Package name is {MELOS_PACKAGE_NAME}" + run: "melos exec -- echo \"Package name is {MELOS_PACKAGE_NAME}\"" description: Debug package name resolution - debug_pkg_path: - run: melos exec -- echo "Package name is {MELOS_PACKAGE_PATH}" - description: Debug package name resolution + run: "melos exec -- echo \"Package name is {MELOS_PACKAGE_PATH}\"" + description: Debug package path resolution + debug:reflectable: + run: "melos exec --scope=\"$MELOS_SCOPE\" -- \" echo \\\"Checking for .reflectable.dart files in {MELOS_PACKAGE_NAME}\\\" && find lib test example -name '*.reflectable.dart' -print 2>\/dev\/null \"\n" + description: Debug script to find .reflectable.dart files (use with MELOS_SCOPE env var) + list:dart:files: + run: "melos exec --scope=\"$MELOS_SCOPE\" -- \" echo \\\"Listing all Dart files in {MELOS_PACKAGE_NAME}:\\\" && find lib test example -name '*.dart' -print 2>\/dev\/null \"\n" + description: List all Dart files in specified package(s) (use with MELOS_SCOPE env var) + combine_config: + run: dart helpers/combine_melos_config.dart + description: Combine Melos configuration files + diff --git a/packages/model/test/dummy_test.dart b/packages/model/test/dummy_test.dart index b4883e3..4907191 100644 --- a/packages/model/test/dummy_test.dart +++ b/packages/model/test/dummy_test.dart @@ -1,19 +1,18 @@ -import 'package:test/test.dart'; - + import "package:test/test.dart"; void main() { - group('Dummy Test', () { - test('Always passes', () { - expect(true, isTrue); - }); + group("Dummy Test", () { + test("Always passes", () { + expect(true, isTrue); + }); - test('Basic arithmetic', () { - expect(2 + 2, equals(4)); - }); + test("Basic arithmetic", () { + expect(2 + 2, equals(4)); + }); - test('String manipulation', () { - String testString = 'Protevus Platform'; - expect(testString.contains('Platform'), isTrue); - expect(testString.toLowerCase(), equals('protevus platform')); - }); - }); -} + test("String manipulation", () { + String testString = "Protevus Platform"; + expect(testString.contains("Platform"), isTrue); + expect(testString.toLowerCase(), equals("protevus platform")); + }); + }); +} diff --git a/pubspec.lock b/pubspec.lock index 998ad77..1d1d903 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -31,7 +31,7 @@ packages: source: hosted version: "0.3.2+1" args: - dependency: transitive + dependency: "direct dev" description: name: args sha256: bf9f5caeea8d8fe6721a9c358dd8a5c1947b27f1cfaa18b39c301273594919e6 @@ -543,7 +543,7 @@ packages: source: hosted version: "1.2.1" yaml: - dependency: transitive + dependency: "direct dev" description: name: yaml sha256: "75769501ea3489fca56601ff33454fe45507ea3bfb014161abc3b43ae25989d5" @@ -551,7 +551,7 @@ packages: source: hosted version: "3.1.2" yaml_edit: - dependency: transitive + dependency: "direct dev" description: name: yaml_edit sha256: e9c1a3543d2da0db3e90270dbb1e4eebc985ee5e3ffe468d83224472b2194a5f diff --git a/pubspec.yaml b/pubspec.yaml index 84ef222..83417ef 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -16,4 +16,7 @@ dev_dependencies: lints: ^4.0.0 melos: ^6.1.0 test: ^1.24.0 + yaml: ^3.1.2 + args: ^2.6.0 + yaml_edit: ^2.2.1 #path: ^1.8.0 \ No newline at end of file