-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathmain.go
More file actions
129 lines (109 loc) · 3.24 KB
/
Copy pathmain.go
File metadata and controls
129 lines (109 loc) · 3.24 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
package main
import (
"context"
"fmt"
"os"
"os/signal"
"syscall"
"github.com/rs/zerolog"
"github.com/rs/zerolog/log"
"github.com/spf13/cobra"
"github.com/joao-costa/multichatmcp/internal/mcp"
"github.com/joao-costa/multichatmcp/internal/messenger"
"github.com/joao-costa/multichatmcp/internal/messenger/teams"
"github.com/joao-costa/multichatmcp/internal/messenger/whatsapp"
)
var (
messengerType string
deviceDB string
webhookURL string
logLevel string
)
var rootCmd = &cobra.Command{
Use: "multichat",
Short: "Multi-messenger MCP server",
Long: `A Model Context Protocol (MCP) server supporting multiple messaging platforms.`,
RunE: run,
}
func init() {
rootCmd.Flags().StringVar(&messengerType, "messenger", "whatsapp", "Messenger type (whatsapp, teams)")
rootCmd.Flags().StringVar(&deviceDB, "device", "device.db", "Device database file path (for WhatsApp)")
rootCmd.Flags().StringVar(&webhookURL, "webhook", "", "Webhook URL (for Teams)")
rootCmd.Flags().StringVar(&logLevel, "log-level", "info", "Log level (debug, info, warn, error)")
}
func run(cmd *cobra.Command, args []string) error {
// Setup logger
setupLogger(logLevel)
log.Info().
Str("messenger", messengerType).
Str("device_db", deviceDB).
Str("log_level", logLevel).
Msg("Starting MultiChat MCP Server")
// Create messenger instance
var msg messenger.Messenger
var err error
switch messengerType {
case "whatsapp":
msg, err = whatsapp.NewWhatsAppMessenger(deviceDB)
if err != nil {
return fmt.Errorf("failed to create WhatsApp messenger: %w", err)
}
case "teams":
msg, err = teams.NewTeamsMessenger(webhookURL)
if err != nil {
return fmt.Errorf("failed to create Teams messenger: %w", err)
}
default:
return fmt.Errorf("unsupported messenger type: %s", messengerType)
}
// Connect to messenger
ctx, cancel := context.WithCancel(context.Background())
defer cancel()
log.Info().Msg("Connecting to messenger...")
if err := msg.Connect(ctx); err != nil {
return fmt.Errorf("failed to connect to messenger: %w", err)
}
defer msg.Disconnect()
log.Info().Msg("Messenger connected successfully")
// Create and start MCP server
mcpServer := mcp.NewServer(msg)
// Handle graceful shutdown
sigChan := make(chan os.Signal, 1)
signal.Notify(sigChan, os.Interrupt, syscall.SIGTERM)
go func() {
<-sigChan
log.Info().Msg("Shutdown signal received, closing connections...")
cancel()
msg.Disconnect()
os.Exit(0)
}()
log.Info().Msg("Starting MCP server (stdio transport)...")
if err := mcpServer.Serve(); err != nil {
return fmt.Errorf("MCP server error: %w", err)
}
return nil
}
func setupLogger(level string) {
// Set up zerolog with human-friendly output for development
zerolog.TimeFieldFormat = zerolog.TimeFormatUnix
log.Logger = log.Output(zerolog.ConsoleWriter{Out: os.Stderr})
// Set log level
switch level {
case "debug":
zerolog.SetGlobalLevel(zerolog.DebugLevel)
case "info":
zerolog.SetGlobalLevel(zerolog.InfoLevel)
case "warn":
zerolog.SetGlobalLevel(zerolog.WarnLevel)
case "error":
zerolog.SetGlobalLevel(zerolog.ErrorLevel)
default:
zerolog.SetGlobalLevel(zerolog.InfoLevel)
}
}
func main() {
if err := rootCmd.Execute(); err != nil {
fmt.Fprintf(os.Stderr, "Error: %v\n", err)
os.Exit(1)
}
}