Search/init.go

212 lines
4.2 KiB
Go
Raw Normal View History

2024-06-12 12:26:50 +00:00
package main
import (
"bufio"
2024-06-30 21:20:52 +00:00
"crypto/rand"
"encoding/base64"
2024-06-12 12:26:50 +00:00
"fmt"
"log"
"os"
"strconv"
2024-06-30 21:20:52 +00:00
"strings"
2024-07-05 01:08:35 +00:00
"sync"
2024-08-08 11:35:50 +00:00
"time"
2024-07-05 01:08:35 +00:00
"github.com/fsnotify/fsnotify"
2024-08-08 13:03:33 +00:00
"gopkg.in/ini.v1"
2024-06-12 12:26:50 +00:00
)
type Config struct {
2024-08-08 13:03:33 +00:00
Port int
AuthCode string
Peers []string
PeerID string
Domain string
2024-06-12 12:26:50 +00:00
}
var defaultConfig = Config{
2024-08-08 13:03:33 +00:00
Port: 5000,
Domain: "localhost",
2024-06-12 12:26:50 +00:00
}
2024-08-08 13:03:33 +00:00
const configFilePath = "config.ini"
2024-06-12 12:26:50 +00:00
2024-07-05 01:08:35 +00:00
var config Config
var configLock sync.RWMutex
2024-06-12 12:26:50 +00:00
func main() {
err := initConfig()
if err != nil {
fmt.Println("Error during initialization:", err)
return
}
2024-06-30 21:20:52 +00:00
loadNodeConfig()
2024-07-05 01:08:35 +00:00
go startFileWatcher()
go checkMasterHeartbeat()
if config.AuthCode == "" {
config.AuthCode = generateStrongRandomString(64)
fmt.Printf("Generated connection code: %s\n", config.AuthCode)
saveConfig(config)
}
// Generate Host ID
hostID, nodeErr := generateHostID()
2024-08-08 11:35:50 +00:00
if nodeErr != nil {
log.Fatalf("Failed to generate host ID: %v", nodeErr)
2024-08-08 11:35:50 +00:00
}
config.PeerID = hostID
2024-08-08 11:35:50 +00:00
2024-07-05 01:08:35 +00:00
if len(config.Peers) > 0 {
2024-08-08 11:35:50 +00:00
time.Sleep(2 * time.Second) // Give some time for connections to establish
2024-07-05 01:08:35 +00:00
startElection()
}
2024-06-30 21:20:52 +00:00
2024-08-08 11:35:50 +00:00
go startNodeClient()
2024-06-12 12:26:50 +00:00
runServer()
}
func initConfig() error {
if _, err := os.Stat(configFilePath); os.IsNotExist(err) {
return createConfig()
}
fmt.Println("Configuration file already exists.")
2024-07-05 01:08:35 +00:00
config = loadConfig()
2024-06-12 12:26:50 +00:00
return nil
}
func createConfig() error {
reader := bufio.NewReader(os.Stdin)
fmt.Println("Configuration file not found.")
fmt.Print("Do you want to use default values? (yes/no): ")
useDefaults, _ := reader.ReadString('\n')
2024-08-08 13:03:33 +00:00
if strings.TrimSpace(useDefaults) != "yes" {
2024-06-12 12:26:50 +00:00
fmt.Print("Enter port (default 5000): ")
portStr, _ := reader.ReadString('\n')
if portStr != "\n" {
2024-08-08 13:03:33 +00:00
port, err := strconv.Atoi(strings.TrimSpace(portStr))
2024-06-12 12:26:50 +00:00
if err != nil {
2024-08-08 13:03:33 +00:00
config.Port = 5000
} else {
config.Port = port
2024-06-12 12:26:50 +00:00
}
}
2024-08-08 13:03:33 +00:00
fmt.Print("Enter your domain address (default localhost): ")
2024-06-12 12:26:50 +00:00
domain, _ := reader.ReadString('\n')
if domain != "\n" {
2024-08-08 13:03:33 +00:00
config.Domain = strings.TrimSpace(domain)
2024-06-30 21:20:52 +00:00
}
2024-08-08 13:03:33 +00:00
} else {
config = defaultConfig
2024-06-30 21:20:52 +00:00
}
2024-07-05 01:08:35 +00:00
if config.AuthCode == "" {
config.AuthCode = generateStrongRandomString(64)
fmt.Printf("Generated connection code: %s\n", config.AuthCode)
2024-06-12 12:26:50 +00:00
}
saveConfig(config)
return nil
}
func saveConfig(config Config) {
2024-08-08 13:03:33 +00:00
cfg := ini.Empty()
sec := cfg.Section("")
sec.Key("Port").SetValue(strconv.Itoa(config.Port))
sec.Key("AuthCode").SetValue(config.AuthCode)
sec.Key("PeerID").SetValue(config.PeerID)
2024-06-12 12:26:50 +00:00
2024-08-08 13:03:33 +00:00
peers := strings.Join(config.Peers, ",")
sec.Key("Peers").SetValue(peers)
sec.Key("Domain").SetValue(config.Domain)
2024-06-12 12:26:50 +00:00
2024-08-08 13:03:33 +00:00
err := cfg.SaveTo(configFilePath)
2024-06-12 12:26:50 +00:00
if err != nil {
fmt.Println("Error writing to config file:", err)
}
}
func loadConfig() Config {
2024-08-08 13:03:33 +00:00
cfg, err := ini.Load(configFilePath)
2024-06-12 12:26:50 +00:00
if err != nil {
log.Fatalf("Error opening config file: %v", err)
}
2024-08-08 13:03:33 +00:00
port, err := cfg.Section("").Key("Port").Int()
if err != nil || port == 0 {
port = 5000 // Default to 5000 if not set or error
}
peersStr := cfg.Section("").Key("Peers").String()
var peers []string
if peersStr != "" {
peers = strings.Split(peersStr, ",")
}
domain := cfg.Section("").Key("Domain").String()
if domain == "" {
domain = "localhost" // Default to localhost if not set
}
config = Config{
Port: port,
AuthCode: cfg.Section("").Key("AuthCode").String(),
PeerID: cfg.Section("").Key("PeerID").String(),
Peers: peers,
Domain: domain,
2024-06-12 12:26:50 +00:00
}
return config
}
2024-06-30 21:20:52 +00:00
func generateStrongRandomString(length int) string {
bytes := make([]byte, length)
_, err := rand.Read(bytes)
if err != nil {
log.Fatalf("Error generating random string: %v", err)
}
return base64.URLEncoding.EncodeToString(bytes)[:length]
}
2024-07-05 01:08:35 +00:00
func startFileWatcher() {
watcher, err := fsnotify.NewWatcher()
if err != nil {
log.Fatal(err)
}
go func() {
defer watcher.Close()
for {
select {
case event, ok := <-watcher.Events:
if !ok {
return
}
if event.Op&fsnotify.Write == fsnotify.Write {
log.Println("Modified file:", event.Name)
configLock.Lock()
config = loadConfig()
configLock.Unlock()
// Perform your logic here to handle the changes in the config file
}
case err, ok := <-watcher.Errors:
if !ok {
return
}
log.Println("Error:", err)
}
}
}()
err = watcher.Add(configFilePath)
if err != nil {
log.Fatal(err)
}
}