-
Notifications
You must be signed in to change notification settings - Fork 870
Home
thank243 edited this page Oct 3, 2023
·
4 revisions
Save below code to main.go
and sync all imports, then go run main.go
.
You can get a custom XrayR backend. Easy to modify and sync with official features.
package main
import (
"flag"
"fmt"
"log"
"os"
"os/signal"
"path"
"runtime"
"strings"
"syscall"
"testing"
"time"
"github.com/fsnotify/fsnotify"
"github.com/spf13/viper"
"github.com/XrayR-project/XrayR/panel"
)
var (
configFile = flag.String("config", "", "Config file for XrayR.")
printVersion = flag.Bool("version", false, "show version")
)
var (
version = "9.9.9"
codename = "Your custom Name"
intro = "Your custom describe"
)
func showVersion() {
fmt.Printf("%s %s (%s) \n", codename, version, intro)
}
func getConfig() *viper.Viper {
config := viper.New()
// Set custom path and name
if *configFile != "" {
configName := path.Base(*configFile)
configFileExt := path.Ext(*configFile)
configNameOnly := strings.TrimSuffix(configName, configFileExt)
configPath := path.Dir(*configFile)
config.SetConfigName(configNameOnly)
config.SetConfigType(strings.TrimPrefix(configFileExt, "."))
config.AddConfigPath(configPath)
// Set ASSET Path and Config Path for XrayR
os.Setenv("XRAY_LOCATION_ASSET", configPath)
os.Setenv("XRAY_LOCATION_CONFIG", configPath)
} else {
// Set default config path
config.SetConfigName("config")
config.SetConfigType("yml")
config.AddConfigPath(".")
}
if err := config.ReadInConfig(); err != nil {
log.Panicf("Config file error: %s \n", err)
}
config.WatchConfig() // Watch the config
return config
}
func main() {
flag.Parse()
showVersion()
if *printVersion {
return
}
config := getConfig()
panelConfig := &panel.Config{}
if err := config.Unmarshal(panelConfig); err != nil {
log.Panicf("Parse config file %v failed: %s \n", configFile, err)
}
p := panel.New(panelConfig)
lastTime := time.Now()
config.OnConfigChange(func(e fsnotify.Event) {
// Discarding event received within a short period of time after receiving an event.
if time.Now().After(lastTime.Add(3 * time.Second)) {
// Hot reload function
fmt.Println("Config file changed:", e.Name)
p.Close()
// Delete old instance and trigger GC
runtime.GC()
if err := config.Unmarshal(panelConfig); err != nil {
log.Panicf("Parse config file %v failed: %s \n", configFile, err)
}
p.Start()
lastTime = time.Now()
}
})
p.Start()
defer p.Close()
// Explicitly triggering GC to remove garbage from config loading.
runtime.GC()
// Running backend
{
osSignals := make(chan os.Signal, 1)
signal.Notify(osSignals, os.Interrupt, os.Kill, syscall.SIGTERM)
<-osSignals
}
}