diff --git a/.env.dist b/.env.dist index 3681e3a..c4bd94d 100644 --- a/.env.dist +++ b/.env.dist @@ -14,6 +14,11 @@ CLEARCASE_AUTH_PROVIDERS_GITEA_PROFILE_URL=https://forge.cadoles.com/login/oauth CLEARCASE_HTTP_SESSION_KEYS=abcdefghijklmnopqrstuvwxyz000000 # LLM Provider -# Example with ollama - llama3.1:8b : +# Example with ollama: CLEARCASE_LLM_PROVIDER_BASE_URL="http://localhost:11434/api/" CLEARCASE_LLM_PROVIDER_MODEL="llama3.1:8b" +# Example with OpenRouter +# CLEARCASE_LLM_PROVIDER_NAME=openrouter +# CLEARCASE_LLM_PROVIDER_KEY= +# CLEARCASE_LLM_PROVIDER_BASE_URL=https://openrouter.ai/api/v1/ +# CLEARCASE_LLM_PROVIDER_MODEL=meta-llama/llama-3.3-70b-instruct:free diff --git a/internal/adapter/gitea/forge.go b/internal/adapter/gitea/forge.go index 620838b..269675b 100644 --- a/internal/adapter/gitea/forge.go +++ b/internal/adapter/gitea/forge.go @@ -2,6 +2,7 @@ package gitea import ( "context" + "net/http" "slices" "strconv" "strings" @@ -33,8 +34,12 @@ func (f *Forge) GetIssueTemplate(ctx context.Context, rawProjectID string) (stri return "", errors.WithStack(err) } - data, _, err := f.client.GetFile(project.Owner.UserName, project.Name, project.DefaultBranch, ".gitea/issue_template.md") + data, res, err := f.client.GetFile(project.Owner.UserName, project.Name, project.DefaultBranch, ".gitea/issue_template.md") if err != nil { + if res.StatusCode == http.StatusNotFound { + return "", errors.WithStack(port.ErrFileNotFound) + } + return "", errors.WithStack(err) } diff --git a/internal/core/port/forge.go b/internal/core/port/forge.go index b0b7f2b..cd1c3d6 100644 --- a/internal/core/port/forge.go +++ b/internal/core/port/forge.go @@ -2,10 +2,15 @@ package port import ( "context" + "errors" "forge.cadoles.com/wpetit/clearcase/internal/core/model" ) +var ( + ErrFileNotFound = errors.New("file not found") +) + type Forge interface { GetProjects(ctx context.Context) ([]*model.Project, error) CreateIssue(ctx context.Context, projectID string, title string, content string) error diff --git a/internal/core/service/issue_default_template.txt b/internal/core/service/issue_default_template.txt new file mode 100644 index 0000000..f7ff471 --- /dev/null +++ b/internal/core/service/issue_default_template.txt @@ -0,0 +1,11 @@ +## Description + +> La description du besoin. + +## Détails d'implémentation + +> Liste des actions à réaliser pour remplir le besoin. + +## Tests d'acceptance + +> Liste des critères d'acception de réalisation du ticket. \ No newline at end of file diff --git a/internal/core/service/issue_manager.go b/internal/core/service/issue_manager.go index adcd352..606fee6 100644 --- a/internal/core/service/issue_manager.go +++ b/internal/core/service/issue_manager.go @@ -25,6 +25,9 @@ var issueSystemPromptRawTemplate string //go:embed issue_user_prompt.gotmpl var issueUserPromptRawTemplate string +//go:embed issue_default_template.txt +var issueDefaultTemplate string + type ForgeFactory interface { Match(user *model.User) bool Create(ctx context.Context, user *model.User) (port.Forge, error) @@ -90,10 +93,14 @@ func (m *IssueManager) getIssueSystemPrompt(ctx context.Context, user *model.Use } issueTemplate, err := forge.GetIssueTemplate(ctx, projectID) - if err != nil { + if err != nil && !errors.Is(err, port.ErrFileNotFound) { return "", errors.WithStack(err) } + if issueTemplate == "" { + issueTemplate = issueDefaultTemplate + } + systemPrompt, err := llm.PromptTemplate(issueSystemPromptRawTemplate, struct { IssueTemplate string }{