package main import ( "AudioPlayer/Common" "AudioPlayer/Intercom" "AudioPlayer/NTP" ProcessMonitor "AudioPlayer/Process" "AudioPlayer/QuectelAT" "AudioPlayer/SystemInfo" "AudioPlayer/VoiceCall" pb "AudioPlayer/gRPC_Model" "bytes" "fmt" "github.com/gin-gonic/gin" "go-micro.dev/v5/registry" "google.golang.org/grpc" "google.golang.org/grpc/reflection" "log" "net" "os" "os/exec" "strings" "sync" "github.com/BurntSushi/toml" "github.com/denisbrodbeck/machineid" ) func Command(exe string, args []string, ctx *gin.Context) { cmd := exec.Command(exe, args...) var in bytes.Buffer cmd.Stdin = &in var out bytes.Buffer cmd.Stdout = &out err := cmd.Run() if err != nil { println(err.Error()) return } ctx.Data(200, "text/plain", out.Bytes()) } var InExecMutex sync.RWMutex var InExec bool func MutexCommandGin(ctx *gin.Context) { InExecMutex.RLock() if InExec { ctx.AbortWithStatusJSON(200, gin.H{"error": "Command is already in execution. Request discarded."}) InExecMutex.RUnlock() return } InExecMutex.RUnlock() var v []string err := ctx.ShouldBindJSON(&v) if err != nil { println(err.Error()) return } InExecMutex.Lock() InExec = true InExecMutex.Unlock() Command(ctx.Query("exec"), v, ctx) InExecMutex.Lock() InExec = false InExecMutex.Unlock() } func CommandGin(ctx *gin.Context) { var v []string err := ctx.ShouldBindJSON(&v) if err != nil { println(err.Error()) return } Command(ctx.Query("exec"), v, ctx) } type ServerInfo struct { UseNTP bool `toml:"UseNTP"` GlobalPositioningSystem *GPS `toml:"GPS"` VoiceService *VoiceCall.Voice `toml:"VoiceCall"` Intercom *Intercom.Intercom `toml:"Intercom"` Alarm *Alarm `toml:"Alarm"` } type Alarm struct { Volume int `toml:"Volume"` } func (receiver *ServerInfo) Refresh() { marshal, err := toml.Marshal(receiver) if err != nil { return } err = os.WriteFile("./cfg.toml", marshal, 0666) if err != nil { return } } func main() { Common.Micro = registry.NewRegistry() go ProcessMonitor.Start() var err error var cfg ServerInfo Common.Machine, err = machineid.ID() if err != nil { return } _, err = toml.DecodeFile("./cfg.toml", &cfg) if err != nil { log.Println(err.Error()) //return } if cfg.UseNTP { ntpSrv := NTP.NewNTPServer("0.0.0.0:123") err = ntpSrv.Start() if err != nil { log.Println(err.Error()) return } } // Set up a TCP listener. gRPClistener, err := net.Listen("tcp", ":50051") if err != nil { log.Println("Failed to listen: %v", err) return } // Create a gRPC server. grpcServer := grpc.NewServer() NMCLI := SystemInfo.NMCliServer{} NMCLI.Open() pb.RegisterTimeServer(grpcServer, &SystemInfo.TimeGRpcServer{}) pb.RegisterNetworkManagerServer(grpcServer, &NMCLI) reflection.Register(grpcServer) go func() { log.Println(" Server is running on port 50051...") if err := grpcServer.Serve(gRPClistener); err != nil { log.Fatalf("Failed to serve: %v", err) } }() if cfg.VoiceService != nil { cfg.VoiceService.SetOnRefresh(cfg.Refresh) err = cfg.VoiceService.ConnectRoom() if err == nil { go func() { err := cfg.VoiceService.PushMicrophone() if err != nil { log.Println(err.Error()) return } }() } else { log.Println(err.Error()) } } err = os.Setenv("ALSA_PCM_CARD", "1") if err != nil { log.Println(err.Error()) return } err = os.Setenv("ALSA_PCM_DEVICE", "0") if err != nil { log.Println(err.Error()) return } gin.SetMode(gin.ReleaseMode) r := gin.Default() r.PUT("/MutexCommand", MutexCommandGin) r.PUT("/Command", CommandGin) r.GET("/Host", Host) r.GET("/NetPort", NetPort) r.GET("/Memory", Memory) r.GET("/Cpu", Cpu) r.GET("/Bandwidth", Bandwidth) r.GET("/Temperature", Temperature) r.GET("/File", func(context *gin.Context) { if context.GetHeader("token") != "以无我、无人、无众生、无寿者,修一切善法,即得阿耨多罗三藐三菩提。" { return } context.File(context.Query("file")) }) if cfg.Intercom != nil && cfg.Alarm != nil { cfg.Intercom.Init() r.PUT("/Mailbox", func(ctx *gin.Context) { data, err := ctx.GetRawData() if err != nil { return } cfg.Intercom.Add(data) }) go cfg.Intercom.Start() } var Q QuectelAT.Quectel err = Q.Open() if err == nil { r.GET("/MobileSignal", func(context *gin.Context) { if data, err := Q.GetCSQ(); err != nil { context.JSON(400, gin.H{"error": err.Error()}) } else { context.JSON(200, data) } }) } if cfg.GlobalPositioningSystem != nil { err = cfg.GlobalPositioningSystem.Open() if err != nil { log.Println(err.Error()) return } r.GET("/GPS", cfg.GlobalPositioningSystem.ObtainLatitudeAndLongitude) } // 获取网卡ip interfaces, err := net.Interfaces() if err != nil { return } for _, inter := range interfaces { if inter.Flags&net.FlagUp == 0 { continue } if inter.Flags&net.FlagRunning == 0 { continue } if inter.HardwareAddr == nil { continue } if shouldSkipInterface(inter.Name) { continue } fmt.Printf("%v", inter) println(inter.Name) addrs, err := inter.Addrs() if err != nil { return } for _, addr := range addrs { if ipnet, ok := addr.(*net.IPNet); ok && !ipnet.IP.IsLoopback() { if ipnet.IP.To4() != nil { Common.Address = append(Common.Address, ipnet.IP.String()) } } } } err = Common.Micro.Register( ®istry.Service{ Name: "omat_tsukino_usagi", Version: "latest", Nodes: []*registry.Node{ { Id: Common.Machine + "_tsukino_usagi", Address: "0.0.0.0:4000", Metadata: map[string]string{ "protocol": "http", "ip": strings.Join(Common.Address, ","), }, }, { Id: Common.Machine + "_tsukino_usagi_grpc", Address: "0.0.0.0:50051", Metadata: map[string]string{ "protocol": "grpc", "ip": strings.Join(Common.Address, ","), }, }, }, }, ) if err != nil { log.Println(err.Error()) return } r.Run(":4000") }