72e6b46cde
- Branding: default app name MokoGitea -> MokoGIT; all standalone 'MokoGitea' brand strings, comments, and copyright headers -> MokoGIT - Special repo/config names: .mokogitea/.mokogitea-private -> .mokogit/ .mokogit-private (workflow discovery, issue/PR templates, profile+wiki repo names in header.go, config dir renamed) - Lowercase: mokogitea -> mokogit (docker image refs, ntfy topic, mail tags, wiki docs, Joomla element/targetplatform, MCP package docs) - Actions system user mokogitea-actions -> mokogit-actions + DB migration #369 to rename the existing id=-2 user in place - Icon: bundle Moko favicon.svg as public/assets/img/{favicon,logo}.svg; wire PWA manifest (SiteManifest) + nav logo to the SVG - CHANGELOG entry documenting the rebrand Shared MOKOGITEA_* CI/compose env + org-secret names are intentionally left for the coordinated server cutover to avoid breaking cross-repo CI. Claude-Session: https://claude.ai/code/session_01Bqe7fAuHQeiLueYfeHFrHw
135 lines
4.1 KiB
Go
135 lines
4.1 KiB
Go
// Copyright 2026 The MokoGIT Authors. All rights reserved.
|
|
// SPDX-License-Identifier: MIT
|
|
|
|
package ai
|
|
|
|
import (
|
|
"context"
|
|
|
|
"code.mokoconsulting.tech/MokoConsulting/MokoGIT/models/db"
|
|
"code.mokoconsulting.tech/MokoConsulting/MokoGIT/modules/timeutil"
|
|
)
|
|
|
|
// OrgSetting stores AI configuration for an organization.
|
|
type OrgSetting struct {
|
|
ID int64 `xorm:"pk autoincr"`
|
|
OrgID int64 `xorm:"UNIQUE NOT NULL"`
|
|
Enabled bool `xorm:"NOT NULL DEFAULT true"`
|
|
APIKeyEncrypted string `xorm:"TEXT"`
|
|
Model string `xorm:"VARCHAR(50) NOT NULL DEFAULT 'claude-sonnet-4-6'"`
|
|
RateLimitRequests int `xorm:"NOT NULL DEFAULT 100"`
|
|
RateLimitTokensMonth int64 `xorm:"NOT NULL DEFAULT 5000000"`
|
|
CreatedUnix timeutil.TimeStamp
|
|
UpdatedUnix timeutil.TimeStamp
|
|
}
|
|
|
|
func init() {
|
|
db.RegisterModel(new(OrgSetting))
|
|
db.RegisterModel(new(RepoSetting))
|
|
db.RegisterModel(new(UsageLog))
|
|
}
|
|
|
|
// TableName returns the table name for OrgSetting.
|
|
func (OrgSetting) TableName() string {
|
|
return "ai_org_setting"
|
|
}
|
|
|
|
// RepoSetting stores AI configuration for a repository.
|
|
type RepoSetting struct {
|
|
ID int64 `xorm:"pk autoincr"`
|
|
RepoID int64 `xorm:"UNIQUE NOT NULL"`
|
|
Enabled bool `xorm:"NOT NULL DEFAULT true"`
|
|
AutoReview bool `xorm:"NOT NULL DEFAULT true"`
|
|
Strictness string `xorm:"VARCHAR(20) NOT NULL DEFAULT 'standard'"`
|
|
IgnorePatterns string `xorm:"TEXT"`
|
|
CreatedUnix timeutil.TimeStamp
|
|
UpdatedUnix timeutil.TimeStamp
|
|
}
|
|
|
|
// TableName returns the table name for RepoSetting.
|
|
func (RepoSetting) TableName() string {
|
|
return "ai_repo_setting"
|
|
}
|
|
|
|
// UsageLog records AI token usage per action.
|
|
type UsageLog struct {
|
|
ID int64 `xorm:"pk autoincr"`
|
|
OrgID int64 `xorm:"INDEX NOT NULL"`
|
|
RepoID int64 `xorm:"INDEX NOT NULL"`
|
|
TriggeredByID int64
|
|
ActionType string `xorm:"VARCHAR(20) NOT NULL"` // review, chat, agent
|
|
Model string `xorm:"VARCHAR(50)"`
|
|
TokensInput int64
|
|
TokensOutput int64
|
|
DurationMs int64
|
|
CreatedUnix timeutil.TimeStamp `xorm:"INDEX"`
|
|
}
|
|
|
|
// TableName returns the table name for UsageLog.
|
|
func (UsageLog) TableName() string {
|
|
return "ai_usage_log"
|
|
}
|
|
|
|
// GetOrgSetting returns the AI settings for an org, or nil if not configured.
|
|
func GetOrgSetting(ctx context.Context, orgID int64) (*OrgSetting, error) {
|
|
setting := &OrgSetting{OrgID: orgID}
|
|
has, err := db.GetEngine(ctx).Where("org_id = ?", orgID).Get(setting)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
if !has {
|
|
return nil, nil
|
|
}
|
|
return setting, nil
|
|
}
|
|
|
|
// GetRepoSetting returns the AI settings for a repo, or nil if not configured.
|
|
func GetRepoSetting(ctx context.Context, repoID int64) (*RepoSetting, error) {
|
|
setting := &RepoSetting{RepoID: repoID}
|
|
has, err := db.GetEngine(ctx).Where("repo_id = ?", repoID).Get(setting)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
if !has {
|
|
return nil, nil
|
|
}
|
|
return setting, nil
|
|
}
|
|
|
|
// CreateOrgSetting inserts a new org AI setting.
|
|
func CreateOrgSetting(ctx context.Context, setting *OrgSetting) error {
|
|
setting.CreatedUnix = timeutil.TimeStampNow()
|
|
setting.UpdatedUnix = timeutil.TimeStampNow()
|
|
_, err := db.GetEngine(ctx).Insert(setting)
|
|
return err
|
|
}
|
|
|
|
// UpdateOrgSetting updates an existing org AI setting.
|
|
func UpdateOrgSetting(ctx context.Context, setting *OrgSetting) error {
|
|
setting.UpdatedUnix = timeutil.TimeStampNow()
|
|
_, err := db.GetEngine(ctx).ID(setting.ID).AllCols().Update(setting)
|
|
return err
|
|
}
|
|
|
|
// CreateRepoSetting inserts a new repo AI setting.
|
|
func CreateRepoSetting(ctx context.Context, setting *RepoSetting) error {
|
|
setting.CreatedUnix = timeutil.TimeStampNow()
|
|
setting.UpdatedUnix = timeutil.TimeStampNow()
|
|
_, err := db.GetEngine(ctx).Insert(setting)
|
|
return err
|
|
}
|
|
|
|
// UpdateRepoSetting updates an existing repo AI setting.
|
|
func UpdateRepoSetting(ctx context.Context, setting *RepoSetting) error {
|
|
setting.UpdatedUnix = timeutil.TimeStampNow()
|
|
_, err := db.GetEngine(ctx).ID(setting.ID).AllCols().Update(setting)
|
|
return err
|
|
}
|
|
|
|
// LogUsage records an AI usage event.
|
|
func LogUsage(ctx context.Context, log *UsageLog) error {
|
|
log.CreatedUnix = timeutil.TimeStampNow()
|
|
_, err := db.GetEngine(ctx).Insert(log)
|
|
return err
|
|
}
|