mirror of
https://github.com/domainaware/parsedmarc.git
synced 2026-04-04 12:48:53 +00:00
Update docs
This commit is contained in:
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Overview: module code — parsedmarc 8.3.0 documentation</title>
|
||||
<title>Overview: module code — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="../_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="../_static/css/theme.css" type="text/css" />
|
||||
<!--[if lt IE 9]>
|
||||
@@ -28,7 +28,7 @@
|
||||
<a href="../index.html" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
8.3.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="../search.html" method="get">
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>parsedmarc — parsedmarc 8.3.0 documentation</title>
|
||||
<title>parsedmarc — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="../_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="../_static/css/theme.css" type="text/css" />
|
||||
<!--[if lt IE 9]>
|
||||
@@ -28,7 +28,7 @@
|
||||
<a href="../index.html" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
8.3.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="../search.html" method="get">
|
||||
@@ -73,7 +73,6 @@
|
||||
<span class="kn">import</span> <span class="nn">email</span>
|
||||
<span class="kn">import</span> <span class="nn">email.utils</span>
|
||||
<span class="kn">import</span> <span class="nn">json</span>
|
||||
<span class="kn">import</span> <span class="nn">logging</span>
|
||||
<span class="kn">import</span> <span class="nn">mailbox</span>
|
||||
<span class="kn">import</span> <span class="nn">os</span>
|
||||
<span class="kn">import</span> <span class="nn">re</span>
|
||||
@@ -95,22 +94,15 @@
|
||||
<span class="kn">from</span> <span class="nn">lxml</span> <span class="kn">import</span> <span class="n">etree</span>
|
||||
<span class="kn">from</span> <span class="nn">mailsuite.smtp</span> <span class="kn">import</span> <span class="n">send_email</span>
|
||||
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.log</span> <span class="kn">import</span> <span class="n">logger</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.mail</span> <span class="kn">import</span> <span class="n">MailboxConnection</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.utils</span> <span class="kn">import</span> <span class="n">get_base_domain</span><span class="p">,</span> <span class="n">get_ip_address_info</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.utils</span> <span class="kn">import</span> <span class="n">is_outlook_msg</span><span class="p">,</span> <span class="n">convert_outlook_msg</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.utils</span> <span class="kn">import</span> <span class="n">parse_email</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.utils</span> <span class="kn">import</span> <span class="n">timestamp_to_human</span><span class="p">,</span> <span class="n">human_timestamp_to_datetime</span>
|
||||
|
||||
<span class="n">__version__</span> <span class="o">=</span> <span class="s2">"8.3.0"</span>
|
||||
<span class="n">__version__</span> <span class="o">=</span> <span class="s2">"8.3.1"</span>
|
||||
|
||||
<span class="n">formatter</span> <span class="o">=</span> <span class="n">logging</span><span class="o">.</span><span class="n">Formatter</span><span class="p">(</span>
|
||||
<span class="n">fmt</span><span class="o">=</span><span class="s1">'</span><span class="si">%(levelname)8s</span><span class="s1">:</span><span class="si">%(filename)s</span><span class="s1">:</span><span class="si">%(lineno)d</span><span class="s1">:</span><span class="si">%(message)s</span><span class="s1">'</span><span class="p">,</span>
|
||||
<span class="n">datefmt</span><span class="o">=</span><span class="s1">'%Y-%m-</span><span class="si">%d</span><span class="s1">:%H:%M:%S'</span><span class="p">)</span>
|
||||
<span class="n">handler</span> <span class="o">=</span> <span class="n">logging</span><span class="o">.</span><span class="n">StreamHandler</span><span class="p">()</span>
|
||||
<span class="n">handler</span><span class="o">.</span><span class="n">setFormatter</span><span class="p">(</span><span class="n">formatter</span><span class="p">)</span>
|
||||
|
||||
<span class="n">logger</span> <span class="o">=</span> <span class="n">logging</span><span class="o">.</span><span class="n">getLogger</span><span class="p">(</span><span class="s2">"parsedmarc"</span><span class="p">)</span>
|
||||
<span class="n">logger</span><span class="o">.</span><span class="n">addHandler</span><span class="p">(</span><span class="n">handler</span><span class="p">)</span>
|
||||
<span class="n">logger</span><span class="o">.</span><span class="n">debug</span><span class="p">(</span><span class="s2">"parsedmarc v</span><span class="si">{0}</span><span class="s2">"</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">__version__</span><span class="p">))</span>
|
||||
|
||||
<span class="n">feedback_report_regex</span> <span class="o">=</span> <span class="n">re</span><span class="o">.</span><span class="n">compile</span><span class="p">(</span><span class="sa">r</span><span class="s2">"^([\w\-]+): (.+)$"</span><span class="p">,</span> <span class="n">re</span><span class="o">.</span><span class="n">MULTILINE</span><span class="p">)</span>
|
||||
@@ -297,11 +289,14 @@
|
||||
<span class="n">xmltodict</span><span class="o">.</span><span class="n">parse</span><span class="p">(</span><span class="n">xml</span><span class="p">)[</span><span class="s2">"feedback"</span><span class="p">]</span>
|
||||
<span class="k">except</span> <span class="ne">Exception</span> <span class="k">as</span> <span class="n">e</span><span class="p">:</span>
|
||||
<span class="n">errors</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="s2">"Invalid XML: </span><span class="si">{0}</span><span class="s2">"</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">e</span><span class="o">.</span><span class="fm">__str__</span><span class="p">()))</span>
|
||||
<span class="n">tree</span> <span class="o">=</span> <span class="n">etree</span><span class="o">.</span><span class="n">parse</span><span class="p">(</span>
|
||||
<span class="n">BytesIO</span><span class="p">(</span><span class="n">xml</span><span class="o">.</span><span class="n">encode</span><span class="p">(</span><span class="s1">'utf-8'</span><span class="p">)),</span>
|
||||
<span class="n">etree</span><span class="o">.</span><span class="n">XMLParser</span><span class="p">(</span><span class="n">recover</span><span class="o">=</span><span class="kc">True</span><span class="p">,</span> <span class="n">resolve_entities</span><span class="o">=</span><span class="kc">False</span><span class="p">))</span>
|
||||
<span class="n">s</span> <span class="o">=</span> <span class="n">etree</span><span class="o">.</span><span class="n">tostring</span><span class="p">(</span><span class="n">tree</span><span class="p">)</span>
|
||||
<span class="n">xml</span> <span class="o">=</span> <span class="s1">''</span> <span class="k">if</span> <span class="n">s</span> <span class="ow">is</span> <span class="kc">None</span> <span class="k">else</span> <span class="n">s</span><span class="o">.</span><span class="n">decode</span><span class="p">(</span><span class="s1">'utf-8'</span><span class="p">)</span>
|
||||
<span class="k">try</span><span class="p">:</span>
|
||||
<span class="n">tree</span> <span class="o">=</span> <span class="n">etree</span><span class="o">.</span><span class="n">parse</span><span class="p">(</span>
|
||||
<span class="n">BytesIO</span><span class="p">(</span><span class="n">xml</span><span class="o">.</span><span class="n">encode</span><span class="p">(</span><span class="s1">'utf-8'</span><span class="p">)),</span>
|
||||
<span class="n">etree</span><span class="o">.</span><span class="n">XMLParser</span><span class="p">(</span><span class="n">recover</span><span class="o">=</span><span class="kc">True</span><span class="p">,</span> <span class="n">resolve_entities</span><span class="o">=</span><span class="kc">False</span><span class="p">))</span>
|
||||
<span class="n">s</span> <span class="o">=</span> <span class="n">etree</span><span class="o">.</span><span class="n">tostring</span><span class="p">(</span><span class="n">tree</span><span class="p">)</span>
|
||||
<span class="n">xml</span> <span class="o">=</span> <span class="s1">''</span> <span class="k">if</span> <span class="n">s</span> <span class="ow">is</span> <span class="kc">None</span> <span class="k">else</span> <span class="n">s</span><span class="o">.</span><span class="n">decode</span><span class="p">(</span><span class="s1">'utf-8'</span><span class="p">)</span>
|
||||
<span class="k">except</span> <span class="ne">Exception</span><span class="p">:</span>
|
||||
<span class="n">xml</span> <span class="o">=</span> <span class="sa">u</span><span class="s1">'<a/>'</span>
|
||||
|
||||
<span class="k">try</span><span class="p">:</span>
|
||||
<span class="c1"># Replace XML header (sometimes they are invalid)</span>
|
||||
@@ -473,7 +468,7 @@
|
||||
<span class="n">dns_timeout</span><span class="o">=</span><span class="mf">2.0</span><span class="p">,</span>
|
||||
<span class="n">parallel</span><span class="o">=</span><span class="kc">False</span><span class="p">,</span>
|
||||
<span class="n">keep_alive</span><span class="o">=</span><span class="kc">None</span><span class="p">):</span>
|
||||
<span class="sd">"""Parses a file at the given path, a file-like object. or bytes as a</span>
|
||||
<span class="sd">"""Parses a file at the given path, a file-like object. or bytes as an</span>
|
||||
<span class="sd"> aggregate DMARC report</span>
|
||||
|
||||
<span class="sd"> Args:</span>
|
||||
@@ -557,11 +552,11 @@
|
||||
<span class="n">row</span><span class="p">[</span><span class="s2">"dmarc_aligned"</span><span class="p">]</span> <span class="o">=</span> <span class="n">record</span><span class="p">[</span><span class="s2">"alignment"</span><span class="p">][</span><span class="s2">"dmarc"</span><span class="p">]</span>
|
||||
<span class="n">row</span><span class="p">[</span><span class="s2">"disposition"</span><span class="p">]</span> <span class="o">=</span> <span class="n">record</span><span class="p">[</span><span class="s2">"policy_evaluated"</span><span class="p">][</span><span class="s2">"disposition"</span><span class="p">]</span>
|
||||
<span class="n">policy_override_reasons</span> <span class="o">=</span> <span class="nb">list</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span>
|
||||
<span class="k">lambda</span> <span class="n">r</span><span class="p">:</span> <span class="n">r</span><span class="p">[</span><span class="s2">"type"</span><span class="p">],</span>
|
||||
<span class="k">lambda</span> <span class="n">r_</span><span class="p">:</span> <span class="n">r_</span><span class="p">[</span><span class="s2">"type"</span><span class="p">],</span>
|
||||
<span class="n">record</span><span class="p">[</span><span class="s2">"policy_evaluated"</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="s2">"policy_override_reasons"</span><span class="p">]))</span>
|
||||
<span class="n">policy_override_comments</span> <span class="o">=</span> <span class="nb">list</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span>
|
||||
<span class="k">lambda</span> <span class="n">r</span><span class="p">:</span> <span class="n">r</span><span class="p">[</span><span class="s2">"comment"</span><span class="p">]</span> <span class="ow">or</span> <span class="s2">"none"</span><span class="p">,</span>
|
||||
<span class="k">lambda</span> <span class="n">r_</span><span class="p">:</span> <span class="n">r_</span><span class="p">[</span><span class="s2">"comment"</span><span class="p">]</span> <span class="ow">or</span> <span class="s2">"none"</span><span class="p">,</span>
|
||||
<span class="n">record</span><span class="p">[</span><span class="s2">"policy_evaluated"</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="s2">"policy_override_reasons"</span><span class="p">]))</span>
|
||||
<span class="n">row</span><span class="p">[</span><span class="s2">"policy_override_reasons"</span><span class="p">]</span> <span class="o">=</span> <span class="s2">","</span><span class="o">.</span><span class="n">join</span><span class="p">(</span>
|
||||
@@ -1154,7 +1149,7 @@
|
||||
<span class="n">connection</span><span class="o">.</span><span class="n">create_folder</span><span class="p">(</span><span class="n">forensic_reports_folder</span><span class="p">)</span>
|
||||
<span class="n">connection</span><span class="o">.</span><span class="n">create_folder</span><span class="p">(</span><span class="n">invalid_reports_folder</span><span class="p">)</span>
|
||||
|
||||
<span class="n">messages</span> <span class="o">=</span> <span class="n">connection</span><span class="o">.</span><span class="n">fetch_messages</span><span class="p">(</span><span class="n">reports_folder</span><span class="p">)</span>
|
||||
<span class="n">messages</span> <span class="o">=</span> <span class="n">connection</span><span class="o">.</span><span class="n">fetch_messages</span><span class="p">(</span><span class="n">reports_folder</span><span class="p">,</span> <span class="n">batch_size</span><span class="o">=</span><span class="n">batch_size</span><span class="p">)</span>
|
||||
<span class="n">total_messages</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">messages</span><span class="p">)</span>
|
||||
<span class="n">logger</span><span class="o">.</span><span class="n">debug</span><span class="p">(</span><span class="s2">"Found </span><span class="si">{0}</span><span class="s2"> messages in </span><span class="si">{1}</span><span class="s2">"</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">messages</span><span class="p">),</span>
|
||||
<span class="n">reports_folder</span><span class="p">))</span>
|
||||
@@ -1333,6 +1328,41 @@
|
||||
<span class="n">check_timeout</span><span class="o">=</span><span class="n">check_timeout</span><span class="p">)</span></div>
|
||||
|
||||
|
||||
<span class="k">def</span> <span class="nf">append_json</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="n">reports</span><span class="p">):</span>
|
||||
<span class="k">with</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s2">"r+"</span><span class="p">,</span> <span class="n">newline</span><span class="o">=</span><span class="s2">"</span><span class="se">\n</span><span class="s2">"</span><span class="p">,</span> <span class="n">encoding</span><span class="o">=</span><span class="s2">"utf-8"</span><span class="p">)</span> <span class="k">as</span> <span class="n">output</span><span class="p">:</span>
|
||||
<span class="n">output_json</span> <span class="o">=</span> <span class="n">json</span><span class="o">.</span><span class="n">dumps</span><span class="p">(</span><span class="n">reports</span><span class="p">,</span> <span class="n">ensure_ascii</span><span class="o">=</span><span class="kc">False</span><span class="p">,</span> <span class="n">indent</span><span class="o">=</span><span class="mi">2</span><span class="p">)</span>
|
||||
<span class="k">if</span> <span class="n">output</span><span class="o">.</span><span class="n">seek</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">os</span><span class="o">.</span><span class="n">SEEK_END</span><span class="p">)</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span>
|
||||
<span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">reports</span><span class="p">)</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
|
||||
<span class="c1"># not appending anything, don't do any dance to append it</span>
|
||||
<span class="c1"># correctly</span>
|
||||
<span class="k">return</span>
|
||||
<span class="n">output</span><span class="o">.</span><span class="n">seek</span><span class="p">(</span><span class="n">output</span><span class="o">.</span><span class="n">tell</span><span class="p">()</span> <span class="o">-</span> <span class="mi">1</span><span class="p">)</span>
|
||||
<span class="n">last_char</span> <span class="o">=</span> <span class="n">output</span><span class="o">.</span><span class="n">read</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span>
|
||||
<span class="k">if</span> <span class="n">last_char</span> <span class="o">==</span> <span class="s2">"]"</span><span class="p">:</span>
|
||||
<span class="c1"># remove the trailing "\n]", leading "[\n", and replace with</span>
|
||||
<span class="c1"># ",\n"</span>
|
||||
<span class="n">output</span><span class="o">.</span><span class="n">seek</span><span class="p">(</span><span class="n">output</span><span class="o">.</span><span class="n">tell</span><span class="p">()</span> <span class="o">-</span> <span class="mi">2</span><span class="p">)</span>
|
||||
<span class="n">output</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s2">",</span><span class="se">\n</span><span class="s2">"</span><span class="p">)</span>
|
||||
<span class="n">output_json</span> <span class="o">=</span> <span class="n">output_json</span><span class="p">[</span><span class="mi">2</span><span class="p">:]</span>
|
||||
<span class="k">else</span><span class="p">:</span>
|
||||
<span class="n">output</span><span class="o">.</span><span class="n">seek</span><span class="p">(</span><span class="mi">0</span><span class="p">)</span>
|
||||
<span class="n">output</span><span class="o">.</span><span class="n">truncate</span><span class="p">()</span>
|
||||
|
||||
<span class="n">output</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="n">output_json</span><span class="p">)</span>
|
||||
|
||||
|
||||
<span class="k">def</span> <span class="nf">append_csv</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="n">csv</span><span class="p">):</span>
|
||||
<span class="k">with</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s2">"r+"</span><span class="p">,</span> <span class="n">newline</span><span class="o">=</span><span class="s2">"</span><span class="se">\n</span><span class="s2">"</span><span class="p">,</span> <span class="n">encoding</span><span class="o">=</span><span class="s2">"utf-8"</span><span class="p">)</span> <span class="k">as</span> <span class="n">output</span><span class="p">:</span>
|
||||
<span class="k">if</span> <span class="n">output</span><span class="o">.</span><span class="n">seek</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">os</span><span class="o">.</span><span class="n">SEEK_END</span><span class="p">)</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span>
|
||||
<span class="c1"># strip the headers from the CSV</span>
|
||||
<span class="n">_headers</span><span class="p">,</span> <span class="n">csv</span> <span class="o">=</span> <span class="n">csv</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s2">"</span><span class="se">\n</span><span class="s2">"</span><span class="p">,</span> <span class="mi">1</span><span class="p">)</span>
|
||||
<span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">csv</span><span class="p">)</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
|
||||
<span class="c1"># not appending anything, don't do any dance to</span>
|
||||
<span class="c1"># append it correctly</span>
|
||||
<span class="k">return</span>
|
||||
<span class="n">output</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="n">csv</span><span class="p">)</span>
|
||||
|
||||
|
||||
<div class="viewcode-block" id="save_output"><a class="viewcode-back" href="../index.html#parsedmarc.save_output">[docs]</a><span class="k">def</span> <span class="nf">save_output</span><span class="p">(</span><span class="n">results</span><span class="p">,</span> <span class="n">output_directory</span><span class="o">=</span><span class="s2">"output"</span><span class="p">,</span>
|
||||
<span class="n">aggregate_json_filename</span><span class="o">=</span><span class="s2">"aggregate.json"</span><span class="p">,</span>
|
||||
<span class="n">forensic_json_filename</span><span class="o">=</span><span class="s2">"forensic.json"</span><span class="p">,</span>
|
||||
@@ -1359,33 +1389,17 @@
|
||||
<span class="k">else</span><span class="p">:</span>
|
||||
<span class="n">os</span><span class="o">.</span><span class="n">makedirs</span><span class="p">(</span><span class="n">output_directory</span><span class="p">)</span>
|
||||
|
||||
<span class="k">with</span> <span class="nb">open</span><span class="p">(</span><span class="s2">"</span><span class="si">{0}</span><span class="s2">"</span>
|
||||
<span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span>
|
||||
<span class="n">aggregate_json_filename</span><span class="p">)),</span>
|
||||
<span class="s2">"w"</span><span class="p">,</span> <span class="n">newline</span><span class="o">=</span><span class="s2">"</span><span class="se">\n</span><span class="s2">"</span><span class="p">,</span> <span class="n">encoding</span><span class="o">=</span><span class="s2">"utf-8"</span><span class="p">)</span> <span class="k">as</span> <span class="n">agg_json</span><span class="p">:</span>
|
||||
<span class="n">agg_json</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="n">json</span><span class="o">.</span><span class="n">dumps</span><span class="p">(</span><span class="n">aggregate_reports</span><span class="p">,</span> <span class="n">ensure_ascii</span><span class="o">=</span><span class="kc">False</span><span class="p">,</span>
|
||||
<span class="n">indent</span><span class="o">=</span><span class="mi">2</span><span class="p">))</span>
|
||||
<span class="n">append_json</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span> <span class="n">aggregate_json_filename</span><span class="p">),</span>
|
||||
<span class="n">aggregate_reports</span><span class="p">)</span>
|
||||
|
||||
<span class="k">with</span> <span class="nb">open</span><span class="p">(</span><span class="s2">"</span><span class="si">{0}</span><span class="s2">"</span>
|
||||
<span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span>
|
||||
<span class="n">aggregate_csv_filename</span><span class="p">)),</span>
|
||||
<span class="s2">"w"</span><span class="p">,</span> <span class="n">newline</span><span class="o">=</span><span class="s2">"</span><span class="se">\n</span><span class="s2">"</span><span class="p">,</span> <span class="n">encoding</span><span class="o">=</span><span class="s2">"utf-8"</span><span class="p">)</span> <span class="k">as</span> <span class="n">agg_csv</span><span class="p">:</span>
|
||||
<span class="n">csv</span> <span class="o">=</span> <span class="n">parsed_aggregate_reports_to_csv</span><span class="p">(</span><span class="n">aggregate_reports</span><span class="p">)</span>
|
||||
<span class="n">agg_csv</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="n">csv</span><span class="p">)</span>
|
||||
<span class="n">append_csv</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span> <span class="n">aggregate_csv_filename</span><span class="p">),</span>
|
||||
<span class="n">parsed_aggregate_reports_to_csv</span><span class="p">(</span><span class="n">aggregate_reports</span><span class="p">))</span>
|
||||
|
||||
<span class="k">with</span> <span class="nb">open</span><span class="p">(</span><span class="s2">"</span><span class="si">{0}</span><span class="s2">"</span>
|
||||
<span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span>
|
||||
<span class="n">forensic_json_filename</span><span class="p">)),</span>
|
||||
<span class="s2">"w"</span><span class="p">,</span> <span class="n">newline</span><span class="o">=</span><span class="s2">"</span><span class="se">\n</span><span class="s2">"</span><span class="p">,</span> <span class="n">encoding</span><span class="o">=</span><span class="s2">"utf-8"</span><span class="p">)</span> <span class="k">as</span> <span class="n">for_json</span><span class="p">:</span>
|
||||
<span class="n">for_json</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="n">json</span><span class="o">.</span><span class="n">dumps</span><span class="p">(</span><span class="n">forensic_reports</span><span class="p">,</span> <span class="n">ensure_ascii</span><span class="o">=</span><span class="kc">False</span><span class="p">,</span>
|
||||
<span class="n">indent</span><span class="o">=</span><span class="mi">2</span><span class="p">))</span>
|
||||
<span class="n">append_json</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span> <span class="n">forensic_json_filename</span><span class="p">),</span>
|
||||
<span class="n">forensic_reports</span><span class="p">)</span>
|
||||
|
||||
<span class="k">with</span> <span class="nb">open</span><span class="p">(</span><span class="s2">"</span><span class="si">{0}</span><span class="s2">"</span>
|
||||
<span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span>
|
||||
<span class="n">forensic_csv_filename</span><span class="p">)),</span>
|
||||
<span class="s2">"w"</span><span class="p">,</span> <span class="n">newline</span><span class="o">=</span><span class="s2">"</span><span class="se">\n</span><span class="s2">"</span><span class="p">,</span> <span class="n">encoding</span><span class="o">=</span><span class="s2">"utf-8"</span><span class="p">)</span> <span class="k">as</span> <span class="n">for_csv</span><span class="p">:</span>
|
||||
<span class="n">csv</span> <span class="o">=</span> <span class="n">parsed_forensic_reports_to_csv</span><span class="p">(</span><span class="n">forensic_reports</span><span class="p">)</span>
|
||||
<span class="n">for_csv</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="n">csv</span><span class="p">)</span>
|
||||
<span class="n">append_csv</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span> <span class="n">forensic_csv_filename</span><span class="p">),</span>
|
||||
<span class="n">parsed_forensic_reports_to_csv</span><span class="p">(</span><span class="n">forensic_reports</span><span class="p">))</span>
|
||||
|
||||
<span class="n">samples_directory</span> <span class="o">=</span> <span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">output_directory</span><span class="p">,</span> <span class="s2">"samples"</span><span class="p">)</span>
|
||||
<span class="k">if</span> <span class="ow">not</span> <span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">exists</span><span class="p">(</span><span class="n">samples_directory</span><span class="p">):</span>
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>parsedmarc.elastic — parsedmarc 7.1.0 documentation</title>
|
||||
<title>parsedmarc.elastic — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="../../_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="../../_static/css/theme.css" type="text/css" />
|
||||
<!--[if lt IE 9]>
|
||||
@@ -13,6 +13,7 @@
|
||||
<script data-url_root="../../" id="documentation_options" src="../../_static/documentation_options.js"></script>
|
||||
<script src="../../_static/jquery.js"></script>
|
||||
<script src="../../_static/underscore.js"></script>
|
||||
<script src="../../_static/_sphinx_javascript_frameworks_compat.js"></script>
|
||||
<script src="../../_static/doctools.js"></script>
|
||||
<script src="../../_static/js/theme.js"></script>
|
||||
<link rel="index" title="Index" href="../../genindex.html" />
|
||||
@@ -27,7 +28,7 @@
|
||||
<a href="../../index.html" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
7.1.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="../../search.html" method="get">
|
||||
@@ -67,7 +68,6 @@
|
||||
<h1>Source code for parsedmarc.elastic</h1><div class="highlight"><pre>
|
||||
<span></span><span class="c1"># -*- coding: utf-8 -*-</span>
|
||||
|
||||
<span class="kn">import</span> <span class="nn">logging</span>
|
||||
<span class="kn">from</span> <span class="nn">collections</span> <span class="kn">import</span> <span class="n">OrderedDict</span>
|
||||
|
||||
<span class="kn">from</span> <span class="nn">elasticsearch_dsl.search</span> <span class="kn">import</span> <span class="n">Q</span>
|
||||
@@ -75,12 +75,10 @@
|
||||
<span class="n">InnerDoc</span><span class="p">,</span> <span class="n">Integer</span><span class="p">,</span> <span class="n">Text</span><span class="p">,</span> <span class="n">Boolean</span><span class="p">,</span> <span class="n">Ip</span><span class="p">,</span> <span class="n">Date</span><span class="p">,</span> <span class="n">Search</span>
|
||||
<span class="kn">from</span> <span class="nn">elasticsearch.helpers</span> <span class="kn">import</span> <span class="n">reindex</span>
|
||||
|
||||
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.log</span> <span class="kn">import</span> <span class="n">logger</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.utils</span> <span class="kn">import</span> <span class="n">human_timestamp_to_datetime</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc</span> <span class="kn">import</span> <span class="n">InvalidForensicReport</span>
|
||||
|
||||
<span class="n">logger</span> <span class="o">=</span> <span class="n">logging</span><span class="o">.</span><span class="n">getLogger</span><span class="p">(</span><span class="s2">"parsedmarc"</span><span class="p">)</span>
|
||||
|
||||
|
||||
<div class="viewcode-block" id="ElasticsearchError"><a class="viewcode-back" href="../../index.html#parsedmarc.elastic.ElasticsearchError">[docs]</a><span class="k">class</span> <span class="nc">ElasticsearchError</span><span class="p">(</span><span class="ne">Exception</span><span class="p">):</span>
|
||||
<span class="sd">"""Raised when an Elasticsearch error occurs"""</span></div>
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>parsedmarc.splunk — parsedmarc 7.1.0 documentation</title>
|
||||
<title>parsedmarc.splunk — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="../../_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="../../_static/css/theme.css" type="text/css" />
|
||||
<!--[if lt IE 9]>
|
||||
@@ -13,6 +13,7 @@
|
||||
<script data-url_root="../../" id="documentation_options" src="../../_static/documentation_options.js"></script>
|
||||
<script src="../../_static/jquery.js"></script>
|
||||
<script src="../../_static/underscore.js"></script>
|
||||
<script src="../../_static/_sphinx_javascript_frameworks_compat.js"></script>
|
||||
<script src="../../_static/doctools.js"></script>
|
||||
<script src="../../_static/js/theme.js"></script>
|
||||
<link rel="index" title="Index" href="../../genindex.html" />
|
||||
@@ -27,7 +28,7 @@
|
||||
<a href="../../index.html" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
7.1.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="../../search.html" method="get">
|
||||
@@ -65,8 +66,7 @@
|
||||
<div itemprop="articleBody">
|
||||
|
||||
<h1>Source code for parsedmarc.splunk</h1><div class="highlight"><pre>
|
||||
<span></span><span class="kn">import</span> <span class="nn">logging</span>
|
||||
<span class="kn">from</span> <span class="nn">urllib.parse</span> <span class="kn">import</span> <span class="n">urlparse</span>
|
||||
<span></span><span class="kn">from</span> <span class="nn">urllib.parse</span> <span class="kn">import</span> <span class="n">urlparse</span>
|
||||
<span class="kn">import</span> <span class="nn">socket</span>
|
||||
<span class="kn">import</span> <span class="nn">json</span>
|
||||
|
||||
@@ -74,12 +74,11 @@
|
||||
<span class="kn">import</span> <span class="nn">requests</span>
|
||||
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc</span> <span class="kn">import</span> <span class="n">__version__</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.log</span> <span class="kn">import</span> <span class="n">logger</span>
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.utils</span> <span class="kn">import</span> <span class="n">human_timestamp_to_timestamp</span>
|
||||
|
||||
<span class="n">urllib3</span><span class="o">.</span><span class="n">disable_warnings</span><span class="p">(</span><span class="n">urllib3</span><span class="o">.</span><span class="n">exceptions</span><span class="o">.</span><span class="n">InsecureRequestWarning</span><span class="p">)</span>
|
||||
|
||||
<span class="n">logger</span> <span class="o">=</span> <span class="n">logging</span><span class="o">.</span><span class="n">getLogger</span><span class="p">(</span><span class="s2">"parsedmarc"</span><span class="p">)</span>
|
||||
|
||||
|
||||
<div class="viewcode-block" id="SplunkError"><a class="viewcode-back" href="../../index.html#parsedmarc.splunk.SplunkError">[docs]</a><span class="k">class</span> <span class="nc">SplunkError</span><span class="p">(</span><span class="ne">RuntimeError</span><span class="p">):</span>
|
||||
<span class="sd">"""Raised when a Splunk API error occurs"""</span></div>
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>parsedmarc.utils — parsedmarc 7.1.0 documentation</title>
|
||||
<title>parsedmarc.utils — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="../../_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="../../_static/css/theme.css" type="text/css" />
|
||||
<!--[if lt IE 9]>
|
||||
@@ -13,6 +13,7 @@
|
||||
<script data-url_root="../../" id="documentation_options" src="../../_static/documentation_options.js"></script>
|
||||
<script src="../../_static/jquery.js"></script>
|
||||
<script src="../../_static/underscore.js"></script>
|
||||
<script src="../../_static/_sphinx_javascript_frameworks_compat.js"></script>
|
||||
<script src="../../_static/doctools.js"></script>
|
||||
<script src="../../_static/js/theme.js"></script>
|
||||
<link rel="index" title="Index" href="../../genindex.html" />
|
||||
@@ -27,7 +28,7 @@
|
||||
<a href="../../index.html" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
7.1.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="../../search.html" method="get">
|
||||
@@ -70,6 +71,7 @@
|
||||
<span class="kn">import</span> <span class="nn">logging</span>
|
||||
<span class="kn">import</span> <span class="nn">os</span>
|
||||
<span class="kn">from</span> <span class="nn">datetime</span> <span class="kn">import</span> <span class="n">datetime</span>
|
||||
<span class="kn">from</span> <span class="nn">datetime</span> <span class="kn">import</span> <span class="n">timezone</span>
|
||||
<span class="kn">from</span> <span class="nn">datetime</span> <span class="kn">import</span> <span class="n">timedelta</span>
|
||||
<span class="kn">from</span> <span class="nn">collections</span> <span class="kn">import</span> <span class="n">OrderedDict</span>
|
||||
<span class="kn">import</span> <span class="nn">tempfile</span>
|
||||
@@ -89,7 +91,7 @@
|
||||
<span class="c1"># Try backported to PY<37 `importlib_resources`</span>
|
||||
<span class="kn">import</span> <span class="nn">importlib_resources</span> <span class="k">as</span> <span class="nn">pkg_resources</span>
|
||||
|
||||
<span class="kn">import</span> <span class="nn">dateparser</span>
|
||||
<span class="kn">from</span> <span class="nn">dateutil.parser</span> <span class="kn">import</span> <span class="n">parse</span> <span class="k">as</span> <span class="n">parse_date</span>
|
||||
<span class="kn">import</span> <span class="nn">dns.reversename</span>
|
||||
<span class="kn">import</span> <span class="nn">dns.resolver</span>
|
||||
<span class="kn">import</span> <span class="nn">dns.exception</span>
|
||||
@@ -98,6 +100,7 @@
|
||||
<span class="kn">import</span> <span class="nn">requests</span>
|
||||
<span class="kn">import</span> <span class="nn">publicsuffix2</span>
|
||||
|
||||
<span class="kn">from</span> <span class="nn">parsedmarc.log</span> <span class="kn">import</span> <span class="n">logger</span>
|
||||
<span class="kn">import</span> <span class="nn">parsedmarc.resources</span>
|
||||
|
||||
<span class="n">USER_AGENT</span> <span class="o">=</span> <span class="s2">"Mozilla/5.0 ((</span><span class="si">{0}</span><span class="s2"> </span><span class="si">{1}</span><span class="s2">)) parsedmarc"</span><span class="o">.</span><span class="n">format</span><span class="p">(</span>
|
||||
@@ -108,7 +111,6 @@
|
||||
<span class="n">parenthesis_regex</span> <span class="o">=</span> <span class="n">re</span><span class="o">.</span><span class="n">compile</span><span class="p">(</span><span class="sa">r</span><span class="s1">'\s*\(.*\)\s*'</span><span class="p">)</span>
|
||||
|
||||
<span class="n">null_file</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">devnull</span><span class="p">,</span> <span class="s2">"w"</span><span class="p">)</span>
|
||||
<span class="n">logger</span> <span class="o">=</span> <span class="n">logging</span><span class="o">.</span><span class="n">getLogger</span><span class="p">(</span><span class="s2">"parsedmarc"</span><span class="p">)</span>
|
||||
<span class="n">mailparser_logger</span> <span class="o">=</span> <span class="n">logging</span><span class="o">.</span><span class="n">getLogger</span><span class="p">(</span><span class="s2">"mailparser"</span><span class="p">)</span>
|
||||
<span class="n">mailparser_logger</span><span class="o">.</span><span class="n">setLevel</span><span class="p">(</span><span class="n">logging</span><span class="o">.</span><span class="n">CRITICAL</span><span class="p">)</span>
|
||||
|
||||
@@ -313,12 +315,9 @@
|
||||
|
||||
<span class="n">human_timestamp</span> <span class="o">=</span> <span class="n">human_timestamp</span><span class="o">.</span><span class="n">replace</span><span class="p">(</span><span class="s2">"-0000"</span><span class="p">,</span> <span class="s2">""</span><span class="p">)</span>
|
||||
<span class="n">human_timestamp</span> <span class="o">=</span> <span class="n">parenthesis_regex</span><span class="o">.</span><span class="n">sub</span><span class="p">(</span><span class="s2">""</span><span class="p">,</span> <span class="n">human_timestamp</span><span class="p">)</span>
|
||||
<span class="n">settings</span> <span class="o">=</span> <span class="p">{}</span>
|
||||
|
||||
<span class="k">if</span> <span class="n">to_utc</span><span class="p">:</span>
|
||||
<span class="n">settings</span> <span class="o">=</span> <span class="p">{</span><span class="s2">"TO_TIMEZONE"</span><span class="p">:</span> <span class="s2">"UTC"</span><span class="p">}</span>
|
||||
|
||||
<span class="k">return</span> <span class="n">dateparser</span><span class="o">.</span><span class="n">parse</span><span class="p">(</span><span class="n">human_timestamp</span><span class="p">,</span> <span class="n">settings</span><span class="o">=</span><span class="n">settings</span><span class="p">)</span></div>
|
||||
<span class="n">dt</span> <span class="o">=</span> <span class="n">parse_date</span><span class="p">(</span><span class="n">human_timestamp</span><span class="p">)</span>
|
||||
<span class="k">return</span> <span class="n">dt</span><span class="o">.</span><span class="n">astimezone</span><span class="p">(</span><span class="n">timezone</span><span class="o">.</span><span class="n">utc</span><span class="p">)</span> <span class="k">if</span> <span class="n">to_utc</span> <span class="k">else</span> <span class="n">dt</span></div>
|
||||
|
||||
|
||||
<div class="viewcode-block" id="human_timestamp_to_timestamp"><a class="viewcode-back" href="../../index.html#parsedmarc.utils.human_timestamp_to_timestamp">[docs]</a><span class="k">def</span> <span class="nf">human_timestamp_to_timestamp</span><span class="p">(</span><span class="n">human_timestamp</span><span class="p">):</span>
|
||||
|
||||
1686
_sources/index.md.txt
Normal file
1686
_sources/index.md.txt
Normal file
File diff suppressed because it is too large
Load Diff
@@ -69,7 +69,7 @@ lookalike domain monitoring, check out `DomainAware <https://github.com/seantheg
|
||||
CLI help
|
||||
========
|
||||
|
||||
::
|
||||
.. code-block:: text
|
||||
|
||||
usage: parsedmarc [-h] [-c CONFIG_FILE] [--strip-attachment-payloads] [-o OUTPUT]
|
||||
[--aggregate-json-filename AGGREGATE_JSON_FILENAME]
|
||||
@@ -117,7 +117,8 @@ CLI help
|
||||
|
||||
.. note::
|
||||
|
||||
Starting in ``parsedmarc`` 6.0.0, most CLI options were moved to a configuration file, described below.
|
||||
Starting in ``parsedmarc`` 6.0.0, most CLI options were moved to a
|
||||
configuration file, described below.
|
||||
|
||||
Configuration file
|
||||
==================
|
||||
@@ -170,78 +171,124 @@ The full set of configuration options are:
|
||||
|
||||
|
||||
- ``general``
|
||||
- ``save_aggregate`` - bool: Save aggregate report data to Elasticsearch, Splunk and/or S3
|
||||
- ``save_forensic`` - bool: Save forensic report data to Elasticsearch, Splunk and/or S3
|
||||
- ``strip_attachment_payloads`` - bool: Remove attachment payloads from results
|
||||
- ``save_aggregate`` - bool: Save aggregate report data to
|
||||
Elasticsearch, Splunk and/or S3
|
||||
- ``save_forensic`` - bool: Save forensic report data to
|
||||
Elasticsearch, Splunk and/or S3
|
||||
- ``strip_attachment_payloads`` - bool: Remove attachment
|
||||
payloads from results
|
||||
- ``output`` - str: Directory to place JSON and CSV files in
|
||||
- ``aggregate_json_filename`` - str: filename for the aggregate JSON output file
|
||||
- ``forensic_json_filename`` - str: filename for the forensic JSON output file
|
||||
- ``ip_db_path`` - str: An optional custom path to a MMDB file from MaxMind or DBIP
|
||||
- ``offline`` - bool: Do not use online queries for geolocation or DNS
|
||||
- ``nameservers`` - str: A comma separated list of DNS resolvers (Default: `Cloudflare's public resolvers`_)
|
||||
- ``aggregate_json_filename`` - str: filename for the aggregate
|
||||
JSON output file
|
||||
- ``forensic_json_filename`` - str: filename for the forensic
|
||||
JSON output file
|
||||
- ``ip_db_path`` - str: An optional custom path to a MMDB file
|
||||
- from MaxMind or DBIP
|
||||
- ``offline`` - bool: Do not use online queries for geolocation
|
||||
or DNS
|
||||
- ``nameservers`` - str: A comma separated list of
|
||||
DNS resolvers (Default: `Cloudflare's public resolvers`_)
|
||||
- ``dns_timeout`` - float: DNS timeout period
|
||||
- ``debug`` - bool: Print debugging messages
|
||||
- ``silent`` - bool: Only print errors (Default: True)
|
||||
- ``log_file`` - str: Write log messages to a file at this path
|
||||
- ``n_procs`` - int: Number of process to run in parallel when parsing in CLI mode (Default: 1)
|
||||
- ``chunk_size`` - int: Number of files to give to each process when running in parallel.
|
||||
- ``n_procs`` - int: Number of process to run in parallel when
|
||||
parsing in CLI mode (Default: 1)
|
||||
- ``chunk_size`` - int: Number of files to give to each process
|
||||
when running in parallel.
|
||||
|
||||
.. note::
|
||||
Setting this to a number larger than one can improve performance when processing thousands of files
|
||||
Setting this to a number larger than one can improve
|
||||
performance when processing thousands of files
|
||||
|
||||
- ``mailbox``
|
||||
- ``reports_folder`` - str: The mailbox folder (or label for Gmail) where the incoming reports can be found (Default: INBOX)
|
||||
- ``archive_folder`` - str: The mailbox folder (or label for Gmail) to sort processed emails into (Default: Archive)
|
||||
- ``watch`` - bool: Use the IMAP ``IDLE`` command to process messages as they arrive or poll MS Graph for new messages
|
||||
- ``delete`` - bool: Delete messages after processing them, instead of archiving them
|
||||
- ``reports_folder`` - str: The mailbox folder (or label for
|
||||
Gmail) where the incoming reports can be found (Default: INBOX)
|
||||
- ``archive_folder`` - str: The mailbox folder (or label for
|
||||
Gmail) to sort processed emails into (Default: Archive)
|
||||
- ``watch`` - bool: Use the IMAP ``IDLE`` command to process
|
||||
- messages as they arrive or poll MS Graph for new messages
|
||||
- ``delete`` - bool: Delete messages after processing them,
|
||||
- instead of archiving them
|
||||
- ``test`` - bool: Do not move or delete messages
|
||||
- ``batch_size`` - int: Number of messages to read and process before saving. Default 10. Use 0 for no limit.
|
||||
- ``batch_size`` - int: Number of messages to read and process
|
||||
before saving. Default 10. Use 0 for no limit.
|
||||
- ``check_timeout`` - int: Number of seconds to wait for a IMAP
|
||||
IDLE response or the number of seconds until the next mai
|
||||
check (Default: 30)
|
||||
|
||||
- ``imap``
|
||||
- ``host`` - str: The IMAP server hostname or IP address
|
||||
- ``port`` - int: The IMAP server port (Default: 993)
|
||||
|
||||
.. note::
|
||||
``%`` characters must be escaped with another ``%`` character, so use ``%%`` wherever a ``%`` character is used.
|
||||
``%`` characters must be escaped with another ``%`` character,
|
||||
so use ``%%`` wherever a ``%`` character is used.
|
||||
|
||||
.. note::
|
||||
Starting in version 8.0.0, most options from the ``imap`` section have been moved to the ``mailbox`` section.
|
||||
Starting in version 8.0.0, most options from the ``imap``
|
||||
section have been moved to the ``mailbox`` section.
|
||||
|
||||
.. note::
|
||||
If your host recommends another port, still try 993
|
||||
|
||||
- ``ssl`` - bool: Use an encrypted SSL/TLS connection (Default: True)
|
||||
- ``skip_certificate_verification`` - bool: Skip certificate verification (not recommended)
|
||||
- ``ssl`` - bool: Use an encrypted SSL/TLS connection
|
||||
(Default: True)
|
||||
- ``skip_certificate_verification`` - bool: Skip certificate
|
||||
verification (not recommended)
|
||||
- ``user`` - str: The IMAP user
|
||||
- ``password`` - str: The IMAP password
|
||||
|
||||
- ``msgraph``
|
||||
- ``auth_method`` - str: Authentication method, valid types are UsernamePassword, DeviceCode, or ClientSecret (Default: UsernamePassword).
|
||||
- ``user`` - str: The M365 user, required when the auth method is UsernamePassword
|
||||
- ``password`` - str: The user password, required when the auth method is UsernamePassword
|
||||
- ``auth_method`` - str: Authentication method, valid types are
|
||||
UsernamePassword, DeviceCode, or ClientSecret
|
||||
(Default: UsernamePassword).
|
||||
- ``user`` - str: The M365 user, required when the auth method is
|
||||
UsernamePassword
|
||||
- ``password`` - str: The user password, required when the auth
|
||||
method is UsernamePassword
|
||||
- ``client_id`` - str: The app registration's client ID
|
||||
- ``client_secret`` - str: The app registration's secret
|
||||
- ``tenant_id`` - str: The Azure AD tenant ID. This is required for all auth methods except UsernamePassword.
|
||||
- ``mailbox`` - str: The mailbox name. This defaults to the current user if using the UsernamePassword auth method, but could be a shared mailbox if the user has access to the mailbox
|
||||
- ``tenant_id`` - str: The Azure AD tenant ID. This is required
|
||||
for all auth methods except UsernamePassword.
|
||||
- ``mailbox`` - str: The mailbox name. This defaults to the
|
||||
current user if using the UsernamePassword auth method, but
|
||||
could be a shared mailbox if the user has access to the mailbox
|
||||
- ``token_file`` - str: Path to save the token file
|
||||
(Default: .token)
|
||||
|
||||
.. note::
|
||||
You must create an app registration in Azure AD and have an admin grant the Microsoft Graph ``Mail.ReadWrite`` (delegated) permission to the app.
|
||||
If you are using `UsernamePassword` auth and the mailbox is different from the username, you must grant the app ``Mail.ReadWrite.Shared``.
|
||||
You must create an app registration in Azure AD and have an
|
||||
admin grant the Microsoft Graph ``Mail.ReadWrite``
|
||||
(delegated) permission to the app. If you are using
|
||||
`UsernamePassword` auth and the mailbox is different from the
|
||||
username, you must grant the app ``Mail.ReadWrite.Shared``.
|
||||
|
||||
.. warning::
|
||||
If you are using the `ClientSecret` auth method, you need to grant the ``Mail.ReadWrite`` (application) permission to the app.
|
||||
You must also restrict the application's access to a specific mailbox since it allows all mailboxes by default.
|
||||
Use the ``New-ApplicationAccessPolicy`` command in the Exchange PowerShell module.
|
||||
If you need to scope the policy to shared mailboxes, you can add them to a mail enabled security group and use that as the group id.
|
||||
If you are using the `ClientSecret` auth method, you need to
|
||||
grant the ``Mail.ReadWrite`` (application) permission to the
|
||||
app. You must also restrict the application's access to a
|
||||
specific mailbox since it allows all mailboxes by default.
|
||||
Use the ``New-ApplicationAccessPolicy`` command in the
|
||||
Exchange PowerShell module. If you need to scope the policy to
|
||||
shared mailboxes, you can add them to a mail enabled security
|
||||
group and use that as the group id.
|
||||
|
||||
``New-ApplicationAccessPolicy -AccessRight RestrictAccess -AppId "<CLIENT_ID>" -PolicyScopeGroupId "<MAILBOX>" -Description "Restrict access to dmarc reports mailbox."``
|
||||
.. code-block:: powershell
|
||||
|
||||
New-ApplicationAccessPolicy -AccessRight RestrictAccess
|
||||
-AppId "<CLIENT_ID>" -PolicyScopeGroupId "<MAILBOX>"
|
||||
-Description "Restrict access to dmarc reports mailbox."
|
||||
|
||||
|
||||
- ``elasticsearch``
|
||||
- ``hosts`` - str: A comma separated list of hostnames and ports or URLs (e.g. ``127.0.0.1:9200`` or ``https://user:secret@localhost``)
|
||||
- ``hosts`` - str: A comma separated list of hostnames and ports
|
||||
or URLs (e.g. ``127.0.0.1:9200`` or
|
||||
``https://user:secret@localhost``)
|
||||
|
||||
.. note::
|
||||
Special characters in the username or password must be `URL encoded`_.
|
||||
Special characters in the username or password must be
|
||||
`URL encoded`_.
|
||||
|
||||
- ``ssl`` - bool: Use an encrypted SSL/TLS connection (Default: True)
|
||||
- ``cert_path`` - str: Path to a trusted certificates
|
||||
@@ -253,30 +300,36 @@ The full set of configuration options are:
|
||||
- ``url`` - str: The URL of the Splunk HTTP Events Collector (HEC)
|
||||
- ``token`` - str: The HEC token
|
||||
- ``index`` - str: The Splunk index to use
|
||||
- ``skip_certificate_verification`` - bool: Skip certificate verification (not recommended)
|
||||
- ``skip_certificate_verification`` - bool: Skip certificate
|
||||
verification (not recommended)
|
||||
- ``kafka``
|
||||
- ``hosts`` - str: A comma separated list of Kafka hosts
|
||||
- ``user`` - str: The Kafka user
|
||||
- ``passsword`` - str: The Kafka password
|
||||
- ``ssl`` - bool: Use an encrypted SSL/TLS connection (Default: True)
|
||||
- ``skip_certificate_verification`` - bool: Skip certificate verification (not recommended)
|
||||
- ``skip_certificate_verification`` - bool: Skip certificate
|
||||
verification (not recommended)
|
||||
- ``aggregate_topic`` - str: The Kafka topic for aggregate reports
|
||||
- ``forensic_topic`` - str: The Kafka topic for forensic reports
|
||||
- ``smtp``
|
||||
- ``host`` - str: The SMTP hostname
|
||||
- ``port`` - int: The SMTP port (Default: 25)
|
||||
- ``ssl`` - bool: Require SSL/TLS instead of using STARTTLS
|
||||
- ``skip_certificate_verification`` - bool: Skip certificate verification (not recommended)
|
||||
- ``skip_certificate_verification`` - bool: Skip certificate
|
||||
verification (not recommended)
|
||||
- ``user`` - str: the SMTP username
|
||||
- ``password`` - str: the SMTP password
|
||||
- ``from`` - str: The From header to use in the email
|
||||
- ``to`` - list: A list of email addresses to send to
|
||||
- ``subject`` - str: The Subject header to use in the email (Default: parsedmarc report)
|
||||
- ``subject`` - str: The Subject header to use in the email
|
||||
(Default: parsedmarc report)
|
||||
- ``attachment`` - str: The ZIP attachment filenames
|
||||
- ``message`` - str: The email message (Default: Please see the attached parsedmarc report.)
|
||||
- ``message`` - str: The email message
|
||||
(Default: Please see the attached parsedmarc report.)
|
||||
|
||||
.. note::
|
||||
``%`` characters must be escaped with another ``%`` character, so use ``%%`` wherever a ``%`` character is used.
|
||||
``%`` characters must be escaped with another ``%`` character,
|
||||
so use ``%%`` wherever a ``%`` character is used.
|
||||
|
||||
- ``s3``
|
||||
- ``bucket`` - str: The S3 bucket name
|
||||
@@ -289,43 +342,52 @@ The full set of configuration options are:
|
||||
- ``server`` - str: The Syslog server name or IP address
|
||||
- ``port`` - int: The UDP port to use (Default: 514)
|
||||
- ``gmail_api``
|
||||
- ``gmail_api_credentials_file`` - str: Path to file containing the credentials, None to disable (Default: None)
|
||||
- ``gmail_api_token_file`` - str: Path to save the token file (Default: .token)
|
||||
- ``gmail_api_include_spam_trash`` - bool: Include messages in Spam and Trash when searching reports (Default: False)
|
||||
- ``gmail_api_scopes`` - str: Comma separated list of scopes to use when acquiring credentials (Default: https://www.googleapis.com/auth/gmail.modify)
|
||||
- ``credentials_file`` - str: Path to file containing the
|
||||
credentials, None to disable (Default: None)
|
||||
- ``token_file`` - str: Path to save the token file
|
||||
(Default: .token)
|
||||
- ``include_spam_trash`` - bool: Include messages in Spam and
|
||||
Trash when searching reports (Default: False)
|
||||
- ``scopes`` - str: Comma separated list of scopes to use when
|
||||
acquiring credentials (Default: https://www.googleapis.com/auth/gmail.modify)
|
||||
- ``oauth2_port`` - int: The TCP port for the local server to
|
||||
listen on for the OAuth2 response (Default: 8080)
|
||||
|
||||
.. warning::
|
||||
|
||||
It is **strongly recommended** to **not** use the ``nameservers`` setting.
|
||||
By default, ``parsedmarc`` uses `Cloudflare's public resolvers`_,
|
||||
which are much faster and more reliable than Google, Cisco OpenDNS, or
|
||||
even most local resolvers.
|
||||
It is **strongly recommended** to **not** use the ``nameservers``
|
||||
setting. By default, ``parsedmarc`` uses
|
||||
`Cloudflare's public resolvers`_, which are much faster and more
|
||||
reliable than Google, Cisco OpenDNS, or even most local resolvers.
|
||||
|
||||
The ``nameservers`` option should only be used if your network blocks DNS
|
||||
requests to outside resolvers.
|
||||
The ``nameservers`` option should only be used if your network
|
||||
blocks DNS requests to outside resolvers.
|
||||
|
||||
.. warning::
|
||||
|
||||
``save_aggregate`` and ``save_forensic`` are separate options because
|
||||
you may not want to save forensic reports (also known as failure reports)
|
||||
to your Elasticsearch instance, particularly if you are in a
|
||||
highly-regulated industry that handles sensitive data, such as healthcare
|
||||
or finance. If your legitimate outgoing email fails DMARC, it is possible
|
||||
``save_aggregate`` and ``save_forensic`` are separate options
|
||||
because you may not want to save forensic reports
|
||||
(also known as failure reports) to your Elasticsearch instance,
|
||||
particularly if you are in a highly-regulated industry that
|
||||
handles sensitive data, such as healthcare or finance. If your
|
||||
legitimate outgoing email fails DMARC, it is possible
|
||||
that email may appear later in a forensic report.
|
||||
|
||||
Forensic reports contain the original headers of an email that failed a
|
||||
DMARC check, and sometimes may also include the full message body,
|
||||
depending on the policy of the reporting organization.
|
||||
Forensic reports contain the original headers of an email that
|
||||
failed a DMARC check, and sometimes may also include the
|
||||
full message body, depending on the policy of the reporting
|
||||
organization.
|
||||
|
||||
Most reporting organizations do not send forensic reports of any kind for
|
||||
privacy reasons. While aggregate DMARC reports are sent at least daily,
|
||||
it is normal to receive very few forensic reports.
|
||||
Most reporting organizations do not send forensic reports of any
|
||||
kind for privacy reasons. While aggregate DMARC reports are sent
|
||||
at least daily, it is normal to receive very few forensic reports.
|
||||
|
||||
An alternative approach is to still collect forensic/failure/ruf reports
|
||||
in your DMARC inbox, but run ``parsedmarc`` with ``save_forensic = True``
|
||||
manually on a separate IMAP folder (using the ``reports_folder`` option),
|
||||
after you have manually moved known samples you want to save to that
|
||||
folder (e.g. malicious samples and non-sensitive legitimate samples).
|
||||
An alternative approach is to still collect forensic/failure/ruf
|
||||
reports in your DMARC inbox, but run ``parsedmarc`` with
|
||||
``save_forensic = True``manually on a separate IMAP folder (using
|
||||
the ``reports_folder`` option), after you have manually moved
|
||||
known samples you want to save to that folder
|
||||
(e.g. malicious samples and non-sensitive legitimate samples).
|
||||
|
||||
|
||||
Sample aggregate report output
|
||||
@@ -337,8 +399,8 @@ report schema standardized in
|
||||
`RFC 7480 Appendix C <https://tools.ietf.org/html/rfc7489#appendix-C>`_.
|
||||
This draft schema is still in wide use.
|
||||
|
||||
``parsedmarc`` produces consistent, normalized output, regardless of the report
|
||||
schema.
|
||||
``parsedmarc`` produces consistent, normalized output, regardless
|
||||
of the report schema.
|
||||
|
||||
JSON
|
||||
----
|
||||
@@ -413,7 +475,7 @@ JSON
|
||||
CSV
|
||||
---
|
||||
|
||||
::
|
||||
.. code-block:: text
|
||||
|
||||
xml_schema,org_name,org_email,org_extra_contact_info,report_id,begin_date,end_date,errors,domain,adkim,aspf,p,sp,pct,fo,source_ip_address,source_country,source_reverse_dns,source_base_domain,count,spf_aligned,dkim_aligned,dmarc_aligned,disposition,policy_override_reasons,policy_override_comments,envelope_from,header_from,envelope_to,dkim_domains,dkim_selectors,dkim_results,spf_domains,spf_scopes,spf_results
|
||||
draft,acme.com,noreply-dmarc-support@acme.com,http://acme.com/dmarc/support,9391651994964116463,2012-04-27 20:00:00,2012-04-28 19:59:59,,example.com,r,r,none,none,100,0,72.150.241.94,US,adsl-72-150-241-94.shv.bellsouth.net,bellsouth.net,2,True,False,True,none,,,example.com,example.com,,example.com,none,fail,example.com,mfrom,pass
|
||||
@@ -521,7 +583,7 @@ JSON
|
||||
CSV
|
||||
---
|
||||
|
||||
::
|
||||
.. code-block:: text
|
||||
|
||||
feedback_type,user_agent,version,original_envelope_id,original_mail_from,original_rcpt_to,arrival_date,arrival_date_utc,subject,message_id,authentication_results,dkim_domain,source_ip_address,source_country,source_reverse_dns,source_base_domain,delivery_result,auth_failure,reported_domain,authentication_mechanisms,sample_headers_only
|
||||
auth-failure,Lua/1.0,1.0,,sharepoint@domain.de,peter.pan@domain.de,"Mon, 01 Oct 2018 11:20:27 +0200",2018-10-01 09:20:27,Subject,<38.E7.30937.BD6E1BB5@ mailrelay.de>,"dmarc=fail (p=none, dis=none) header.from=domain.de",,10.10.10.10,,,,policy,dmarc,domain.de,,False
|
||||
@@ -544,7 +606,7 @@ Installation
|
||||
to use that proxy. To do this, edit ``/etc/environment`` and add your
|
||||
proxy details there, for example:
|
||||
|
||||
::
|
||||
.. code-block:: bash
|
||||
|
||||
http_proxy=http://user:password@prox-server:3128
|
||||
https_proxy=https://user:password@prox-server:3128
|
||||
@@ -552,7 +614,7 @@ Installation
|
||||
|
||||
Or if no credentials are needed:
|
||||
|
||||
::
|
||||
.. code-block:: bash
|
||||
|
||||
http_proxy=http://prox-server:3128
|
||||
https_proxy=https://prox-server:3128
|
||||
@@ -604,14 +666,17 @@ On CentOS or RHEL systems, run:
|
||||
|
||||
sudo dnf install -y geoipupdate
|
||||
|
||||
The latest builds for Linux, macOS, and Windows can be downloaded from the `geoipupdate releases page on GitHub`_.
|
||||
The latest builds for Linux, macOS, and Windows can be downloaded
|
||||
from the `geoipupdate releases page on GitHub`_.
|
||||
|
||||
On December 30th, 2019, MaxMind started requiring free accounts to access the free Geolite2 databases, in order `to
|
||||
On December 30th, 2019, MaxMind started requiring free accounts to
|
||||
access the free Geolite2 databases, in order `to
|
||||
comply with various privacy regulations`_.
|
||||
|
||||
Start by `registering for a free GeoLite2 account`_, and signing in.
|
||||
|
||||
Then, navigate the to the `License Keys`_ page under your account, and create a new license key for the version of
|
||||
Then, navigate the to the `License Keys`_ page under your account,
|
||||
and create a new license key for the version of
|
||||
``geoipupdate`` that was installed.
|
||||
|
||||
.. warning::
|
||||
@@ -629,9 +694,11 @@ Then, navigate the to the `License Keys`_ page under your account, and create a
|
||||
|
||||
You can use ``parsedmarc`` as the description for the key.
|
||||
|
||||
Once you have generated a key, download the config pre-filled configuration file.
|
||||
This file should be saved at ``/etc/GeoIP.conf`` on Linux or macOS systems, or at
|
||||
``%SystemDrive%\ProgramData\MaxMind\GeoIPUpdate\GeoIP.conf`` on Windows systems.
|
||||
Once you have generated a key, download the config pre-filled
|
||||
configuration file. This file should be saved at ``/etc/GeoIP.conf``
|
||||
on Linux or macOS systems, or at
|
||||
``%SystemDrive%\ProgramData\MaxMind\GeoIPUpdate\GeoIP.conf`` on
|
||||
Windows systems.
|
||||
|
||||
Then run
|
||||
|
||||
@@ -641,10 +708,12 @@ Then run
|
||||
|
||||
To download the databases for the first time.
|
||||
|
||||
The GeoLite2 Country, City, and ASN databases are updated weekly, every Tuesday.
|
||||
``geoipupdate`` can be run weekly by adding a cron job or scheduled task.
|
||||
The GeoLite2 Country, City, and ASN databases are updated weekly,
|
||||
every Tuesday. ``geoipupdate`` can be run weekly by adding a cron
|
||||
job or scheduled task.
|
||||
|
||||
More information about ``geoipupdate`` can be found at the `MaxMind geoipupdate page`_.
|
||||
More information about ``geoipupdate`` can be found at the
|
||||
`MaxMind geoipupdate page`_.
|
||||
|
||||
Installing parsedmarc
|
||||
---------------------
|
||||
@@ -681,7 +750,8 @@ Install parsedmarc in a virtualenv
|
||||
|
||||
sudo -u parsedmarc virtualenv /opt/parsedmarc/venv
|
||||
|
||||
CentOS/RHEL 8 systems use Python 3.6 by default, so on those systems explicitly tell ``virtualenv`` to use ``python3.9`` instead
|
||||
CentOS/RHEL 8 systems use Python 3.6 by default, so on those systems
|
||||
explicitly tell ``virtualenv`` to use ``python3.9`` instead
|
||||
|
||||
.. code-block:: bash
|
||||
|
||||
@@ -721,7 +791,7 @@ Accessing an inbox using OWA/EWS
|
||||
Starting in 8.0.0, parsedmarc supports accessing Microsoft/Office 365
|
||||
inboxes via the Microsoft Graph API, which is preferred over Davmail.
|
||||
|
||||
Some organisations do not allow IMAP or the Microsoft Graph API,
|
||||
Some organizations do not allow IMAP or the Microsoft Graph API,
|
||||
and only support Exchange Web Services (EWS)/Outlook Web Access (OWA).
|
||||
In that case, Davmail will need to be set up
|
||||
as a local EWS/OWA IMAP gateway. It can even work where
|
||||
@@ -963,7 +1033,8 @@ For CentOS, RHEL, and other RPM systems, follow the Elastic RPM guides for
|
||||
sudo service elasticsearch start
|
||||
sudo service kibana start
|
||||
|
||||
Without the commercial X-Pack_ or ReadonlyREST_ products, Kibana does not have any authentication
|
||||
Without the commercial X-Pack_ or ReadonlyREST_ products, Kibana
|
||||
does not have any authentication
|
||||
mechanism of its own. You can use nginx as a reverse proxy that provides basic
|
||||
authentication.
|
||||
|
||||
@@ -1298,7 +1369,7 @@ is using a particular service. With that information, you can contact them and
|
||||
have them set up DKIM.
|
||||
|
||||
.. note::
|
||||
|
||||
|
||||
If you have a lot of B2C customers, you may see a high volume of emails as
|
||||
your domains coming from consumer email services, such as Google/Gmail and
|
||||
Yahoo! This occurs when customers have mailbox rules in place that forward
|
||||
@@ -1383,24 +1454,26 @@ What if a sender won't support DKIM/DMARC?
|
||||
.. warning ::
|
||||
|
||||
Do not alter the ``p`` or ``sp`` values of the DMARC record on the
|
||||
Top-Level Domain (TLD) – that would leave you vulnerable to spoofing of
|
||||
your TLD and/or any subdomain.
|
||||
Top-Level Domain (TLD) – that would leave you vulnerable to
|
||||
spoofing of your TLD and/or any subdomain.
|
||||
|
||||
What about mailing lists?
|
||||
=========================
|
||||
|
||||
When you deploy DMARC on your domain, you might find that messages relayed by
|
||||
mailing lists are failing DMARC, most likely because the mailing list is
|
||||
spoofing your from address, and modifying the subject, footer, or other part
|
||||
of the message, thereby breaking the DKIM signature.
|
||||
When you deploy DMARC on your domain, you might find that messages
|
||||
relayed by mailing lists are failing DMARC, most likely because the mailing
|
||||
list is spoofing your from address, and modifying the subject,
|
||||
footer, or other part of the message, thereby breaking the
|
||||
DKIM signature.
|
||||
|
||||
Mailing list list best practices
|
||||
--------------------------------
|
||||
|
||||
Ideally, a mailing list should forward messages without altering the headers
|
||||
or body content at all. `Joe Nelson`_ does a fantastic job of explaining exactly
|
||||
what mailing lists should and shouldn't do to be fully DMARC compliant.
|
||||
Rather than repeat his fine work, here's a summary:
|
||||
Ideally, a mailing list should forward messages without altering the
|
||||
headers or body content at all. `Joe Nelson`_ does a fantastic job of
|
||||
explaining exactly what mailing lists should and shouldn't do to be
|
||||
fully DMARC compliant. Rather than repeat his fine work, here's a
|
||||
summary:
|
||||
|
||||
**Do**
|
||||
|
||||
@@ -1470,7 +1543,7 @@ Navigate to Privacy Options> Sending Filters, and configure the settings below
|
||||
====================================== ==========
|
||||
**Setting** **Value**
|
||||
**dmarc_moderation_action** Accept
|
||||
**dmarc_quarentine_moderation_action** Yes
|
||||
**dmarc_quarantine_moderation_action** Yes
|
||||
**dmarc_none_moderation_action** Yes
|
||||
====================================== ==========
|
||||
|
||||
@@ -1492,7 +1565,7 @@ Configure the settings below
|
||||
**Include RFC2369 headers** Yes
|
||||
**Include the list post header** Yes
|
||||
**Explicit reply-to address**
|
||||
**First strip replyo** No
|
||||
**First strip replyto** No
|
||||
**Reply goes to list** No munging
|
||||
====================================== ==========
|
||||
|
||||
@@ -1538,7 +1611,7 @@ Navigate to Privacy Options> Sending Filters, and configure the settings below
|
||||
====================================== ==========
|
||||
**Setting** **Value**
|
||||
**dmarc_moderation_action** Munge From
|
||||
**dmarc_quarentine_moderation_action** Yes
|
||||
**dmarc_quarantine_moderation_action** Yes
|
||||
**dmarc_none_moderation_action** Yes
|
||||
====================================== ==========
|
||||
|
||||
|
||||
@@ -608,8 +608,6 @@ ol.simple p,
|
||||
ul.simple p {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
/* Docutils 0.17 and older (footnotes & citations) */
|
||||
dl.footnote > dt,
|
||||
dl.citation > dt {
|
||||
float: left;
|
||||
@@ -627,33 +625,6 @@ dl.citation > dd:after {
|
||||
clear: both;
|
||||
}
|
||||
|
||||
/* Docutils 0.18+ (footnotes & citations) */
|
||||
aside.footnote > span,
|
||||
div.citation > span {
|
||||
float: left;
|
||||
}
|
||||
aside.footnote > span:last-of-type,
|
||||
div.citation > span:last-of-type {
|
||||
padding-right: 0.5em;
|
||||
}
|
||||
aside.footnote > p {
|
||||
margin-left: 2em;
|
||||
}
|
||||
div.citation > p {
|
||||
margin-left: 4em;
|
||||
}
|
||||
aside.footnote > p:last-of-type,
|
||||
div.citation > p:last-of-type {
|
||||
margin-bottom: 0em;
|
||||
}
|
||||
aside.footnote > p:last-of-type:after,
|
||||
div.citation > p:last-of-type:after {
|
||||
content: "";
|
||||
clear: both;
|
||||
}
|
||||
|
||||
/* Footnotes & citations ends */
|
||||
|
||||
dl.field-list {
|
||||
display: grid;
|
||||
grid-template-columns: fit-content(30%) auto;
|
||||
@@ -665,11 +636,11 @@ dl.field-list > dt {
|
||||
padding-left: 0.5em;
|
||||
padding-right: 5px;
|
||||
}
|
||||
|
||||
dl.field-list > dt:after {
|
||||
content: ":";
|
||||
}
|
||||
|
||||
|
||||
dl.field-list > dd {
|
||||
padding-left: 0.5em;
|
||||
margin-top: 0em;
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
var DOCUMENTATION_OPTIONS = {
|
||||
URL_ROOT: document.getElementById("documentation_options").getAttribute('data-url_root'),
|
||||
VERSION: '8.3.0',
|
||||
VERSION: '8.3.1',
|
||||
LANGUAGE: 'en',
|
||||
COLLAPSE_INDEX: false,
|
||||
BUILDER: 'html',
|
||||
@@ -10,5 +10,5 @@ var DOCUMENTATION_OPTIONS = {
|
||||
SOURCELINK_SUFFIX: '.txt',
|
||||
NAVIGATION_WITH_KEYS: false,
|
||||
SHOW_SEARCH_SUMMARY: true,
|
||||
ENABLE_SEARCH_SHORTCUTS: false,
|
||||
ENABLE_SEARCH_SHORTCUTS: true,
|
||||
};
|
||||
@@ -4,71 +4,71 @@ span.linenos { color: inherit; background-color: transparent; padding-left: 5px;
|
||||
td.linenos .special { color: #000000; background-color: #ffffc0; padding-left: 5px; padding-right: 5px; }
|
||||
span.linenos.special { color: #000000; background-color: #ffffc0; padding-left: 5px; padding-right: 5px; }
|
||||
.highlight .hll { background-color: #ffffcc }
|
||||
.highlight { background: #eeffcc; }
|
||||
.highlight .c { color: #408090; font-style: italic } /* Comment */
|
||||
.highlight { background: #f8f8f8; }
|
||||
.highlight .c { color: #3D7B7B; font-style: italic } /* Comment */
|
||||
.highlight .err { border: 1px solid #FF0000 } /* Error */
|
||||
.highlight .k { color: #007020; font-weight: bold } /* Keyword */
|
||||
.highlight .k { color: #008000; font-weight: bold } /* Keyword */
|
||||
.highlight .o { color: #666666 } /* Operator */
|
||||
.highlight .ch { color: #408090; font-style: italic } /* Comment.Hashbang */
|
||||
.highlight .cm { color: #408090; font-style: italic } /* Comment.Multiline */
|
||||
.highlight .cp { color: #007020 } /* Comment.Preproc */
|
||||
.highlight .cpf { color: #408090; font-style: italic } /* Comment.PreprocFile */
|
||||
.highlight .c1 { color: #408090; font-style: italic } /* Comment.Single */
|
||||
.highlight .cs { color: #408090; background-color: #fff0f0 } /* Comment.Special */
|
||||
.highlight .ch { color: #3D7B7B; font-style: italic } /* Comment.Hashbang */
|
||||
.highlight .cm { color: #3D7B7B; font-style: italic } /* Comment.Multiline */
|
||||
.highlight .cp { color: #9C6500 } /* Comment.Preproc */
|
||||
.highlight .cpf { color: #3D7B7B; font-style: italic } /* Comment.PreprocFile */
|
||||
.highlight .c1 { color: #3D7B7B; font-style: italic } /* Comment.Single */
|
||||
.highlight .cs { color: #3D7B7B; font-style: italic } /* Comment.Special */
|
||||
.highlight .gd { color: #A00000 } /* Generic.Deleted */
|
||||
.highlight .ge { font-style: italic } /* Generic.Emph */
|
||||
.highlight .gr { color: #FF0000 } /* Generic.Error */
|
||||
.highlight .gr { color: #E40000 } /* Generic.Error */
|
||||
.highlight .gh { color: #000080; font-weight: bold } /* Generic.Heading */
|
||||
.highlight .gi { color: #00A000 } /* Generic.Inserted */
|
||||
.highlight .go { color: #333333 } /* Generic.Output */
|
||||
.highlight .gp { color: #c65d09; font-weight: bold } /* Generic.Prompt */
|
||||
.highlight .gi { color: #008400 } /* Generic.Inserted */
|
||||
.highlight .go { color: #717171 } /* Generic.Output */
|
||||
.highlight .gp { color: #000080; font-weight: bold } /* Generic.Prompt */
|
||||
.highlight .gs { font-weight: bold } /* Generic.Strong */
|
||||
.highlight .gu { color: #800080; font-weight: bold } /* Generic.Subheading */
|
||||
.highlight .gt { color: #0044DD } /* Generic.Traceback */
|
||||
.highlight .kc { color: #007020; font-weight: bold } /* Keyword.Constant */
|
||||
.highlight .kd { color: #007020; font-weight: bold } /* Keyword.Declaration */
|
||||
.highlight .kn { color: #007020; font-weight: bold } /* Keyword.Namespace */
|
||||
.highlight .kp { color: #007020 } /* Keyword.Pseudo */
|
||||
.highlight .kr { color: #007020; font-weight: bold } /* Keyword.Reserved */
|
||||
.highlight .kt { color: #902000 } /* Keyword.Type */
|
||||
.highlight .m { color: #208050 } /* Literal.Number */
|
||||
.highlight .s { color: #4070a0 } /* Literal.String */
|
||||
.highlight .na { color: #4070a0 } /* Name.Attribute */
|
||||
.highlight .nb { color: #007020 } /* Name.Builtin */
|
||||
.highlight .nc { color: #0e84b5; font-weight: bold } /* Name.Class */
|
||||
.highlight .no { color: #60add5 } /* Name.Constant */
|
||||
.highlight .nd { color: #555555; font-weight: bold } /* Name.Decorator */
|
||||
.highlight .ni { color: #d55537; font-weight: bold } /* Name.Entity */
|
||||
.highlight .ne { color: #007020 } /* Name.Exception */
|
||||
.highlight .nf { color: #06287e } /* Name.Function */
|
||||
.highlight .nl { color: #002070; font-weight: bold } /* Name.Label */
|
||||
.highlight .nn { color: #0e84b5; font-weight: bold } /* Name.Namespace */
|
||||
.highlight .nt { color: #062873; font-weight: bold } /* Name.Tag */
|
||||
.highlight .nv { color: #bb60d5 } /* Name.Variable */
|
||||
.highlight .ow { color: #007020; font-weight: bold } /* Operator.Word */
|
||||
.highlight .kc { color: #008000; font-weight: bold } /* Keyword.Constant */
|
||||
.highlight .kd { color: #008000; font-weight: bold } /* Keyword.Declaration */
|
||||
.highlight .kn { color: #008000; font-weight: bold } /* Keyword.Namespace */
|
||||
.highlight .kp { color: #008000 } /* Keyword.Pseudo */
|
||||
.highlight .kr { color: #008000; font-weight: bold } /* Keyword.Reserved */
|
||||
.highlight .kt { color: #B00040 } /* Keyword.Type */
|
||||
.highlight .m { color: #666666 } /* Literal.Number */
|
||||
.highlight .s { color: #BA2121 } /* Literal.String */
|
||||
.highlight .na { color: #687822 } /* Name.Attribute */
|
||||
.highlight .nb { color: #008000 } /* Name.Builtin */
|
||||
.highlight .nc { color: #0000FF; font-weight: bold } /* Name.Class */
|
||||
.highlight .no { color: #880000 } /* Name.Constant */
|
||||
.highlight .nd { color: #AA22FF } /* Name.Decorator */
|
||||
.highlight .ni { color: #717171; font-weight: bold } /* Name.Entity */
|
||||
.highlight .ne { color: #CB3F38; font-weight: bold } /* Name.Exception */
|
||||
.highlight .nf { color: #0000FF } /* Name.Function */
|
||||
.highlight .nl { color: #767600 } /* Name.Label */
|
||||
.highlight .nn { color: #0000FF; font-weight: bold } /* Name.Namespace */
|
||||
.highlight .nt { color: #008000; font-weight: bold } /* Name.Tag */
|
||||
.highlight .nv { color: #19177C } /* Name.Variable */
|
||||
.highlight .ow { color: #AA22FF; font-weight: bold } /* Operator.Word */
|
||||
.highlight .w { color: #bbbbbb } /* Text.Whitespace */
|
||||
.highlight .mb { color: #208050 } /* Literal.Number.Bin */
|
||||
.highlight .mf { color: #208050 } /* Literal.Number.Float */
|
||||
.highlight .mh { color: #208050 } /* Literal.Number.Hex */
|
||||
.highlight .mi { color: #208050 } /* Literal.Number.Integer */
|
||||
.highlight .mo { color: #208050 } /* Literal.Number.Oct */
|
||||
.highlight .sa { color: #4070a0 } /* Literal.String.Affix */
|
||||
.highlight .sb { color: #4070a0 } /* Literal.String.Backtick */
|
||||
.highlight .sc { color: #4070a0 } /* Literal.String.Char */
|
||||
.highlight .dl { color: #4070a0 } /* Literal.String.Delimiter */
|
||||
.highlight .sd { color: #4070a0; font-style: italic } /* Literal.String.Doc */
|
||||
.highlight .s2 { color: #4070a0 } /* Literal.String.Double */
|
||||
.highlight .se { color: #4070a0; font-weight: bold } /* Literal.String.Escape */
|
||||
.highlight .sh { color: #4070a0 } /* Literal.String.Heredoc */
|
||||
.highlight .si { color: #70a0d0; font-style: italic } /* Literal.String.Interpol */
|
||||
.highlight .sx { color: #c65d09 } /* Literal.String.Other */
|
||||
.highlight .sr { color: #235388 } /* Literal.String.Regex */
|
||||
.highlight .s1 { color: #4070a0 } /* Literal.String.Single */
|
||||
.highlight .ss { color: #517918 } /* Literal.String.Symbol */
|
||||
.highlight .bp { color: #007020 } /* Name.Builtin.Pseudo */
|
||||
.highlight .fm { color: #06287e } /* Name.Function.Magic */
|
||||
.highlight .vc { color: #bb60d5 } /* Name.Variable.Class */
|
||||
.highlight .vg { color: #bb60d5 } /* Name.Variable.Global */
|
||||
.highlight .vi { color: #bb60d5 } /* Name.Variable.Instance */
|
||||
.highlight .vm { color: #bb60d5 } /* Name.Variable.Magic */
|
||||
.highlight .il { color: #208050 } /* Literal.Number.Integer.Long */
|
||||
.highlight .mb { color: #666666 } /* Literal.Number.Bin */
|
||||
.highlight .mf { color: #666666 } /* Literal.Number.Float */
|
||||
.highlight .mh { color: #666666 } /* Literal.Number.Hex */
|
||||
.highlight .mi { color: #666666 } /* Literal.Number.Integer */
|
||||
.highlight .mo { color: #666666 } /* Literal.Number.Oct */
|
||||
.highlight .sa { color: #BA2121 } /* Literal.String.Affix */
|
||||
.highlight .sb { color: #BA2121 } /* Literal.String.Backtick */
|
||||
.highlight .sc { color: #BA2121 } /* Literal.String.Char */
|
||||
.highlight .dl { color: #BA2121 } /* Literal.String.Delimiter */
|
||||
.highlight .sd { color: #BA2121; font-style: italic } /* Literal.String.Doc */
|
||||
.highlight .s2 { color: #BA2121 } /* Literal.String.Double */
|
||||
.highlight .se { color: #AA5D1F; font-weight: bold } /* Literal.String.Escape */
|
||||
.highlight .sh { color: #BA2121 } /* Literal.String.Heredoc */
|
||||
.highlight .si { color: #A45A77; font-weight: bold } /* Literal.String.Interpol */
|
||||
.highlight .sx { color: #008000 } /* Literal.String.Other */
|
||||
.highlight .sr { color: #A45A77 } /* Literal.String.Regex */
|
||||
.highlight .s1 { color: #BA2121 } /* Literal.String.Single */
|
||||
.highlight .ss { color: #19177C } /* Literal.String.Symbol */
|
||||
.highlight .bp { color: #008000 } /* Name.Builtin.Pseudo */
|
||||
.highlight .fm { color: #0000FF } /* Name.Function.Magic */
|
||||
.highlight .vc { color: #19177C } /* Name.Variable.Class */
|
||||
.highlight .vg { color: #19177C } /* Name.Variable.Global */
|
||||
.highlight .vi { color: #19177C } /* Name.Variable.Instance */
|
||||
.highlight .vm { color: #19177C } /* Name.Variable.Magic */
|
||||
.highlight .il { color: #666666 } /* Literal.Number.Integer.Long */
|
||||
@@ -88,7 +88,7 @@ const _displayItem = (item, highlightTerms, searchTerms) => {
|
||||
linkEl.href = linkUrl + "?" + params.toString() + anchor;
|
||||
linkEl.innerHTML = title;
|
||||
if (descr)
|
||||
listItem.appendChild(document.createElement("span")).innerText =
|
||||
listItem.appendChild(document.createElement("span")).innerHTML =
|
||||
" (" + descr + ")";
|
||||
else if (showSearchSummary)
|
||||
fetch(requestUrl)
|
||||
@@ -155,10 +155,8 @@ const Search = {
|
||||
_pulse_status: -1,
|
||||
|
||||
htmlToText: (htmlString) => {
|
||||
const htmlElement = document
|
||||
.createRange()
|
||||
.createContextualFragment(htmlString);
|
||||
_removeChildren(htmlElement.querySelectorAll(".headerlink"));
|
||||
const htmlElement = new DOMParser().parseFromString(htmlString, 'text/html');
|
||||
htmlElement.querySelectorAll(".headerlink").forEach((el) => { el.remove() });
|
||||
const docContent = htmlElement.querySelector('[role="main"]');
|
||||
if (docContent !== undefined) return docContent.textContent;
|
||||
console.warn(
|
||||
@@ -504,11 +502,12 @@ const Search = {
|
||||
* latter for highlighting it.
|
||||
*/
|
||||
makeSearchSummary: (htmlText, keywords, highlightWords) => {
|
||||
const text = Search.htmlToText(htmlText).toLowerCase();
|
||||
const text = Search.htmlToText(htmlText);
|
||||
if (text === "") return null;
|
||||
|
||||
const textLower = text.toLowerCase();
|
||||
const actualStartPosition = [...keywords]
|
||||
.map((k) => text.indexOf(k.toLowerCase()))
|
||||
.map((k) => textLower.indexOf(k.toLowerCase()))
|
||||
.filter((i) => i > -1)
|
||||
.slice(-1)[0];
|
||||
const startWithContext = Math.max(actualStartPosition - 120, 0);
|
||||
@@ -516,9 +515,9 @@ const Search = {
|
||||
const top = startWithContext === 0 ? "" : "...";
|
||||
const tail = startWithContext + 240 < text.length ? "..." : "";
|
||||
|
||||
let summary = document.createElement("div");
|
||||
let summary = document.createElement("p");
|
||||
summary.classList.add("context");
|
||||
summary.innerText = top + text.substr(startWithContext, 240).trim() + tail;
|
||||
summary.textContent = top + text.substr(startWithContext, 240).trim() + tail;
|
||||
|
||||
highlightWords.forEach((highlightWord) =>
|
||||
_highlightText(summary, highlightWord, "highlighted")
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Index — parsedmarc 8.3.0 documentation</title>
|
||||
<title>Index — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="_static/css/theme.css" type="text/css" />
|
||||
<!--[if lt IE 9]>
|
||||
@@ -28,7 +28,7 @@
|
||||
<a href="index.html" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
8.3.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="search.html" method="get">
|
||||
|
||||
516
index.html
516
index.html
@@ -4,7 +4,7 @@
|
||||
<meta charset="utf-8" /><meta name="generator" content="Docutils 0.17.1: http://docutils.sourceforge.net/" />
|
||||
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>parsedmarc documentation - Open source DMARC report analyzer and visualizer — parsedmarc 8.3.0 documentation</title>
|
||||
<title>parsedmarc documentation - Open source DMARC report analyzer and visualizer — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="_static/css/theme.css" type="text/css" />
|
||||
<!--[if lt IE 9]>
|
||||
@@ -29,7 +29,7 @@
|
||||
<a href="#" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
8.3.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="search.html" method="get">
|
||||
@@ -87,9 +87,11 @@
|
||||
</ul>
|
||||
</li>
|
||||
<li><a class="reference internal" href="#dmarc-alignment-guide">DMARC Alignment Guide</a></li>
|
||||
<li><a class="reference internal" href="#what-if-a-sender-won-t-support-dkim-dmarc">What if a sender won’t support DKIM/DMARC?</a></li>
|
||||
<li><a class="reference internal" href="#what-if-a-sender-wont-support-dkim-dmarc">What if a sender won’t support DKIM/DMARC?</a></li>
|
||||
<li><a class="reference internal" href="#what-about-mailing-lists">What about mailing lists?</a><ul>
|
||||
<li><a class="reference internal" href="#mailing-list-list-best-practices">Mailing list list best practices</a><ul>
|
||||
<li><a class="reference internal" href="#do">Do</a></li>
|
||||
<li><a class="reference internal" href="#do-not">Do not</a></li>
|
||||
<li><a class="reference internal" href="#mailman-2">Mailman 2</a></li>
|
||||
<li><a class="reference internal" href="#mailman-3">Mailman 3</a></li>
|
||||
</ul>
|
||||
@@ -129,7 +131,7 @@
|
||||
<li><a href="#" class="icon icon-home"></a> »</li>
|
||||
<li>parsedmarc documentation - Open source DMARC report analyzer and visualizer</li>
|
||||
<li class="wy-breadcrumbs-aside">
|
||||
<a href="_sources/index.rst.txt" rel="nofollow"> View page source</a>
|
||||
<a href="_sources/index.md.txt" rel="nofollow"> View page source</a>
|
||||
</li>
|
||||
</ul>
|
||||
<hr/>
|
||||
@@ -137,9 +139,11 @@
|
||||
<div role="main" class="document" itemscope="itemscope" itemtype="http://schema.org/Article">
|
||||
<div itemprop="articleBody">
|
||||
|
||||
<section id="parsedmarc-documentation-open-source-dmarc-report-analyzer-and-visualizer">
|
||||
<section class="tex2jax_ignore mathjax_ignore" id="parsedmarc-documentation-open-source-dmarc-report-analyzer-and-visualizer">
|
||||
<h1>parsedmarc documentation - Open source DMARC report analyzer and visualizer<a class="headerlink" href="#parsedmarc-documentation-open-source-dmarc-report-analyzer-and-visualizer" title="Permalink to this heading"></a></h1>
|
||||
<p><a class="reference external" href="https://github.com/domainaware/parsedmarc/actions/workflows/python-tests.yml"><img alt="Build Status" src="https://github.com/domainaware/parsedmarc/actions/workflows/python-tests.yml/badge.svg" /></a> <a class="reference external" href="https://codecov.io/gh/domainaware/parsedmarc"><img alt="Code Coverage" src="https://codecov.io/gh/domainaware/parsedmarc/branch/master/graph/badge.svg" /></a> <a class="reference external" href="https://pypi.org/project/parsedmarc/"><img alt="PyPI Package" src="https://img.shields.io/pypi/v/parsedmarc.svg" /></a></p>
|
||||
<p><a class="reference external" href="https://github.com/domainaware/parsedmarc/actions/workflows/python-tests.yml"><img alt="BuildStatus" src="https://github.com/domainaware/parsedmarc/actions/workflows/python-tests.yml/badge.svg" /></a>
|
||||
<a class="reference external" href="https://codecov.io/gh/domainaware/parsedmarc"><img alt="CodeCoverage" src="https://codecov.io/gh/domainaware/parsedmarc/branch/master/graph/badge.svg" /></a>
|
||||
<a class="reference external" href="https://pypi.org/project/parsedmarc/"><img alt="PyPIPackage" src="https://img.shields.io/pypi/v/parsedmarc.svg" /></a></p>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p><strong>Help Wanted</strong></p>
|
||||
@@ -191,53 +195,54 @@ lookalike domain monitoring, check out <a class="reference external" href="https
|
||||
</section>
|
||||
<section id="cli-help">
|
||||
<h2>CLI help<a class="headerlink" href="#cli-help" title="Permalink to this heading"></a></h2>
|
||||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">usage</span><span class="p">:</span> <span class="n">parsedmarc</span> <span class="p">[</span><span class="o">-</span><span class="n">h</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">c</span> <span class="n">CONFIG_FILE</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">strip</span><span class="o">-</span><span class="n">attachment</span><span class="o">-</span><span class="n">payloads</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">o</span> <span class="n">OUTPUT</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="o">--</span><span class="n">aggregate</span><span class="o">-</span><span class="n">json</span><span class="o">-</span><span class="n">filename</span> <span class="n">AGGREGATE_JSON_FILENAME</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="o">--</span><span class="n">forensic</span><span class="o">-</span><span class="n">json</span><span class="o">-</span><span class="n">filename</span> <span class="n">FORENSIC_JSON_FILENAME</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="o">--</span><span class="n">aggregate</span><span class="o">-</span><span class="n">csv</span><span class="o">-</span><span class="n">filename</span> <span class="n">AGGREGATE_CSV_FILENAME</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="o">--</span><span class="n">forensic</span><span class="o">-</span><span class="n">csv</span><span class="o">-</span><span class="n">filename</span> <span class="n">FORENSIC_CSV_FILENAME</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="o">-</span><span class="n">n</span> <span class="n">NAMESERVERS</span> <span class="p">[</span><span class="n">NAMESERVERS</span> <span class="o">...</span><span class="p">]]</span> <span class="p">[</span><span class="o">-</span><span class="n">t</span> <span class="n">DNS_TIMEOUT</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">offline</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="o">-</span><span class="n">s</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">verbose</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">debug</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">log</span><span class="o">-</span><span class="n">file</span> <span class="n">LOG_FILE</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">v</span><span class="p">]</span>
|
||||
<span class="p">[</span><span class="n">file_path</span> <span class="o">...</span><span class="p">]</span>
|
||||
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: parsedmarc [-h] [-c CONFIG_FILE] [--strip-attachment-payloads] [-o OUTPUT]
|
||||
[--aggregate-json-filename AGGREGATE_JSON_FILENAME]
|
||||
[--forensic-json-filename FORENSIC_JSON_FILENAME]
|
||||
[--aggregate-csv-filename AGGREGATE_CSV_FILENAME]
|
||||
[--forensic-csv-filename FORENSIC_CSV_FILENAME]
|
||||
[-n NAMESERVERS [NAMESERVERS ...]] [-t DNS_TIMEOUT] [--offline]
|
||||
[-s] [--verbose] [--debug] [--log-file LOG_FILE] [-v]
|
||||
[file_path ...]
|
||||
|
||||
<span class="n">Parses</span> <span class="n">DMARC</span> <span class="n">reports</span>
|
||||
Parses DMARC reports
|
||||
|
||||
<span class="n">positional</span> <span class="n">arguments</span><span class="p">:</span>
|
||||
<span class="n">file_path</span> <span class="n">one</span> <span class="ow">or</span> <span class="n">more</span> <span class="n">paths</span> <span class="n">to</span> <span class="n">aggregate</span> <span class="ow">or</span> <span class="n">forensic</span> <span class="n">report</span>
|
||||
<span class="n">files</span><span class="p">,</span> <span class="n">emails</span><span class="p">,</span> <span class="ow">or</span> <span class="n">mbox</span> <span class="n">files</span><span class="s1">'</span>
|
||||
positional arguments:
|
||||
file_path one or more paths to aggregate or forensic report
|
||||
files, emails, or mbox files'
|
||||
|
||||
<span class="n">optional</span> <span class="n">arguments</span><span class="p">:</span>
|
||||
<span class="o">-</span><span class="n">h</span><span class="p">,</span> <span class="o">--</span><span class="n">help</span> <span class="n">show</span> <span class="n">this</span> <span class="n">help</span> <span class="n">message</span> <span class="ow">and</span> <span class="n">exit</span>
|
||||
<span class="o">-</span><span class="n">c</span> <span class="n">CONFIG_FILE</span><span class="p">,</span> <span class="o">--</span><span class="n">config</span><span class="o">-</span><span class="n">file</span> <span class="n">CONFIG_FILE</span>
|
||||
<span class="n">a</span> <span class="n">path</span> <span class="n">to</span> <span class="n">a</span> <span class="n">configuration</span> <span class="n">file</span> <span class="p">(</span><span class="o">--</span><span class="n">silent</span> <span class="n">implied</span><span class="p">)</span>
|
||||
<span class="o">--</span><span class="n">strip</span><span class="o">-</span><span class="n">attachment</span><span class="o">-</span><span class="n">payloads</span>
|
||||
<span class="n">remove</span> <span class="n">attachment</span> <span class="n">payloads</span> <span class="kn">from</span> <span class="nn">forensic</span> <span class="n">report</span> <span class="n">output</span>
|
||||
<span class="o">-</span><span class="n">o</span> <span class="n">OUTPUT</span><span class="p">,</span> <span class="o">--</span><span class="n">output</span> <span class="n">OUTPUT</span>
|
||||
<span class="n">write</span> <span class="n">output</span> <span class="n">files</span> <span class="n">to</span> <span class="n">the</span> <span class="n">given</span> <span class="n">directory</span>
|
||||
<span class="o">--</span><span class="n">aggregate</span><span class="o">-</span><span class="n">json</span><span class="o">-</span><span class="n">filename</span> <span class="n">AGGREGATE_JSON_FILENAME</span>
|
||||
<span class="n">filename</span> <span class="k">for</span> <span class="n">the</span> <span class="n">aggregate</span> <span class="n">JSON</span> <span class="n">output</span> <span class="n">file</span>
|
||||
<span class="o">--</span><span class="n">forensic</span><span class="o">-</span><span class="n">json</span><span class="o">-</span><span class="n">filename</span> <span class="n">FORENSIC_JSON_FILENAME</span>
|
||||
<span class="n">filename</span> <span class="k">for</span> <span class="n">the</span> <span class="n">forensic</span> <span class="n">JSON</span> <span class="n">output</span> <span class="n">file</span>
|
||||
<span class="o">--</span><span class="n">aggregate</span><span class="o">-</span><span class="n">csv</span><span class="o">-</span><span class="n">filename</span> <span class="n">AGGREGATE_CSV_FILENAME</span>
|
||||
<span class="n">filename</span> <span class="k">for</span> <span class="n">the</span> <span class="n">aggregate</span> <span class="n">CSV</span> <span class="n">output</span> <span class="n">file</span>
|
||||
<span class="o">--</span><span class="n">forensic</span><span class="o">-</span><span class="n">csv</span><span class="o">-</span><span class="n">filename</span> <span class="n">FORENSIC_CSV_FILENAME</span>
|
||||
<span class="n">filename</span> <span class="k">for</span> <span class="n">the</span> <span class="n">forensic</span> <span class="n">CSV</span> <span class="n">output</span> <span class="n">file</span>
|
||||
<span class="o">-</span><span class="n">n</span> <span class="n">NAMESERVERS</span> <span class="p">[</span><span class="n">NAMESERVERS</span> <span class="o">...</span><span class="p">],</span> <span class="o">--</span><span class="n">nameservers</span> <span class="n">NAMESERVERS</span> <span class="p">[</span><span class="n">NAMESERVERS</span> <span class="o">...</span><span class="p">]</span>
|
||||
<span class="n">nameservers</span> <span class="n">to</span> <span class="n">query</span>
|
||||
<span class="o">-</span><span class="n">t</span> <span class="n">DNS_TIMEOUT</span><span class="p">,</span> <span class="o">--</span><span class="n">dns_timeout</span> <span class="n">DNS_TIMEOUT</span>
|
||||
<span class="n">number</span> <span class="n">of</span> <span class="n">seconds</span> <span class="n">to</span> <span class="n">wait</span> <span class="k">for</span> <span class="n">an</span> <span class="n">answer</span> <span class="kn">from</span> <span class="nn">DNS</span>
|
||||
<span class="p">(</span><span class="n">default</span><span class="p">:</span> <span class="mf">2.0</span><span class="p">)</span>
|
||||
<span class="o">--</span><span class="n">offline</span> <span class="n">do</span> <span class="ow">not</span> <span class="n">make</span> <span class="n">online</span> <span class="n">queries</span> <span class="k">for</span> <span class="n">geolocation</span> <span class="ow">or</span> <span class="n">DNS</span>
|
||||
<span class="o">-</span><span class="n">s</span><span class="p">,</span> <span class="o">--</span><span class="n">silent</span> <span class="n">only</span> <span class="nb">print</span> <span class="n">errors</span> <span class="ow">and</span> <span class="n">warnings</span>
|
||||
<span class="o">--</span><span class="n">verbose</span> <span class="n">more</span> <span class="n">verbose</span> <span class="n">output</span>
|
||||
<span class="o">--</span><span class="n">debug</span> <span class="nb">print</span> <span class="n">debugging</span> <span class="n">information</span>
|
||||
<span class="o">--</span><span class="n">log</span><span class="o">-</span><span class="n">file</span> <span class="n">LOG_FILE</span> <span class="n">output</span> <span class="n">logging</span> <span class="n">to</span> <span class="n">a</span> <span class="n">file</span>
|
||||
<span class="o">-</span><span class="n">v</span><span class="p">,</span> <span class="o">--</span><span class="n">version</span> <span class="n">show</span> <span class="n">program</span><span class="s1">'s version number and exit</span>
|
||||
optional arguments:
|
||||
-h, --help show this help message and exit
|
||||
-c CONFIG_FILE, --config-file CONFIG_FILE
|
||||
a path to a configuration file (--silent implied)
|
||||
--strip-attachment-payloads
|
||||
remove attachment payloads from forensic report output
|
||||
-o OUTPUT, --output OUTPUT
|
||||
write output files to the given directory
|
||||
--aggregate-json-filename AGGREGATE_JSON_FILENAME
|
||||
filename for the aggregate JSON output file
|
||||
--forensic-json-filename FORENSIC_JSON_FILENAME
|
||||
filename for the forensic JSON output file
|
||||
--aggregate-csv-filename AGGREGATE_CSV_FILENAME
|
||||
filename for the aggregate CSV output file
|
||||
--forensic-csv-filename FORENSIC_CSV_FILENAME
|
||||
filename for the forensic CSV output file
|
||||
-n NAMESERVERS [NAMESERVERS ...], --nameservers NAMESERVERS [NAMESERVERS ...]
|
||||
nameservers to query
|
||||
-t DNS_TIMEOUT, --dns_timeout DNS_TIMEOUT
|
||||
number of seconds to wait for an answer from DNS
|
||||
(default: 2.0)
|
||||
--offline do not make online queries for geolocation or DNS
|
||||
-s, --silent only print errors and warnings
|
||||
--verbose more verbose output
|
||||
--debug print debugging information
|
||||
--log-file LOG_FILE output logging to a file
|
||||
-v, --version show program's version number and exit
|
||||
</pre></div>
|
||||
</div>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p>Starting in <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> 6.0.0, most CLI options were moved to a configuration file, described below.</p>
|
||||
<p>Starting in <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> 6.0.0, most CLI options were moved to a
|
||||
configuration file, described below.</p>
|
||||
</div>
|
||||
</section>
|
||||
<section id="configuration-file">
|
||||
@@ -282,103 +287,160 @@ lookalike domain monitoring, check out <a class="reference external" href="https
|
||||
</div>
|
||||
<p>The full set of configuration options are:</p>
|
||||
<ul>
|
||||
<li><dl>
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">general</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">save_aggregate</span></code> - bool: Save aggregate report data to Elasticsearch, Splunk and/or S3</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">save_forensic</span></code> - bool: Save forensic report data to Elasticsearch, Splunk and/or S3</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">strip_attachment_payloads</span></code> - bool: Remove attachment payloads from results</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">save_aggregate</span></code> - bool: Save aggregate report data to
|
||||
Elasticsearch, Splunk and/or S3</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">save_forensic</span></code> - bool: Save forensic report data to
|
||||
Elasticsearch, Splunk and/or S3</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">strip_attachment_payloads</span></code> - bool: Remove attachment
|
||||
payloads from results</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">output</span></code> - str: Directory to place JSON and CSV files in</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">aggregate_json_filename</span></code> - str: filename for the aggregate JSON output file</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">forensic_json_filename</span></code> - str: filename for the forensic JSON output file</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">ip_db_path</span></code> - str: An optional custom path to a MMDB file from MaxMind or DBIP</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">offline</span></code> - bool: Do not use online queries for geolocation or DNS</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">nameservers</span></code> - str: A comma separated list of DNS resolvers (Default: <a class="reference external" href="https://1.1.1.1/">Cloudflare’s public resolvers</a>)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">aggregate_json_filename</span></code> - str: filename for the aggregate
|
||||
JSON output file</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">forensic_json_filename</span></code> - str: filename for the forensic
|
||||
JSON output file</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">ip_db_path</span></code> - str: An optional custom path to a MMDB file</p></li>
|
||||
<li><p>from MaxMind or DBIP</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">offline</span></code> - bool: Do not use online queries for geolocation
|
||||
or DNS</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">nameservers</span></code> - str: A comma separated list of
|
||||
DNS resolvers (Default: <a class="reference external" href="https://1.1.1.1/">Cloudflare’s public resolvers</a>)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">dns_timeout</span></code> - float: DNS timeout period</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">debug</span></code> - bool: Print debugging messages</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">silent</span></code> - bool: Only print errors (Default: True)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">log_file</span></code> - str: Write log messages to a file at this path</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">n_procs</span></code> - int: Number of process to run in parallel when parsing in CLI mode (Default: 1)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">chunk_size</span></code> - int: Number of files to give to each process when running in parallel.</p></li>
|
||||
</ul>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">n_procs</span></code> - int: Number of process to run in parallel when
|
||||
parsing in CLI mode (Default: 1)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">chunk_size</span></code> - int: Number of files to give to each process
|
||||
when running in parallel.</p>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p>Setting this to a number larger than one can improve performance when processing thousands of files</p>
|
||||
<p>Setting this to a number larger than one can improve
|
||||
performance when processing thousands of files</p>
|
||||
</div>
|
||||
</dd>
|
||||
</dl>
|
||||
</li>
|
||||
<li><dl class="simple">
|
||||
</ul>
|
||||
</li>
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">mailbox</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">reports_folder</span></code> - str: The mailbox folder (or label for Gmail) where the incoming reports can be found (Default: INBOX)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">archive_folder</span></code> - str: The mailbox folder (or label for Gmail) to sort processed emails into (Default: Archive)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">watch</span></code> - bool: Use the IMAP <code class="docutils literal notranslate"><span class="pre">IDLE</span></code> command to process messages as they arrive or poll MS Graph for new messages</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">delete</span></code> - bool: Delete messages after processing them, instead of archiving them</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">test</span></code> - bool: Do not move or delete messages</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">batch_size</span></code> - int: Number of messages to read and process before saving. Default 10. Use 0 for no limit.</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">reports_folder</span></code> - str: The mailbox folder (or label for
|
||||
Gmail) where the incoming reports can be found (Default: INBOX)</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">archive_folder</span></code> - str: The mailbox folder (or label for
|
||||
Gmail) to sort processed emails into (Default: Archive)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">watch</span></code> - bool: Use the IMAP <code class="docutils literal notranslate"><span class="pre">IDLE</span></code> command to process</p></li>
|
||||
<li><p>messages as they arrive or poll MS Graph for new messages</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">delete</span></code> - bool: Delete messages after processing them,</p></li>
|
||||
<li><p>instead of archiving them</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">test</span></code> - bool: Do not move or delete messages</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">batch_size</span></code> - int: Number of messages to read and process
|
||||
before saving. Default 10. Use 0 for no limit.</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">check_timeout</span></code> - int: Number of seconds to wait for a IMAP
|
||||
IDLE response or the number of seconds until the next mai
|
||||
check (Default: 30)</p></li>
|
||||
</ul>
|
||||
</li>
|
||||
<li><dl>
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">imap</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">host</span></code> - str: The IMAP server hostname or IP address</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">port</span></code> - int: The IMAP server port (Default: 993)</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">port</span></code> - int: The IMAP server port (Default: 993)</p>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p><code class="docutils literal notranslate"><span class="pre">%</span></code> characters must be escaped with another <code class="docutils literal notranslate"><span class="pre">%</span></code> character, so use <code class="docutils literal notranslate"><span class="pre">%%</span></code> wherever a <code class="docutils literal notranslate"><span class="pre">%</span></code> character is used.</p>
|
||||
<p><code class="docutils literal notranslate"><span class="pre">%</span></code> characters must be escaped with another <code class="docutils literal notranslate"><span class="pre">%</span></code> character,
|
||||
so use <code class="docutils literal notranslate"><span class="pre">%%</span></code> wherever a <code class="docutils literal notranslate"><span class="pre">%</span></code> character is used.</p>
|
||||
</div>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p>Starting in version 8.0.0, most options from the <code class="docutils literal notranslate"><span class="pre">imap</span></code> section have been moved to the <code class="docutils literal notranslate"><span class="pre">mailbox</span></code> section.</p>
|
||||
<p>Starting in version 8.0.0, most options from the <code class="docutils literal notranslate"><span class="pre">imap</span></code>
|
||||
section have been moved to the <code class="docutils literal notranslate"><span class="pre">mailbox</span></code> section.</p>
|
||||
</div>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p>If your host recommends another port, still try 993</p>
|
||||
</div>
|
||||
<ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">ssl</span></code> - bool: Use an encrypted SSL/TLS connection (Default: True)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">skip_certificate_verification</span></code> - bool: Skip certificate verification (not recommended)</p></li>
|
||||
</li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">ssl</span></code> - bool: Use an encrypted SSL/TLS connection
|
||||
(Default: True)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">skip_certificate_verification</span></code> - bool: Skip certificate
|
||||
verification (not recommended)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">user</span></code> - str: The IMAP user</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">password</span></code> - str: The IMAP password</p></li>
|
||||
</ul>
|
||||
</li>
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">msgraph</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">auth_method</span></code> - str: Authentication method, valid types are
|
||||
UsernamePassword, DeviceCode, or ClientSecret
|
||||
(Default: UsernamePassword).</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
</li>
|
||||
<li><dl>
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">msgraph</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">auth_method</span></code> - str: Authentication method, valid types are UsernamePassword, DeviceCode, or ClientSecret (Default: UsernamePassword).</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">user</span></code> - str: The M365 user, required when the auth method is UsernamePassword</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">password</span></code> - str: The user password, required when the auth method is UsernamePassword</p></li>
|
||||
<ul>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">user</span></code> - str: The M365 user, required when the auth method is
|
||||
UsernamePassword</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">password</span></code> - str: The user password, required when the auth
|
||||
method is UsernamePassword</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">client_id</span></code> - str: The app registration’s client ID</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">client_secret</span></code> - str: The app registration’s secret</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">tenant_id</span></code> - str: The Azure AD tenant ID. This is required for all auth methods except UsernamePassword.</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">mailbox</span></code> - str: The mailbox name. This defaults to the current user if using the UsernamePassword auth method, but could be a shared mailbox if the user has access to the mailbox</p></li>
|
||||
</ul>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">tenant_id</span></code> - str: The Azure AD tenant ID. This is required
|
||||
for all auth methods except UsernamePassword.</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">mailbox</span></code> - str: The mailbox name. This defaults to the
|
||||
current user if using the UsernamePassword auth method, but
|
||||
could be a shared mailbox if the user has access to the mailbox</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">token_file</span></code> - str: Path to save the token file
|
||||
(Default: .token)</p>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p>You must create an app registration in Azure AD and have an admin grant the Microsoft Graph <code class="docutils literal notranslate"><span class="pre">Mail.ReadWrite</span></code> (delegated) permission to the app.
|
||||
If you are using <cite>UsernamePassword</cite> auth and the mailbox is different from the username, you must grant the app <code class="docutils literal notranslate"><span class="pre">Mail.ReadWrite.Shared</span></code>.</p>
|
||||
<p>You must create an app registration in Azure AD and have an
|
||||
admin grant the Microsoft Graph <code class="docutils literal notranslate"><span class="pre">Mail.ReadWrite</span></code>
|
||||
(delegated) permission to the app. If you are using
|
||||
<code class="docutils literal notranslate"><span class="pre">UsernamePassword</span></code> auth and the mailbox is different from the
|
||||
username, you must grant the app <code class="docutils literal notranslate"><span class="pre">Mail.ReadWrite.Shared</span></code>.</p>
|
||||
</div>
|
||||
<div class="admonition warning">
|
||||
<p class="admonition-title">Warning</p>
|
||||
<p>If you are using the <cite>ClientSecret</cite> auth method, you need to grant the <code class="docutils literal notranslate"><span class="pre">Mail.ReadWrite</span></code> (application) permission to the app.
|
||||
You must also restrict the application’s access to a specific mailbox since it allows all mailboxes by default.
|
||||
Use the <code class="docutils literal notranslate"><span class="pre">New-ApplicationAccessPolicy</span></code> command in the Exchange PowerShell module.
|
||||
If you need to scope the policy to shared mailboxes, you can add them to a mail enabled security group and use that as the group id.</p>
|
||||
<p><code class="docutils literal notranslate"><span class="pre">New-ApplicationAccessPolicy</span> <span class="pre">-AccessRight</span> <span class="pre">RestrictAccess</span> <span class="pre">-AppId</span> <span class="pre">"<CLIENT_ID>"</span> <span class="pre">-PolicyScopeGroupId</span> <span class="pre">"<MAILBOX>"</span> <span class="pre">-Description</span> <span class="pre">"Restrict</span> <span class="pre">access</span> <span class="pre">to</span> <span class="pre">dmarc</span> <span class="pre">reports</span> <span class="pre">mailbox."</span></code></p>
|
||||
<p>If you are using the <code class="docutils literal notranslate"><span class="pre">ClientSecret</span></code> auth method, you need to
|
||||
grant the <code class="docutils literal notranslate"><span class="pre">Mail.ReadWrite</span></code> (application) permission to the
|
||||
app. You must also restrict the application’s access to a
|
||||
specific mailbox since it allows all mailboxes by default.
|
||||
Use the <code class="docutils literal notranslate"><span class="pre">New-ApplicationAccessPolicy</span></code> command in the
|
||||
Exchange PowerShell module. If you need to scope the policy to
|
||||
shared mailboxes, you can add them to a mail enabled security
|
||||
group and use that as the group id.</p>
|
||||
<div class="highlight-powershell notranslate"><div class="highlight"><pre><span></span><span class="nb">New-ApplicationAccessPolicy</span> <span class="n">-AccessRight</span> <span class="n">RestrictAccess</span>
|
||||
<span class="n">-AppId</span> <span class="s2">"<CLIENT_ID>"</span> <span class="n">-PolicyScopeGroupId</span> <span class="s2">"<MAILBOX>"</span>
|
||||
<span class="n">-Description</span> <span class="s2">"Restrict access to dmarc reports mailbox."</span>
|
||||
</pre></div>
|
||||
</div>
|
||||
</div>
|
||||
</dd>
|
||||
</dl>
|
||||
</li>
|
||||
<li><dl>
|
||||
</ul>
|
||||
</li>
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">elasticsearch</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">hosts</span></code> - str: A comma separated list of hostnames and ports or URLs (e.g. <code class="docutils literal notranslate"><span class="pre">127.0.0.1:9200</span></code> or <code class="docutils literal notranslate"><span class="pre">https://user:secret@localhost</span></code>)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">hosts</span></code> - str: A comma separated list of hostnames and ports
|
||||
or URLs (e.g. <code class="docutils literal notranslate"><span class="pre">127.0.0.1:9200</span></code> or
|
||||
<code class="docutils literal notranslate"><span class="pre">https://user:secret@localhost</span></code>)</p></li>
|
||||
</ul>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p>Special characters in the username or password must be <a class="reference external" href="https://en.wikipedia.org/wiki/Percent-encoding#Percent-encoding_reserved_characters">URL encoded</a>.</p>
|
||||
<p>Special characters in the username or password must be
|
||||
<a class="reference external" href="https://en.wikipedia.org/wiki/Percent-encoding#Percent-encoding_reserved_characters">URL encoded</a>.</p>
|
||||
</div>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">ssl</span></code> - bool: Use an encrypted SSL/TLS connection (Default: True)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">cert_path</span></code> - str: Path to a trusted certificates</p></li>
|
||||
@@ -387,123 +449,148 @@ If you need to scope the policy to shared mailboxes, you can add them to a mail
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">number_of_shards</span></code> - int: The number of shards to use when creating the index (Default: 1)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">number_of_replicas</span></code> - int: The number of replicas to use when creating the index (Default: 1)</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
</li>
|
||||
<li><dl class="simple">
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">splunk_hec</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">url</span></code> - str: The URL of the Splunk HTTP Events Collector (HEC)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">token</span></code> - str: The HEC token</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">index</span></code> - str: The Splunk index to use</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">skip_certificate_verification</span></code> - bool: Skip certificate verification (not recommended)</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">token</span></code> - str: The HEC token</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">index</span></code> - str: The Splunk index to use</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">skip_certificate_verification</span></code> - bool: Skip certificate
|
||||
verification (not recommended)</p></li>
|
||||
</ul>
|
||||
</li>
|
||||
<li><dl class="simple">
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">kafka</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">hosts</span></code> - str: A comma separated list of Kafka hosts</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">user</span></code> - str: The Kafka user</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">passsword</span></code> - str: The Kafka password</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">ssl</span></code> - bool: Use an encrypted SSL/TLS connection (Default: True)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">skip_certificate_verification</span></code> - bool: Skip certificate verification (not recommended)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">skip_certificate_verification</span></code> - bool: Skip certificate
|
||||
verification (not recommended)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">aggregate_topic</span></code> - str: The Kafka topic for aggregate reports</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">forensic_topic</span></code> - str: The Kafka topic for forensic reports</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
</li>
|
||||
<li><dl>
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">smtp</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">host</span></code> - str: The SMTP hostname</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">port</span></code> - int: The SMTP port (Default: 25)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">ssl</span></code> - bool: Require SSL/TLS instead of using STARTTLS</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">skip_certificate_verification</span></code> - bool: Skip certificate verification (not recommended)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">skip_certificate_verification</span></code> - bool: Skip certificate
|
||||
verification (not recommended)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">user</span></code> - str: the SMTP username</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">password</span></code> - str: the SMTP password</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">from</span></code> - str: The From header to use in the email</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">to</span></code> - list: A list of email addresses to send to</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">subject</span></code> - str: The Subject header to use in the email (Default: parsedmarc report)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">subject</span></code> - str: The Subject header to use in the email
|
||||
(Default: parsedmarc report)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">attachment</span></code> - str: The ZIP attachment filenames</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">message</span></code> - str: The email message (Default: Please see the attached parsedmarc report.)</p></li>
|
||||
</ul>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">message</span></code> - str: The email message
|
||||
(Default: Please see the attached parsedmarc report.)</p>
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p><code class="docutils literal notranslate"><span class="pre">%</span></code> characters must be escaped with another <code class="docutils literal notranslate"><span class="pre">%</span></code> character, so use <code class="docutils literal notranslate"><span class="pre">%%</span></code> wherever a <code class="docutils literal notranslate"><span class="pre">%</span></code> character is used.</p>
|
||||
<p><code class="docutils literal notranslate"><span class="pre">%</span></code> characters must be escaped with another <code class="docutils literal notranslate"><span class="pre">%</span></code> character,
|
||||
so use <code class="docutils literal notranslate"><span class="pre">%%</span></code> wherever a <code class="docutils literal notranslate"><span class="pre">%</span></code> character is used.</p>
|
||||
</div>
|
||||
</dd>
|
||||
</dl>
|
||||
</li>
|
||||
<li><dl class="simple">
|
||||
</ul>
|
||||
</li>
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">s3</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">bucket</span></code> - str: The S3 bucket name</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">path</span></code> - str: The path to upload reports to (Default: /)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">region_name</span></code> - str: The region name (Optional)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">endpoint_url</span></code> - str: The endpoint URL (Optional)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">access_key_id</span></code> - str: The access key id (Optional)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">secret_access_key</span></code> - str: The secret access key (Optional)</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
</li>
|
||||
<li><dl class="simple">
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">syslog</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">server</span></code> - str: The Syslog server name or IP address</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">port</span></code> - int: The UDP port to use (Default: 514)</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
</li>
|
||||
<li><dl class="simple">
|
||||
<li><dl class="simple myst">
|
||||
<dt><code class="docutils literal notranslate"><span class="pre">gmail_api</span></code></dt><dd><ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">gmail_api_credentials_file</span></code> - str: Path to file containing the credentials, None to disable (Default: None)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">gmail_api_token_file</span></code> - str: Path to save the token file (Default: .token)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">gmail_api_include_spam_trash</span></code> - bool: Include messages in Spam and Trash when searching reports (Default: False)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">gmail_api_scopes</span></code> - str: Comma separated list of scopes to use when acquiring credentials (Default: <a class="reference external" href="https://www.googleapis.com/auth/gmail.modify">https://www.googleapis.com/auth/gmail.modify</a>)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">credentials_file</span></code> - str: Path to file containing the
|
||||
credentials, None to disable (Default: None)</p></li>
|
||||
</ul>
|
||||
</dd>
|
||||
</dl>
|
||||
<ul class="simple">
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">token_file</span></code> - str: Path to save the token file
|
||||
(Default: .token)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">include_spam_trash</span></code> - bool: Include messages in Spam and
|
||||
Trash when searching reports (Default: False)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">scopes</span></code> - str: Comma separated list of scopes to use when
|
||||
acquiring credentials (Default: <a class="reference external" href="https://www.googleapis.com/auth/gmail.modify">https://www.googleapis.com/auth/gmail.modify</a>)</p></li>
|
||||
<li><p><code class="docutils literal notranslate"><span class="pre">oauth2_port</span></code> - int: The TCP port for the local server to
|
||||
listen on for the OAuth2 response (Default: 8080)</p></li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
<div class="admonition warning">
|
||||
<p class="admonition-title">Warning</p>
|
||||
<p>It is <strong>strongly recommended</strong> to <strong>not</strong> use the <code class="docutils literal notranslate"><span class="pre">nameservers</span></code> setting.
|
||||
By default, <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> uses <a class="reference external" href="https://1.1.1.1/">Cloudflare’s public resolvers</a>,
|
||||
which are much faster and more reliable than Google, Cisco OpenDNS, or
|
||||
even most local resolvers.</p>
|
||||
<p>The <code class="docutils literal notranslate"><span class="pre">nameservers</span></code> option should only be used if your network blocks DNS
|
||||
requests to outside resolvers.</p>
|
||||
<p>It is <strong>strongly recommended</strong> to <strong>not</strong> use the <code class="docutils literal notranslate"><span class="pre">nameservers</span></code>
|
||||
setting. By default, <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> uses
|
||||
<a class="reference external" href="https://1.1.1.1/">Cloudflare’s public resolvers</a>, which are much faster and more
|
||||
reliable than Google, Cisco OpenDNS, or even most local resolvers.</p>
|
||||
<p>The <code class="docutils literal notranslate"><span class="pre">nameservers</span></code> option should only be used if your network
|
||||
blocks DNS requests to outside resolvers.</p>
|
||||
</div>
|
||||
<div class="admonition warning">
|
||||
<p class="admonition-title">Warning</p>
|
||||
<p><code class="docutils literal notranslate"><span class="pre">save_aggregate</span></code> and <code class="docutils literal notranslate"><span class="pre">save_forensic</span></code> are separate options because
|
||||
you may not want to save forensic reports (also known as failure reports)
|
||||
to your Elasticsearch instance, particularly if you are in a
|
||||
highly-regulated industry that handles sensitive data, such as healthcare
|
||||
or finance. If your legitimate outgoing email fails DMARC, it is possible
|
||||
<p><code class="docutils literal notranslate"><span class="pre">save_aggregate</span></code> and <code class="docutils literal notranslate"><span class="pre">save_forensic</span></code> are separate options
|
||||
because you may not want to save forensic reports
|
||||
(also known as failure reports) to your Elasticsearch instance,
|
||||
particularly if you are in a highly-regulated industry that
|
||||
handles sensitive data, such as healthcare or finance. If your
|
||||
legitimate outgoing email fails DMARC, it is possible
|
||||
that email may appear later in a forensic report.</p>
|
||||
<p>Forensic reports contain the original headers of an email that failed a
|
||||
DMARC check, and sometimes may also include the full message body,
|
||||
depending on the policy of the reporting organization.</p>
|
||||
<p>Most reporting organizations do not send forensic reports of any kind for
|
||||
privacy reasons. While aggregate DMARC reports are sent at least daily,
|
||||
it is normal to receive very few forensic reports.</p>
|
||||
<p>An alternative approach is to still collect forensic/failure/ruf reports
|
||||
in your DMARC inbox, but run <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> with <code class="docutils literal notranslate"><span class="pre">save_forensic</span> <span class="pre">=</span> <span class="pre">True</span></code>
|
||||
manually on a separate IMAP folder (using the <code class="docutils literal notranslate"><span class="pre">reports_folder</span></code> option),
|
||||
after you have manually moved known samples you want to save to that
|
||||
folder (e.g. malicious samples and non-sensitive legitimate samples).</p>
|
||||
<p>Forensic reports contain the original headers of an email that
|
||||
failed a DMARC check, and sometimes may also include the
|
||||
full message body, depending on the policy of the reporting
|
||||
organization.</p>
|
||||
<p>Most reporting organizations do not send forensic reports of any
|
||||
kind for privacy reasons. While aggregate DMARC reports are sent
|
||||
at least daily, it is normal to receive very few forensic reports.</p>
|
||||
<p>An alternative approach is to still collect forensic/failure/ruf
|
||||
reports in your DMARC inbox, but run <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> with
|
||||
<code class="docutils literal notranslate"><span class="pre">save_forensic</span> <span class="pre">=</span> <span class="pre">True``manually</span> <span class="pre">on</span> <span class="pre">a</span> <span class="pre">separate</span> <span class="pre">IMAP</span> <span class="pre">folder</span> <span class="pre">(using</span> <span class="pre">the</span>  <span class="pre">``reports_folder</span></code> option), after you have manually moved
|
||||
known samples you want to save to that folder
|
||||
(e.g. malicious samples and non-sensitive legitimate samples).</p>
|
||||
</div>
|
||||
</section>
|
||||
<section id="sample-aggregate-report-output">
|
||||
<h2>Sample aggregate report output<a class="headerlink" href="#sample-aggregate-report-output" title="Permalink to this heading"></a></h2>
|
||||
<p>Here are the results from parsing the <a class="reference external" href="https://dmarc.org/wiki/FAQ#I_need_to_implement_aggregate_reports.2C_what_do_they_look_like.3F">example</a>
|
||||
report from the dmarc.org wiki. It’s actually an older draft of the the 1.0
|
||||
report from the <a class="reference external" href="http://dmarc.org">dmarc.org</a> wiki. It’s actually an older draft of the the 1.0
|
||||
report schema standardized in
|
||||
<a class="reference external" href="https://tools.ietf.org/html/rfc7489#appendix-C">RFC 7480 Appendix C</a>.
|
||||
This draft schema is still in wide use.</p>
|
||||
<p><code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> produces consistent, normalized output, regardless of the report
|
||||
schema.</p>
|
||||
<p><code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> produces consistent, normalized output, regardless
|
||||
of the report schema.</p>
|
||||
<section id="json">
|
||||
<h3>JSON<a class="headerlink" href="#json" title="Permalink to this heading"></a></h3>
|
||||
<div class="highlight-json notranslate"><div class="highlight"><pre><span></span><span class="p">{</span><span class="w"></span>
|
||||
@@ -575,8 +662,8 @@ schema.</p>
|
||||
</section>
|
||||
<section id="csv">
|
||||
<h3>CSV<a class="headerlink" href="#csv" title="Permalink to this heading"></a></h3>
|
||||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">xml_schema</span><span class="p">,</span><span class="n">org_name</span><span class="p">,</span><span class="n">org_email</span><span class="p">,</span><span class="n">org_extra_contact_info</span><span class="p">,</span><span class="n">report_id</span><span class="p">,</span><span class="n">begin_date</span><span class="p">,</span><span class="n">end_date</span><span class="p">,</span><span class="n">errors</span><span class="p">,</span><span class="n">domain</span><span class="p">,</span><span class="n">adkim</span><span class="p">,</span><span class="n">aspf</span><span class="p">,</span><span class="n">p</span><span class="p">,</span><span class="n">sp</span><span class="p">,</span><span class="n">pct</span><span class="p">,</span><span class="n">fo</span><span class="p">,</span><span class="n">source_ip_address</span><span class="p">,</span><span class="n">source_country</span><span class="p">,</span><span class="n">source_reverse_dns</span><span class="p">,</span><span class="n">source_base_domain</span><span class="p">,</span><span class="n">count</span><span class="p">,</span><span class="n">spf_aligned</span><span class="p">,</span><span class="n">dkim_aligned</span><span class="p">,</span><span class="n">dmarc_aligned</span><span class="p">,</span><span class="n">disposition</span><span class="p">,</span><span class="n">policy_override_reasons</span><span class="p">,</span><span class="n">policy_override_comments</span><span class="p">,</span><span class="n">envelope_from</span><span class="p">,</span><span class="n">header_from</span><span class="p">,</span><span class="n">envelope_to</span><span class="p">,</span><span class="n">dkim_domains</span><span class="p">,</span><span class="n">dkim_selectors</span><span class="p">,</span><span class="n">dkim_results</span><span class="p">,</span><span class="n">spf_domains</span><span class="p">,</span><span class="n">spf_scopes</span><span class="p">,</span><span class="n">spf_results</span>
|
||||
<span class="n">draft</span><span class="p">,</span><span class="n">acme</span><span class="o">.</span><span class="n">com</span><span class="p">,</span><span class="n">noreply</span><span class="o">-</span><span class="n">dmarc</span><span class="o">-</span><span class="n">support</span><span class="nd">@acme</span><span class="o">.</span><span class="n">com</span><span class="p">,</span><span class="n">http</span><span class="p">:</span><span class="o">//</span><span class="n">acme</span><span class="o">.</span><span class="n">com</span><span class="o">/</span><span class="n">dmarc</span><span class="o">/</span><span class="n">support</span><span class="p">,</span><span class="mi">9391651994964116463</span><span class="p">,</span><span class="mi">2012</span><span class="o">-</span><span class="mi">04</span><span class="o">-</span><span class="mi">27</span> <span class="mi">20</span><span class="p">:</span><span class="mi">00</span><span class="p">:</span><span class="mi">00</span><span class="p">,</span><span class="mi">2012</span><span class="o">-</span><span class="mi">04</span><span class="o">-</span><span class="mi">28</span> <span class="mi">19</span><span class="p">:</span><span class="mi">59</span><span class="p">:</span><span class="mi">59</span><span class="p">,,</span><span class="n">example</span><span class="o">.</span><span class="n">com</span><span class="p">,</span><span class="n">r</span><span class="p">,</span><span class="n">r</span><span class="p">,</span><span class="n">none</span><span class="p">,</span><span class="n">none</span><span class="p">,</span><span class="mi">100</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mf">72.150.241.94</span><span class="p">,</span><span class="n">US</span><span class="p">,</span><span class="n">adsl</span><span class="o">-</span><span class="mi">72</span><span class="o">-</span><span class="mi">150</span><span class="o">-</span><span class="mi">241</span><span class="o">-</span><span class="mf">94.</span><span class="n">shv</span><span class="o">.</span><span class="n">bellsouth</span><span class="o">.</span><span class="n">net</span><span class="p">,</span><span class="n">bellsouth</span><span class="o">.</span><span class="n">net</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="kc">True</span><span class="p">,</span><span class="kc">False</span><span class="p">,</span><span class="kc">True</span><span class="p">,</span><span class="n">none</span><span class="p">,,,</span><span class="n">example</span><span class="o">.</span><span class="n">com</span><span class="p">,</span><span class="n">example</span><span class="o">.</span><span class="n">com</span><span class="p">,,</span><span class="n">example</span><span class="o">.</span><span class="n">com</span><span class="p">,</span><span class="n">none</span><span class="p">,</span><span class="n">fail</span><span class="p">,</span><span class="n">example</span><span class="o">.</span><span class="n">com</span><span class="p">,</span><span class="n">mfrom</span><span class="p">,</span><span class="k">pass</span>
|
||||
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>xml_schema,org_name,org_email,org_extra_contact_info,report_id,begin_date,end_date,errors,domain,adkim,aspf,p,sp,pct,fo,source_ip_address,source_country,source_reverse_dns,source_base_domain,count,spf_aligned,dkim_aligned,dmarc_aligned,disposition,policy_override_reasons,policy_override_comments,envelope_from,header_from,envelope_to,dkim_domains,dkim_selectors,dkim_results,spf_domains,spf_scopes,spf_results
|
||||
draft,acme.com,noreply-dmarc-support@acme.com,http://acme.com/dmarc/support,9391651994964116463,2012-04-27 20:00:00,2012-04-28 19:59:59,,example.com,r,r,none,none,100,0,72.150.241.94,US,adsl-72-150-241-94.shv.bellsouth.net,bellsouth.net,2,True,False,True,none,,,example.com,example.com,,example.com,none,fail,example.com,mfrom,pass
|
||||
</pre></div>
|
||||
</div>
|
||||
</section>
|
||||
@@ -676,8 +763,8 @@ schema.</p>
|
||||
</section>
|
||||
<section id="id2">
|
||||
<h3>CSV<a class="headerlink" href="#id2" title="Permalink to this heading"></a></h3>
|
||||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">feedback_type</span><span class="p">,</span><span class="n">user_agent</span><span class="p">,</span><span class="n">version</span><span class="p">,</span><span class="n">original_envelope_id</span><span class="p">,</span><span class="n">original_mail_from</span><span class="p">,</span><span class="n">original_rcpt_to</span><span class="p">,</span><span class="n">arrival_date</span><span class="p">,</span><span class="n">arrival_date_utc</span><span class="p">,</span><span class="n">subject</span><span class="p">,</span><span class="n">message_id</span><span class="p">,</span><span class="n">authentication_results</span><span class="p">,</span><span class="n">dkim_domain</span><span class="p">,</span><span class="n">source_ip_address</span><span class="p">,</span><span class="n">source_country</span><span class="p">,</span><span class="n">source_reverse_dns</span><span class="p">,</span><span class="n">source_base_domain</span><span class="p">,</span><span class="n">delivery_result</span><span class="p">,</span><span class="n">auth_failure</span><span class="p">,</span><span class="n">reported_domain</span><span class="p">,</span><span class="n">authentication_mechanisms</span><span class="p">,</span><span class="n">sample_headers_only</span>
|
||||
<span class="n">auth</span><span class="o">-</span><span class="n">failure</span><span class="p">,</span><span class="n">Lua</span><span class="o">/</span><span class="mf">1.0</span><span class="p">,</span><span class="mf">1.0</span><span class="p">,,</span><span class="n">sharepoint</span><span class="nd">@domain</span><span class="o">.</span><span class="n">de</span><span class="p">,</span><span class="n">peter</span><span class="o">.</span><span class="n">pan</span><span class="nd">@domain</span><span class="o">.</span><span class="n">de</span><span class="p">,</span><span class="s2">"Mon, 01 Oct 2018 11:20:27 +0200"</span><span class="p">,</span><span class="mi">2018</span><span class="o">-</span><span class="mi">10</span><span class="o">-</span><span class="mi">01</span> <span class="mi">09</span><span class="p">:</span><span class="mi">20</span><span class="p">:</span><span class="mi">27</span><span class="p">,</span><span class="n">Subject</span><span class="p">,</span><span class="o"><</span><span class="mf">38.E7.30937</span><span class="o">.</span><span class="n">BD6E1BB5</span><span class="o">@</span> <span class="n">mailrelay</span><span class="o">.</span><span class="n">de</span><span class="o">></span><span class="p">,</span><span class="s2">"dmarc=fail (p=none, dis=none) header.from=domain.de"</span><span class="p">,,</span><span class="mf">10.10.10.10</span><span class="p">,,,,</span><span class="n">policy</span><span class="p">,</span><span class="n">dmarc</span><span class="p">,</span><span class="n">domain</span><span class="o">.</span><span class="n">de</span><span class="p">,,</span><span class="kc">False</span>
|
||||
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>feedback_type,user_agent,version,original_envelope_id,original_mail_from,original_rcpt_to,arrival_date,arrival_date_utc,subject,message_id,authentication_results,dkim_domain,source_ip_address,source_country,source_reverse_dns,source_base_domain,delivery_result,auth_failure,reported_domain,authentication_mechanisms,sample_headers_only
|
||||
auth-failure,Lua/1.0,1.0,,sharepoint@domain.de,peter.pan@domain.de,"Mon, 01 Oct 2018 11:20:27 +0200",2018-10-01 09:20:27,Subject,<38.E7.30937.BD6E1BB5@ mailrelay.de>,"dmarc=fail (p=none, dis=none) header.from=domain.de",,10.10.10.10,,,,policy,dmarc,domain.de,,False
|
||||
</pre></div>
|
||||
</div>
|
||||
</section>
|
||||
@@ -695,15 +782,15 @@ schema.</p>
|
||||
<p>If your system is behind a web proxy, you need to configure your system
|
||||
to use that proxy. To do this, edit <code class="docutils literal notranslate"><span class="pre">/etc/environment</span></code> and add your
|
||||
proxy details there, for example:</p>
|
||||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">http_proxy</span><span class="o">=</span><span class="n">http</span><span class="p">:</span><span class="o">//</span><span class="n">user</span><span class="p">:</span><span class="n">password</span><span class="nd">@prox</span><span class="o">-</span><span class="n">server</span><span class="p">:</span><span class="mi">3128</span>
|
||||
<span class="n">https_proxy</span><span class="o">=</span><span class="n">https</span><span class="p">:</span><span class="o">//</span><span class="n">user</span><span class="p">:</span><span class="n">password</span><span class="nd">@prox</span><span class="o">-</span><span class="n">server</span><span class="p">:</span><span class="mi">3128</span>
|
||||
<span class="n">ftp_proxy</span><span class="o">=</span><span class="n">http</span><span class="p">:</span><span class="o">//</span><span class="n">user</span><span class="p">:</span><span class="n">password</span><span class="nd">@prox</span><span class="o">-</span><span class="n">server</span><span class="p">:</span><span class="mi">3128</span>
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span><span class="nv">http_proxy</span><span class="o">=</span>http://user:password@prox-server:3128
|
||||
<span class="nv">https_proxy</span><span class="o">=</span>https://user:password@prox-server:3128
|
||||
<span class="nv">ftp_proxy</span><span class="o">=</span>http://user:password@prox-server:3128
|
||||
</pre></div>
|
||||
</div>
|
||||
<p>Or if no credentials are needed:</p>
|
||||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">http_proxy</span><span class="o">=</span><span class="n">http</span><span class="p">:</span><span class="o">//</span><span class="n">prox</span><span class="o">-</span><span class="n">server</span><span class="p">:</span><span class="mi">3128</span>
|
||||
<span class="n">https_proxy</span><span class="o">=</span><span class="n">https</span><span class="p">:</span><span class="o">//</span><span class="n">prox</span><span class="o">-</span><span class="n">server</span><span class="p">:</span><span class="mi">3128</span>
|
||||
<span class="n">ftp_proxy</span><span class="o">=</span><span class="n">http</span><span class="p">:</span><span class="o">//</span><span class="n">prox</span><span class="o">-</span><span class="n">server</span><span class="p">:</span><span class="mi">3128</span>
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span><span class="nv">http_proxy</span><span class="o">=</span>http://prox-server:3128
|
||||
<span class="nv">https_proxy</span><span class="o">=</span>https://prox-server:3128
|
||||
<span class="nv">ftp_proxy</span><span class="o">=</span>http://prox-server:3128
|
||||
</pre></div>
|
||||
</div>
|
||||
<p>This will set the the proxy up for use system-wide, including for
|
||||
@@ -744,11 +831,14 @@ sudo apt install -y geoipupdate
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo dnf install -y geoipupdate
|
||||
</pre></div>
|
||||
</div>
|
||||
<p>The latest builds for Linux, macOS, and Windows can be downloaded from the <a class="reference external" href="https://github.com/maxmind/geoipupdate/releases">geoipupdate releases page on GitHub</a>.</p>
|
||||
<p>On December 30th, 2019, MaxMind started requiring free accounts to access the free Geolite2 databases, in order <a class="reference external" href="https://blog.maxmind.com/2019/12/18/significant-changes-to-accessing-and-using-geolite2-databases/">to
|
||||
<p>The latest builds for Linux, macOS, and Windows can be downloaded
|
||||
from the <a class="reference external" href="https://github.com/maxmind/geoipupdate/releases">geoipupdate releases page on GitHub</a>.</p>
|
||||
<p>On December 30th, 2019, MaxMind started requiring free accounts to
|
||||
access the free Geolite2 databases, in order <a class="reference external" href="https://blog.maxmind.com/2019/12/18/significant-changes-to-accessing-and-using-geolite2-databases/">to
|
||||
comply with various privacy regulations</a>.</p>
|
||||
<p>Start by <a class="reference external" href="https://www.maxmind.com/en/geolite2/signup">registering for a free GeoLite2 account</a>, and signing in.</p>
|
||||
<p>Then, navigate the to the <a class="reference external" href="https://www.maxmind.com/en/accounts/current/license-key">License Keys</a> page under your account, and create a new license key for the version of
|
||||
<p>Then, navigate the to the <a class="reference external" href="https://www.maxmind.com/en/accounts/current/license-key">License Keys</a> page under your account,
|
||||
and create a new license key for the version of
|
||||
<code class="docutils literal notranslate"><span class="pre">geoipupdate</span></code> that was installed.</p>
|
||||
<div class="admonition warning">
|
||||
<p class="admonition-title">Warning</p>
|
||||
@@ -763,17 +853,21 @@ of <code class="docutils literal notranslate"><span class="pre">geoipupdate</spa
|
||||
</div>
|
||||
</div>
|
||||
<p>You can use <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> as the description for the key.</p>
|
||||
<p>Once you have generated a key, download the config pre-filled configuration file.
|
||||
This file should be saved at <code class="docutils literal notranslate"><span class="pre">/etc/GeoIP.conf</span></code> on Linux or macOS systems, or at
|
||||
<code class="docutils literal notranslate"><span class="pre">%SystemDrive%\ProgramData\MaxMind\GeoIPUpdate\GeoIP.conf</span></code> on Windows systems.</p>
|
||||
<p>Once you have generated a key, download the config pre-filled
|
||||
configuration file. This file should be saved at <code class="docutils literal notranslate"><span class="pre">/etc/GeoIP.conf</span></code>
|
||||
on Linux or macOS systems, or at
|
||||
<code class="docutils literal notranslate"><span class="pre">%SystemDrive%\ProgramData\MaxMind\GeoIPUpdate\GeoIP.conf</span></code> on
|
||||
Windows systems.</p>
|
||||
<p>Then run</p>
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo geoipupdate
|
||||
</pre></div>
|
||||
</div>
|
||||
<p>To download the databases for the first time.</p>
|
||||
<p>The GeoLite2 Country, City, and ASN databases are updated weekly, every Tuesday.
|
||||
<code class="docutils literal notranslate"><span class="pre">geoipupdate</span></code> can be run weekly by adding a cron job or scheduled task.</p>
|
||||
<p>More information about <code class="docutils literal notranslate"><span class="pre">geoipupdate</span></code> can be found at the <a class="reference external" href="https://dev.maxmind.com/geoip/geoipupdate/">MaxMind geoipupdate page</a>.</p>
|
||||
<p>The GeoLite2 Country, City, and ASN databases are updated weekly,
|
||||
every Tuesday. <code class="docutils literal notranslate"><span class="pre">geoipupdate</span></code> can be run weekly by adding a cron
|
||||
job or scheduled task.</p>
|
||||
<p>More information about <code class="docutils literal notranslate"><span class="pre">geoipupdate</span></code> can be found at the
|
||||
<a class="reference external" href="https://dev.maxmind.com/geoip/geoipupdate/">MaxMind geoipupdate page</a>.</p>
|
||||
</section>
|
||||
<section id="installing-parsedmarc">
|
||||
<h3>Installing parsedmarc<a class="headerlink" href="#installing-parsedmarc" title="Permalink to this heading"></a></h3>
|
||||
@@ -796,7 +890,8 @@ sudo useradd parsedmarc -r -s /bin/false -m -b /opt
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo -u parsedmarc virtualenv /opt/parsedmarc/venv
|
||||
</pre></div>
|
||||
</div>
|
||||
<p>CentOS/RHEL 8 systems use Python 3.6 by default, so on those systems explicitly tell <code class="docutils literal notranslate"><span class="pre">virtualenv</span></code> to use <code class="docutils literal notranslate"><span class="pre">python3.9</span></code> instead</p>
|
||||
<p>CentOS/RHEL 8 systems use Python 3.6 by default, so on those systems
|
||||
explicitly tell <code class="docutils literal notranslate"><span class="pre">virtualenv</span></code> to use <code class="docutils literal notranslate"><span class="pre">python3.9</span></code> instead</p>
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo -u parsedmarc virtualenv -p python3.9 /opt/parsedmarc/venv
|
||||
</pre></div>
|
||||
</div>
|
||||
@@ -827,7 +922,7 @@ tags in your DMARC record, separated by commas.</p>
|
||||
<p>Starting in 8.0.0, parsedmarc supports accessing Microsoft/Office 365
|
||||
inboxes via the Microsoft Graph API, which is preferred over Davmail.</p>
|
||||
</div>
|
||||
<p>Some organisations do not allow IMAP or the Microsoft Graph API,
|
||||
<p>Some organizations do not allow IMAP or the Microsoft Graph API,
|
||||
and only support Exchange Web Services (EWS)/Outlook Web Access (OWA).
|
||||
In that case, Davmail will need to be set up
|
||||
as a local EWS/OWA IMAP gateway. It can even work where
|
||||
@@ -964,7 +1059,7 @@ sudo service davmail restart
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p>In the event of a crash, systemd will restart the service after 5 minutes,
|
||||
but the <cite>service davmail status</cite> command will only show the logs for the
|
||||
but the <code class="docutils literal notranslate"><span class="pre">service</span> <span class="pre">davmail</span> <span class="pre">status</span></code> command will only show the logs for the
|
||||
current process. To vew the logs for previous runs as well as the
|
||||
current process (newest to oldest), run:</p>
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>journalctl -u davmail.service -r
|
||||
@@ -1032,7 +1127,8 @@ sudo service elasticsearch start
|
||||
sudo service kibana start
|
||||
</pre></div>
|
||||
</div>
|
||||
<p>Without the commercial <a class="reference external" href="https://www.elastic.co/products/x-pack">X-Pack</a> or <a class="reference external" href="https://readonlyrest.com/">ReadonlyREST</a> products, Kibana does not have any authentication
|
||||
<p>Without the commercial <a class="reference external" href="https://www.elastic.co/products/x-pack">X-Pack</a> or <a class="reference external" href="https://readonlyrest.com/">ReadonlyREST</a> products, Kibana
|
||||
does not have any authentication
|
||||
mechanism of its own. You can use nginx as a reverse proxy that provides basic
|
||||
authentication.</p>
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo apt-get install -y nginx apache2-utils
|
||||
@@ -1241,7 +1337,7 @@ sudo service parsedmarc restart
|
||||
<div class="admonition note">
|
||||
<p class="admonition-title">Note</p>
|
||||
<p>In the event of a crash, systemd will restart the service after 10 minutes,
|
||||
but the <cite>service parsedmarc status</cite> command will only show the logs for the
|
||||
but the <code class="docutils literal notranslate"><span class="pre">service</span> <span class="pre">parsedmarc</span> <span class="pre">status</span></code> command will only show the logs for the
|
||||
current process. To vew the logs for previous runs as well as the
|
||||
current process (newest to oldest), run:</p>
|
||||
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>journalctl -u parsedmarc.service -r
|
||||
@@ -1377,8 +1473,8 @@ header</p></td>
|
||||
</tbody>
|
||||
</table>
|
||||
</section>
|
||||
<section id="what-if-a-sender-won-t-support-dkim-dmarc">
|
||||
<h2>What if a sender won’t support DKIM/DMARC?<a class="headerlink" href="#what-if-a-sender-won-t-support-dkim-dmarc" title="Permalink to this heading"></a></h2>
|
||||
<section id="what-if-a-sender-wont-support-dkim-dmarc">
|
||||
<h2>What if a sender won’t support DKIM/DMARC?<a class="headerlink" href="#what-if-a-sender-wont-support-dkim-dmarc" title="Permalink to this heading"></a></h2>
|
||||
<ol class="arabic simple">
|
||||
<li><p>Some vendors don’t know about DMARC yet; ask about SPF and DKIM/email
|
||||
authentication.</p></li>
|
||||
@@ -1393,44 +1489,46 @@ separate SPF and DMARC records on <code class="docutils literal notranslate"><sp
|
||||
<div class="admonition warning">
|
||||
<p class="admonition-title">Warning</p>
|
||||
<p>Do not alter the <code class="docutils literal notranslate"><span class="pre">p</span></code> or <code class="docutils literal notranslate"><span class="pre">sp</span></code> values of the DMARC record on the
|
||||
Top-Level Domain (TLD) – that would leave you vulnerable to spoofing of
|
||||
your TLD and/or any subdomain.</p>
|
||||
Top-Level Domain (TLD) – that would leave you vulnerable to
|
||||
spoofing of your TLD and/or any subdomain.</p>
|
||||
</div>
|
||||
</section>
|
||||
<section id="what-about-mailing-lists">
|
||||
<h2>What about mailing lists?<a class="headerlink" href="#what-about-mailing-lists" title="Permalink to this heading"></a></h2>
|
||||
<p>When you deploy DMARC on your domain, you might find that messages relayed by
|
||||
mailing lists are failing DMARC, most likely because the mailing list is
|
||||
spoofing your from address, and modifying the subject, footer, or other part
|
||||
of the message, thereby breaking the DKIM signature.</p>
|
||||
<p>When you deploy DMARC on your domain, you might find that messages
|
||||
relayed by mailing lists are failing DMARC, most likely because the mailing
|
||||
list is spoofing your from address, and modifying the subject,
|
||||
footer, or other part of the message, thereby breaking the
|
||||
DKIM signature.</p>
|
||||
<section id="mailing-list-list-best-practices">
|
||||
<h3>Mailing list list best practices<a class="headerlink" href="#mailing-list-list-best-practices" title="Permalink to this heading"></a></h3>
|
||||
<p>Ideally, a mailing list should forward messages without altering the headers
|
||||
or body content at all. <a class="reference external" href="https://begriffs.com/posts/2018-09-18-dmarc-mailing-list.html">Joe Nelson</a> does a fantastic job of explaining exactly
|
||||
what mailing lists should and shouldn’t do to be fully DMARC compliant.
|
||||
Rather than repeat his fine work, here’s a summary:</p>
|
||||
<p><strong>Do</strong></p>
|
||||
<ul>
|
||||
<p>Ideally, a mailing list should forward messages without altering the
|
||||
headers or body content at all. <a class="reference external" href="https://begriffs.com/posts/2018-09-18-dmarc-mailing-list.html">Joe Nelson</a> does a fantastic job of
|
||||
explaining exactly what mailing lists should and shouldn’t do to be
|
||||
fully DMARC compliant. Rather than repeat his fine work, here’s a
|
||||
summary:</p>
|
||||
<section id="do">
|
||||
<h4>Do<a class="headerlink" href="#do" title="Permalink to this heading"></a></h4>
|
||||
<ul class="simple">
|
||||
<li><p>Retain headers from the original message</p></li>
|
||||
<li><p>Add <a class="reference external" href="https://tools.ietf.org/html/rfc2369">RFC 2369</a> List-Unsubscribe headers to outgoing messages, instead of
|
||||
adding unsubscribe links to the body</p>
|
||||
adding unsubscribe links to the body</p></li>
|
||||
</ul>
|
||||
<blockquote>
|
||||
<div><div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">List</span><span class="o">-</span><span class="n">Unsubscribe</span><span class="p">:</span> <span class="o"><</span><span class="n">https</span><span class="p">:</span><span class="o">//</span><span class="nb">list</span><span class="o">.</span><span class="n">example</span><span class="o">.</span><span class="n">com</span><span class="o">/</span><span class="n">unsubscribe</span><span class="o">-</span><span class="n">link</span><span class="o">></span>
|
||||
</pre></div>
|
||||
</div>
|
||||
<div><p>List-Unsubscribe: <a class="reference external" href="https://list.example.com/unsubscribe-link">https://list.example.com/unsubscribe-link</a></p>
|
||||
</div></blockquote>
|
||||
</li>
|
||||
<ul>
|
||||
<li><p>Add <a class="reference external" href="https://tools.ietf.org/html/rfc2919">RFC 2919</a> List-Id headers instead of modifying the subject</p>
|
||||
<blockquote>
|
||||
<div><div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">List</span><span class="o">-</span><span class="n">Id</span><span class="p">:</span> <span class="n">Example</span> <span class="n">Mailing</span> <span class="n">List</span> <span class="o"><</span><span class="nb">list</span><span class="o">.</span><span class="n">example</span><span class="o">.</span><span class="n">com</span><span class="o">></span>
|
||||
</pre></div>
|
||||
</div>
|
||||
<div><p>List-Id: Example Mailing List <<a class="reference external" href="http://list.example.com">list.example.com</a>></p>
|
||||
</div></blockquote>
|
||||
</li>
|
||||
</ul>
|
||||
<p>Modern mail clients and webmail services generate unsubscribe buttons based on
|
||||
these headers.</p>
|
||||
<p><strong>Do not</strong></p>
|
||||
</section>
|
||||
<section id="do-not">
|
||||
<h4>Do not<a class="headerlink" href="#do-not" title="Permalink to this heading"></a></h4>
|
||||
<ul class="simple">
|
||||
<li><p>Remove or modify any existing headers from the original message, including
|
||||
From, Date, Subject, etc.</p></li>
|
||||
@@ -1445,6 +1543,7 @@ list.</p>
|
||||
tell that a message came from the mailing list, because the message was sent
|
||||
to the mailing list post address, and not their email address.</p>
|
||||
<p>Configuration steps for common mailing list platforms are listed below.</p>
|
||||
</section>
|
||||
<section id="mailman-2">
|
||||
<h4>Mailman 2<a class="headerlink" href="#mailman-2" title="Permalink to this heading"></a></h4>
|
||||
<p>Navigate to General Settings, and configure the settings below</p>
|
||||
@@ -1514,7 +1613,7 @@ to the mailing list post address, and not their email address.</p>
|
||||
<tr class="row-even"><td><p><strong>dmarc_moderation_action</strong></p></td>
|
||||
<td><p>Accept</p></td>
|
||||
</tr>
|
||||
<tr class="row-odd"><td><p><strong>dmarc_quarentine_moderation_action</strong></p></td>
|
||||
<tr class="row-odd"><td><p><strong>dmarc_quarantine_moderation_action</strong></p></td>
|
||||
<td><p>Yes</p></td>
|
||||
</tr>
|
||||
<tr class="row-even"><td><p><strong>dmarc_none_moderation_action</strong></p></td>
|
||||
@@ -1550,7 +1649,7 @@ to the mailing list post address, and not their email address.</p>
|
||||
<tr class="row-odd"><td><p><strong>Explicit reply-to address</strong></p></td>
|
||||
<td></td>
|
||||
</tr>
|
||||
<tr class="row-even"><td><p><strong>First strip replyo</strong></p></td>
|
||||
<tr class="row-even"><td><p><strong>First strip replyto</strong></p></td>
|
||||
<td><p>No</p></td>
|
||||
</tr>
|
||||
<tr class="row-odd"><td><p><strong>Reply goes to list</strong></p></td>
|
||||
@@ -1611,7 +1710,7 @@ no longer spoof email addresses with domains protected by DMARC.</p>
|
||||
<tr class="row-even"><td><p><strong>dmarc_moderation_action</strong></p></td>
|
||||
<td><p>Munge From</p></td>
|
||||
</tr>
|
||||
<tr class="row-odd"><td><p><strong>dmarc_quarentine_moderation_action</strong></p></td>
|
||||
<tr class="row-odd"><td><p><strong>dmarc_quarantine_moderation_action</strong></p></td>
|
||||
<td><p>Yes</p></td>
|
||||
</tr>
|
||||
<tr class="row-even"><td><p><strong>dmarc_none_moderation_action</strong></p></td>
|
||||
@@ -1823,7 +1922,7 @@ DMARC reports</p>
|
||||
<dl class="py function">
|
||||
<dt class="sig sig-object py" id="parsedmarc.parse_aggregate_report_file">
|
||||
<span class="sig-prename descclassname"><span class="pre">parsedmarc.</span></span><span class="sig-name descname"><span class="pre">parse_aggregate_report_file</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">_input</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">offline</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">False</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">ip_db_path</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">None</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">nameservers</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">None</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">dns_timeout</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">2.0</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">parallel</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">False</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">keep_alive</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">None</span></span></em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#parse_aggregate_report_file"><span class="viewcode-link"><span class="pre">[source]</span></span></a><a class="headerlink" href="#parsedmarc.parse_aggregate_report_file" title="Permalink to this definition"></a></dt>
|
||||
<dd><p>Parses a file at the given path, a file-like object. or bytes as a
|
||||
<dd><p>Parses a file at the given path, a file-like object. or bytes as an
|
||||
aggregate DMARC report</p>
|
||||
<dl class="field-list simple">
|
||||
<dt class="field-odd">Parameters</dt>
|
||||
@@ -2194,7 +2293,20 @@ index</p></li>
|
||||
<dl class="py class">
|
||||
<dt class="sig sig-object py" id="parsedmarc.splunk.HECClient">
|
||||
<em class="property"><span class="pre">class</span><span class="w"> </span></em><span class="sig-prename descclassname"><span class="pre">parsedmarc.splunk.</span></span><span class="sig-name descname"><span class="pre">HECClient</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">url</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">access_token</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">index</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">source</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">'parsedmarc'</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">verify</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">True</span></span></em>, <em class="sig-param"><span class="n"><span class="pre">timeout</span></span><span class="o"><span class="pre">=</span></span><span class="default_value"><span class="pre">60</span></span></em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/splunk.html#HECClient"><span class="viewcode-link"><span class="pre">[source]</span></span></a><a class="headerlink" href="#parsedmarc.splunk.HECClient" title="Permalink to this definition"></a></dt>
|
||||
<dd><p>A client for a Splunk HTTP Events Collector (HEC)</p>
|
||||
<dd><p>Initializes the HECClient
|
||||
:param url: The URL of the HEC
|
||||
:type url: str
|
||||
:param access_token: The HEC access token
|
||||
:type access_token: str
|
||||
:param index: The name of the index
|
||||
:type index: str
|
||||
:param source: The source name
|
||||
:type source: str
|
||||
:param verify: Verify SSL certificates
|
||||
:type verify: bool
|
||||
:param timeout: Number of seconds to wait for the server to send
|
||||
:type timeout: float
|
||||
:param data before giving up:</p>
|
||||
<dl class="py method">
|
||||
<dt class="sig sig-object py" id="parsedmarc.splunk.HECClient.save_aggregate_reports_to_splunk">
|
||||
<span class="sig-name descname"><span class="pre">save_aggregate_reports_to_splunk</span></span><span class="sig-paren">(</span><em class="sig-param"><span class="n"><span class="pre">aggregate_reports</span></span></em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/splunk.html#HECClient.save_aggregate_reports_to_splunk"><span class="viewcode-link"><span class="pre">[source]</span></span></a><a class="headerlink" href="#parsedmarc.splunk.HECClient.save_aggregate_reports_to_splunk" title="Permalink to this definition"></a></dt>
|
||||
|
||||
BIN
objects.inv
BIN
objects.inv
Binary file not shown.
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Python Module Index — parsedmarc 8.3.0 documentation</title>
|
||||
<title>Python Module Index — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="_static/css/theme.css" type="text/css" />
|
||||
<!--[if lt IE 9]>
|
||||
@@ -31,7 +31,7 @@
|
||||
<a href="index.html" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
8.3.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="search.html" method="get">
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Search — parsedmarc 8.3.0 documentation</title>
|
||||
<title>Search — parsedmarc 8.3.1 documentation</title>
|
||||
<link rel="stylesheet" href="_static/pygments.css" type="text/css" />
|
||||
<link rel="stylesheet" href="_static/css/theme.css" type="text/css" />
|
||||
|
||||
@@ -31,7 +31,7 @@
|
||||
<a href="index.html" class="icon icon-home"> parsedmarc
|
||||
</a>
|
||||
<div class="version">
|
||||
8.3.0
|
||||
8.3.1
|
||||
</div>
|
||||
<div role="search">
|
||||
<form id="rtd-search-form" class="wy-form" action="#" method="get">
|
||||
|
||||
File diff suppressed because one or more lines are too long
Reference in New Issue
Block a user