[MM-53968] Includes mattermost-plugin-api into the mono repo (#24235)

Include https://github.com/mattermost/mattermost-plugin-api into the mono repo

Co-authored-by: Jesse Hallam <jesse.hallam@gmail.com>
Co-authored-by: Michael Kochell <mjkochell@gmail.com>
Co-authored-by: Alejandro García Montoro <alejandro.garciamontoro@gmail.com>
Co-authored-by: Ben Schumacher <ben.schumacher@mattermost.com>
Co-authored-by: Alex Dovenmuehle <alex.dovenmuehle@mattermost.com>
Co-authored-by: Michael Kochell <6913320+mickmister@users.noreply.github.com>
Co-authored-by: Christopher Poile <cpoile@gmail.com>
Co-authored-by: İlker Göktuğ Öztürk <ilkergoktugozturk@gmail.com>
Co-authored-by: Shota Gvinepadze <wineson@gmail.com>
Co-authored-by: Ali Farooq <ali.farooq0@pm.me>
Co-authored-by: Maria A Nunez <maria.nunez@mattermost.com>
Co-authored-by: Daniel Espino García <larkox@gmail.com>
Co-authored-by: Christopher Speller <crspeller@gmail.com>
Co-authored-by: Alex Dovenmuehle <adovenmuehle@gmail.com>
Co-authored-by: Szymon Gibała <szymongib@gmail.com>
Co-authored-by: Lev <1187448+levb@users.noreply.github.com>
Co-authored-by: Jason Frerich <jason.frerich@mattermost.com>
Co-authored-by: Agniva De Sarker <agnivade@yahoo.co.in>
Co-authored-by: Artur M. Wolff <artur.m.wolff@gmail.com>
Co-authored-by: Madhav Hugar <16546715+madhavhugar@users.noreply.github.com>
Co-authored-by: Joe <security.joe@pm.me>
Co-authored-by: Ibrahim Serdar Acikgoz <serdaracikgoz86@gmail.com>
Co-authored-by: José Peso <trilopin@users.noreply.github.com>
Этот коммит содержится в:
Ben Schumacher
2023-08-21 09:50:30 +02:00
коммит произвёл GitHub
родитель bc11b29807
Коммит 3ee5432664
117 изменённых файлов: 14912 добавлений и 5 удалений

Просмотреть файл

@@ -0,0 +1,97 @@
package admincclogger
import (
"fmt"
"github.com/mattermost/mattermost/server/public/pluginapi/experimental/bot/logger"
"github.com/mattermost/mattermost/server/public/pluginapi/experimental/bot/poster"
"github.com/mattermost/mattermost/server/public/pluginapi/experimental/common"
)
type adminCCLogger struct {
logger.Logger
dmer poster.DMer
logLevel logger.LogLevel
includeContext bool
userIDs []string
}
/*
New promotes the provided logger into a admin cc logger, sending direct messages to all the admin
ids provided through the dmer provided, about all events below the logLevel. If logVerbose is set,
it will also send the context.
- l Logger: A logger to promote.
- dmer DMer: A DMer to send the messages to the admins.
- logLevel: The highest type of message to be stored in telemetry.
- includeContext: Whether the log context should be messaged to the admins.
- userIDs: The user IDs of the admins.
*/
func New(l logger.Logger, dmer poster.DMer, logLevel logger.LogLevel, includeContext bool, userIDs ...string) logger.Logger {
return &adminCCLogger{
Logger: l,
dmer: dmer,
logLevel: logLevel,
includeContext: includeContext,
userIDs: userIDs,
}
}
// NewFromAPI creates a adminCCLogger directly from a LogAPI instead of passing a logger.
func NewFromAPI(api common.LogAPI, dmer poster.DMer, logLevel logger.LogLevel, includeContext bool, userIDs ...string) logger.Logger {
return New(logger.New(api), dmer, logLevel, includeContext, userIDs...)
}
func (l *adminCCLogger) Debugf(format string, args ...interface{}) {
l.Logger.Debugf(format, args...)
message := fmt.Sprintf(format, args...)
if logger.Level(l.logLevel) >= 4 {
l.logToAdmins("DEBUG", message)
}
}
func (l *adminCCLogger) Errorf(format string, args ...interface{}) {
l.Logger.Errorf(format, args...)
message := fmt.Sprintf(format, args...)
if logger.Level(l.logLevel) >= 1 {
l.logToAdmins("ERROR", message)
}
}
func (l *adminCCLogger) Infof(format string, args ...interface{}) {
l.Logger.Infof(format, args...)
message := fmt.Sprintf(format, args...)
if logger.Level(l.logLevel) >= 3 {
l.logToAdmins("INFO", message)
}
}
func (l *adminCCLogger) Warnf(format string, args ...interface{}) {
l.Logger.Warnf(format, args...)
message := fmt.Sprintf(format, args...)
if logger.Level(l.logLevel) >= 2 {
l.logToAdmins("WARN", message)
}
}
func (l *adminCCLogger) logToAdmins(level, message string) {
context := l.Context()
if l.includeContext && len(context) > 0 {
message += "\n" + common.JSONBlock(context)
}
_ = l.dmAdmins("(log " + level + ") " + message)
}
func (l *adminCCLogger) dmAdmins(format string, args ...interface{}) error {
for _, id := range l.userIDs {
_, err := l.dmer.DM(id, format, args)
if err != nil {
return err
}
}
return nil
}

Просмотреть файл

@@ -0,0 +1,82 @@
// Copyright (c) 2019-present Mattermost, Inc. All Rights Reserved.
// See License for license information.
package logger
import (
"fmt"
"time"
"github.com/mattermost/mattermost/server/public/pluginapi/experimental/common"
)
type defaultLogger struct {
logContext LogContext
logAPI common.LogAPI
}
/*
New creates a new logger.
- api: LogAPI implementation
*/
func New(api common.LogAPI) Logger {
l := &defaultLogger{
logAPI: api,
}
return l
}
func (l *defaultLogger) With(logContext LogContext) Logger {
newLogger := *l
if len(newLogger.logContext) == 0 {
newLogger.logContext = map[string]interface{}{}
}
for k, v := range logContext {
newLogger.logContext[k] = v
}
return &newLogger
}
func (l *defaultLogger) WithError(err error) Logger {
newLogger := *l
if len(newLogger.logContext) == 0 {
newLogger.logContext = map[string]interface{}{}
}
newLogger.logContext[ErrorKey] = err.Error()
return &newLogger
}
func (l *defaultLogger) Context() LogContext {
return l.logContext
}
func (l *defaultLogger) Timed() Logger {
return l.With(LogContext{
timed: time.Now(),
})
}
func (l *defaultLogger) Debugf(format string, args ...interface{}) {
measure(l.logContext)
message := fmt.Sprintf(format, args...)
l.logAPI.LogDebug(message, toKeyValuePairs(l.logContext)...)
}
func (l *defaultLogger) Errorf(format string, args ...interface{}) {
measure(l.logContext)
message := fmt.Sprintf(format, args...)
l.logAPI.LogError(message, toKeyValuePairs(l.logContext)...)
}
func (l *defaultLogger) Infof(format string, args ...interface{}) {
measure(l.logContext)
message := fmt.Sprintf(format, args...)
l.logAPI.LogInfo(message, toKeyValuePairs(l.logContext)...)
}
func (l *defaultLogger) Warnf(format string, args ...interface{}) {
measure(l.logContext)
message := fmt.Sprintf(format, args...)
l.logAPI.LogWarn(message, toKeyValuePairs(l.logContext)...)
}

Просмотреть файл

@@ -0,0 +1,78 @@
package logger
import "time"
const (
timed = "__since"
elapsed = "Elapsed"
ErrorKey = "error"
)
// LogLevel defines the level of log messages
type LogLevel string
const (
// LogLevelDebug denotes debug messages
LogLevelDebug = "debug"
// LogLevelInfo denotes info messages
LogLevelInfo = "info"
// LogLevelWarn denotes warn messages
LogLevelWarn = "warn"
// LogLevelError denotes error messages
LogLevelError = "error"
)
// LogContext defines the context for the logs.
type LogContext map[string]interface{}
// Logger defines an object able to log messages.
type Logger interface {
// With adds a logContext to the logger.
With(LogContext) Logger
// WithError adds an Error to the logger.
WithError(error) Logger
// Context returns the current context
Context() LogContext
// Timed add a timed log context.
Timed() Logger
// Debugf logs a formatted string as a debug message.
Debugf(format string, args ...interface{})
// Errorf logs a formatted string as an error message.
Errorf(format string, args ...interface{})
// Infof logs a formatted string as an info message.
Infof(format string, args ...interface{})
// Warnf logs a formatted string as an warning message.
Warnf(format string, args ...interface{})
}
func measure(lc LogContext) {
if lc[timed] == nil {
return
}
started := lc[timed].(time.Time)
lc[elapsed] = time.Since(started).String()
delete(lc, timed)
}
// Level assigns an integer to the LogLevel string
func Level(l LogLevel) int {
switch l {
case LogLevelDebug:
return 4
case LogLevelInfo:
return 3
case LogLevelWarn:
return 2
case LogLevelError:
return 1
}
return 0
}
func toKeyValuePairs(in map[string]interface{}) (out []interface{}) {
for k, v := range in {
out = append(out, k, v)
}
return out
}

Просмотреть файл

@@ -0,0 +1,17 @@
package logger
type nilLogger struct{}
// NewNilLogger returns a logger that performs no action.
func NewNilLogger() Logger {
return &nilLogger{}
}
func (l *nilLogger) With(LogContext) Logger { return l }
func (l *nilLogger) WithError(error) Logger { return l }
func (l *nilLogger) Context() LogContext { return nil }
func (l *nilLogger) Timed() Logger { return l }
func (l *nilLogger) Debugf(string, ...interface{}) {}
func (l *nilLogger) Errorf(string, ...interface{}) {}
func (l *nilLogger) Infof(string, ...interface{}) {}
func (l *nilLogger) Warnf(string, ...interface{}) {}

Просмотреть файл

@@ -0,0 +1,80 @@
package telemetrylogger
import (
"fmt"
"github.com/mattermost/mattermost/server/public/pluginapi/experimental/bot/logger"
"github.com/mattermost/mattermost/server/public/pluginapi/experimental/common"
"github.com/mattermost/mattermost/server/public/pluginapi/experimental/telemetry"
)
type telemetryLogger struct {
logger.Logger
logLevel logger.LogLevel
tracker telemetry.Tracker
}
/*
New promotes the provided logger into a telemetry logger, storing all events below the logLevel
through the tracker.
- l Logger: A logger to promote.
- logLevel: The highest type of message to be stored in telemetry.
- tracker: The telemetry tracker to store the messages.
*/
func New(l logger.Logger, logLevel logger.LogLevel, tracker telemetry.Tracker) logger.Logger {
return &telemetryLogger{
Logger: l,
logLevel: logLevel,
tracker: tracker,
}
}
// NewFromAPI creates a telemetryLogger directly from a LogAPI instead of passing a logger.
func NewFromAPI(api common.LogAPI, logLevel logger.LogLevel, tracker telemetry.Tracker) logger.Logger {
return New(logger.New(api), logLevel, tracker)
}
func (l *telemetryLogger) Debugf(format string, args ...interface{}) {
l.Logger.Debugf(format, args...)
message := fmt.Sprintf(format, args...)
if logger.Level(l.logLevel) >= 4 {
l.logToTelemetry("DEBUG", message)
}
}
func (l *telemetryLogger) Errorf(format string, args ...interface{}) {
l.Logger.Errorf(format, args...)
message := fmt.Sprintf(format, args...)
if logger.Level(l.logLevel) >= 1 {
l.logToTelemetry("ERROR", message)
}
}
func (l *telemetryLogger) Infof(format string, args ...interface{}) {
l.Logger.Infof(format, args...)
message := fmt.Sprintf(format, args...)
if logger.Level(l.logLevel) >= 3 {
l.logToTelemetry("INFO", message)
}
}
func (l *telemetryLogger) Warnf(format string, args ...interface{}) {
l.Logger.Warnf(format, args...)
message := fmt.Sprintf(format, args...)
if logger.Level(l.logLevel) >= 2 {
l.logToTelemetry("WARN", message)
}
}
func (l *telemetryLogger) logToTelemetry(level, message string) {
properties := map[string]interface{}{}
properties["message"] = message
for k, v := range l.Context() {
properties["context_"+k] = fmt.Sprintf("%v", v)
}
_ = l.tracker.TrackEvent("logger_"+level, properties)
}

Просмотреть файл

@@ -0,0 +1,61 @@
package logger
import (
"fmt"
"testing"
"time"
)
type testLogger struct {
testing.TB
logContext LogContext
}
// NewTestLogger creates a logger for testing purposes.
func NewTestLogger() Logger {
return &testLogger{}
}
func (l *testLogger) With(logContext LogContext) Logger {
newl := *l
if len(newl.logContext) == 0 {
newl.logContext = map[string]interface{}{}
}
for k, v := range logContext {
newl.logContext[k] = v
}
return &newl
}
func (l *testLogger) WithError(err error) Logger {
newl := *l
if len(newl.logContext) == 0 {
newl.logContext = map[string]interface{}{}
}
newl.logContext[ErrorKey] = err.Error()
return &newl
}
func (l *testLogger) Context() LogContext {
return l.logContext
}
func (l *testLogger) Timed() Logger {
return l.With(LogContext{
timed: time.Now(),
})
}
func (l *testLogger) logf(prefix, format string, args ...interface{}) {
out := fmt.Sprintf(prefix+": "+format, args...)
if len(l.logContext) > 0 {
measure(l.logContext)
out += fmt.Sprintf(" -- %+v", l.logContext)
}
l.TB.Logf(out)
}
func (l *testLogger) Debugf(format string, args ...interface{}) { l.logf("DEBUG", format, args...) }
func (l *testLogger) Errorf(format string, args ...interface{}) { l.logf("ERROR", format, args...) }
func (l *testLogger) Infof(format string, args ...interface{}) { l.logf("INFO", format, args...) }
func (l *testLogger) Warnf(format string, args ...interface{}) { l.logf("WARN", format, args...) }