update
This commit is contained in:
parent
9ddc3ce347
commit
ab17255bdc
BIN
FlexDXCluster.exe
Normal file
BIN
FlexDXCluster.exe
Normal file
Binary file not shown.
96
TCPClient.go
96
TCPClient.go
@ -13,7 +13,7 @@ import (
|
||||
|
||||
var spotRe *regexp.Regexp = regexp.MustCompile(`DX\sde\s([\w\d]+).*:\s+(\d+.\d)\s+([\w\d]+)\s+(CW|SSB|FT8|FT4|RTTY|USB|LSB)?\s+(.*)\s\s\s+([\d]+\w{1})`)
|
||||
|
||||
type TelnetClient struct {
|
||||
type TCPClient struct {
|
||||
Login string
|
||||
Password string
|
||||
Address string
|
||||
@ -31,89 +31,107 @@ type TelnetClient struct {
|
||||
Log *log.Logger
|
||||
}
|
||||
|
||||
func (tc *TelnetClient) setDefaultParams() {
|
||||
if tc.Timeout == 0 {
|
||||
tc.Timeout = 600 * time.Second
|
||||
}
|
||||
if tc.LogWriter == nil {
|
||||
tc.LogWriter = bufio.NewWriter(os.Stdout)
|
||||
func NewTCPClient(cfg Config, TCPServer *TCPServer, FlexClient *FlexClient, log *log.Logger) *TCPClient {
|
||||
return &TCPClient{
|
||||
Address: Cfg.Cluster.Server,
|
||||
Port: Cfg.Cluster.Port,
|
||||
Login: Cfg.Cluster.Login,
|
||||
MsgChan: TCPServer.MsgChan,
|
||||
CmdChan: TCPServer.CmdChan,
|
||||
SpotChan: FlexClient.SpotChan,
|
||||
Log: log,
|
||||
TCPServer: *TCPServer,
|
||||
FlexClient: *FlexClient,
|
||||
}
|
||||
}
|
||||
|
||||
func (tc *TelnetClient) StartClient() {
|
||||
func (c *TCPClient) setDefaultParams() {
|
||||
if c.Timeout == 0 {
|
||||
c.Timeout = 600 * time.Second
|
||||
}
|
||||
if c.LogWriter == nil {
|
||||
c.LogWriter = bufio.NewWriter(os.Stdout)
|
||||
}
|
||||
}
|
||||
|
||||
func (c *TCPClient) StartClient() {
|
||||
var err error
|
||||
|
||||
addr, err := net.ResolveTCPAddr("tcp", tc.Address+":"+tc.Port)
|
||||
addr, err := net.ResolveTCPAddr("tcp", c.Address+":"+c.Port)
|
||||
if err != nil {
|
||||
tc.Log.Error("cannot resolve Telnet Client address:", err)
|
||||
c.Log.Error("cannot resolve Telnet Client address:", err)
|
||||
}
|
||||
|
||||
tc.setDefaultParams()
|
||||
tc.Conn, err = net.DialTCP("tcp", nil, addr)
|
||||
c.setDefaultParams()
|
||||
c.Conn, err = net.DialTCP("tcp", nil, addr)
|
||||
if err != nil {
|
||||
tc.Log.Error("cannot connect to Telnet Client:", err)
|
||||
c.Log.Error("cannot connect to Telnet Client:", err)
|
||||
}
|
||||
tc.Log.Infof("connected to %s:%s", tc.Address, tc.Port)
|
||||
c.Log.Infof("connected to %s:%s", c.Address, c.Port)
|
||||
|
||||
err = tc.Conn.SetKeepAlive(true)
|
||||
err = c.Conn.SetKeepAlive(true)
|
||||
if err != nil {
|
||||
tc.Log.Error("error while setting keep alive:", err)
|
||||
c.Log.Error("error while setting keep alive:", err)
|
||||
}
|
||||
|
||||
tc.Reader = bufio.NewReader(tc.Conn)
|
||||
tc.Writer = bufio.NewWriter(tc.Conn)
|
||||
c.Reader = bufio.NewReader(c.Conn)
|
||||
c.Writer = bufio.NewWriter(c.Conn)
|
||||
|
||||
go tc.ReadLine()
|
||||
go c.ReadLine()
|
||||
}
|
||||
|
||||
func (tc *TelnetClient) Close() {
|
||||
tc.Writer.WriteString("bye")
|
||||
func (c *TCPClient) Close() {
|
||||
c.Writer.WriteString("bye")
|
||||
}
|
||||
|
||||
func (tc *TelnetClient) SetFilters() {
|
||||
func (c *TCPClient) SetFilters() {
|
||||
if Cfg.Cluster.FT8 {
|
||||
tc.Write([]byte("set/ft8\r\n"))
|
||||
tc.Log.Info("FT8 is on as defined in the config file")
|
||||
c.Write([]byte("set/ft8\r\n"))
|
||||
c.Log.Info("FT8 is on as defined in the config file")
|
||||
}
|
||||
|
||||
if Cfg.Cluster.Skimmer {
|
||||
tc.Write([]byte("set/skimmer\r\n"))
|
||||
tc.Log.Info("Skimmer is on as defined in the config file")
|
||||
c.Write([]byte("set/skimmer\r\n"))
|
||||
c.Log.Info("Skimmer is on as defined in the config file")
|
||||
}
|
||||
|
||||
if !Cfg.Cluster.FT8 {
|
||||
tc.Write([]byte("set/noft8\r\n"))
|
||||
tc.Log.Info("FT8 is off as defined in the config file")
|
||||
c.Write([]byte("set/noft8\r\n"))
|
||||
c.Log.Info("FT8 is off as defined in the config file")
|
||||
}
|
||||
|
||||
if !Cfg.Cluster.Skimmer {
|
||||
tc.Write([]byte("set/noskimmer\r\n"))
|
||||
tc.Log.Info("Skimmer is off as defined in the config file")
|
||||
c.Write([]byte("set/noskimmer\r\n"))
|
||||
c.Log.Info("Skimmer is off as defined in the config file")
|
||||
}
|
||||
}
|
||||
|
||||
func (tc *TelnetClient) ReadLine() {
|
||||
func (c *TCPClient) ReadLine() {
|
||||
for {
|
||||
message, err := tc.Reader.ReadString('\n')
|
||||
message, err := c.Reader.ReadString('\n')
|
||||
if err != nil {
|
||||
tc.Log.Errorf("Error reading message: %s", err)
|
||||
c.Log.Errorf("Error reading message: %s", err)
|
||||
continue
|
||||
}
|
||||
|
||||
if strings.Contains(message, "Login: \r\n") || strings.Contains(message, "Please enter your call: \r\n") {
|
||||
tc.Log.Info("Found login prompt...sending callsign")
|
||||
tc.Write([]byte(tc.Login + "\r\n"))
|
||||
c.Log.Info("Found login prompt...sending callsign")
|
||||
c.Write([]byte(c.Login + "\r\n"))
|
||||
time.Sleep(time.Second * 2)
|
||||
tc.SetFilters()
|
||||
c.SetFilters()
|
||||
}
|
||||
|
||||
ProcessTelnetSpot(spotRe, message, tc.SpotChan, tc.Log)
|
||||
tc.MsgChan <- message
|
||||
ProcessTelnetSpot(spotRe, message, c.SpotChan, c.Log)
|
||||
|
||||
// Send the spot message to TCP server
|
||||
if len(c.TCPServer.Clients) > 0 {
|
||||
c.MsgChan <- message
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Write sends raw data to remove telnet server
|
||||
func (tc *TelnetClient) Write(data []byte) (n int, err error) {
|
||||
func (tc *TCPClient) Write(data []byte) (n int, err error) {
|
||||
n, err = tc.Writer.Write(data)
|
||||
if err == nil {
|
||||
err = tc.Writer.Flush()
|
||||
|
26
TCPServer.go
26
TCPServer.go
@ -50,7 +50,7 @@ func (s *TCPServer) StartServer() {
|
||||
|
||||
defer s.Listener.Close()
|
||||
|
||||
s.Log.Info("telnet server listening on %s:%s", Cfg.Telnet.Host, Cfg.Telnet.Port)
|
||||
s.Log.Infof("telnet server listening on %s:%s", Cfg.Telnet.Host, Cfg.Telnet.Port)
|
||||
|
||||
go func() {
|
||||
for message := range s.MsgChan {
|
||||
@ -74,39 +74,43 @@ func (s *TCPServer) StartServer() {
|
||||
}
|
||||
|
||||
func (s *TCPServer) handleConnection() {
|
||||
defer s.Conn.Close()
|
||||
s.Conn.Write([]byte("Welcome to the FlexDXCluster telnet server! Type 'bye' to exit.\n"))
|
||||
|
||||
// s.Conn.Write([]byte(`To ALL de XV9Q <0234Z> : Clicked on "JH2UNG"\n`))
|
||||
s.Reader = bufio.NewReader(s.Conn)
|
||||
s.Writer = bufio.NewWriter(s.Conn)
|
||||
|
||||
reader := bufio.NewReader(s.Conn)
|
||||
for {
|
||||
|
||||
message, err := reader.ReadString('\n')
|
||||
message, err := s.Reader.ReadString('\n')
|
||||
if err != nil {
|
||||
s.Mutex.Lock()
|
||||
delete(s.Clients, s.Conn)
|
||||
s.Mutex.Unlock()
|
||||
s.Log.Info("client disconnected")
|
||||
s.Log.Infof("client %s disconnected", s.Conn.RemoteAddr().String())
|
||||
return
|
||||
}
|
||||
|
||||
message = strings.TrimSpace(message)
|
||||
|
||||
if message == "bye" {
|
||||
s.Log.Infof("Message reçu du client: %s\n", message)
|
||||
|
||||
switch message {
|
||||
case "bye":
|
||||
s.Mutex.Lock()
|
||||
delete(s.Clients, s.Conn)
|
||||
s.Mutex.Unlock()
|
||||
s.Log.Info("client disconnected")
|
||||
s.Log.Infof("client %s disconnected", s.Conn.RemoteAddr().String())
|
||||
return
|
||||
case "SH/DX 30":
|
||||
return
|
||||
default:
|
||||
s.Write("cannot identify command\n")
|
||||
}
|
||||
|
||||
s.Log.Info("Message reçu du client: %s\n", message)
|
||||
}
|
||||
}
|
||||
|
||||
func (s *TCPServer) Write(message string) (n int, err error) {
|
||||
n, err = s.Writer.Write([]byte(message))
|
||||
_, err = s.Writer.Write([]byte(message))
|
||||
if err == nil {
|
||||
err = s.Writer.Flush()
|
||||
}
|
||||
|
@ -11,7 +11,7 @@ cluster:
|
||||
ft8: false
|
||||
flex:
|
||||
ip: 10.10.10.120
|
||||
spot_life: 300
|
||||
spot_life: 600
|
||||
clublog:
|
||||
api: 5767f19333363a9ef432ee9cd4141fe76b8adf38
|
||||
telnet:
|
||||
|
28
database.go
28
database.go
@ -54,7 +54,7 @@ func NewFlexDXDatabase(filePath string, log *log.Logger) *FlexDXClusterRepositor
|
||||
`CREATE TABLE IF NOT EXISTS "spots" (
|
||||
"id" INTEGER NOT NULL UNIQUE,
|
||||
"commandNumber" INTEGER NOT NULL UNIQUE,
|
||||
"flexSpotNumber" INTEGER UNIQUE,
|
||||
"flexSpotNumber" INTEGER,
|
||||
"dx" TEXT NOT NULL,
|
||||
"freqMhz" TEXT,
|
||||
"freqHz" TEXT,
|
||||
@ -63,6 +63,7 @@ func NewFlexDXDatabase(filePath string, log *log.Logger) *FlexDXClusterRepositor
|
||||
"spotter" INTEGER,
|
||||
"flexMode" TEXT,
|
||||
"source" TEXT,
|
||||
"time" TEXT,
|
||||
"timestamp" INTEGER,
|
||||
"lifeTime" TEXT,
|
||||
"priority" TEXT,
|
||||
@ -195,7 +196,7 @@ func (r *FlexDXClusterRepository) FindDXSameBand(spot FlexSpot) (*FlexSpot, erro
|
||||
|
||||
s := FlexSpot{}
|
||||
for rows.Next() {
|
||||
if err := rows.Scan(&s.ID, &s.CommandNumber, &s.FlexSpotNumber, &s.DX, &s.FrequencyMhz, &s.FrequencyHz, &s.Band, &s.Mode, &s.SpotterCallsign, &s.FlexMode, &s.Source, &s.TimeStamp, &s.LifeTime, &s.Priority,
|
||||
if err := rows.Scan(&s.ID, &s.CommandNumber, &s.FlexSpotNumber, &s.DX, &s.FrequencyMhz, &s.FrequencyHz, &s.Band, &s.Mode, &s.SpotterCallsign, &s.FlexMode, &s.Source, &s.UTCTime, &s.TimeStamp, &s.LifeTime, &s.Priority,
|
||||
&s.Comment, &s.Color, &s.BackgroundColor); err != nil {
|
||||
fmt.Println(err)
|
||||
return nil, err
|
||||
@ -205,8 +206,8 @@ func (r *FlexDXClusterRepository) FindDXSameBand(spot FlexSpot) (*FlexSpot, erro
|
||||
}
|
||||
|
||||
func (r *FlexDXClusterRepository) CreateSpot(spot FlexSpot) {
|
||||
query := "INSERT INTO `spots` (`commandNumber`, `flexSpotNumber`, `dx`, `freqMhz`, `freqHz`, `band`, `mode`, `spotter`, `flexMode`, `source`, `timestamp`, `lifeTime`, `priority`, `comment`, `color`, `backgroundColor`) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"
|
||||
insertResult, err := r.db.ExecContext(context.Background(), query, spot.CommandNumber, spot.CommandNumber, spot.DX, spot.FrequencyMhz, spot.FrequencyHz, spot.Band, spot.Mode, spot.SpotterCallsign, spot.FlexMode, spot.Source, time.Now().Unix(), spot.LifeTime, spot.Priority, spot.Comment, spot.Color, spot.BackgroundColor)
|
||||
query := "INSERT INTO `spots` (`commandNumber`, `flexSpotNumber`, `dx`, `freqMhz`, `freqHz`, `band`, `mode`, `spotter`, `flexMode`, `source`, `time`, `timestamp`, `lifeTime`, `priority`, `comment`, `color`, `backgroundColor`) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"
|
||||
insertResult, err := r.db.ExecContext(context.Background(), query, spot.CommandNumber, spot.CommandNumber, spot.DX, spot.FrequencyMhz, spot.FrequencyHz, spot.Band, spot.Mode, spot.SpotterCallsign, spot.FlexMode, spot.Source, spot.UTCTime, time.Now().Unix(), spot.LifeTime, spot.Priority, spot.Comment, spot.Color, spot.BackgroundColor)
|
||||
if err != nil {
|
||||
log.Errorf("cannot insert spot in database: %s", err)
|
||||
}
|
||||
@ -231,7 +232,7 @@ func (r *FlexDXClusterRepository) FindSpotByCommandNumber(commandNumber string)
|
||||
|
||||
s := FlexSpot{}
|
||||
for rows.Next() {
|
||||
if err := rows.Scan(&s.ID, &s.CommandNumber, &s.FlexSpotNumber, &s.DX, &s.FrequencyMhz, &s.FrequencyHz, &s.Band, &s.Mode, &s.SpotterCallsign, &s.FlexMode, &s.Source, &s.TimeStamp, &s.LifeTime, &s.Priority,
|
||||
if err := rows.Scan(&s.ID, &s.CommandNumber, &s.FlexSpotNumber, &s.DX, &s.FrequencyMhz, &s.FrequencyHz, &s.Band, &s.Mode, &s.SpotterCallsign, &s.FlexMode, &s.Source, &s.UTCTime, &s.TimeStamp, &s.LifeTime, &s.Priority,
|
||||
&s.Comment, &s.Color, &s.BackgroundColor); err != nil {
|
||||
fmt.Println(err)
|
||||
return nil, err
|
||||
@ -249,7 +250,7 @@ func (r *FlexDXClusterRepository) FindSpotByFlexSpotNumber(spotNumber string) (*
|
||||
|
||||
s := FlexSpot{}
|
||||
for rows.Next() {
|
||||
if err := rows.Scan(&s.ID, &s.CommandNumber, &s.FlexSpotNumber, &s.DX, &s.FrequencyMhz, &s.FrequencyHz, &s.Band, &s.Mode, &s.SpotterCallsign, &s.FlexMode, &s.Source, &s.TimeStamp, &s.LifeTime, &s.Priority,
|
||||
if err := rows.Scan(&s.ID, &s.CommandNumber, &s.FlexSpotNumber, &s.DX, &s.FrequencyMhz, &s.FrequencyHz, &s.Band, &s.Mode, &s.SpotterCallsign, &s.FlexMode, &s.Source, &s.UTCTime, &s.TimeStamp, &s.LifeTime, &s.Priority,
|
||||
&s.Comment, &s.Color, &s.BackgroundColor); err != nil {
|
||||
fmt.Println(err)
|
||||
return nil, err
|
||||
@ -258,8 +259,8 @@ func (r *FlexDXClusterRepository) FindSpotByFlexSpotNumber(spotNumber string) (*
|
||||
return &s, nil
|
||||
}
|
||||
|
||||
func (r *FlexDXClusterRepository) UpdateFlexSpotNumberByID(flexSpot string, spot FlexSpot) (*FlexSpot, error) {
|
||||
flexSpotNumberInt, _ := strconv.Atoi(flexSpot)
|
||||
func (r *FlexDXClusterRepository) UpdateFlexSpotNumberByID(flexSpotNumber string, spot FlexSpot) (*FlexSpot, error) {
|
||||
flexSpotNumberInt, _ := strconv.Atoi(flexSpotNumber)
|
||||
rows, err := r.db.Query(`UPDATE spots SET flexSpotNumber = ? WHERE id = ? RETURNING *`, flexSpotNumberInt, spot.ID)
|
||||
if err != nil {
|
||||
r.Log.Errorf("could not update database: %s", err)
|
||||
@ -267,7 +268,7 @@ func (r *FlexDXClusterRepository) UpdateFlexSpotNumberByID(flexSpot string, spot
|
||||
|
||||
s := FlexSpot{}
|
||||
for rows.Next() {
|
||||
if err := rows.Scan(&s.ID, &s.CommandNumber, &s.FlexSpotNumber, &s.DX, &s.FrequencyMhz, &s.FrequencyHz, &s.Band, &s.Mode, &s.SpotterCallsign, &s.FlexMode, &s.Source, &s.TimeStamp, &s.LifeTime, &s.Priority,
|
||||
if err := rows.Scan(&s.ID, &s.CommandNumber, &s.FlexSpotNumber, &s.DX, &s.FrequencyMhz, &s.FrequencyHz, &s.Band, &s.Mode, &s.SpotterCallsign, &s.FlexMode, &s.Source, &s.UTCTime, &s.TimeStamp, &s.LifeTime, &s.Priority,
|
||||
&s.Comment, &s.Color, &s.BackgroundColor); err != nil {
|
||||
fmt.Println(err)
|
||||
return nil, err
|
||||
@ -277,6 +278,15 @@ func (r *FlexDXClusterRepository) UpdateFlexSpotNumberByID(flexSpot string, spot
|
||||
return &s, nil
|
||||
}
|
||||
|
||||
func (r *FlexDXClusterRepository) DeleteSpotByFlexSpotNumber(flexSpotNumber string) {
|
||||
flexSpotNumberInt, _ := strconv.Atoi(flexSpotNumber)
|
||||
query := "DELETE from spots WHERE flexSpotNumber = ?"
|
||||
_, err := r.db.Exec(query, flexSpotNumberInt)
|
||||
if err != nil {
|
||||
r.Log.Errorf("could not delete spot %v from database", flexSpotNumberInt)
|
||||
}
|
||||
}
|
||||
|
||||
func DeleteDatabase(filePath string, log *log.Logger) {
|
||||
_, err := os.Stat(filePath)
|
||||
if !os.IsNotExist(err) {
|
||||
|
BIN
flex.sqlite
BIN
flex.sqlite
Binary file not shown.
116
flexradio.go
116
flexradio.go
@ -5,14 +5,14 @@ import (
|
||||
"fmt"
|
||||
"net"
|
||||
"os"
|
||||
"strconv"
|
||||
"regexp"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
log "github.com/sirupsen/logrus"
|
||||
)
|
||||
|
||||
var command int = 1
|
||||
var CommandNumber int = 1
|
||||
|
||||
type FlexSpot struct {
|
||||
ID int
|
||||
@ -27,6 +27,7 @@ type FlexSpot struct {
|
||||
Source string
|
||||
SpotterCallsign string
|
||||
TimeStamp int64
|
||||
UTCTime string
|
||||
LifeTime string
|
||||
Priority string
|
||||
Comment string
|
||||
@ -46,10 +47,10 @@ type FlexClient struct {
|
||||
MsgChan chan string
|
||||
Repo FlexDXClusterRepository
|
||||
Log *log.Logger
|
||||
TCPServer *TCPServer
|
||||
TCPServer TCPServer
|
||||
}
|
||||
|
||||
func NewFlexClient(repo FlexDXClusterRepository, TCPServer *TCPServer, log *log.Logger) *FlexClient {
|
||||
func NewFlexClient(repo FlexDXClusterRepository, TCPServer TCPServer, log *log.Logger) *FlexClient {
|
||||
return &FlexClient{
|
||||
Address: Cfg.Flex.IP,
|
||||
Port: "4992",
|
||||
@ -74,7 +75,7 @@ func (fc *FlexClient) StartFlexClient() {
|
||||
fc.Timeout = 600 * time.Second
|
||||
fc.Conn, err = net.DialTCP("tcp", nil, addr)
|
||||
if err != nil {
|
||||
fc.Log.Error("could not dial flex client:", err)
|
||||
fc.Log.Error("could not connect to flex radio, exiting...", err)
|
||||
os.Exit(1)
|
||||
}
|
||||
fc.Log.Infof("connected to %s:%s", fc.Address, fc.Port)
|
||||
@ -94,14 +95,22 @@ func (fc *FlexClient) StartFlexClient() {
|
||||
}
|
||||
|
||||
go fc.ReadLine()
|
||||
|
||||
subSpotAllCmd := fmt.Sprintf("C%v|sub spot all", CommandNumber)
|
||||
fc.Write(subSpotAllCmd)
|
||||
CommandNumber++
|
||||
|
||||
clrSpotAllCmd := fmt.Sprintf("C%v|spot clear", CommandNumber)
|
||||
fc.Write(clrSpotAllCmd)
|
||||
CommandNumber++
|
||||
}
|
||||
|
||||
func (fc *FlexClient) SendSpottoFlex(spot TelnetSpot) (n int, err error) {
|
||||
func (fc *FlexClient) SendSpottoFlex(spot TelnetSpot) {
|
||||
|
||||
freq := FreqMhztoHz(spot.Frequency)
|
||||
|
||||
flexSpot := FlexSpot{
|
||||
CommandNumber: command,
|
||||
CommandNumber: CommandNumber,
|
||||
DX: spot.DX,
|
||||
FrequencyMhz: freq,
|
||||
FrequencyHz: spot.Frequency,
|
||||
@ -110,6 +119,7 @@ func (fc *FlexClient) SendSpottoFlex(spot TelnetSpot) (n int, err error) {
|
||||
Source: "FlexDXCluster",
|
||||
SpotterCallsign: spot.Spotter,
|
||||
TimeStamp: time.Now().Unix(),
|
||||
UTCTime: spot.Time,
|
||||
LifeTime: Cfg.Flex.SpotLife,
|
||||
Comment: spot.Comment,
|
||||
Color: "#eaeaea",
|
||||
@ -149,70 +159,82 @@ func (fc *FlexClient) SendSpottoFlex(spot TelnetSpot) (n int, err error) {
|
||||
fc.Log.Error("could not find the DX in the database: ", err)
|
||||
}
|
||||
|
||||
var stringSpot string
|
||||
spotLife, _ := strconv.Atoi(Cfg.Flex.SpotLife)
|
||||
spotTime := time.Unix(srcFlexSpot.TimeStamp, 0)
|
||||
elapsed := time.Since(spotTime)
|
||||
|
||||
if srcFlexSpot.DX == "" {
|
||||
fc.Repo.CreateSpot(flexSpot)
|
||||
stringSpot = fmt.Sprintf("C%v|spot add rx_freq=%v callsign=%s mode=%s source=%s spotter_callsign=%s timestamp=%v lifetime_seconds=%s comment=%s color=%s background_color=%s priority=%s", flexSpot.CommandNumber, flexSpot.FrequencyMhz,
|
||||
stringSpot := fmt.Sprintf("C%v|spot add rx_freq=%v callsign=%s mode=%s source=%s spotter_callsign=%s timestamp=%v lifetime_seconds=%s comment=%s color=%s background_color=%s priority=%s", flexSpot.CommandNumber, flexSpot.FrequencyMhz,
|
||||
flexSpot.DX, flexSpot.Mode, flexSpot.Source, flexSpot.SpotterCallsign, flexSpot.TimeStamp, flexSpot.LifeTime, flexSpot.Comment, flexSpot.Color, flexSpot.BackgroundColor, flexSpot.Priority)
|
||||
} else if srcFlexSpot.DX != "" && elapsed > time.Duration(spotLife) {
|
||||
fc.SendSpot(stringSpot)
|
||||
} else if srcFlexSpot.DX != "" && srcFlexSpot.Band == flexSpot.Band && srcFlexSpot.FrequencyMhz != flexSpot.FrequencyMhz {
|
||||
fc.Repo.UpdateSpotSameBand(flexSpot)
|
||||
stringSpot = fmt.Sprintf("C%v|spot add rx_freq=%v callsign=%s mode=%s source=%s spotter_callsign=%s timestamp=%v lifetime_seconds=%s comment=%s color=%s background_color=%s priority=%s", flexSpot.CommandNumber, flexSpot.FrequencyMhz,
|
||||
flexSpot.DX, flexSpot.Mode, flexSpot.Source, flexSpot.SpotterCallsign, flexSpot.TimeStamp, flexSpot.LifeTime, flexSpot.Comment, flexSpot.Color, flexSpot.BackgroundColor, flexSpot.Priority)
|
||||
} else if srcFlexSpot.DX != "" && srcFlexSpot.Band == flexSpot.Band && srcFlexSpot.FrequencyMhz != flexSpot.FrequencyMhz && elapsed < time.Duration(spotLife) {
|
||||
fc.Repo.UpdateSpotSameBand(flexSpot)
|
||||
stringSpot = fmt.Sprintf("C%v|spot set %v rx_freq=%v callsign=%s mode=%s source=%s spotter_callsign=%s timestamp=%v lifetime_seconds=%s comment=%s color=%s background_color=%s priority=%s", flexSpot.CommandNumber, srcFlexSpot.CommandNumber, flexSpot.FrequencyMhz,
|
||||
stringSpot := fmt.Sprintf("C%v|spot set %v rx_freq=%v callsign=%s mode=%s source=%s spotter_callsign=%s timestamp=%v lifetime_seconds=%s comment=%s color=%s background_color=%s priority=%s", flexSpot.CommandNumber, srcFlexSpot.CommandNumber, flexSpot.FrequencyMhz,
|
||||
flexSpot.DX, flexSpot.Mode, flexSpot.Source, flexSpot.SpotterCallsign, flexSpot.TimeStamp, flexSpot.LifeTime, flexSpot.Comment, flexSpot.Color, flexSpot.BackgroundColor, flexSpot.Priority)
|
||||
CommandNumber++
|
||||
stringDelete := fmt.Sprintf("C%v|spot remove %v", CommandNumber, srcFlexSpot.FlexSpotNumber)
|
||||
fc.DeleteAndSendSpot(stringSpot, stringDelete)
|
||||
}
|
||||
|
||||
CommandNumber++
|
||||
|
||||
}
|
||||
|
||||
func (fc *FlexClient) SendSpot(stringSpot string) {
|
||||
fc.Write(stringSpot)
|
||||
}
|
||||
|
||||
command++
|
||||
return
|
||||
|
||||
func (fc *FlexClient) DeleteAndSendSpot(stringSpot string, deleteSpot string) {
|
||||
fc.Write(deleteSpot)
|
||||
fc.Write(stringSpot)
|
||||
}
|
||||
|
||||
func (fc *FlexClient) ReadLine() {
|
||||
|
||||
for {
|
||||
message, err := fc.Reader.ReadString(byte('\n'))
|
||||
if err != nil {
|
||||
fc.Log.Errorf("error reading message: %s", err)
|
||||
continue
|
||||
fc.Log.Errorf("error reading message from flexradio closing program: %s", err)
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
// regRespSpot := *regexp.MustCompile(`R(\d+)\|0\|(\d+)\n`)
|
||||
// respSpot := regRespSpot.FindStringSubmatch(message)
|
||||
// msgRaw := strings.TrimSpace(message)
|
||||
// fc.Log.Info(msgRaw)
|
||||
|
||||
// if len(respSpot) > 0 {
|
||||
// spot, _ := fc.Repo.FindSpotByCommandNumber(respSpot[1])
|
||||
// _, err := fc.Repo.UpdateFlexSpotNumberByID(respSpot[2], *spot)
|
||||
// if err != nil {
|
||||
// fc.Log.Errorf("could not update flex spot number in database: %s", err)
|
||||
// }
|
||||
// }
|
||||
// Response when spot is added
|
||||
regRespSpot := *regexp.MustCompile(`R(\d+)\|0\|(\d+)\n`)
|
||||
respSpot := regRespSpot.FindStringSubmatch(message)
|
||||
|
||||
// regTriggerSpot := *regexp.MustCompile(`.*\|spot\s(\d+)\striggered.*`)
|
||||
// respTrigger := regTriggerSpot.FindStringSubmatch(message)
|
||||
if len(respSpot) > 0 {
|
||||
spot, _ := fc.Repo.FindSpotByCommandNumber(respSpot[1])
|
||||
_, err := fc.Repo.UpdateFlexSpotNumberByID(respSpot[2], *spot)
|
||||
if err != nil {
|
||||
fc.Log.Errorf("could not update flex spot number in database: %s", err)
|
||||
}
|
||||
}
|
||||
|
||||
// if len(respTrigger) > 0 {
|
||||
// spot, err := fc.Repo.FindSpotByFlexSpotNumber(respTrigger[1])
|
||||
// if err != nil {
|
||||
// fc.Log.Errorf("could not find spot by flex spot number in database: %s", err)
|
||||
// }
|
||||
// Response when a spot is clicked
|
||||
regTriggerSpot := *regexp.MustCompile(`.*spot (\d+) triggered.*\n`)
|
||||
respTrigger := regTriggerSpot.FindStringSubmatch(message)
|
||||
|
||||
// msg := fmt.Sprintf(`To ALL de %s <0233z> : Clicked on %s at %s`, Cfg.SQLite.Callsign, spot.DX, spot.FrequencyHz)
|
||||
// if len(fc.TCPServer.Clients) > 0 {
|
||||
// fc.MsgChan <- msg
|
||||
// }
|
||||
if len(respTrigger) > 0 {
|
||||
spot, err := fc.Repo.FindSpotByFlexSpotNumber(respTrigger[1])
|
||||
if err != nil {
|
||||
fc.Log.Errorf("could not find spot by flex spot number in database: %s", err)
|
||||
}
|
||||
|
||||
// }
|
||||
msg := fmt.Sprintf(`To ALL de %s <%s> : Clicked on "%s" at %s`, Cfg.SQLite.Callsign, spot.UTCTime, spot.DX, spot.FrequencyHz)
|
||||
if len(fc.TCPServer.Clients) > 0 {
|
||||
fc.MsgChan <- msg
|
||||
fc.Log.Infof("%s clicked on spot \"%s\" at %s", Cfg.SQLite.Callsign, spot.DX, spot.FrequencyMhz)
|
||||
}
|
||||
}
|
||||
|
||||
msg := strings.TrimSpace(message)
|
||||
fc.Log.Info(msg)
|
||||
// Status when a spot is deleted
|
||||
regSpotDeleted := *regexp.MustCompile(`S\d+\|spot (\d+) removed`)
|
||||
respDelete := regSpotDeleted.FindStringSubmatch(message)
|
||||
|
||||
if len(respDelete) > 0 {
|
||||
fc.Repo.DeleteSpotByFlexSpotNumber(respDelete[1])
|
||||
fc.Log.Infof("deleted spot %v from database", respDelete[1])
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
195396
flexradio.log
195396
flexradio.log
File diff suppressed because it is too large
Load Diff
@ -8,8 +8,6 @@ import (
|
||||
prefixed "github.com/x-cray/logrus-prefixed-formatter"
|
||||
)
|
||||
|
||||
var Log *log.Logger
|
||||
|
||||
func NewLog() *log.Logger {
|
||||
f, err := os.OpenFile("flexradio.log", os.O_RDWR|os.O_CREATE|os.O_APPEND, 0666)
|
||||
if err != nil {
|
||||
@ -18,7 +16,7 @@ func NewLog() *log.Logger {
|
||||
|
||||
w := io.MultiWriter(os.Stdout, f)
|
||||
|
||||
Log := &log.Logger{
|
||||
l := &log.Logger{
|
||||
Out: w,
|
||||
Level: log.DebugLevel,
|
||||
Formatter: &prefixed.TextFormatter{
|
||||
@ -29,7 +27,9 @@ func NewLog() *log.Logger {
|
||||
},
|
||||
}
|
||||
|
||||
return Log
|
||||
l.Level = log.DebugLevel
|
||||
|
||||
return l
|
||||
}
|
||||
|
||||
// Info ...
|
||||
@ -47,6 +47,10 @@ func Error(format string, v ...interface{}) {
|
||||
log.Errorf(format, v...)
|
||||
}
|
||||
|
||||
func Debug(format string, v ...interface{}) {
|
||||
log.Debugf(format, v...)
|
||||
}
|
||||
|
||||
var (
|
||||
|
||||
// ConfigError ...
|
||||
|
23
main.go
23
main.go
@ -44,33 +44,18 @@ func main() {
|
||||
log := logger.NewLog()
|
||||
|
||||
log.Info("config loaded.")
|
||||
log.Infof("Callsign: %s\n", Cfg.SQLite.Callsign)
|
||||
log.Infof("Callsign: %s", Cfg.SQLite.Callsign)
|
||||
|
||||
DeleteDatabase("./flex.sqlite", log)
|
||||
|
||||
repo := NewFlexDXDatabase("flex.sqlite", log)
|
||||
|
||||
// Create TelnetServer
|
||||
TCPServer := NewTCPServer(Cfg.Telnet.Host, Cfg.Telnet.Port, log)
|
||||
FlexClient := NewFlexClient(*repo, *TCPServer, log)
|
||||
TCPClient := NewTCPClient(*Cfg, TCPServer, FlexClient, log)
|
||||
|
||||
// Connect to Flex Radio (ip defined in config file)
|
||||
FlexClient := NewFlexClient(*repo, TCPServer, log)
|
||||
go FlexClient.StartFlexClient()
|
||||
|
||||
// Connect to DX Cluster
|
||||
TelnetClient := TelnetClient{
|
||||
Address: Cfg.Cluster.Server,
|
||||
Port: Cfg.Cluster.Port,
|
||||
Login: Cfg.Cluster.Login,
|
||||
MsgChan: TCPServer.MsgChan,
|
||||
CmdChan: TCPServer.CmdChan,
|
||||
SpotChan: FlexClient.SpotChan,
|
||||
Log: log,
|
||||
}
|
||||
|
||||
go TelnetClient.StartClient()
|
||||
|
||||
// Start TelnetServer
|
||||
go TCPClient.StartClient()
|
||||
go TCPServer.StartServer()
|
||||
|
||||
select {}
|
||||
|
1
spot.go
1
spot.go
@ -105,6 +105,7 @@ func ProcessTelnetSpot(re *regexp.Regexp, spotRaw string, SpotChan chan TelnetSp
|
||||
spot.DX, spot.Spotter, spot.Frequency, spot.Band, spot.Mode, spot.Comment, spot.Time, spot.DXCC)
|
||||
}
|
||||
|
||||
// send spot to SpotChan to Flex Client to send the spot to Flex radio
|
||||
SpotChan <- spot
|
||||
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user