mirror of
https://github.com/indig0fox/Arma3-AttendanceTracker.git/
synced 2025-12-08 09:51:47 -06:00
add hemtt support, major refactor
- no longer supports server events - can now more easily build using hemtt - extension vastly improved in both structure and functionality - tested on listen server - includes schema change
This commit is contained in:
62
extension/AttendanceTracker/internal/db/db.go
Normal file
62
extension/AttendanceTracker/internal/db/db.go
Normal file
@@ -0,0 +1,62 @@
|
||||
package db
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/indig0fox/a3go/a3interface"
|
||||
"gorm.io/driver/mysql"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
var db *gorm.DB
|
||||
var config ConfigStruct
|
||||
|
||||
type ConfigStruct struct {
|
||||
MySQLHost string `json:"mysqlHost"`
|
||||
MySQLPort int `json:"mysqlPort"`
|
||||
MySQLUser string `json:"mysqlUser"`
|
||||
MySQLPassword string `json:"mysqlPassword"`
|
||||
MySQLDatabase string `json:"mysqlDatabase"`
|
||||
}
|
||||
|
||||
func SetConfig(c ConfigStruct) {
|
||||
config = c
|
||||
}
|
||||
|
||||
func Client() *gorm.DB {
|
||||
return db
|
||||
}
|
||||
|
||||
func Connect() error {
|
||||
|
||||
// connect to database
|
||||
var err error
|
||||
dsn := fmt.Sprintf(
|
||||
"%s:%s@tcp(%s:%d)/%s?charset=utf8mb4&parseTime=True",
|
||||
config.MySQLUser,
|
||||
config.MySQLPassword,
|
||||
config.MySQLHost,
|
||||
config.MySQLPort,
|
||||
config.MySQLDatabase,
|
||||
)
|
||||
|
||||
db, err = gorm.Open(mysql.Open(dsn), &gorm.Config{})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// try ping
|
||||
sqlDB, err := db.DB()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = sqlDB.Ping()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
a3interface.WriteArmaCallback("connectDB", `["Database connected", "INFO"]`)
|
||||
a3interface.WriteArmaCallback("connectDB", `["SUCCESS", "INFO"]`)
|
||||
|
||||
return nil
|
||||
}
|
||||
129
extension/AttendanceTracker/internal/logger/logger.go
Normal file
129
extension/AttendanceTracker/internal/logger/logger.go
Normal file
@@ -0,0 +1,129 @@
|
||||
package logger
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/indig0fox/a3go/a3interface"
|
||||
"github.com/rs/zerolog"
|
||||
"gopkg.in/natefinch/lumberjack.v2"
|
||||
)
|
||||
|
||||
var ll *lumberjack.Logger
|
||||
var armaWriter *armaIoWriter
|
||||
|
||||
var Log, FileOnly, ArmaOnly zerolog.Logger
|
||||
var ActiveOptions *LoggerOptionsType = &LoggerOptionsType{}
|
||||
|
||||
type LoggerOptionsType struct {
|
||||
// LogPath is the path to the log file
|
||||
Path string
|
||||
// LogAddonName is the name of the addon that will be used to send log messages to arma
|
||||
AddonName string
|
||||
// LogExtensionName is the name of the extension that will be used to send log messages to arma
|
||||
ExtensionName string
|
||||
// ExtensionVersion is the version of this extension
|
||||
ExtensionVersion string
|
||||
// LogDebug determines if we should send Debug level messages to file & arma
|
||||
Debug bool
|
||||
// LogTrace is used to determine if file should receive trace level, regardless of debug
|
||||
Trace bool
|
||||
}
|
||||
|
||||
func RotateLogs() {
|
||||
ll.Rotate()
|
||||
}
|
||||
|
||||
// ArmaIoWriter is a custom type that implements the io.Writer interface and sends the output to Arma with the "log" callback
|
||||
type armaIoWriter struct{}
|
||||
|
||||
func (w *armaIoWriter) Write(p []byte) (n int, err error) {
|
||||
// write to arma log
|
||||
a3interface.WriteArmaCallback(ActiveOptions.ExtensionName, ":LOG:", string(p))
|
||||
return len(p), nil
|
||||
}
|
||||
|
||||
// console writer
|
||||
func InitLoggers(o *LoggerOptionsType) {
|
||||
ActiveOptions = o
|
||||
|
||||
// create a new lumberjack file logger (adds log rotation and compression)
|
||||
ll = &lumberjack.Logger{
|
||||
Filename: ActiveOptions.Path,
|
||||
MaxSize: 1,
|
||||
MaxBackups: 5,
|
||||
MaxAge: 14,
|
||||
Compress: true,
|
||||
LocalTime: true,
|
||||
}
|
||||
|
||||
// create a new io writer using the a3go callback function
|
||||
// this will be used to write to the arma log
|
||||
armaWriter = new(armaIoWriter)
|
||||
|
||||
// create format functions for RPT log messages
|
||||
armaLogFormatLevel := func(i interface{}) string {
|
||||
return strings.ToUpper(
|
||||
fmt.Sprintf(
|
||||
"(%s)",
|
||||
i,
|
||||
))
|
||||
}
|
||||
armaLogFormatTimestamp := func(i interface{}) string {
|
||||
return ""
|
||||
}
|
||||
|
||||
FileOnly = zerolog.New(zerolog.ConsoleWriter{
|
||||
Out: ll,
|
||||
TimeFormat: time.RFC3339,
|
||||
NoColor: true,
|
||||
}).With().Timestamp().Caller().Logger()
|
||||
|
||||
if ActiveOptions.Trace {
|
||||
FileOnly = FileOnly.Level(zerolog.TraceLevel)
|
||||
} else if ActiveOptions.Debug {
|
||||
FileOnly = FileOnly.Level(zerolog.DebugLevel)
|
||||
} else {
|
||||
FileOnly = FileOnly.Level(zerolog.InfoLevel)
|
||||
}
|
||||
|
||||
ArmaOnly = zerolog.New(zerolog.ConsoleWriter{
|
||||
Out: armaWriter,
|
||||
TimeFormat: "",
|
||||
NoColor: true,
|
||||
FormatLevel: armaLogFormatLevel,
|
||||
FormatTimestamp: armaLogFormatTimestamp,
|
||||
}).With().Str("extension_version", ActiveOptions.ExtensionVersion).Logger()
|
||||
|
||||
if ActiveOptions.Debug {
|
||||
ArmaOnly = ArmaOnly.Level(zerolog.DebugLevel)
|
||||
} else {
|
||||
ArmaOnly = ArmaOnly.Level(zerolog.InfoLevel)
|
||||
}
|
||||
|
||||
// create something that can send the same message to both loggers
|
||||
// this is used to send messages to the arma log
|
||||
// and the file log
|
||||
Log = zerolog.New(zerolog.MultiLevelWriter(
|
||||
zerolog.ConsoleWriter{
|
||||
Out: ll,
|
||||
TimeFormat: time.RFC3339,
|
||||
NoColor: true,
|
||||
},
|
||||
zerolog.ConsoleWriter{
|
||||
Out: armaWriter,
|
||||
TimeFormat: "",
|
||||
NoColor: true,
|
||||
FormatTimestamp: armaLogFormatTimestamp,
|
||||
FormatLevel: armaLogFormatLevel,
|
||||
},
|
||||
)).With().Timestamp().Caller().Logger()
|
||||
|
||||
if ActiveOptions.Debug {
|
||||
Log = Log.Level(zerolog.DebugLevel)
|
||||
} else {
|
||||
Log = Log.Level(zerolog.InfoLevel)
|
||||
}
|
||||
|
||||
}
|
||||
65
extension/AttendanceTracker/internal/util/config.go
Normal file
65
extension/AttendanceTracker/internal/util/config.go
Normal file
@@ -0,0 +1,65 @@
|
||||
package util
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"os"
|
||||
|
||||
"github.com/spf13/viper"
|
||||
)
|
||||
|
||||
var ConfigJSON = viper.New()
|
||||
|
||||
func LoadConfig(modulePathDir string) (string, error) {
|
||||
ConfigJSON.SetConfigName("AttendanceTracker.config")
|
||||
ConfigJSON.SetConfigType("json")
|
||||
ConfigJSON.AddConfigPath(".")
|
||||
ConfigJSON.AddConfigPath(modulePathDir)
|
||||
|
||||
ConfigJSON.SetDefault("armaConfig.dbUpdateInterval", "90s")
|
||||
ConfigJSON.SetDefault("armaConfig.debug", true)
|
||||
ConfigJSON.SetDefault("sqlConfig", map[string]interface{}{
|
||||
"mysqlHost": "localhost",
|
||||
"mysqlPort": 3306,
|
||||
"mysqlUser": "root",
|
||||
"mysqlPassword": "password",
|
||||
"mysqlDatabase": "a3attendance",
|
||||
})
|
||||
ConfigJSON.SetDefault("armaConfig", map[string]interface{}{
|
||||
"debug": true,
|
||||
"traceLogToFile": false,
|
||||
"dbUpdateIntervalS": 60,
|
||||
})
|
||||
|
||||
wd, err := os.Getwd()
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
if err := ConfigJSON.ReadInConfig(); err != nil {
|
||||
if _, ok := err.(viper.ConfigFileNotFoundError); ok {
|
||||
// Config file not found; ignore error if desired
|
||||
return "", fmt.Errorf(
|
||||
"config file not found, using defaults! searched in %s",
|
||||
[]string{
|
||||
ConfigJSON.ConfigFileUsed(),
|
||||
modulePathDir,
|
||||
wd,
|
||||
},
|
||||
)
|
||||
} else {
|
||||
// Config file was found but another error was produced
|
||||
return "", err
|
||||
}
|
||||
}
|
||||
|
||||
return "Config loaded successfully!", nil
|
||||
}
|
||||
|
||||
func ConfigArmaFormat() (string, error) {
|
||||
armaConfig := ConfigJSON.GetStringMap("armaConfig")
|
||||
bytes, err := json.Marshal(armaConfig)
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
return string(bytes), nil
|
||||
}
|
||||
Reference in New Issue
Block a user