FRix counts for naughty failures - dns, karma and helo

This commit is contained in:
Brian Read 2024-06-19 22:44:21 +01:00
parent 44b811d09e
commit 0947689c0f
2 changed files with 41 additions and 13 deletions

View File

@ -9,7 +9,7 @@
<tr tal:repeat="item array_2d"> <tr tal:repeat="item array_2d">
<td>${item[0]}</td> <td>${item[0]}</td>
<td>${item[1]}</td> <td>${item[1]}</td>
<td>${item[2]}</td> <td>${item[2]}%</td>
</tr> </tr>
</tbody> </tbody>
</table> </table>

View File

@ -26,6 +26,7 @@
# 5. Chase disparity in counts betweeen old mailstats and this # 5. Chase disparity in counts betweeen old mailstats and this
# 6. Count emails delivered over ports 25/587/465 (SMTPS?) # 6. Count emails delivered over ports 25/587/465 (SMTPS?)
# 7. Arrange that the spec file overwrites the date even if it has been overwritten before # 7. Arrange that the spec file overwrites the date even if it has been overwritten before
# 8. Allow mailstats pages to be public or private (=> templating the fragment))
# #
# Future: # Future:
# 1. Write summary line for each transaction to DB and link to it through cell in main table # 1. Write summary line for each transaction to DB and link to it through cell in main table
@ -579,8 +580,13 @@ def get_heading():
# SMTP connection stats # SMTP connection stats
smtp_stats = f"External SMTP connections accepted: {totalexternalsmtpsessions}\n"\ smtp_stats = f"External SMTP connections accepted: {totalexternalsmtpsessions}\n"\
f"Internal SMTP connections accepted: {totalinternalsmtpsessions}\n"\ f"Internal SMTP connections accepted: {totalinternalsmtpsessions}"
f"Emails per hour: {emailperhour:.1f}/hr\n"\
if len(connection_type_counts)>0:
for connect_type in connection_type_counts.keys():
smtp_stats = smtp_stats + f"\nCount of {connection_type} connections:{connection_type_counts[connect_type]}"
smtp_stats = smtp_stats + f"\nEmails per hour: {emailperhour:.1f}/hr\n"\
f"Average spam score (accepted): {spamavg or 0:.2f}\n"\ f"Average spam score (accepted): {spamavg or 0:.2f}\n"\
f"Average spam score (rejected): {rejectspamavg or 0:.2f}\n"\ f"Average spam score (rejected): {rejectspamavg or 0:.2f}\n"\
f"Average ham score: {hamavg or 0:.2f}\n"\ f"Average ham score: {hamavg or 0:.2f}\n"\
@ -851,6 +857,7 @@ if __name__ == "__main__":
#print(f"Found plugin {parsed_data['error-plugin']}") #print(f"Found plugin {parsed_data['error-plugin']}")
if parsed_data['error-plugin']: if parsed_data['error-plugin']:
row = search_2d_list(parsed_data['error-plugin'],columnPlugin) row = search_2d_list(parsed_data['error-plugin'],columnPlugin)
#print(row,parsed_data['error-plugin'])
if not row == -1: if not row == -1:
#print(f"Found row: {row}") #print(f"Found row: {row}")
columnCounts_2d[hour][row] += 1 columnCounts_2d[hour][row] += 1
@ -862,16 +869,28 @@ if __name__ == "__main__":
found_viruses[match.group(1)] += 1 found_viruses[match.group(1)] += 1
else: else:
found_viruses[parsed_data['action1']] += 1 found_viruses[parsed_data['action1']] += 1
elif parsed_data['error-plugin'] == 'naughty': elif parsed_data['error-plugin'].strip() == 'naughty':
match = qpcodes_pattern.match(parsed_data['action1']) #print(f"Found naughty {parsed_data['error-msg']}")
if match: if parsed_data['error-msg'].startswith("(dnsbl)"):
rejReason = match.group(1) #print("Found dnsbl")
found_qpcodes[parsed_data['error-plugin']+"-"+rejReason] += 1 columnCounts_2d[hour][RBLDNS]+= 1
else: columnCounts_2d[ColTotals][RBLDNS]+= 1
found_qpcodes['Unknown'] += 1 elif parsed_data['error-msg'].startswith("(karma)"):
columnCounts_2d[hour][KARMA] += 1
columnCounts_2d[ColTotals][KARMA]+= 1
elif parsed_data['error-msg'].startswith("(helo)"):
columnCounts_2d[hour][RBLDNS] += 1
columnCounts_2d[ColTotals][RBLDNS]+= 1
# match = qpcodes_pattern.match(parsed_data['action1'])
# if match:
# rejReason = match.group(1)
# found_qpcodes[parsed_data['error-plugin']+"-"+rejReason] += 1
else: else:
found_qpcodes[parsed_data['action1']] += 1 found_qpcodes['Unknown'] += 1
print() #seperate the [progress bar] else:
found_qpcodes[parsed_data['action1']] += 1
if isThonny:
print() #seperate the [progress bar]
# Compute percentages # Compute percentages
total_Count = columnCounts_2d[ColTotals][TOTALS] total_Count = columnCounts_2d[ColTotals][TOTALS]
#Column of percentages #Column of percentages
@ -907,6 +926,7 @@ if __name__ == "__main__":
geoip_pattern = re.compile(r".*check_badcountries: GeoIP Country: (.*)") geoip_pattern = re.compile(r".*check_badcountries: GeoIP Country: (.*)")
dmarc_pattern = re.compile(r".*dmarc: pass") dmarc_pattern = re.compile(r".*dmarc: pass")
helo_pattern = re.compile(r".*Accepted connection.*?from (\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}) \/ ([\w.-]+)") helo_pattern = re.compile(r".*Accepted connection.*?from (\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}) \/ ([\w.-]+)")
connect_type_pattern = re.compile(r".*connect via (.*)")
total_countries = 0 total_countries = 0
DMARCOkCount = 0 DMARCOkCount = 0
totalinternalsmtpsessions = 0 totalinternalsmtpsessions = 0
@ -915,6 +935,7 @@ if __name__ == "__main__":
i = 0 i = 0
j = 0 j = 0
log_len = len(log_entries) log_len = len(log_entries)
connection_type_counts = defaultdict(int)
if log_len > 0: if log_len > 0:
if isThonny: if isThonny:
print_progress_bar(0, log_len, prefix='Progress:', suffix='Complete', length=50) print_progress_bar(0, log_len, prefix='Progress:', suffix='Complete', length=50)
@ -949,6 +970,13 @@ if __name__ == "__main__":
DMARCOkCount += 1 DMARCOkCount += 1
continue continue
#Pull out type of connection
match = connect_type_pattern.match(data[1])
if match:
connection_type = match.group(1)
connection_type_counts[connection_type] += 1
continue
#Now apply the results to the chameleon template - main table #Now apply the results to the chameleon template - main table
# Path to the template file # Path to the template file