fix
This commit is contained in:
@@ -24,6 +24,27 @@ type Engine struct {
|
||||
syslogRules []models.SyslogRule
|
||||
trapRules []models.TrapRule
|
||||
shields []models.TrapShield
|
||||
resourceByIP map[string]resourceRef
|
||||
resourceByHN map[string]resourceRef
|
||||
}
|
||||
|
||||
type resourceRef struct {
|
||||
ResourceType string
|
||||
ResourceID string
|
||||
ResourceName string
|
||||
}
|
||||
|
||||
func resourceTypePriority(resourceType string) int {
|
||||
switch strings.ToLower(strings.TrimSpace(resourceType)) {
|
||||
case "server":
|
||||
return 3
|
||||
case "collector":
|
||||
return 2
|
||||
case "device":
|
||||
return 1
|
||||
default:
|
||||
return 0
|
||||
}
|
||||
}
|
||||
|
||||
var Global = &Engine{}
|
||||
@@ -33,6 +54,7 @@ func (e *Engine) Refresh() error {
|
||||
var syslog []models.SyslogRule
|
||||
var trap []models.TrapRule
|
||||
var shield []models.TrapShield
|
||||
var mappings []models.ResourceMapping
|
||||
|
||||
if err := impl.DBService.Where("enabled = ?", true).Find(&dict).Error; err != nil {
|
||||
return err
|
||||
@@ -54,12 +76,51 @@ func (e *Engine) Refresh() error {
|
||||
if err := impl.DBService.Where("enabled = ?", true).Find(&shield).Error; err != nil {
|
||||
return err
|
||||
}
|
||||
if err := impl.DBService.Where("is_deleted = ?", false).Order("updated_at desc, id desc").Find(&mappings).Error; err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
ipMap := make(map[string]resourceRef)
|
||||
hnMap := make(map[string]resourceRef)
|
||||
for _, m := range mappings {
|
||||
ref := resourceRef{
|
||||
ResourceType: m.ResourceType,
|
||||
ResourceID: m.ResourceID,
|
||||
ResourceName: m.ResourceName,
|
||||
}
|
||||
var ips []string
|
||||
if err := json.Unmarshal([]byte(m.IPsJSON), &ips); err == nil {
|
||||
for _, ip := range ips {
|
||||
key := strings.TrimSpace(ip)
|
||||
if key == "" {
|
||||
continue
|
||||
}
|
||||
if cur, exists := ipMap[key]; !exists || resourceTypePriority(ref.ResourceType) > resourceTypePriority(cur.ResourceType) {
|
||||
ipMap[key] = ref
|
||||
}
|
||||
}
|
||||
}
|
||||
var hostnames []string
|
||||
if err := json.Unmarshal([]byte(m.HostnamesJSON), &hostnames); err == nil {
|
||||
for _, hn := range hostnames {
|
||||
key := strings.ToLower(strings.TrimSpace(hn))
|
||||
if key == "" {
|
||||
continue
|
||||
}
|
||||
if cur, exists := hnMap[key]; !exists || resourceTypePriority(ref.ResourceType) > resourceTypePriority(cur.ResourceType) {
|
||||
hnMap[key] = ref
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
e.mu.Lock()
|
||||
e.trapDict = dict
|
||||
e.syslogRules = syslog
|
||||
e.trapRules = trap
|
||||
e.shields = shield
|
||||
e.resourceByIP = ipMap
|
||||
e.resourceByHN = hnMap
|
||||
e.mu.Unlock()
|
||||
return nil
|
||||
}
|
||||
@@ -99,14 +160,21 @@ func (e *Engine) HandleSyslog(addr *net.UDPAddr, payload []byte) {
|
||||
detailBytes, _ := json.Marshal(detailObj)
|
||||
summary := formatSyslogSummary(parsed)
|
||||
sev := syslogPriorityToSeverity(parsed.Priority)
|
||||
ref, method := e.resolveResource(addr.IP.String(), device)
|
||||
|
||||
ev := models.LogEvent{
|
||||
SourceKind: "syslog",
|
||||
RemoteAddr: addr.String(),
|
||||
SourceIP: addr.IP.String(),
|
||||
RawPayload: string(payload),
|
||||
NormalizedSummary: summary,
|
||||
NormalizedDetail: string(detailBytes),
|
||||
DeviceName: device,
|
||||
ResourceType: ref.ResourceType,
|
||||
ResourceID: ref.ResourceID,
|
||||
ResourceName: ref.ResourceName,
|
||||
MatchMethod: method,
|
||||
DispatchStatus: "not_applicable",
|
||||
SeverityCode: sev,
|
||||
}
|
||||
|
||||
@@ -166,8 +234,8 @@ func (e *Engine) HandleSyslog(addr *net.UDPAddr, payload []byte) {
|
||||
PolicyID: matched.PolicyID,
|
||||
RawData: rawBytes,
|
||||
}
|
||||
if err := forwardAlert(body); err == nil {
|
||||
_ = impl.DBService.Model(&ev).Update("alert_sent", true).Error
|
||||
if err := enqueueAlert(ev.ID, body); err == nil {
|
||||
_ = impl.DBService.Model(&ev).Update("dispatch_status", "pending").Error
|
||||
}
|
||||
}
|
||||
|
||||
@@ -204,10 +272,7 @@ func trapShielded(e *Engine, addr *net.UDPAddr, trapOID string, pkt *gosnmp.Snmp
|
||||
if !s.Enabled {
|
||||
continue
|
||||
}
|
||||
if strings.TrimSpace(s.SourceIPCIDR) == "" {
|
||||
continue
|
||||
}
|
||||
if !ipMatchesCIDR(ip, s.SourceIPCIDR) {
|
||||
if cidr := strings.TrimSpace(s.SourceIPCIDR); cidr != "" && !ipMatchesCIDR(ip, cidr) {
|
||||
continue
|
||||
}
|
||||
if p := strings.TrimSpace(s.OIDPrefix); p != "" && !strings.HasPrefix(normOID(trapOID), normOID(p)) {
|
||||
@@ -265,14 +330,21 @@ func (e *Engine) HandleTrap(addr *net.UDPAddr, pkt *gosnmp.SnmpPacket) {
|
||||
}
|
||||
}
|
||||
detailBytes, _ := json.Marshal(detailObj)
|
||||
ref, method := e.resolveResource(addr.IP.String(), addr.IP.String())
|
||||
|
||||
ev := models.LogEvent{
|
||||
SourceKind: "snmp_trap",
|
||||
RemoteAddr: addr.String(),
|
||||
SourceIP: addr.IP.String(),
|
||||
RawPayload: fp,
|
||||
NormalizedSummary: readable,
|
||||
NormalizedDetail: string(detailBytes),
|
||||
DeviceName: addr.IP.String(),
|
||||
ResourceType: ref.ResourceType,
|
||||
ResourceID: ref.ResourceID,
|
||||
ResourceName: ref.ResourceName,
|
||||
MatchMethod: method,
|
||||
DispatchStatus: "not_applicable",
|
||||
SeverityCode: sev,
|
||||
TrapOID: trapOID,
|
||||
}
|
||||
@@ -360,8 +432,8 @@ func (e *Engine) HandleTrap(addr *net.UDPAddr, pkt *gosnmp.SnmpPacket) {
|
||||
PolicyID: matched.PolicyID,
|
||||
RawData: rawBytes,
|
||||
}
|
||||
if err := forwardAlert(body); err == nil {
|
||||
_ = impl.DBService.Model(&ev).Update("alert_sent", true).Error
|
||||
if err := enqueueAlert(ev.ID, body); err == nil {
|
||||
_ = impl.DBService.Model(&ev).Update("dispatch_status", "pending").Error
|
||||
}
|
||||
}
|
||||
|
||||
@@ -440,3 +512,18 @@ func firstNonEmpty(a, b string) string {
|
||||
}
|
||||
return b
|
||||
}
|
||||
|
||||
func (e *Engine) resolveResource(sourceIP, hostname string) (resourceRef, string) {
|
||||
e.mu.RLock()
|
||||
ipMap := e.resourceByIP
|
||||
hnMap := e.resourceByHN
|
||||
e.mu.RUnlock()
|
||||
|
||||
if ref, ok := ipMap[strings.TrimSpace(sourceIP)]; ok {
|
||||
return ref, "ip"
|
||||
}
|
||||
if ref, ok := hnMap[strings.ToLower(strings.TrimSpace(hostname))]; ok {
|
||||
return ref, "hostname"
|
||||
}
|
||||
return resourceRef{}, "none"
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user