@muverse/core 0.1.0
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 +22 -0
- package/dist/adapters/gradle/constants.d.ts +13 -0
- package/dist/adapters/gradle/constants.d.ts.map +1 -0
- package/dist/adapters/gradle/constants.js +12 -0
- package/dist/adapters/gradle/gradle-project-information.d.ts +18 -0
- package/dist/adapters/gradle/gradle-project-information.d.ts.map +1 -0
- package/dist/adapters/gradle/gradle-project-information.js +93 -0
- package/dist/adapters/gradle/gradle-properties.d.ts +15 -0
- package/dist/adapters/gradle/gradle-properties.d.ts.map +1 -0
- package/dist/adapters/gradle/gradle-properties.js +46 -0
- package/dist/adapters/gradle/init-project-information.gradle.kts +143 -0
- package/dist/adapters/gradle/services/gradle-adapter-identifier.d.ts +21 -0
- package/dist/adapters/gradle/services/gradle-adapter-identifier.d.ts.map +1 -0
- package/dist/adapters/gradle/services/gradle-adapter-identifier.js +44 -0
- package/dist/adapters/gradle/services/gradle-module-detector.d.ts +18 -0
- package/dist/adapters/gradle/services/gradle-module-detector.d.ts.map +1 -0
- package/dist/adapters/gradle/services/gradle-module-detector.js +26 -0
- package/dist/adapters/gradle/services/gradle-module-system-factory.d.ts +23 -0
- package/dist/adapters/gradle/services/gradle-module-system-factory.d.ts.map +1 -0
- package/dist/adapters/gradle/services/gradle-module-system-factory.js +27 -0
- package/dist/adapters/gradle/services/gradle-version-update-strategy.d.ts +21 -0
- package/dist/adapters/gradle/services/gradle-version-update-strategy.d.ts.map +1 -0
- package/dist/adapters/gradle/services/gradle-version-update-strategy.js +36 -0
- package/dist/adapters/project-information.d.ts +58 -0
- package/dist/adapters/project-information.d.ts.map +1 -0
- package/dist/adapters/project-information.js +1 -0
- package/dist/changelog/index.d.ts +27 -0
- package/dist/changelog/index.d.ts.map +1 -0
- package/dist/changelog/index.js +204 -0
- package/dist/config/index.d.ts +122 -0
- package/dist/config/index.d.ts.map +1 -0
- package/dist/config/index.js +115 -0
- package/dist/factories/adapter-identifier-registry.d.ts +12 -0
- package/dist/factories/adapter-identifier-registry.d.ts.map +1 -0
- package/dist/factories/adapter-identifier-registry.js +24 -0
- package/dist/factories/module-system-factory.d.ts +10 -0
- package/dist/factories/module-system-factory.d.ts.map +1 -0
- package/dist/factories/module-system-factory.js +18 -0
- package/dist/git/index.d.ts +253 -0
- package/dist/git/index.d.ts.map +1 -0
- package/dist/git/index.js +581 -0
- package/dist/index.d.ts +23 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +22 -0
- package/dist/semver/index.d.ts +85 -0
- package/dist/semver/index.d.ts.map +1 -0
- package/dist/semver/index.js +176 -0
- package/dist/services/adapter-identifier-registry.d.ts +38 -0
- package/dist/services/adapter-identifier-registry.d.ts.map +1 -0
- package/dist/services/adapter-identifier-registry.js +59 -0
- package/dist/services/adapter-identifier.d.ts +31 -0
- package/dist/services/adapter-identifier.d.ts.map +1 -0
- package/dist/services/adapter-identifier.js +1 -0
- package/dist/services/adapter-metadata-provider.d.ts +51 -0
- package/dist/services/adapter-metadata-provider.d.ts.map +1 -0
- package/dist/services/adapter-metadata-provider.js +66 -0
- package/dist/services/changelog-generator.d.ts +13 -0
- package/dist/services/changelog-generator.d.ts.map +1 -0
- package/dist/services/changelog-generator.js +26 -0
- package/dist/services/commit-analyzer.d.ts +44 -0
- package/dist/services/commit-analyzer.d.ts.map +1 -0
- package/dist/services/commit-analyzer.js +86 -0
- package/dist/services/configuration-loader.d.ts +23 -0
- package/dist/services/configuration-loader.d.ts.map +1 -0
- package/dist/services/configuration-loader.js +79 -0
- package/dist/services/configuration-validator.d.ts +16 -0
- package/dist/services/configuration-validator.d.ts.map +1 -0
- package/dist/services/configuration-validator.js +24 -0
- package/dist/services/git-operations.d.ts +16 -0
- package/dist/services/git-operations.d.ts.map +1 -0
- package/dist/services/git-operations.js +89 -0
- package/dist/services/module-detector.d.ts +24 -0
- package/dist/services/module-detector.d.ts.map +1 -0
- package/dist/services/module-detector.js +1 -0
- package/dist/services/module-registry.d.ts +45 -0
- package/dist/services/module-registry.d.ts.map +1 -0
- package/dist/services/module-registry.js +57 -0
- package/dist/services/module-system-factory.d.ts +24 -0
- package/dist/services/module-system-factory.d.ts.map +1 -0
- package/dist/services/module-system-factory.js +1 -0
- package/dist/services/verse-runner.d.ts +45 -0
- package/dist/services/verse-runner.d.ts.map +1 -0
- package/dist/services/verse-runner.js +182 -0
- package/dist/services/version-applier.d.ts +26 -0
- package/dist/services/version-applier.d.ts.map +1 -0
- package/dist/services/version-applier.js +63 -0
- package/dist/services/version-bumper.d.ts +156 -0
- package/dist/services/version-bumper.d.ts.map +1 -0
- package/dist/services/version-bumper.js +291 -0
- package/dist/services/version-manager.d.ts +68 -0
- package/dist/services/version-manager.d.ts.map +1 -0
- package/dist/services/version-manager.js +94 -0
- package/dist/services/version-update-strategy.d.ts +18 -0
- package/dist/services/version-update-strategy.d.ts.map +1 -0
- package/dist/services/version-update-strategy.js +1 -0
- package/dist/utils/banner.d.ts +2 -0
- package/dist/utils/banner.d.ts.map +1 -0
- package/dist/utils/banner.js +8 -0
- package/dist/utils/commits.d.ts +12 -0
- package/dist/utils/commits.d.ts.map +1 -0
- package/dist/utils/commits.js +24 -0
- package/dist/utils/file.d.ts +7 -0
- package/dist/utils/file.d.ts.map +1 -0
- package/dist/utils/file.js +19 -0
- package/dist/utils/index.d.ts +6 -0
- package/dist/utils/index.d.ts.map +1 -0
- package/dist/utils/index.js +5 -0
- package/dist/utils/logger.d.ts +14 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/logger.js +22 -0
- package/dist/utils/properties.d.ts +16 -0
- package/dist/utils/properties.d.ts.map +1 -0
- package/dist/utils/properties.js +62 -0
- package/dist/utils/versioning.d.ts +8 -0
- package/dist/utils/versioning.d.ts.map +1 -0
- package/dist/utils/versioning.js +17 -0
- package/package.json +70 -0
package/README.md
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# @muverse/core
|
|
2
|
+
|
|
3
|
+
Core business logic for μVERSE — independent of GitHub Actions.
|
|
4
|
+
|
|
5
|
+
Build
|
|
6
|
+
|
|
7
|
+
```bash
|
|
8
|
+
npm run -w packages/core build
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
Test
|
|
12
|
+
|
|
13
|
+
```bash
|
|
14
|
+
npm run -w packages/core test
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
Publish to npm
|
|
18
|
+
|
|
19
|
+
```bash
|
|
20
|
+
# ensure dist is built
|
|
21
|
+
npm publish --workspace packages/core --access public
|
|
22
|
+
```
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/** Standard filename for Gradle project properties file ('gradle.properties'). */
|
|
2
|
+
export declare const GRADLE_PROPERTIES_FILE = "gradle.properties";
|
|
3
|
+
/** Standard filename for Gradle build script using Groovy DSL ('build.gradle'). */
|
|
4
|
+
export declare const GRADLE_BUILD_FILE = "build.gradle";
|
|
5
|
+
/** Standard filename for Gradle build script using Kotlin DSL ('build.gradle.kts'). */
|
|
6
|
+
export declare const GRADLE_BUILD_KTS_FILE = "build.gradle.kts";
|
|
7
|
+
/** Standard filename for Gradle settings file using Groovy DSL ('settings.gradle'). */
|
|
8
|
+
export declare const GRADLE_SETTINGS_FILE = "settings.gradle";
|
|
9
|
+
/** Standard filename for Gradle settings file using Kotlin DSL ('settings.gradle.kts'). */
|
|
10
|
+
export declare const GRADLE_SETTINGS_KTS_FILE = "settings.gradle.kts";
|
|
11
|
+
/** Unique identifier for the Gradle adapter ('gradle'). */
|
|
12
|
+
export declare const GRADLE_ID = "gradle";
|
|
13
|
+
//# sourceMappingURL=constants.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../../src/adapters/gradle/constants.ts"],"names":[],"mappings":"AAAA,kFAAkF;AAClF,eAAO,MAAM,sBAAsB,sBAAsB,CAAC;AAE1D,mFAAmF;AACnF,eAAO,MAAM,iBAAiB,iBAAiB,CAAC;AAEhD,uFAAuF;AACvF,eAAO,MAAM,qBAAqB,qBAAqB,CAAC;AAExD,uFAAuF;AACvF,eAAO,MAAM,oBAAoB,oBAAoB,CAAC;AAEtD,2FAA2F;AAC3F,eAAO,MAAM,wBAAwB,wBAAwB,CAAC;AAE9D,2DAA2D;AAC3D,eAAO,MAAM,SAAS,WAAW,CAAC"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/** Standard filename for Gradle project properties file ('gradle.properties'). */
|
|
2
|
+
export const GRADLE_PROPERTIES_FILE = 'gradle.properties';
|
|
3
|
+
/** Standard filename for Gradle build script using Groovy DSL ('build.gradle'). */
|
|
4
|
+
export const GRADLE_BUILD_FILE = 'build.gradle';
|
|
5
|
+
/** Standard filename for Gradle build script using Kotlin DSL ('build.gradle.kts'). */
|
|
6
|
+
export const GRADLE_BUILD_KTS_FILE = 'build.gradle.kts';
|
|
7
|
+
/** Standard filename for Gradle settings file using Groovy DSL ('settings.gradle'). */
|
|
8
|
+
export const GRADLE_SETTINGS_FILE = 'settings.gradle';
|
|
9
|
+
/** Standard filename for Gradle settings file using Kotlin DSL ('settings.gradle.kts'). */
|
|
10
|
+
export const GRADLE_SETTINGS_KTS_FILE = 'settings.gradle.kts';
|
|
11
|
+
/** Unique identifier for the Gradle adapter ('gradle'). */
|
|
12
|
+
export const GRADLE_ID = 'gradle';
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { ProjectInformation, RawProjectInformation } from '../project-information.js';
|
|
2
|
+
/**
|
|
3
|
+
* Executes Gradle to collect raw project structure information.
|
|
4
|
+
* Runs gradlew with init script to output JSON containing module hierarchy, versions, and dependencies.
|
|
5
|
+
* @param projectRoot - Absolute path to the Gradle project root directory
|
|
6
|
+
* @returns Promise resolving to raw project information as JSON
|
|
7
|
+
* @throws {Error} If initialization script not found or Gradle execution fails
|
|
8
|
+
*/
|
|
9
|
+
export declare function getRawProjectInformation(projectRoot: string): Promise<RawProjectInformation>;
|
|
10
|
+
/**
|
|
11
|
+
* Transforms raw project information into structured, queryable format.
|
|
12
|
+
* Normalizes modules, identifies root, parses versions, and maps dependencies.
|
|
13
|
+
* @param projectInformation - Raw project information from Gradle
|
|
14
|
+
* @returns Structured ProjectInformation with normalized data
|
|
15
|
+
* @throws {Error} If no root module found in hierarchy
|
|
16
|
+
*/
|
|
17
|
+
export declare function getProjectInformation(projectInformation: RawProjectInformation): ProjectInformation;
|
|
18
|
+
//# sourceMappingURL=gradle-project-information.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gradle-project-information.d.ts","sourceRoot":"","sources":["../../../src/adapters/gradle/gradle-project-information.ts"],"names":[],"mappings":"AAGA,OAAO,EAAU,kBAAkB,EAAE,qBAAqB,EAAE,MAAM,2BAA2B,CAAC;AAgB9F;;;;;;GAMG;AACH,wBAAsB,wBAAwB,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,qBAAqB,CAAC,CAsClG;AAED;;;;;;GAMG;AACH,wBAAgB,qBAAqB,CAAC,kBAAkB,EAAE,qBAAqB,GAAG,kBAAkB,CAuCnG"}
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
import path, { join } from 'path';
|
|
2
|
+
import { createInitialVersion, parseSemVer } from '../../semver/index.js';
|
|
3
|
+
import { exists } from '../../utils/file.js';
|
|
4
|
+
import { fileURLToPath } from 'url';
|
|
5
|
+
import { execa } from 'execa';
|
|
6
|
+
/**
|
|
7
|
+
* Name of the Gradle wrapper script file.
|
|
8
|
+
* Ensures consistent builds without requiring pre-installed Gradle.
|
|
9
|
+
*/
|
|
10
|
+
const GRADLE_WRAPPER = 'gradlew';
|
|
11
|
+
/**
|
|
12
|
+
* Relative path to the Gradle initialization script within the action.
|
|
13
|
+
* Injected into Gradle to collect project structure information as JSON.
|
|
14
|
+
*/
|
|
15
|
+
const GRADLE_INIT_SCRIPT = './init-project-information.gradle.kts';
|
|
16
|
+
/**
|
|
17
|
+
* Executes Gradle to collect raw project structure information.
|
|
18
|
+
* Runs gradlew with init script to output JSON containing module hierarchy, versions, and dependencies.
|
|
19
|
+
* @param projectRoot - Absolute path to the Gradle project root directory
|
|
20
|
+
* @returns Promise resolving to raw project information as JSON
|
|
21
|
+
* @throws {Error} If initialization script not found or Gradle execution fails
|
|
22
|
+
*/
|
|
23
|
+
export async function getRawProjectInformation(projectRoot) {
|
|
24
|
+
const gradlew = join(projectRoot, GRADLE_WRAPPER);
|
|
25
|
+
const dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
26
|
+
const initScriptPath = join(dirname, GRADLE_INIT_SCRIPT);
|
|
27
|
+
// Check if init script exists
|
|
28
|
+
const scriptExists = await exists(initScriptPath);
|
|
29
|
+
if (!scriptExists) {
|
|
30
|
+
throw new Error(`Init script not found at ${initScriptPath}. ` +
|
|
31
|
+
`Please create the ${GRADLE_INIT_SCRIPT} file.`);
|
|
32
|
+
}
|
|
33
|
+
// Prepare Gradle command arguments
|
|
34
|
+
const args = [
|
|
35
|
+
'--quiet', // Suppress non-error output for clean JSON
|
|
36
|
+
'--console=plain', // Disable ANSI formatting
|
|
37
|
+
'--init-script', // Inject initialization script
|
|
38
|
+
initScriptPath,
|
|
39
|
+
'structure' // Custom task that outputs project structure
|
|
40
|
+
];
|
|
41
|
+
// Execute Gradle wrapper with the prepared arguments
|
|
42
|
+
const result = await execa(gradlew, args, {
|
|
43
|
+
cwd: projectRoot, // Run from project root
|
|
44
|
+
reject: false // Handle non-zero exit codes ourselves
|
|
45
|
+
});
|
|
46
|
+
// Check for Gradle execution failure
|
|
47
|
+
if (result.exitCode !== 0) {
|
|
48
|
+
throw new Error(`Gradle command failed with exit code ${result.exitCode}: ${result.stderr}`);
|
|
49
|
+
}
|
|
50
|
+
// Parse JSON output from Gradle
|
|
51
|
+
return JSON.parse(result.stdout.trim() || '{}');
|
|
52
|
+
}
|
|
53
|
+
/**
|
|
54
|
+
* Transforms raw project information into structured, queryable format.
|
|
55
|
+
* Normalizes modules, identifies root, parses versions, and maps dependencies.
|
|
56
|
+
* @param projectInformation - Raw project information from Gradle
|
|
57
|
+
* @returns Structured ProjectInformation with normalized data
|
|
58
|
+
* @throws {Error} If no root module found in hierarchy
|
|
59
|
+
*/
|
|
60
|
+
export function getProjectInformation(projectInformation) {
|
|
61
|
+
const moduleIds = Object.keys(projectInformation);
|
|
62
|
+
const modules = new Map();
|
|
63
|
+
// Find root module by looking for the one with type 'root'
|
|
64
|
+
let rootModule;
|
|
65
|
+
for (const [moduleId, module] of Object.entries(projectInformation)) {
|
|
66
|
+
if (module.type === 'root') {
|
|
67
|
+
rootModule = moduleId;
|
|
68
|
+
}
|
|
69
|
+
// Create normalized Module object
|
|
70
|
+
modules.set(moduleId, {
|
|
71
|
+
id: moduleId,
|
|
72
|
+
name: module.name,
|
|
73
|
+
path: module.path,
|
|
74
|
+
type: module.type,
|
|
75
|
+
affectedModules: new Set(module.affectedModules),
|
|
76
|
+
// Parse version if present, otherwise create initial version
|
|
77
|
+
version: module.version === undefined ?
|
|
78
|
+
createInitialVersion() :
|
|
79
|
+
parseSemVer(module.version),
|
|
80
|
+
declaredVersion: module.declaredVersion,
|
|
81
|
+
});
|
|
82
|
+
}
|
|
83
|
+
// Validate that a root module was found
|
|
84
|
+
if (!rootModule) {
|
|
85
|
+
throw new Error('No root module found in hierarchy. ' +
|
|
86
|
+
'Every project hierarchy must contain exactly one module with type "root".');
|
|
87
|
+
}
|
|
88
|
+
return {
|
|
89
|
+
moduleIds,
|
|
90
|
+
modules,
|
|
91
|
+
rootModule
|
|
92
|
+
};
|
|
93
|
+
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Converts a gradle.properties version property name to a Gradle module ID.
|
|
3
|
+
* @param propertyName - Version property name from gradle.properties
|
|
4
|
+
* @returns Corresponding Gradle module ID
|
|
5
|
+
*/
|
|
6
|
+
export declare function versionPropertyNameToModuleId(propertyName: string): string;
|
|
7
|
+
/**
|
|
8
|
+
* Converts a Gradle module ID to a gradle.properties version property name.
|
|
9
|
+
* Uses only the last component of the module path (e.g., ':lib:core' → 'core.version').
|
|
10
|
+
* @param moduleId - Gradle module ID (e.g., ':', ':app', ':lib:core')
|
|
11
|
+
* @returns Corresponding property name for gradle.properties
|
|
12
|
+
* @throws {Error} If the module ID is invalid or cannot be parsed
|
|
13
|
+
*/
|
|
14
|
+
export declare function moduleIdToVersionPropertyName(moduleId: string): string;
|
|
15
|
+
//# sourceMappingURL=gradle-properties.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gradle-properties.d.ts","sourceRoot":"","sources":["../../../src/adapters/gradle/gradle-properties.ts"],"names":[],"mappings":"AAeA;;;;GAIG;AACH,wBAAgB,6BAA6B,CAAC,YAAY,EAAE,MAAM,GAAG,MAAM,CAW1E;AAED;;;;;;GAMG;AACH,wBAAgB,6BAA6B,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAgBtE"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
/** Gradle module identifier for the root project (':'). */
|
|
2
|
+
const ROOT_MODULE_ID = ':';
|
|
3
|
+
/** Property name for version configuration in gradle.properties ('version'). */
|
|
4
|
+
const VERSION = 'version';
|
|
5
|
+
/** Separator character used in Gradle module identifiers (':'). */
|
|
6
|
+
const MODULE_SEPARATOR = ':';
|
|
7
|
+
/** Separator character used in gradle.properties property names ('.'). */
|
|
8
|
+
const DOT_SEPARATOR = '.';
|
|
9
|
+
/** Regular expression to match and remove the '.version' suffix. */
|
|
10
|
+
const VERSION_REGEX = /\.version$/;
|
|
11
|
+
/**
|
|
12
|
+
* Converts a gradle.properties version property name to a Gradle module ID.
|
|
13
|
+
* @param propertyName - Version property name from gradle.properties
|
|
14
|
+
* @returns Corresponding Gradle module ID
|
|
15
|
+
*/
|
|
16
|
+
export function versionPropertyNameToModuleId(propertyName) {
|
|
17
|
+
// Handle root project special case
|
|
18
|
+
if (propertyName === VERSION) {
|
|
19
|
+
return ROOT_MODULE_ID;
|
|
20
|
+
}
|
|
21
|
+
// Remove '.version' suffix
|
|
22
|
+
const nameWithoutSuffix = propertyName.replace(VERSION_REGEX, '');
|
|
23
|
+
// Convert dot-separated to colon-separated module path: "x.y" -> ":x:y"
|
|
24
|
+
return `${ROOT_MODULE_ID}${nameWithoutSuffix.replaceAll(DOT_SEPARATOR, MODULE_SEPARATOR)}`;
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Converts a Gradle module ID to a gradle.properties version property name.
|
|
28
|
+
* Uses only the last component of the module path (e.g., ':lib:core' → 'core.version').
|
|
29
|
+
* @param moduleId - Gradle module ID (e.g., ':', ':app', ':lib:core')
|
|
30
|
+
* @returns Corresponding property name for gradle.properties
|
|
31
|
+
* @throws {Error} If the module ID is invalid or cannot be parsed
|
|
32
|
+
*/
|
|
33
|
+
export function moduleIdToVersionPropertyName(moduleId) {
|
|
34
|
+
// Handle root project special case
|
|
35
|
+
if (moduleId === ROOT_MODULE_ID) {
|
|
36
|
+
return VERSION;
|
|
37
|
+
}
|
|
38
|
+
// Split by module separator and get the last component (module name)
|
|
39
|
+
const name = moduleId.split(MODULE_SEPARATOR).at(-1);
|
|
40
|
+
// Validate that we got a valid module name
|
|
41
|
+
if (!name) {
|
|
42
|
+
throw new Error(`Invalid module ID: ${moduleId}`);
|
|
43
|
+
}
|
|
44
|
+
// Return property name: {name}.version
|
|
45
|
+
return `${name}.${VERSION}`;
|
|
46
|
+
}
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
import groovy.json.JsonOutput
|
|
2
|
+
import groovy.json.JsonGenerator
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Computes the qualified property name for a project's version in gradle.properties.
|
|
6
|
+
* Returns "version" for root, "{name}.version" for subprojects.
|
|
7
|
+
*/
|
|
8
|
+
fun Project.qualifiedVersionProperty(): String {
|
|
9
|
+
val name = if (name.contains(":")) name.split(':').last() else ""
|
|
10
|
+
return if (name.isEmpty()) "version" else "${name}.version"
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
gradle.rootProject {
|
|
14
|
+
/**
|
|
15
|
+
* Collects and outputs project structure information as JSON.
|
|
16
|
+
* Includes module hierarchy, paths, versions, and affected modules.
|
|
17
|
+
*/
|
|
18
|
+
tasks.register("printProjectInformation") {
|
|
19
|
+
group = "help"
|
|
20
|
+
description = "Shows which subprojects are affected by changes (hierarchy + direct dependencies)."
|
|
21
|
+
|
|
22
|
+
// Capture hierarchy data at configuration time
|
|
23
|
+
val hierarchyDepsProvider = provider {
|
|
24
|
+
val hierarchyEdges = linkedMapOf<String, Set<String>>()
|
|
25
|
+
|
|
26
|
+
gradle.rootProject.allprojects.forEach { project ->
|
|
27
|
+
val affectedChildren = mutableSetOf<String>()
|
|
28
|
+
|
|
29
|
+
// Recursively collect all subprojects
|
|
30
|
+
fun collectSubprojects(parent: org.gradle.api.Project) {
|
|
31
|
+
parent.subprojects.forEach { child ->
|
|
32
|
+
affectedChildren.add(child.path)
|
|
33
|
+
collectSubprojects(child)
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
collectSubprojects(project)
|
|
38
|
+
hierarchyEdges[project.path] = affectedChildren.toSet()
|
|
39
|
+
}
|
|
40
|
+
hierarchyEdges
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
// Capture direct project dependencies at configuration time
|
|
44
|
+
val dependencyDepsProvider = provider {
|
|
45
|
+
val dependencyEdges = linkedMapOf<String, Set<String>>()
|
|
46
|
+
|
|
47
|
+
gradle.rootProject.allprojects.forEach { project ->
|
|
48
|
+
val directDeps = mutableSetOf<String>()
|
|
49
|
+
|
|
50
|
+
project.configurations.forEach { config ->
|
|
51
|
+
// Check regular dependencies
|
|
52
|
+
config.dependencies.forEach { dep ->
|
|
53
|
+
if (dep is ProjectDependency) {
|
|
54
|
+
directDeps.add(dep.dependencyProject.path)
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
// Check dependency constraints (platform/BOM imports)
|
|
59
|
+
config.dependencyConstraints.forEach { constraint ->
|
|
60
|
+
// Constraints reference projects by group:name, need to resolve to project path
|
|
61
|
+
val constraintProject = gradle.rootProject.allprojects.find { proj ->
|
|
62
|
+
proj.group.toString() == constraint.group && proj.name == constraint.name
|
|
63
|
+
}
|
|
64
|
+
constraintProject?.let { directDeps.add(it.path) }
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
dependencyEdges[project.path] = directDeps.toSet()
|
|
69
|
+
}
|
|
70
|
+
dependencyEdges
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
// Capture project metadata at configuration time
|
|
74
|
+
val projectDataProvider = provider {
|
|
75
|
+
val projectData = linkedMapOf<String, Map<String, Any?>>()
|
|
76
|
+
|
|
77
|
+
gradle.rootProject.allprojects.forEach { project ->
|
|
78
|
+
val relativePath = gradle.rootProject.projectDir.toPath().relativize(project.projectDir.toPath()).toString()
|
|
79
|
+
val path = if (relativePath.isEmpty()) "." else relativePath
|
|
80
|
+
val version = if (project.version == "unspecified") null else project.version
|
|
81
|
+
val type = if (project == gradle.rootProject) "root" else "module"
|
|
82
|
+
val versionPropertyKey = project.qualifiedVersionProperty()
|
|
83
|
+
val versionFromProperty = project.findProperty(versionPropertyKey) as? String
|
|
84
|
+
|
|
85
|
+
projectData[project.path] = mapOf(
|
|
86
|
+
"path" to path,
|
|
87
|
+
"version" to version,
|
|
88
|
+
"type" to type,
|
|
89
|
+
"name" to project.name,
|
|
90
|
+
"declaredVersion" to (versionFromProperty != null)
|
|
91
|
+
)
|
|
92
|
+
}
|
|
93
|
+
projectData
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
doLast {
|
|
97
|
+
val hierarchyMap = hierarchyDepsProvider.get()
|
|
98
|
+
val dependencyMap = dependencyDepsProvider.get()
|
|
99
|
+
val projectDataMap = projectDataProvider.get()
|
|
100
|
+
|
|
101
|
+
// Calculate directly affected modules only
|
|
102
|
+
val result = projectDataMap.keys.sorted().associateWith { projectPath ->
|
|
103
|
+
val projectInfo = projectDataMap.getValue(projectPath)
|
|
104
|
+
val affectedModules = mutableSetOf<String>()
|
|
105
|
+
|
|
106
|
+
// Add hierarchy children
|
|
107
|
+
hierarchyMap[projectPath]?.let { affectedModules.addAll(it) }
|
|
108
|
+
|
|
109
|
+
// Add projects that directly depend on this one
|
|
110
|
+
dependencyMap.forEach { (dependent, dependencies) ->
|
|
111
|
+
if (projectPath in dependencies) {
|
|
112
|
+
affectedModules.add(dependent)
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
mapOf(
|
|
117
|
+
"path" to projectInfo["path"],
|
|
118
|
+
"affectedModules" to affectedModules.toSortedSet(),
|
|
119
|
+
"version" to projectInfo["version"],
|
|
120
|
+
"type" to projectInfo["type"],
|
|
121
|
+
"name" to projectInfo["name"],
|
|
122
|
+
"declaredVersion" to projectInfo["declaredVersion"]
|
|
123
|
+
)
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
val generator = JsonGenerator.Options()
|
|
127
|
+
.excludeNulls()
|
|
128
|
+
.build()
|
|
129
|
+
|
|
130
|
+
println(JsonOutput.prettyPrint(generator.toJson(result)))
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
/**
|
|
135
|
+
* Convenience alias for printProjectInformation task.
|
|
136
|
+
* Usage: ./gradlew --init-script <path> structure
|
|
137
|
+
*/
|
|
138
|
+
tasks.register("structure") {
|
|
139
|
+
group = "help"
|
|
140
|
+
description = "Show project structure information"
|
|
141
|
+
dependsOn("printProjectInformation")
|
|
142
|
+
}
|
|
143
|
+
}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { AdapterIdentifier } from '../../../services/adapter-identifier.js';
|
|
2
|
+
/**
|
|
3
|
+
* Adapter identifier for Gradle-based projects.
|
|
4
|
+
* Detects Gradle projects by looking for gradle.properties, build.gradle(.kts), or settings.gradle(.kts) files.
|
|
5
|
+
*/
|
|
6
|
+
export declare class GradleAdapterIdentifier implements AdapterIdentifier {
|
|
7
|
+
/** Metadata describing this Gradle adapter (id: 'gradle', supports snapshots). */
|
|
8
|
+
readonly metadata: {
|
|
9
|
+
id: string;
|
|
10
|
+
capabilities: {
|
|
11
|
+
supportsSnapshots: boolean;
|
|
12
|
+
};
|
|
13
|
+
};
|
|
14
|
+
/**
|
|
15
|
+
* Determines whether the specified project is a Gradle project.
|
|
16
|
+
* @param projectRoot - Absolute path to the project root directory
|
|
17
|
+
* @returns True if any Gradle-specific file is found in the project root
|
|
18
|
+
*/
|
|
19
|
+
accept(projectRoot: string): Promise<boolean>;
|
|
20
|
+
}
|
|
21
|
+
//# sourceMappingURL=gradle-adapter-identifier.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gradle-adapter-identifier.d.ts","sourceRoot":"","sources":["../../../../src/adapters/gradle/services/gradle-adapter-identifier.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,yCAAyC,CAAC;AAe5E;;;GAGG;AACH,qBAAa,uBAAwB,YAAW,iBAAiB;IAC/D,kFAAkF;IAClF,QAAQ,CAAC,QAAQ;;;;;MAKf;IAEF;;;;OAIG;IACG,MAAM,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;CAkBpD"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import * as fs from 'fs/promises';
|
|
2
|
+
import { GRADLE_PROPERTIES_FILE, GRADLE_BUILD_FILE, GRADLE_BUILD_KTS_FILE, GRADLE_SETTINGS_FILE, GRADLE_SETTINGS_KTS_FILE, GRADLE_ID } from '../constants.js';
|
|
3
|
+
import { exists } from '../../../utils/file.js';
|
|
4
|
+
import { logger } from '../../../utils/logger.js';
|
|
5
|
+
/** List of file names that indicate a Gradle project. */
|
|
6
|
+
const GRADLE_FILES = [
|
|
7
|
+
GRADLE_PROPERTIES_FILE,
|
|
8
|
+
GRADLE_BUILD_FILE,
|
|
9
|
+
GRADLE_BUILD_KTS_FILE,
|
|
10
|
+
GRADLE_SETTINGS_FILE,
|
|
11
|
+
GRADLE_SETTINGS_KTS_FILE
|
|
12
|
+
];
|
|
13
|
+
/**
|
|
14
|
+
* Adapter identifier for Gradle-based projects.
|
|
15
|
+
* Detects Gradle projects by looking for gradle.properties, build.gradle(.kts), or settings.gradle(.kts) files.
|
|
16
|
+
*/
|
|
17
|
+
export class GradleAdapterIdentifier {
|
|
18
|
+
/** Metadata describing this Gradle adapter (id: 'gradle', supports snapshots). */
|
|
19
|
+
metadata = {
|
|
20
|
+
id: GRADLE_ID,
|
|
21
|
+
capabilities: {
|
|
22
|
+
supportsSnapshots: true
|
|
23
|
+
}
|
|
24
|
+
};
|
|
25
|
+
/**
|
|
26
|
+
* Determines whether the specified project is a Gradle project.
|
|
27
|
+
* @param projectRoot - Absolute path to the project root directory
|
|
28
|
+
* @returns True if any Gradle-specific file is found in the project root
|
|
29
|
+
*/
|
|
30
|
+
async accept(projectRoot) {
|
|
31
|
+
// Check if project root directory exists
|
|
32
|
+
const projectRootExists = await exists(projectRoot);
|
|
33
|
+
if (!projectRootExists) {
|
|
34
|
+
// Log for debugging and return false immediately
|
|
35
|
+
logger.debug(`Project root does not exist: ${projectRoot}`);
|
|
36
|
+
return false;
|
|
37
|
+
}
|
|
38
|
+
// Read directory contents (only top-level files)
|
|
39
|
+
const files = await fs.readdir(projectRoot);
|
|
40
|
+
// Check if any known Gradle file is present in the directory
|
|
41
|
+
const hasGradleFile = GRADLE_FILES.some(file => files.includes(file));
|
|
42
|
+
return hasGradleFile;
|
|
43
|
+
}
|
|
44
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { ModuleDetector } from "../../../services/module-detector.js";
|
|
2
|
+
import { ModuleRegistry } from '../../../services/module-registry.js';
|
|
3
|
+
/**
|
|
4
|
+
* Module detector for Gradle-based projects.
|
|
5
|
+
* Executes Gradle to discover all modules and their dependencies, returning a ModuleRegistry.
|
|
6
|
+
*/
|
|
7
|
+
export declare class GradleModuleDetector implements ModuleDetector {
|
|
8
|
+
readonly repoRoot: string;
|
|
9
|
+
/** Absolute path to the repository root directory. */
|
|
10
|
+
constructor(repoRoot: string);
|
|
11
|
+
/**
|
|
12
|
+
* Detects and catalogs all modules in the Gradle project.
|
|
13
|
+
* @returns ModuleRegistry containing all discovered modules and their relationships
|
|
14
|
+
* @throws {Error} If Gradle execution fails or project information cannot be parsed
|
|
15
|
+
*/
|
|
16
|
+
detect(): Promise<ModuleRegistry>;
|
|
17
|
+
}
|
|
18
|
+
//# sourceMappingURL=gradle-module-detector.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gradle-module-detector.d.ts","sourceRoot":"","sources":["../../../../src/adapters/gradle/services/gradle-module-detector.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,sCAAsC,CAAC;AACtE,OAAO,EAAE,cAAc,EAAE,MAAM,sCAAsC,CAAC;AAMtE;;;GAGG;AACH,qBAAa,oBAAqB,YAAW,cAAc;IAE7C,QAAQ,CAAC,QAAQ,EAAE,MAAM;IADrC,sDAAsD;gBACjC,QAAQ,EAAE,MAAM;IAErC;;;;OAIG;IACG,MAAM,IAAI,OAAO,CAAC,cAAc,CAAC;CAUxC"}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { ModuleRegistry } from '../../../services/module-registry.js';
|
|
2
|
+
import { getRawProjectInformation, getProjectInformation } from '../gradle-project-information.js';
|
|
3
|
+
/**
|
|
4
|
+
* Module detector for Gradle-based projects.
|
|
5
|
+
* Executes Gradle to discover all modules and their dependencies, returning a ModuleRegistry.
|
|
6
|
+
*/
|
|
7
|
+
export class GradleModuleDetector {
|
|
8
|
+
repoRoot;
|
|
9
|
+
/** Absolute path to the repository root directory. */
|
|
10
|
+
constructor(repoRoot) {
|
|
11
|
+
this.repoRoot = repoRoot;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Detects and catalogs all modules in the Gradle project.
|
|
15
|
+
* @returns ModuleRegistry containing all discovered modules and their relationships
|
|
16
|
+
* @throws {Error} If Gradle execution fails or project information cannot be parsed
|
|
17
|
+
*/
|
|
18
|
+
async detect() {
|
|
19
|
+
// Step 1: Execute Gradle and collect raw project structure data
|
|
20
|
+
const rawProjectInformation = await getRawProjectInformation(this.repoRoot);
|
|
21
|
+
// Step 2: Parse and transform raw data into structured module information
|
|
22
|
+
const projectInformation = getProjectInformation(rawProjectInformation);
|
|
23
|
+
// Step 3: Create a registry for efficient module access and querying
|
|
24
|
+
return new ModuleRegistry(projectInformation);
|
|
25
|
+
}
|
|
26
|
+
}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { ModuleSystemFactory } from "../../../services/module-system-factory.js";
|
|
2
|
+
import { ModuleDetector } from "../../../services/module-detector.js";
|
|
3
|
+
import { VersionUpdateStrategy } from "../../../services/version-update-strategy.js";
|
|
4
|
+
/**
|
|
5
|
+
* Factory for creating Gradle-specific module system components.
|
|
6
|
+
* Creates module detector and version update strategy instances.
|
|
7
|
+
*/
|
|
8
|
+
export declare class GradleModuleSystemFactory implements ModuleSystemFactory {
|
|
9
|
+
private readonly repoRoot;
|
|
10
|
+
/** Absolute path to the repository root directory. */
|
|
11
|
+
constructor(repoRoot: string);
|
|
12
|
+
/**
|
|
13
|
+
* Creates a Gradle-specific module detector.
|
|
14
|
+
* @returns GradleModuleDetector instance configured with the repository root
|
|
15
|
+
*/
|
|
16
|
+
createDetector(): ModuleDetector;
|
|
17
|
+
/**
|
|
18
|
+
* Creates a Gradle-specific version update strategy.
|
|
19
|
+
* @returns GradleVersionUpdateStrategy instance configured with the repository root
|
|
20
|
+
*/
|
|
21
|
+
createVersionUpdateStrategy(): VersionUpdateStrategy;
|
|
22
|
+
}
|
|
23
|
+
//# sourceMappingURL=gradle-module-system-factory.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gradle-module-system-factory.d.ts","sourceRoot":"","sources":["../../../../src/adapters/gradle/services/gradle-module-system-factory.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,MAAM,4CAA4C,CAAC;AACjF,OAAO,EAAE,cAAc,EAAE,MAAM,sCAAsC,CAAC;AACtE,OAAO,EAAE,qBAAqB,EAAE,MAAM,8CAA8C,CAAC;AAIrF;;;GAGG;AACH,qBAAa,yBAA0B,YAAW,mBAAmB;IAEvD,OAAO,CAAC,QAAQ,CAAC,QAAQ;IADrC,sDAAsD;gBACzB,QAAQ,EAAE,MAAM;IAE7C;;;OAGG;IACH,cAAc,IAAI,cAAc;IAIhC;;;OAGG;IACH,2BAA2B,IAAI,qBAAqB;CAGrD"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { GradleModuleDetector } from './gradle-module-detector.js';
|
|
2
|
+
import { GradleVersionUpdateStrategy } from './gradle-version-update-strategy.js';
|
|
3
|
+
/**
|
|
4
|
+
* Factory for creating Gradle-specific module system components.
|
|
5
|
+
* Creates module detector and version update strategy instances.
|
|
6
|
+
*/
|
|
7
|
+
export class GradleModuleSystemFactory {
|
|
8
|
+
repoRoot;
|
|
9
|
+
/** Absolute path to the repository root directory. */
|
|
10
|
+
constructor(repoRoot) {
|
|
11
|
+
this.repoRoot = repoRoot;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Creates a Gradle-specific module detector.
|
|
15
|
+
* @returns GradleModuleDetector instance configured with the repository root
|
|
16
|
+
*/
|
|
17
|
+
createDetector() {
|
|
18
|
+
return new GradleModuleDetector(this.repoRoot);
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Creates a Gradle-specific version update strategy.
|
|
22
|
+
* @returns GradleVersionUpdateStrategy instance configured with the repository root
|
|
23
|
+
*/
|
|
24
|
+
createVersionUpdateStrategy() {
|
|
25
|
+
return new GradleVersionUpdateStrategy(this.repoRoot);
|
|
26
|
+
}
|
|
27
|
+
}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { VersionUpdateStrategy } from "../../../services/version-update-strategy.js";
|
|
2
|
+
/**
|
|
3
|
+
* Gradle-specific implementation for version update operations.
|
|
4
|
+
* Updates module versions by modifying gradle.properties file.
|
|
5
|
+
*/
|
|
6
|
+
export declare class GradleVersionUpdateStrategy implements VersionUpdateStrategy {
|
|
7
|
+
/** Absolute path to the gradle.properties file. */
|
|
8
|
+
private readonly versionFilePath;
|
|
9
|
+
/**
|
|
10
|
+
* Creates a new Gradle version update strategy.
|
|
11
|
+
* @param repoRoot - Absolute path to the repository root directory
|
|
12
|
+
*/
|
|
13
|
+
constructor(repoRoot: string);
|
|
14
|
+
/**
|
|
15
|
+
* Writes version updates for multiple modules to gradle.properties.
|
|
16
|
+
* @param moduleVersions - Map of module IDs to new version strings
|
|
17
|
+
* @throws {Error} If the file cannot be read or written
|
|
18
|
+
*/
|
|
19
|
+
writeVersionUpdates(moduleVersions: Map<string, string>): Promise<void>;
|
|
20
|
+
}
|
|
21
|
+
//# sourceMappingURL=gradle-version-update-strategy.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gradle-version-update-strategy.d.ts","sourceRoot":"","sources":["../../../../src/adapters/gradle/services/gradle-version-update-strategy.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,qBAAqB,EAAE,MAAM,8CAA8C,CAAC;AAKrF;;;GAGG;AACH,qBAAa,2BAA4B,YAAW,qBAAqB;IACvE,mDAAmD;IACnD,OAAO,CAAC,QAAQ,CAAC,eAAe,CAAS;IAEzC;;;OAGG;gBACS,QAAQ,EAAE,MAAM;IAI5B;;;;OAIG;IACG,mBAAmB,CAAC,cAAc,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC;CAc9E"}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import { join } from 'path';
|
|
2
|
+
import { moduleIdToVersionPropertyName } from '../gradle-properties.js';
|
|
3
|
+
import { upsertProperties } from '../../../utils/properties.js';
|
|
4
|
+
import { GRADLE_PROPERTIES_FILE } from '../constants.js';
|
|
5
|
+
/**
|
|
6
|
+
* Gradle-specific implementation for version update operations.
|
|
7
|
+
* Updates module versions by modifying gradle.properties file.
|
|
8
|
+
*/
|
|
9
|
+
export class GradleVersionUpdateStrategy {
|
|
10
|
+
/** Absolute path to the gradle.properties file. */
|
|
11
|
+
versionFilePath;
|
|
12
|
+
/**
|
|
13
|
+
* Creates a new Gradle version update strategy.
|
|
14
|
+
* @param repoRoot - Absolute path to the repository root directory
|
|
15
|
+
*/
|
|
16
|
+
constructor(repoRoot) {
|
|
17
|
+
this.versionFilePath = join(repoRoot, GRADLE_PROPERTIES_FILE);
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* Writes version updates for multiple modules to gradle.properties.
|
|
21
|
+
* @param moduleVersions - Map of module IDs to new version strings
|
|
22
|
+
* @throws {Error} If the file cannot be read or written
|
|
23
|
+
*/
|
|
24
|
+
async writeVersionUpdates(moduleVersions) {
|
|
25
|
+
// Convert module IDs to property names
|
|
26
|
+
// Example: ':app' → 'app.version', ':' → 'version'
|
|
27
|
+
const propertyUpdates = new Map();
|
|
28
|
+
for (const [moduleId, versionString] of moduleVersions) {
|
|
29
|
+
const propertyName = moduleIdToVersionPropertyName(moduleId);
|
|
30
|
+
propertyUpdates.set(propertyName, versionString);
|
|
31
|
+
}
|
|
32
|
+
// Write all properties to gradle.properties file in one atomic operation
|
|
33
|
+
// This ensures consistency and prevents partial updates
|
|
34
|
+
await upsertProperties(this.versionFilePath, propertyUpdates);
|
|
35
|
+
}
|
|
36
|
+
}
|