diff --git a/src/Commands/GenerateCommitMessage.cs b/src/Commands/GenerateCommitMessage.cs index 9cfb8a1c..3bcf7010 100644 --- a/src/Commands/GenerateCommitMessage.cs +++ b/src/Commands/GenerateCommitMessage.cs @@ -10,33 +10,6 @@ namespace SourceGit.Commands /// public class GenerateCommitMessage { - private const string DEFAULT_SUMMARY_PROMPT = """ - You are an expert developer specialist in creating commits. - Provide a super concise one sentence overall changes summary of the user `git diff` output following strictly the next rules: - - Do not use any code snippets, imports, file routes or bullets points. - - Do not mention the route of file that has been change. - - Simply describe the MAIN GOAL of the changes. - - Output directly the summary in plain text. - """; - - private const string DEFAULT_SUBJECT_PROMPT = """ - You are an expert developer specialist in creating commits messages. - Your only goal is to retrieve a single commit message. - Based on the provided user changes, combine them in ONE SINGLE commit message retrieving the global idea, following strictly the next rules: - - Assign the commit {type} according to the next conditions: - feat: Only when adding a new feature. - fix: When fixing a bug. - docs: When updating documentation. - style: When changing elements styles or design and/or making changes to the code style (formatting, missing semicolons, etc.) without changing the code logic. - test: When adding or updating tests. - chore: When making changes to the build process or auxiliary tools and libraries. - revert: When undoing a previous commit. - refactor: When restructuring code without changing its external behavior, or is any of the other refactor types. - - Do not add any issues numeration, explain your output nor introduce your answer. - - Output directly only one commit message in plain text with the next format: {type}: {commit_message}. - - Be as concise as possible, keep the message under 50 characters. - """; - public class GetDiffContent : Command { public GetDiffContent(string repo, Models.DiffOption opt) @@ -59,31 +32,36 @@ namespace SourceGit.Commands { try { - var summaries = new List(); + var summarybuilder = new StringBuilder(); + var bodyBuilder = new StringBuilder(); foreach (var change in _changes) { if (_cancelToken.IsCancellationRequested) return ""; _onProgress?.Invoke($"Analyzing {change.Path}..."); + var summary = GenerateChangeSummary(change); - summaries.Add(summary); + summarybuilder.Append("- "); + summarybuilder.Append(summary); + summarybuilder.Append("(file: "); + summarybuilder.Append(change.Path); + summarybuilder.Append(")"); + summarybuilder.AppendLine(); + + bodyBuilder.Append("- "); + bodyBuilder.Append(summary); + bodyBuilder.AppendLine(); } if (_cancelToken.IsCancellationRequested) return ""; _onProgress?.Invoke($"Generating commit message..."); - var builder = new StringBuilder(); - builder.Append(GenerateSubject(string.Join("", summaries))); - builder.Append("\n"); - foreach (var summary in summaries) - { - builder.Append("\n- "); - builder.Append(summary.Trim()); - } - return builder.ToString(); + var body = bodyBuilder.ToString(); + var subject = GenerateSubject(summarybuilder.ToString()); + return string.Format("{0}\n\n{1}", subject, body); } catch (Exception e) { @@ -97,12 +75,7 @@ namespace SourceGit.Commands var rs = new GetDiffContent(_repo, new Models.DiffOption(change, false)).ReadToEnd(); var diff = rs.IsSuccess ? rs.StdOut : "unknown change"; - var prompt = string.IsNullOrWhiteSpace(Models.OpenAI.SummaryPrompt) - ? DEFAULT_SUMMARY_PROMPT - : Models.OpenAI.SummaryPrompt; - - var rsp = Models.OpenAI.Chat(prompt, $"Here is the `git diff` output: {diff}", _cancelToken); - + var rsp = Models.OpenAI.Chat(Models.OpenAI.AnalyzeDiffPrompt, $"Here is the `git diff` output: {diff}", _cancelToken); if (rsp != null && rsp.Choices.Count > 0) return rsp.Choices[0].Message.Content; @@ -111,12 +84,7 @@ namespace SourceGit.Commands private string GenerateSubject(string summary) { - var prompt = string.IsNullOrWhiteSpace(Models.OpenAI.SubjectPrompt) - ? DEFAULT_SUBJECT_PROMPT - : Models.OpenAI.SubjectPrompt; - - var rsp = Models.OpenAI.Chat(prompt, $"Here are the summaries changes: {summary}", _cancelToken); - + var rsp = Models.OpenAI.Chat(Models.OpenAI.GenerateSubjectPrompt, $"Here are the summaries changes:\n{summary}", _cancelToken); if (rsp != null && rsp.Choices.Count > 0) return rsp.Choices[0].Message.Content; diff --git a/src/Models/OpenAI.cs b/src/Models/OpenAI.cs index 16feabd7..b1bb9465 100644 --- a/src/Models/OpenAI.cs +++ b/src/Models/OpenAI.cs @@ -94,13 +94,13 @@ namespace SourceGit.Models set; } - public static string SubjectPrompt + public static string AnalyzeDiffPrompt { get; set; } - public static string SummaryPrompt + public static string GenerateSubjectPrompt { get; set; diff --git a/src/Resources/Locales/en_US.axaml b/src/Resources/Locales/en_US.axaml index f5a2f989..93b3febf 100644 --- a/src/Resources/Locales/en_US.axaml +++ b/src/Resources/Locales/en_US.axaml @@ -400,34 +400,11 @@ {0} years ago Preference OPEN AI - Server + Analyze Diff Prompt API Key + Generate Subject Prompt Model - Summary Prompt - Subject Prompt - You are an expert developer specialist in creating commits. -Provide a super concise one sentence overall changes summary of the user `git diff` output following strictly the next rules: -- Do not use any code snippets, imports, file routes or bullets points. -- Do not mention the route of file that has been change. -- Simply describe the MAIN GOAL of the changes. -- Output directly the summary in plain text. - - You are an expert developer specialist in creating commits messages. -Your only goal is to retrieve a single commit message. -Based on the provided user changes, combine them in ONE SINGLE commit message retrieving the global idea, following strictly the next rules: -- Assign the commit {type} according to the next conditions: - feat: Only when adding a new feature. - fix: When fixing a bug. - docs: When updating documentation. - style: When changing elements styles or design and/or making changes to the code style (formatting, missing semicolons, etc.) without changing the code logic. - test: When adding or updating tests. - chore: When making changes to the build process or auxiliary tools and libraries. - revert: When undoing a previous commit. - refactor: When restructuring code without changing its external behavior, or is any of the other refactor types. -- Do not add any issues numeration, explain your output nor introduce your answer. -- Output directly only one commit message in plain text with the next format: {type}: {commit_message}. -- Be as concise as possible, keep the message under 50 characters. - + Server APPEARANCE Default Font Default Font Size diff --git a/src/ViewModels/Preference.cs b/src/ViewModels/Preference.cs index c315a912..72667f54 100644 --- a/src/ViewModels/Preference.cs +++ b/src/ViewModels/Preference.cs @@ -25,6 +25,7 @@ namespace SourceGit.ViewModels _instance.PrepareGit(); _instance.PrepareShellOrTerminal(); _instance.PrepareWorkspaces(); + _instance.PrepareOpenAIPrompt(); return _instance; } @@ -315,27 +316,27 @@ namespace SourceGit.ViewModels } } - public string OpenAISubjectPrompt + public string OpenAIAnalyzeDiffPrompt { - get => Models.OpenAI.SubjectPrompt; + get => Models.OpenAI.AnalyzeDiffPrompt; set { - if (value != Models.OpenAI.SubjectPrompt) + if (value != Models.OpenAI.AnalyzeDiffPrompt) { - Models.OpenAI.SubjectPrompt = value; + Models.OpenAI.AnalyzeDiffPrompt = value; OnPropertyChanged(); } } } - public string OpenAISummaryPrompt + public string OpenAIGenerateSubjectPrompt { - get => Models.OpenAI.SummaryPrompt; + get => Models.OpenAI.GenerateSubjectPrompt; set { - if (value != Models.OpenAI.SummaryPrompt) + if (value != Models.OpenAI.GenerateSubjectPrompt) { - Models.OpenAI.SummaryPrompt = value; + Models.OpenAI.GenerateSubjectPrompt = value; OnPropertyChanged(); } } @@ -553,6 +554,45 @@ namespace SourceGit.ViewModels } } + private void PrepareOpenAIPrompt() + { + if (string.IsNullOrEmpty(Models.OpenAI.AnalyzeDiffPrompt)) + { + Models.OpenAI.AnalyzeDiffPrompt = """ + You are an expert developer specialist in creating commits. + Provide a super concise one sentence overall changes summary of the user `git diff` output following strictly the next rules: + - Do not use any code snippets, imports, file routes or bullets points. + - Do not mention the route of file that has been change. + - Write clear, concise, and descriptive messages that explain the MAIN GOAL made of the changes. + - Use the present tense and active voice in the message, for example, "Fix bug" instead of "Fixed bug.". + - Use the imperative mood, which gives the message a sense of command, e.g. "Add feature" instead of "Added feature". + - Avoid using general terms like "update" or "change", be specific about what was updated or changed. + - Avoid using terms like "The main goal of", just output directly the summary in plain text + """; + } + + if (string.IsNullOrEmpty(Models.OpenAI.GenerateSubjectPrompt)) + { + Models.OpenAI.GenerateSubjectPrompt = """ + You are an expert developer specialist in creating commits messages. + Your only goal is to retrieve a single commit message. + Based on the provided user changes, combine them in ONE SINGLE commit message retrieving the global idea, following strictly the next rules: + - Assign the commit {type} according to the next conditions: + feat: Only when adding a new feature. + fix: When fixing a bug. + docs: When updating documentation. + style: When changing elements styles or design and/or making changes to the code style (formatting, missing semicolons, etc.) without changing the code logic. + test: When adding or updating tests. + chore: When making changes to the build process or auxiliary tools and libraries. + revert: When undoing a previous commit. + refactor: When restructuring code without changing its external behavior, or is any of the other refactor types. + - Do not add any issues numeration, explain your output nor introduce your answer. + - Output directly only one commit message in plain text with the next format: {type}: {commit_message}. + - Be as concise as possible, keep the message under 50 characters. + """; + } + } + private RepositoryNode FindNodeRecursive(string id, List collection) { foreach (var node in collection) diff --git a/src/Views/Preference.axaml b/src/Views/Preference.axaml index 82436e1f..74ed1021 100644 --- a/src/Views/Preference.axaml +++ b/src/Views/Preference.axaml @@ -499,31 +499,27 @@ Text="{Binding OpenAIApiKey, Mode=TwoWay}"/> - -