gitpt 1.6.1 → 1.7.2
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 +34 -167
- package/dist/commands/commit/commitFlags.js +7 -0
- package/dist/commands/commit/context/buildPrompt.js +13 -10
- package/dist/commands/commit/context/summaryPrompt.js +5 -2
- package/dist/commands/commit/context/systemPrompt.js +4 -1
- package/dist/commands/commit/context/userPrompt.js +4 -1
- package/dist/commands/commit/generateCommitMessage.js +14 -17
- package/dist/commands/commit/index.js +186 -179
- package/dist/commands/commit/summarizeDiff.js +183 -162
- package/dist/commands/config.js +24 -9
- package/dist/commands/hook/index.js +68 -0
- package/dist/commands/middleware/capabilitiesMiddleware/ghCapability.js +20 -20
- package/dist/commands/middleware/capabilitiesMiddleware/gitCapability.js +13 -10
- package/dist/commands/middleware/capabilitiesMiddleware/index.js +12 -11
- package/dist/commands/middleware/hasStagedChangesMiddleware.js +9 -6
- package/dist/commands/middleware/setupMiddleware/defaultModels.js +14 -10
- package/dist/commands/middleware/setupMiddleware/index.js +65 -71
- package/dist/commands/model.js +7 -4
- package/dist/commands/passthroughArgs.js +11 -0
- package/dist/commands/pr/context/systemPrompt.js +4 -1
- package/dist/commands/pr/context/userPrompt.js +4 -1
- package/dist/commands/pr/generatePRDetails.js +24 -23
- package/dist/commands/pr/getPRContext.js +37 -62
- package/dist/commands/pr/index.js +57 -62
- package/dist/commands/reset.js +23 -23
- package/dist/commands/review/index.js +31 -0
- package/dist/commands/setup.js +38 -13
- package/dist/config.js +63 -60
- package/dist/index.js +30 -67
- package/dist/llm/budget.js +10 -0
- package/dist/llm/index.js +12 -7
- package/dist/llm/providers/anthropic/index.js +30 -30
- package/dist/llm/providers/apiKey.js +36 -35
- package/dist/llm/providers/apple/client.js +73 -83
- package/dist/llm/providers/apple/index.js +64 -72
- package/dist/llm/providers/apple/models.js +27 -19
- package/dist/llm/providers/base.js +36 -36
- package/dist/llm/providers/local/index.js +79 -91
- package/dist/llm/providers/openai/index.js +19 -16
- package/dist/llm/providers/openaiCompatible.js +59 -62
- package/dist/llm/providers/openrouter/index.js +18 -15
- package/dist/llm/registry.js +30 -34
- package/dist/llm/setup/getAvailableModels.js +15 -9
- package/dist/llm/setup/selectModel.js +36 -44
- package/dist/llm/tokenCount.js +4 -3
- package/dist/package.js +67 -0
- package/dist/services/gh/createPullRequest.js +38 -58
- package/dist/services/gh/index.js +6 -3
- package/dist/services/gh/isAvailable.js +10 -8
- package/dist/services/git/executeGitAdd.js +11 -12
- package/dist/services/git/executeGitCommit.js +10 -11
- package/dist/services/git/getAmendChanges.js +23 -0
- package/dist/services/git/getChangedFiles.js +28 -61
- package/dist/services/git/getCommitsSinceBaseBranch.js +28 -56
- package/dist/services/git/getCurrentBranch.js +10 -8
- package/dist/services/git/getDefaultBranch.js +35 -60
- package/dist/services/git/getStagedChanges.js +10 -8
- package/dist/services/git/getStagedFiles.js +10 -9
- package/dist/services/git/hasStagedChanges.js +9 -8
- package/dist/services/git/index.js +17 -12
- package/dist/services/git/isAvailable.js +10 -8
- package/dist/services/git/isGitRepository.js +10 -8
- package/dist/utils/commitlint.js +97 -135
- package/dist/utils/formatBaseURL.js +7 -6
- package/dist/utils/maskApiKey.js +6 -7
- package/package.json +14 -4
- package/dist/commands/commit/context/buildPrompt.d.ts +0 -4
- package/dist/commands/commit/context/summaryPrompt.d.ts +0 -2
- package/dist/commands/commit/context/systemPrompt.d.ts +0 -1
- package/dist/commands/commit/context/userPrompt.d.ts +0 -1
- package/dist/commands/commit/generateCommitMessage.d.ts +0 -1
- package/dist/commands/commit/index.d.ts +0 -7
- package/dist/commands/commit/summarizeDiff.d.ts +0 -1
- package/dist/commands/config.d.ts +0 -1
- package/dist/commands/middleware/capabilitiesMiddleware/ghCapability.d.ts +0 -1
- package/dist/commands/middleware/capabilitiesMiddleware/gitCapability.d.ts +0 -1
- package/dist/commands/middleware/capabilitiesMiddleware/index.d.ts +0 -3
- package/dist/commands/middleware/hasStagedChangesMiddleware.d.ts +0 -1
- package/dist/commands/middleware/setupMiddleware/defaultModels.d.ts +0 -8
- package/dist/commands/middleware/setupMiddleware/index.d.ts +0 -4
- package/dist/commands/model.d.ts +0 -1
- package/dist/commands/pr/context/systemPrompt.d.ts +0 -1
- package/dist/commands/pr/context/userPrompt.d.ts +0 -1
- package/dist/commands/pr/generatePRDetails.d.ts +0 -4
- package/dist/commands/pr/getPRContext.d.ts +0 -1
- package/dist/commands/pr/index.d.ts +0 -10
- package/dist/commands/reset.d.ts +0 -3
- package/dist/commands/setup.d.ts +0 -3
- package/dist/config.d.ts +0 -14
- package/dist/index.d.ts +0 -2
- package/dist/llm/client.d.ts +0 -24
- package/dist/llm/client.js +0 -1
- package/dist/llm/index.d.ts +0 -6
- package/dist/llm/providers/anthropic/index.d.ts +0 -9
- package/dist/llm/providers/apiKey.d.ts +0 -3
- package/dist/llm/providers/apple/client.d.ts +0 -3
- package/dist/llm/providers/apple/index.d.ts +0 -13
- package/dist/llm/providers/apple/models.d.ts +0 -14
- package/dist/llm/providers/base.d.ts +0 -30
- package/dist/llm/providers/local/index.d.ts +0 -11
- package/dist/llm/providers/openai/index.d.ts +0 -10
- package/dist/llm/providers/openaiCompatible.d.ts +0 -15
- package/dist/llm/providers/openrouter/index.d.ts +0 -9
- package/dist/llm/registry.d.ts +0 -8
- package/dist/llm/setup/getAvailableModels.d.ts +0 -5
- package/dist/llm/setup/selectModel.d.ts +0 -5
- package/dist/llm/setup/types.d.ts +0 -13
- package/dist/llm/setup/types.js +0 -1
- package/dist/llm/tokenCount.d.ts +0 -3
- package/dist/services/gh/createPullRequest.d.ts +0 -1
- package/dist/services/gh/index.d.ts +0 -4
- package/dist/services/gh/isAvailable.d.ts +0 -1
- package/dist/services/git/executeGitAdd.d.ts +0 -1
- package/dist/services/git/executeGitCommit.d.ts +0 -1
- package/dist/services/git/getChangedFiles.d.ts +0 -1
- package/dist/services/git/getCommitsSinceBaseBranch.d.ts +0 -1
- package/dist/services/git/getCurrentBranch.d.ts +0 -1
- package/dist/services/git/getDefaultBranch.d.ts +0 -1
- package/dist/services/git/getStagedChanges.d.ts +0 -1
- package/dist/services/git/getStagedFiles.d.ts +0 -1
- package/dist/services/git/hasStagedChanges.d.ts +0 -1
- package/dist/services/git/index.d.ts +0 -13
- package/dist/services/git/isAvailable.d.ts +0 -1
- package/dist/services/git/isGitRepository.d.ts +0 -1
- package/dist/utils/commitlint.d.ts +0 -25
- package/dist/utils/formatBaseURL.d.ts +0 -1
- package/dist/utils/maskApiKey.d.ts +0 -1
package/dist/llm/registry.js
CHANGED
|
@@ -1,43 +1,39 @@
|
|
|
1
1
|
import { getConfig } from "../config.js";
|
|
2
|
-
import { AnthropicProvider } from "./providers/anthropic/index.js";
|
|
3
2
|
import { getApiKey } from "./providers/apiKey.js";
|
|
3
|
+
import { AnthropicProvider } from "./providers/anthropic/index.js";
|
|
4
4
|
import { AppleProvider } from "./providers/apple/index.js";
|
|
5
5
|
import { LocalProvider } from "./providers/local/index.js";
|
|
6
6
|
import { OpenAIProvider } from "./providers/openai/index.js";
|
|
7
7
|
import { OpenRouterProvider } from "./providers/openrouter/index.js";
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
8
|
+
//#region src/llm/registry.ts
|
|
9
|
+
var PROVIDERS = [
|
|
10
|
+
AppleProvider,
|
|
11
|
+
OpenRouterProvider,
|
|
12
|
+
OpenAIProvider,
|
|
13
|
+
AnthropicProvider,
|
|
14
|
+
LocalProvider
|
|
14
15
|
];
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
}
|
|
22
|
-
return new ProviderImpl(model ?? "");
|
|
16
|
+
var getProviderClass = (id) => PROVIDERS.find((p) => p.id === id);
|
|
17
|
+
var getProvider = () => {
|
|
18
|
+
const { provider, model } = getConfig();
|
|
19
|
+
const ProviderImpl = getProviderClass(provider);
|
|
20
|
+
if (!ProviderImpl) throw new Error(`Unknown provider: ${provider ?? "(none)"}. Run "gitpt setup".`);
|
|
21
|
+
return new ProviderImpl(model ?? "");
|
|
23
22
|
};
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
}
|
|
39
|
-
if (!model) {
|
|
40
|
-
errors.push("Model is required.");
|
|
41
|
-
}
|
|
42
|
-
return { isValid: errors.length === 0, errors };
|
|
23
|
+
var validateConfig = () => {
|
|
24
|
+
const { provider, customLLMEndpoint, model } = getConfig();
|
|
25
|
+
const errors = [];
|
|
26
|
+
const spec = getProviderClass(provider);
|
|
27
|
+
if (!spec) errors.push("No provider configured. Run 'gitpt setup'.");
|
|
28
|
+
else {
|
|
29
|
+
if (spec.requiresApiKey && !getApiKey()) errors.push(`API key is required for ${spec.label}.`);
|
|
30
|
+
if (spec.requiresEndpoint && !customLLMEndpoint) errors.push(`Custom endpoint is required for ${spec.label}.`);
|
|
31
|
+
}
|
|
32
|
+
if (!model) errors.push("Model is required.");
|
|
33
|
+
return {
|
|
34
|
+
isValid: errors.length === 0,
|
|
35
|
+
errors
|
|
36
|
+
};
|
|
43
37
|
};
|
|
38
|
+
//#endregion
|
|
39
|
+
export { PROVIDERS, getProvider, getProviderClass, validateConfig };
|
|
@@ -1,11 +1,17 @@
|
|
|
1
1
|
import { getLLMClient } from "../index.js";
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
2
|
+
//#region src/llm/setup/getAvailableModels.ts
|
|
3
|
+
var getAvailableModels = async (options) => {
|
|
4
|
+
const { baseURLOverride, apiKey } = options || {};
|
|
5
|
+
let modelsList = await getLLMClient({
|
|
6
|
+
baseURLOverride,
|
|
7
|
+
apiKey
|
|
8
|
+
}).models.list();
|
|
9
|
+
const modelsData = modelsList.data;
|
|
10
|
+
while (modelsList.hasNextPage()) {
|
|
11
|
+
modelsList = await modelsList.getNextPage();
|
|
12
|
+
modelsData.push(...modelsList.data);
|
|
13
|
+
}
|
|
14
|
+
return modelsData;
|
|
11
15
|
};
|
|
16
|
+
//#endregion
|
|
17
|
+
export { getAvailableModels };
|
|
@@ -1,48 +1,40 @@
|
|
|
1
1
|
import chalk from "chalk";
|
|
2
2
|
import inquirer from "inquirer";
|
|
3
|
+
//#region src/llm/setup/selectModel.ts
|
|
3
4
|
/**
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
{
|
|
38
|
-
type: "input",
|
|
39
|
-
name: "customModel",
|
|
40
|
-
message: "Enter model identifier:",
|
|
41
|
-
when: (answers) => answers.modelChoice === "custom",
|
|
42
|
-
validate: (input) => input ? true : "Model identifier is required",
|
|
43
|
-
},
|
|
44
|
-
]);
|
|
45
|
-
return answers.modelChoice === "custom"
|
|
46
|
-
? answers.customModel
|
|
47
|
-
: answers.modelChoice;
|
|
5
|
+
* Show a list of models to select from
|
|
6
|
+
*/
|
|
7
|
+
var selectModel = async (models, existingModel, notes) => {
|
|
8
|
+
const modelChoices = models.map((model) => ({
|
|
9
|
+
name: model.name ? model.context_length ? `${model.name} (Context: ${model.context_length})` : model.name : model.id,
|
|
10
|
+
value: model.id
|
|
11
|
+
}));
|
|
12
|
+
modelChoices.push({
|
|
13
|
+
name: "Other (specify model identifier)",
|
|
14
|
+
value: "custom"
|
|
15
|
+
});
|
|
16
|
+
const choices = [...modelChoices];
|
|
17
|
+
if (notes && notes.length > 0) {
|
|
18
|
+
choices.push(new inquirer.Separator(" "));
|
|
19
|
+
for (const note of notes) choices.push(new inquirer.Separator(chalk.gray(note)));
|
|
20
|
+
}
|
|
21
|
+
const answers = await inquirer.prompt([{
|
|
22
|
+
type: "list",
|
|
23
|
+
name: "modelChoice",
|
|
24
|
+
message: "Select an AI model:",
|
|
25
|
+
choices,
|
|
26
|
+
default: () => {
|
|
27
|
+
const currentIndex = modelChoices.findIndex((choice) => choice.value === existingModel);
|
|
28
|
+
return currentIndex >= 0 ? currentIndex : 0;
|
|
29
|
+
}
|
|
30
|
+
}, {
|
|
31
|
+
type: "input",
|
|
32
|
+
name: "customModel",
|
|
33
|
+
message: "Enter model identifier:",
|
|
34
|
+
when: (answers) => answers.modelChoice === "custom",
|
|
35
|
+
validate: (input) => input ? true : "Model identifier is required"
|
|
36
|
+
}]);
|
|
37
|
+
return answers.modelChoice === "custom" ? answers.customModel : answers.modelChoice;
|
|
48
38
|
};
|
|
39
|
+
//#endregion
|
|
40
|
+
export { selectModel };
|
package/dist/llm/tokenCount.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { getProvider } from "./registry.js";
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
2
|
+
//#region src/llm/tokenCount.ts
|
|
3
|
+
var countTokens = (text) => getProvider().countTokens(text);
|
|
4
|
+
//#endregion
|
|
5
|
+
export { countTokens };
|
package/dist/package.js
ADDED
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
var package_default = {
|
|
2
|
+
name: "gitpt",
|
|
3
|
+
version: "1.7.2",
|
|
4
|
+
description: "CLI tool that helps you write commit messages & pull request descriptions using AI",
|
|
5
|
+
main: "dist/index.js",
|
|
6
|
+
type: "module",
|
|
7
|
+
bin: { "gitpt": "dist/index.js" },
|
|
8
|
+
files: [
|
|
9
|
+
"dist/**/*",
|
|
10
|
+
"README.md",
|
|
11
|
+
"LICENSE"
|
|
12
|
+
],
|
|
13
|
+
scripts: {
|
|
14
|
+
"typecheck": "tsc --noEmit",
|
|
15
|
+
"lint": "oxlint",
|
|
16
|
+
"build": "vite build",
|
|
17
|
+
"test": "vitest run",
|
|
18
|
+
"test:watch": "vitest",
|
|
19
|
+
"test:apple": "npm run build && node tests/apple-foundation-models/run.mjs",
|
|
20
|
+
"bench:apple": "npm run build && node tests/apple-foundation-models/benchmark.mjs",
|
|
21
|
+
"bench:local": "npm run build && node tests/local-model/run.mjs",
|
|
22
|
+
"bench:all": "npm run build && node tests/run-all.mjs",
|
|
23
|
+
"check:prompt": "npm run build && node tests/snapshots/check.mjs",
|
|
24
|
+
"build:demo": "node scripts/build-demo.mjs",
|
|
25
|
+
"prepublishOnly": "npm run build"
|
|
26
|
+
},
|
|
27
|
+
repository: {
|
|
28
|
+
"type": "git",
|
|
29
|
+
"url": "git+https://github.com/bartaxyz/GitPT.git"
|
|
30
|
+
},
|
|
31
|
+
keywords: [
|
|
32
|
+
"git",
|
|
33
|
+
"ai",
|
|
34
|
+
"prompt"
|
|
35
|
+
],
|
|
36
|
+
author: "@bartaxyz",
|
|
37
|
+
license: "MIT",
|
|
38
|
+
bugs: { "url": "https://github.com/bartaxyz/GitPT/issues" },
|
|
39
|
+
homepage: "https://github.com/bartaxyz/GitPT#readme",
|
|
40
|
+
devDependencies: {
|
|
41
|
+
"@types/configstore": "^6.0.2",
|
|
42
|
+
"@types/inquirer": "^9.0.7",
|
|
43
|
+
"@types/node": "^22.14.1",
|
|
44
|
+
"@types/node-fetch": "^2.6.12",
|
|
45
|
+
"ffmpeg-static": "^5.3.0",
|
|
46
|
+
"oxlint": "^1.71.0",
|
|
47
|
+
"pngjs": "^7.0.0",
|
|
48
|
+
"tsc-alias": "^1.8.16",
|
|
49
|
+
"typescript": "^5.8.3",
|
|
50
|
+
"vite": "^8.1.0",
|
|
51
|
+
"vitest": "^4.1.9"
|
|
52
|
+
},
|
|
53
|
+
dependencies: {
|
|
54
|
+
"@commitlint/cli": "^19.8.1",
|
|
55
|
+
"@commitlint/config-conventional": "^19.8.1",
|
|
56
|
+
"@commitlint/load": "^19.8.1",
|
|
57
|
+
"chalk": "^5.4.1",
|
|
58
|
+
"commander": "^13.1.0",
|
|
59
|
+
"configstore": "^7.0.0",
|
|
60
|
+
"inquirer": "^12.5.2",
|
|
61
|
+
"node-fetch": "^3.3.2",
|
|
62
|
+
"openai": "^4.100.0",
|
|
63
|
+
"ora": "^8.2.0"
|
|
64
|
+
}
|
|
65
|
+
};
|
|
66
|
+
//#endregion
|
|
67
|
+
export { package_default as default };
|
|
@@ -1,63 +1,43 @@
|
|
|
1
1
|
import chalk from "chalk";
|
|
2
2
|
import { execSync } from "child_process";
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
execSync(`cat > "${tempFilePath}" << 'GITPT_EOF'
|
|
3
|
+
//#region src/services/gh/createPullRequest.ts
|
|
4
|
+
var createPullRequest = (title, body, baseBranch, draft) => {
|
|
5
|
+
const draftFlag = draft ? "--draft" : "";
|
|
6
|
+
try {
|
|
7
|
+
console.log(chalk.blue(`Creating pull request to ${baseBranch}...`));
|
|
8
|
+
const tempFilePath = `/tmp/gitpt-pr-body-${Date.now()}.md`;
|
|
9
|
+
try {
|
|
10
|
+
execSync(`cat > "${tempFilePath}" << 'GITPT_EOF'
|
|
12
11
|
${body}
|
|
13
12
|
GITPT_EOF`);
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
finally {
|
|
43
|
-
// Clean up temporary file
|
|
44
|
-
try {
|
|
45
|
-
execSync(`rm -f "${tempFilePath}"`);
|
|
46
|
-
}
|
|
47
|
-
catch (e) {
|
|
48
|
-
// Ignore cleanup errors
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
}
|
|
52
|
-
catch (error) {
|
|
53
|
-
if (error instanceof Error && error.message.includes("timeout")) {
|
|
54
|
-
console.error(chalk.red("Error: GitHub CLI command timed out after 60 seconds."));
|
|
55
|
-
console.log(chalk.yellow("You may need to create the PR manually using:"));
|
|
56
|
-
console.log(chalk.yellow(`gh pr create --title "${title}" --base "${baseBranch}" ${draftFlag}`));
|
|
57
|
-
}
|
|
58
|
-
else {
|
|
59
|
-
console.error(chalk.red("Error creating pull request:"), error);
|
|
60
|
-
}
|
|
61
|
-
throw new Error("Failed to create pull request");
|
|
62
|
-
}
|
|
13
|
+
let repoUrlArg = "";
|
|
14
|
+
try {
|
|
15
|
+
const repoUrl = execSync("git config --get remote.origin.url").toString().trim();
|
|
16
|
+
if (repoUrl) repoUrlArg = `--repo "${repoUrl}"`;
|
|
17
|
+
} catch (e) {}
|
|
18
|
+
const command = `gh pr create --title "${title.replace(/"/g, "\\\"")}" --body-file "${tempFilePath}" --base "${baseBranch}" ${draftFlag} ${repoUrlArg}`;
|
|
19
|
+
console.log(chalk.gray("Running GitHub PR creation command..."));
|
|
20
|
+
console.log(chalk.gray(`Using base branch: ${baseBranch}`));
|
|
21
|
+
console.log(chalk.gray("Executing command with 60s timeout:"));
|
|
22
|
+
const result = execSync(command, {
|
|
23
|
+
stdio: "pipe",
|
|
24
|
+
timeout: 6e4
|
|
25
|
+
}).toString();
|
|
26
|
+
console.log(result);
|
|
27
|
+
console.log(chalk.green("✓ Pull request created successfully"));
|
|
28
|
+
} finally {
|
|
29
|
+
try {
|
|
30
|
+
execSync(`rm -f "${tempFilePath}"`);
|
|
31
|
+
} catch (e) {}
|
|
32
|
+
}
|
|
33
|
+
} catch (error) {
|
|
34
|
+
if (error instanceof Error && error.message.includes("timeout")) {
|
|
35
|
+
console.error(chalk.red("Error: GitHub CLI command timed out after 60 seconds."));
|
|
36
|
+
console.log(chalk.yellow("You may need to create the PR manually using:"));
|
|
37
|
+
console.log(chalk.yellow(`gh pr create --title "${title}" --base "${baseBranch}" ${draftFlag}`));
|
|
38
|
+
} else console.error(chalk.red("Error creating pull request:"), error);
|
|
39
|
+
throw new Error("Failed to create pull request");
|
|
40
|
+
}
|
|
63
41
|
};
|
|
42
|
+
//#endregion
|
|
43
|
+
export { createPullRequest };
|
|
@@ -1,6 +1,9 @@
|
|
|
1
1
|
import { createPullRequest } from "./createPullRequest.js";
|
|
2
2
|
import { isAvailable } from "./isAvailable.js";
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
3
|
+
//#region src/services/gh/index.ts
|
|
4
|
+
var gh = {
|
|
5
|
+
createPullRequest,
|
|
6
|
+
isAvailable
|
|
6
7
|
};
|
|
8
|
+
//#endregion
|
|
9
|
+
export { gh };
|
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
import { execSync } from "child_process";
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
2
|
+
//#region src/services/gh/isAvailable.ts
|
|
3
|
+
var isAvailable = () => {
|
|
4
|
+
try {
|
|
5
|
+
execSync("gh --version", { stdio: "ignore" });
|
|
6
|
+
return true;
|
|
7
|
+
} catch (error) {
|
|
8
|
+
return false;
|
|
9
|
+
}
|
|
10
10
|
};
|
|
11
|
+
//#endregion
|
|
12
|
+
export { isAvailable };
|
|
@@ -1,15 +1,14 @@
|
|
|
1
1
|
import chalk from "chalk";
|
|
2
2
|
import { execSync } from "child_process";
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
console.error(chalk.red("Error adding files:"), error);
|
|
13
|
-
throw new Error("Failed to add files to git");
|
|
14
|
-
}
|
|
3
|
+
//#region src/services/git/executeGitAdd.ts
|
|
4
|
+
var executeGitAdd = (files) => {
|
|
5
|
+
try {
|
|
6
|
+
if (files.length === 0) throw new Error("No files specified");
|
|
7
|
+
execSync(`git add ${files.join(" ")}`, { stdio: "inherit" });
|
|
8
|
+
} catch (error) {
|
|
9
|
+
console.error(chalk.red("Error adding files:"), error);
|
|
10
|
+
throw new Error("Failed to add files to git");
|
|
11
|
+
}
|
|
15
12
|
};
|
|
13
|
+
//#endregion
|
|
14
|
+
export { executeGitAdd };
|
|
@@ -1,12 +1,11 @@
|
|
|
1
|
-
import
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
console.error(chalk.red("Error committing changes:"), error);
|
|
10
|
-
throw new Error("Failed to commit changes");
|
|
11
|
-
}
|
|
1
|
+
import { spawnSync } from "child_process";
|
|
2
|
+
//#region src/services/git/executeGitCommit.ts
|
|
3
|
+
var executeGitCommit = (message, additionalArgs = []) => {
|
|
4
|
+
if (spawnSync("git", [
|
|
5
|
+
"commit",
|
|
6
|
+
...message === null ? [] : ["-m", message],
|
|
7
|
+
...additionalArgs
|
|
8
|
+
], { stdio: "inherit" }).status !== 0) throw new Error("Failed to commit changes");
|
|
12
9
|
};
|
|
10
|
+
//#endregion
|
|
11
|
+
export { executeGitCommit };
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import chalk from "chalk";
|
|
2
|
+
import { execSync } from "child_process";
|
|
3
|
+
//#region src/services/git/getAmendChanges.ts
|
|
4
|
+
/**
|
|
5
|
+
* The content of the commit being amended: the staged tree compared to the
|
|
6
|
+
* commit before HEAD — so a plain reword still has a diff (even with nothing
|
|
7
|
+
* staged), and any new staged changes are folded in. Falls back to the staged
|
|
8
|
+
* diff when there is no previous commit (amending the very first commit).
|
|
9
|
+
*/
|
|
10
|
+
var getAmendChanges = () => {
|
|
11
|
+
try {
|
|
12
|
+
return execSync("git diff --staged --function-context HEAD~1").toString();
|
|
13
|
+
} catch {
|
|
14
|
+
try {
|
|
15
|
+
return execSync("git diff --staged --function-context").toString();
|
|
16
|
+
} catch (error) {
|
|
17
|
+
console.error(chalk.red("Error getting amend changes:"), error);
|
|
18
|
+
throw new Error("Failed to get amend changes");
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
};
|
|
22
|
+
//#endregion
|
|
23
|
+
export { getAmendChanges };
|
|
@@ -1,64 +1,31 @@
|
|
|
1
1
|
import chalk from "chalk";
|
|
2
2
|
import { execSync } from "child_process";
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
// Method 3: Direct comparison with two dots
|
|
30
|
-
try {
|
|
31
|
-
const changedFiles = execSync(`git diff --name-only ${baseBranch}..HEAD`)
|
|
32
|
-
.toString()
|
|
33
|
-
.trim();
|
|
34
|
-
if (changedFiles) {
|
|
35
|
-
return changedFiles.split("\n").filter(Boolean);
|
|
36
|
-
}
|
|
37
|
-
}
|
|
38
|
-
catch (error) {
|
|
39
|
-
// Continue to next method
|
|
40
|
-
}
|
|
41
|
-
// Method 4: Get recently modified files
|
|
42
|
-
try {
|
|
43
|
-
console.log(chalk.yellow(`Could not determine changed files relative to ${baseBranch}, using recently modified files...`));
|
|
44
|
-
const changedFiles = execSync("git ls-files --modified --others --exclude-standard")
|
|
45
|
-
.toString()
|
|
46
|
-
.trim();
|
|
47
|
-
if (changedFiles) {
|
|
48
|
-
return changedFiles.split("\n").filter(Boolean);
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
catch (error) {
|
|
52
|
-
// Last resort
|
|
53
|
-
}
|
|
54
|
-
// Method 5: List all files in the repo as a last resort
|
|
55
|
-
try {
|
|
56
|
-
console.log(chalk.yellow("Using all tracked files as fallback..."));
|
|
57
|
-
const allFiles = execSync("git ls-files").toString().trim();
|
|
58
|
-
return allFiles.split("\n").filter(Boolean).slice(0, 50); // Limit to first 50 files
|
|
59
|
-
}
|
|
60
|
-
catch (error) {
|
|
61
|
-
console.error(chalk.red("Could not determine changed files."));
|
|
62
|
-
return [];
|
|
63
|
-
}
|
|
3
|
+
//#region src/services/git/getChangedFiles.ts
|
|
4
|
+
var getChangedFiles = (baseBranch) => {
|
|
5
|
+
try {
|
|
6
|
+
const changedFiles = execSync(`git diff --name-only origin/${baseBranch}...HEAD`).toString().trim();
|
|
7
|
+
if (changedFiles) return changedFiles.split("\n").filter(Boolean);
|
|
8
|
+
} catch (error) {}
|
|
9
|
+
try {
|
|
10
|
+
const changedFiles = execSync(`git diff --name-only ${baseBranch}...HEAD`).toString().trim();
|
|
11
|
+
if (changedFiles) return changedFiles.split("\n").filter(Boolean);
|
|
12
|
+
} catch (error) {}
|
|
13
|
+
try {
|
|
14
|
+
const changedFiles = execSync(`git diff --name-only ${baseBranch}..HEAD`).toString().trim();
|
|
15
|
+
if (changedFiles) return changedFiles.split("\n").filter(Boolean);
|
|
16
|
+
} catch (error) {}
|
|
17
|
+
try {
|
|
18
|
+
console.log(chalk.yellow(`Could not determine changed files relative to ${baseBranch}, using recently modified files...`));
|
|
19
|
+
const changedFiles = execSync("git ls-files --modified --others --exclude-standard").toString().trim();
|
|
20
|
+
if (changedFiles) return changedFiles.split("\n").filter(Boolean);
|
|
21
|
+
} catch (error) {}
|
|
22
|
+
try {
|
|
23
|
+
console.log(chalk.yellow("Using all tracked files as fallback..."));
|
|
24
|
+
return execSync("git ls-files").toString().trim().split("\n").filter(Boolean).slice(0, 50);
|
|
25
|
+
} catch (error) {
|
|
26
|
+
console.error(chalk.red("Could not determine changed files."));
|
|
27
|
+
return [];
|
|
28
|
+
}
|
|
64
29
|
};
|
|
30
|
+
//#endregion
|
|
31
|
+
export { getChangedFiles };
|