mirror of
https://codeberg.org/forgejo/forgejo.git
synced 2025-07-07 09:55:41 +02:00
Some checks are pending
/ release (push) Waiting to run
testing-integration / test-unit (push) Waiting to run
testing-integration / test-sqlite (push) Waiting to run
testing / backend-checks (push) Waiting to run
testing / frontend-checks (push) Waiting to run
testing / test-unit (push) Blocked by required conditions
testing / test-e2e (push) Blocked by required conditions
testing / test-remote-cacher (redis) (push) Blocked by required conditions
testing / test-remote-cacher (valkey) (push) Blocked by required conditions
testing / test-remote-cacher (garnet) (push) Blocked by required conditions
testing / test-remote-cacher (redict) (push) Blocked by required conditions
testing / test-mysql (push) Blocked by required conditions
testing / test-pgsql (push) Blocked by required conditions
testing / test-sqlite (push) Blocked by required conditions
testing / security-check (push) Blocked by required conditions
This feature is intended to help reduce noisy logs generated by routine Kubernetes probes and Prometheus scraping. While logs are essential, these specific requests (e.g., to /metrics and /api/healthz) generally don't provide useful information and tend to clutter the output. The goal is to introduce functionality that effectively acts as the inverse of the existing EXPRESSION mode—allowing logging to be excluded based on a condition, rather than included. Reviewed-on: https://codeberg.org/forgejo/forgejo/pulls/8212 Reviewed-by: Gusted <gusted@noreply.codeberg.org> Co-authored-by: zokki <zokki.softwareschmiede@gmail.com> Co-committed-by: zokki <zokki.softwareschmiede@gmail.com>
196 lines
5.8 KiB
Go
196 lines
5.8 KiB
Go
// Copyright 2020 The Gitea Authors. All rights reserved.
|
|
// SPDX-License-Identifier: MIT
|
|
|
|
package private
|
|
|
|
import (
|
|
"fmt"
|
|
"net/http"
|
|
|
|
"forgejo.org/models/db"
|
|
"forgejo.org/modules/graceful"
|
|
"forgejo.org/modules/graceful/releasereopen"
|
|
"forgejo.org/modules/log"
|
|
"forgejo.org/modules/private"
|
|
"forgejo.org/modules/queue"
|
|
"forgejo.org/modules/setting"
|
|
"forgejo.org/modules/templates"
|
|
"forgejo.org/modules/web"
|
|
"forgejo.org/services/context"
|
|
)
|
|
|
|
// ReloadTemplates reloads all the templates
|
|
func ReloadTemplates(ctx *context.PrivateContext) {
|
|
err := templates.ReloadHTMLTemplates()
|
|
if err != nil {
|
|
ctx.JSON(http.StatusInternalServerError, private.Response{
|
|
UserMsg: fmt.Sprintf("Template error: %v", err),
|
|
})
|
|
return
|
|
}
|
|
ctx.PlainText(http.StatusOK, "success")
|
|
}
|
|
|
|
// FlushQueues flushes all the Queues
|
|
func FlushQueues(ctx *context.PrivateContext) {
|
|
opts := web.GetForm(ctx).(*private.FlushOptions)
|
|
if opts.NonBlocking {
|
|
// Save the hammer ctx here - as a new one is created each time you call this.
|
|
baseCtx := graceful.GetManager().HammerContext()
|
|
go func() {
|
|
err := queue.GetManager().FlushAll(baseCtx, opts.Timeout)
|
|
if err != nil {
|
|
log.Error("Flushing request timed-out with error: %v", err)
|
|
}
|
|
}()
|
|
ctx.JSON(http.StatusAccepted, private.Response{
|
|
UserMsg: "Flushing",
|
|
})
|
|
return
|
|
}
|
|
err := queue.GetManager().FlushAll(ctx, opts.Timeout)
|
|
if err != nil {
|
|
ctx.JSON(http.StatusRequestTimeout, private.Response{
|
|
UserMsg: fmt.Sprintf("%v", err),
|
|
})
|
|
}
|
|
ctx.PlainText(http.StatusOK, "success")
|
|
}
|
|
|
|
// PauseLogging pauses logging
|
|
func PauseLogging(ctx *context.PrivateContext) {
|
|
log.GetManager().PauseAll()
|
|
ctx.PlainText(http.StatusOK, "success")
|
|
}
|
|
|
|
// ResumeLogging resumes logging
|
|
func ResumeLogging(ctx *context.PrivateContext) {
|
|
log.GetManager().ResumeAll()
|
|
ctx.PlainText(http.StatusOK, "success")
|
|
}
|
|
|
|
// ReleaseReopenLogging releases and reopens logging files
|
|
func ReleaseReopenLogging(ctx *context.PrivateContext) {
|
|
if err := releasereopen.GetManager().ReleaseReopen(); err != nil {
|
|
ctx.JSON(http.StatusInternalServerError, private.Response{
|
|
Err: fmt.Sprintf("Error during release and reopen: %v", err),
|
|
})
|
|
return
|
|
}
|
|
ctx.PlainText(http.StatusOK, "success")
|
|
}
|
|
|
|
// SetLogSQL re-sets database SQL logging
|
|
func SetLogSQL(ctx *context.PrivateContext) {
|
|
db.SetLogSQL(ctx, ctx.FormBool("on"))
|
|
ctx.PlainText(http.StatusOK, "success")
|
|
}
|
|
|
|
// RemoveLogger removes a logger
|
|
func RemoveLogger(ctx *context.PrivateContext) {
|
|
logger := ctx.Params("logger")
|
|
writer := ctx.Params("writer")
|
|
err := log.GetManager().GetLogger(logger).RemoveWriter(writer)
|
|
if err != nil {
|
|
ctx.JSON(http.StatusInternalServerError, private.Response{
|
|
Err: fmt.Sprintf("Failed to remove log writer: %s %s %v", logger, writer, err),
|
|
})
|
|
return
|
|
}
|
|
ctx.PlainText(http.StatusOK, fmt.Sprintf("Removed %s %s", logger, writer))
|
|
}
|
|
|
|
// AddLogger adds a logger
|
|
func AddLogger(ctx *context.PrivateContext) {
|
|
opts := web.GetForm(ctx).(*private.LoggerOptions)
|
|
|
|
if len(opts.Logger) == 0 {
|
|
opts.Logger = log.DEFAULT
|
|
}
|
|
|
|
writerMode := log.WriterMode{}
|
|
writerType := opts.Mode
|
|
|
|
var flags string
|
|
var ok bool
|
|
if flags, ok = opts.Config["flags"].(string); !ok {
|
|
switch opts.Logger {
|
|
case "access":
|
|
flags = ""
|
|
case "router":
|
|
flags = "date,time"
|
|
default:
|
|
flags = "stdflags"
|
|
}
|
|
}
|
|
writerMode.Flags = log.FlagsFromString(flags)
|
|
|
|
if writerMode.Colorize, ok = opts.Config["colorize"].(bool); !ok && opts.Mode == "console" {
|
|
if _, ok := opts.Config["stderr"]; ok {
|
|
writerMode.Colorize = log.CanColorStderr
|
|
} else {
|
|
writerMode.Colorize = log.CanColorStdout
|
|
}
|
|
}
|
|
|
|
writerMode.Level = setting.Log.Level
|
|
if level, ok := opts.Config["level"].(string); ok {
|
|
writerMode.Level = log.LevelFromString(level)
|
|
}
|
|
|
|
writerMode.StacktraceLevel = setting.Log.StacktraceLogLevel
|
|
if stacktraceLevel, ok := opts.Config["level"].(string); ok {
|
|
writerMode.StacktraceLevel = log.LevelFromString(stacktraceLevel)
|
|
}
|
|
|
|
writerMode.Prefix, _ = opts.Config["prefix"].(string)
|
|
writerMode.Expression, _ = opts.Config["expression"].(string)
|
|
writerMode.Exclusion, _ = opts.Config["exclusion"].(string)
|
|
|
|
switch writerType {
|
|
case "console":
|
|
writerOption := log.WriterConsoleOption{}
|
|
writerOption.Stderr, _ = opts.Config["stderr"].(bool)
|
|
writerMode.WriterOption = writerOption
|
|
case "file":
|
|
writerOption := log.WriterFileOption{}
|
|
fileName, _ := opts.Config["filename"].(string)
|
|
writerOption.FileName = setting.LogPrepareFilenameForWriter(fileName, opts.Writer+".log")
|
|
writerOption.LogRotate, _ = opts.Config["rotate"].(bool)
|
|
maxSizeShift, _ := opts.Config["maxsize"].(int)
|
|
if maxSizeShift == 0 {
|
|
maxSizeShift = 28
|
|
}
|
|
writerOption.MaxSize = 1 << maxSizeShift
|
|
writerOption.DailyRotate, _ = opts.Config["daily"].(bool)
|
|
writerOption.MaxDays, _ = opts.Config["maxdays"].(int)
|
|
if writerOption.MaxDays == 0 {
|
|
writerOption.MaxDays = 7
|
|
}
|
|
writerOption.Compress, _ = opts.Config["compress"].(bool)
|
|
writerOption.CompressionLevel, _ = opts.Config["compressionLevel"].(int)
|
|
if writerOption.CompressionLevel == 0 {
|
|
writerOption.CompressionLevel = -1
|
|
}
|
|
writerMode.WriterOption = writerOption
|
|
case "conn":
|
|
writerOption := log.WriterConnOption{}
|
|
writerOption.ReconnectOnMsg, _ = opts.Config["reconnectOnMsg"].(bool)
|
|
writerOption.Reconnect, _ = opts.Config["reconnect"].(bool)
|
|
writerOption.Protocol, _ = opts.Config["net"].(string)
|
|
writerOption.Addr, _ = opts.Config["address"].(string)
|
|
writerMode.WriterOption = writerOption
|
|
default:
|
|
panic(fmt.Sprintf("invalid log writer mode: %s", writerType))
|
|
}
|
|
writer, err := log.NewEventWriter(opts.Writer, writerType, writerMode)
|
|
if err != nil {
|
|
log.Error("Failed to create new log writer: %v", err)
|
|
ctx.JSON(http.StatusInternalServerError, private.Response{
|
|
Err: fmt.Sprintf("Failed to create new log writer: %v", err),
|
|
})
|
|
return
|
|
}
|
|
log.GetManager().GetLogger(opts.Logger).AddWriters(writer)
|
|
ctx.PlainText(http.StatusOK, "success")
|
|
}
|