Files
parsedmarc/index.html
Sean Whalen d73cdfaed4 4.3.0
2018-10-12 14:18:53 -04:00

1934 lines
153 KiB
HTML
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<!DOCTYPE html>
<!--[if IE 8]><html class="no-js lt-ie9" lang="en" > <![endif]-->
<!--[if gt IE 8]><!--> <html class="no-js" lang="en" > <!--<![endif]-->
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>parsedmarc documentation - Open source DMARC report analyzer and visualizer &mdash; parsedmarc 4.3.0 documentation</title>
<link rel="stylesheet" href="_static/css/theme.css" type="text/css" />
<link rel="stylesheet" href="_static/pygments.css" type="text/css" />
<link rel="index" title="Index" href="genindex.html" />
<link rel="search" title="Search" href="search.html" />
<script src="_static/js/modernizr.min.js"></script>
</head>
<body class="wy-body-for-nav">
<div class="wy-grid-for-nav">
<nav data-toggle="wy-nav-shift" class="wy-nav-side">
<div class="wy-side-scroll">
<div class="wy-side-nav-search">
<a href="#" class="icon icon-home"> parsedmarc
</a>
<div class="version">
4.3.0
</div>
<div role="search">
<form id="rtd-search-form" class="wy-form" action="search.html" method="get">
<input type="text" name="q" placeholder="Search docs" />
<input type="hidden" name="check_keywords" value="yes" />
<input type="hidden" name="area" value="default" />
</form>
</div>
</div>
<div class="wy-menu wy-menu-vertical" data-spy="affix" role="navigation" aria-label="main navigation">
<!-- Local TOC -->
<div class="local-toc"><ul>
<li><a class="reference internal" href="#">parsedmarc documentation - Open source DMARC report analyzer and visualizer</a><ul>
<li><a class="reference internal" href="#features">Features</a></li>
<li><a class="reference internal" href="#resources">Resources</a><ul>
<li><a class="reference internal" href="#dmarc-guides">DMARC guides</a></li>
<li><a class="reference internal" href="#spf-and-dmarc-record-validation">SPF and DMARC record validation</a></li>
<li><a class="reference internal" href="#lookalike-domains">Lookalike domains</a></li>
</ul>
</li>
<li><a class="reference internal" href="#cli-help">CLI help</a></li>
<li><a class="reference internal" href="#sample-aggregate-report-output">Sample aggregate report output</a><ul>
<li><a class="reference internal" href="#json">JSON</a></li>
<li><a class="reference internal" href="#csv">CSV</a></li>
</ul>
</li>
<li><a class="reference internal" href="#sample-forensic-report-output">Sample forensic report output</a><ul>
<li><a class="reference internal" href="#id1">JSON</a></li>
<li><a class="reference internal" href="#id2">CSV</a></li>
</ul>
</li>
<li><a class="reference internal" href="#bug-reports">Bug reports</a></li>
<li><a class="reference internal" href="#installation">Installation</a><ul>
<li><a class="reference internal" href="#installation-using-pypy3">Installation using pypy3</a></li>
<li><a class="reference internal" href="#optional-dependencies">Optional dependencies</a></li>
<li><a class="reference internal" href="#dns-performance">DNS performance</a></li>
<li><a class="reference internal" href="#testing-multiple-report-analyzers">Testing multiple report analyzers</a></li>
<li><a class="reference internal" href="#elasticsearch-and-kibana">Elasticsearch and Kibana</a><ul>
<li><a class="reference internal" href="#records-retention">Records retention</a></li>
</ul>
</li>
<li><a class="reference internal" href="#splunk">Splunk</a></li>
<li><a class="reference internal" href="#running-parsedmarc-as-a-systemd-service">Running parsedmarc as a systemd service</a></li>
</ul>
</li>
<li><a class="reference internal" href="#using-the-kibana-dashboards">Using the Kibana dashboards</a><ul>
<li><a class="reference internal" href="#dmarc-summary">DMARC Summary</a></li>
<li><a class="reference internal" href="#dmarc-forensic-samples">DMARC Forensic Samples</a></li>
</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 wont support DKIM/DMARC?</a></li>
<li><a class="reference internal" href="#module-parsedmarc">API</a><ul>
<li><a class="reference internal" href="#module-parsedmarc.elastic">parsedmarc.elastic</a><ul>
</ul>
</li>
</ul>
</li>
<li><a class="reference internal" href="#indices-and-tables">Indices and tables</a></li>
</ul>
</li>
</ul>
</div>
</div>
</div>
</nav>
<section data-toggle="wy-nav-shift" class="wy-nav-content-wrap">
<nav class="wy-nav-top" aria-label="top navigation">
<i data-toggle="wy-nav-top" class="fa fa-bars"></i>
<a href="#">parsedmarc</a>
</nav>
<div class="wy-nav-content">
<div class="rst-content">
<div role="navigation" aria-label="breadcrumbs navigation">
<ul class="wy-breadcrumbs">
<li><a href="#">Docs</a> &raquo;</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>
</li>
</ul>
<hr/>
</div>
<div role="main" class="document" itemscope="itemscope" itemtype="http://schema.org/Article">
<div itemprop="articleBody">
<div class="section" 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 headline"></a></h1>
<p><a class="reference external" href="https://travis-ci.org/domainaware/parsedmarc"><img alt="Build Status" src="https://travis-ci.org/domainaware/parsedmarc.svg?branch=master" /></a></p>
<a class="reference external image-reference" href="_static/screenshots/dmarc-summary-charts.png"><img alt="A screenshot of DMARC summary charts in Kibana" class="align-center" src="_images/dmarc-summary-charts.png" style="width: 597.0px; height: 381.0px;" /></a>
<p><code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> is a Python module and CLI utility for parsing DMARC reports.
When used with Elasticsearch and Kibana (or Splunk), it works as a self-hosted
open source alternative to commercial DMARC report processing services such
as Agari, Dmarcian, OnDMARC, ProofPoint Email Fraud Defense.</p>
<div class="section" id="features">
<h2>Features<a class="headerlink" href="#features" title="Permalink to this headline"></a></h2>
<ul class="simple">
<li>Parses draft and 1.0 standard aggregate/rua reports</li>
<li>Parses forensic/failure/ruf reports</li>
<li>Can parse reports from an inbox over IMAP</li>
<li>Transparently handles gzip or zip compressed reports</li>
<li>Consistent data structures</li>
<li>Simple JSON and/or CSV output</li>
<li>Optionally email the results</li>
<li>Optionally send the results to Elasticsearch and/or Splunk, for use with
premade dashboards</li>
<li>Optionally send reports to Apache Kafka</li>
</ul>
</div>
<div class="section" id="resources">
<h2>Resources<a class="headerlink" href="#resources" title="Permalink to this headline"></a></h2>
<div class="section" id="dmarc-guides">
<h3>DMARC guides<a class="headerlink" href="#dmarc-guides" title="Permalink to this headline"></a></h3>
<ul class="simple">
<li><a class="reference external" href="https://seanthegeek.net/459/demystifying-dmarc/">Demystifying DMARC</a> - A complete guide to SPF, DKIM, and DMARC</li>
</ul>
</div>
<div class="section" id="spf-and-dmarc-record-validation">
<h3>SPF and DMARC record validation<a class="headerlink" href="#spf-and-dmarc-record-validation" title="Permalink to this headline"></a></h3>
<p>If you are looking for SPF and DMARC record validation and parsing,
check out the sister project,
<a class="reference external" href="https://domainaware.github.io/checkdmarc/">checkdmarc</a>.</p>
</div>
<div class="section" id="lookalike-domains">
<h3>Lookalike domains<a class="headerlink" href="#lookalike-domains" title="Permalink to this headline"></a></h3>
<p>DMARC protects against domain spoofing, not lookalike domains. for open source
lookalike domain monitoring, check out <a class="reference external" href="https://github.com/seanthegeek/domainaware">DomainAware</a>.</p>
</div>
</div>
<div class="section" id="cli-help">
<h2>CLI help<a class="headerlink" href="#cli-help" title="Permalink to this headline"></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">o</span> <span class="n">OUTPUT</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">TIMEOUT</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">H</span> <span class="n">HOST</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">u</span> <span class="n">USER</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">p</span> <span class="n">PASSWORD</span><span class="p">]</span>
<span class="p">[</span><span class="o">--</span><span class="n">imap</span><span class="o">-</span><span class="n">port</span> <span class="n">IMAP_PORT</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">imap</span><span class="o">-</span><span class="n">no</span><span class="o">-</span><span class="n">ssl</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">r</span> <span class="n">REPORTS_FOLDER</span><span class="p">]</span>
<span class="p">[</span><span class="o">-</span><span class="n">a</span> <span class="n">ARCHIVE_FOLDER</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">d</span><span class="p">]</span>
<span class="p">[</span><span class="o">-</span><span class="n">E</span> <span class="p">[</span><span class="n">ELASTICSEARCH_HOST</span> <span class="p">[</span><span class="n">ELASTICSEARCH_HOST</span> <span class="o">...</span><span class="p">]]]</span>
<span class="p">[</span><span class="o">--</span><span class="n">elasticsearch</span><span class="o">-</span><span class="n">index</span><span class="o">-</span><span class="n">prefix</span> <span class="n">ELASTICSEARCH_INDEX_PREFIX</span><span class="p">]</span>
<span class="p">[</span><span class="o">--</span><span class="n">elasticsearch</span><span class="o">-</span><span class="n">index</span><span class="o">-</span><span class="n">suffix</span> <span class="n">ELASTICSEARCH_INDEX_SUFFIX</span><span class="p">]</span>
<span class="p">[</span><span class="o">--</span><span class="n">hec</span> <span class="n">HEC</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">token</span> <span class="n">HEC_TOKEN</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">index</span> <span class="n">HEC_INDEX</span><span class="p">]</span>
<span class="p">[</span><span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">skip</span><span class="o">-</span><span class="n">certificate</span><span class="o">-</span><span class="n">verification</span><span class="p">]</span>
<span class="p">[</span><span class="o">-</span><span class="n">K</span> <span class="p">[</span><span class="n">KAFKA_HOSTS</span> <span class="p">[</span><span class="n">KAFKA_HOSTS</span> <span class="o">...</span><span class="p">]]]</span>
<span class="p">[</span><span class="o">--</span><span class="n">kafka</span><span class="o">-</span><span class="n">aggregate</span><span class="o">-</span><span class="n">topic</span> <span class="n">KAFKA_AGGREGATE_TOPIC</span><span class="p">]</span>
<span class="p">[</span><span class="o">--</span><span class="n">kafka</span><span class="o">-</span><span class="n">forensic_topic</span> <span class="n">KAFKA_FORENSIC_TOPIC</span><span class="p">]</span>
<span class="p">[</span><span class="o">--</span><span class="n">save</span><span class="o">-</span><span class="n">aggregate</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">save</span><span class="o">-</span><span class="n">forensic</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">O</span> <span class="n">OUTGOING_HOST</span><span class="p">]</span>
<span class="p">[</span><span class="o">-</span><span class="n">U</span> <span class="n">OUTGOING_USER</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">P</span> <span class="n">OUTGOING_PASSWORD</span><span class="p">]</span>
<span class="p">[</span><span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">port</span> <span class="n">OUTGOING_PORT</span><span class="p">]</span>
<span class="p">[</span><span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">ssl</span> <span class="n">OUTGOING_SSL</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">F</span> <span class="n">OUTGOING_FROM</span><span class="p">]</span>
<span class="p">[</span><span class="o">-</span><span class="n">T</span> <span class="n">OUTGOING_TO</span> <span class="p">[</span><span class="n">OUTGOING_TO</span> <span class="o">...</span><span class="p">]]</span> <span class="p">[</span><span class="o">-</span><span class="n">S</span> <span class="n">OUTGOING_SUBJECT</span><span class="p">]</span>
<span class="p">[</span><span class="o">-</span><span class="n">A</span> <span class="n">OUTGOING_ATTACHMENT</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">M</span> <span class="n">OUTGOING_MESSAGE</span><span class="p">]</span> <span class="p">[</span><span class="o">-</span><span class="n">w</span><span class="p">]</span> <span class="p">[</span><span class="o">--</span><span class="n">test</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">debug</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="p">[</span><span class="n">file_path</span> <span class="o">...</span><span class="p">]]</span>
<span class="n">Parses</span> <span class="n">DMARC</span> <span class="n">reports</span>
<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="ow">or</span> <span class="n">emails</span>
<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">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">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="p">(</span><span class="n">Default</span> <span class="ow">is</span> <span class="n">Cloudflare</span><span class="s1">&#39;s</span>
<span class="n">nameservers</span><span class="p">)</span>
<span class="o">-</span><span class="n">t</span> <span class="n">TIMEOUT</span><span class="p">,</span> <span class="o">--</span><span class="n">timeout</span> <span class="n">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">H</span> <span class="n">HOST</span><span class="p">,</span> <span class="o">--</span><span class="n">host</span> <span class="n">HOST</span> <span class="n">IMAP</span> <span class="n">hostname</span> <span class="ow">or</span> <span class="n">IP</span> <span class="n">address</span>
<span class="o">-</span><span class="n">u</span> <span class="n">USER</span><span class="p">,</span> <span class="o">--</span><span class="n">user</span> <span class="n">USER</span> <span class="n">IMAP</span> <span class="n">user</span>
<span class="o">-</span><span class="n">p</span> <span class="n">PASSWORD</span><span class="p">,</span> <span class="o">--</span><span class="n">password</span> <span class="n">PASSWORD</span>
<span class="n">IMAP</span> <span class="n">password</span>
<span class="o">--</span><span class="n">imap</span><span class="o">-</span><span class="n">port</span> <span class="n">IMAP_PORT</span>
<span class="n">IMAP</span> <span class="n">port</span>
<span class="o">--</span><span class="n">imap</span><span class="o">-</span><span class="n">no</span><span class="o">-</span><span class="n">ssl</span> <span class="n">Do</span> <span class="ow">not</span> <span class="n">use</span> <span class="n">SSL</span><span class="o">/</span><span class="n">TLS</span> <span class="n">when</span> <span class="n">connecting</span> <span class="n">to</span> <span class="n">IMAP</span>
<span class="o">-</span><span class="n">r</span> <span class="n">REPORTS_FOLDER</span><span class="p">,</span> <span class="o">--</span><span class="n">reports</span><span class="o">-</span><span class="n">folder</span> <span class="n">REPORTS_FOLDER</span>
<span class="n">The</span> <span class="n">IMAP</span> <span class="n">folder</span> <span class="n">containing</span> <span class="n">the</span> <span class="n">reports</span> <span class="p">(</span><span class="n">Default</span><span class="p">:</span>
<span class="n">INBOX</span><span class="p">)</span>
<span class="o">-</span><span class="n">a</span> <span class="n">ARCHIVE_FOLDER</span><span class="p">,</span> <span class="o">--</span><span class="n">archive</span><span class="o">-</span><span class="n">folder</span> <span class="n">ARCHIVE_FOLDER</span>
<span class="n">Specifies</span> <span class="n">the</span> <span class="n">IMAP</span> <span class="n">folder</span> <span class="n">to</span> <span class="n">move</span> <span class="n">messages</span> <span class="n">to</span> <span class="n">after</span>
<span class="n">processing</span> <span class="n">them</span> <span class="p">(</span><span class="n">Default</span><span class="p">:</span> <span class="n">Archive</span><span class="p">)</span>
<span class="o">-</span><span class="n">d</span><span class="p">,</span> <span class="o">--</span><span class="n">delete</span> <span class="n">Delete</span> <span class="n">the</span> <span class="n">reports</span> <span class="n">after</span> <span class="n">processing</span> <span class="n">them</span>
<span class="o">-</span><span class="n">E</span> <span class="p">[</span><span class="n">ELASTICSEARCH_HOST</span> <span class="p">[</span><span class="n">ELASTICSEARCH_HOST</span> <span class="o">...</span><span class="p">]],</span> <span class="o">--</span><span class="n">elasticsearch</span><span class="o">-</span><span class="n">host</span> <span class="p">[</span><span class="n">ELASTICSEARCH_HOST</span> <span class="p">[</span><span class="n">ELASTICSEARCH_HOST</span> <span class="o">...</span><span class="p">]]</span>
<span class="n">One</span> <span class="ow">or</span> <span class="n">more</span> <span class="n">Elasticsearch</span> <span class="n">hostnames</span> <span class="ow">or</span> <span class="n">URLs</span> <span class="n">to</span> <span class="n">use</span>
<span class="p">(</span><span class="n">e</span><span class="o">.</span><span class="n">g</span><span class="o">.</span> <span class="n">localhost</span><span class="p">:</span><span class="mi">9200</span><span class="p">)</span>
<span class="o">--</span><span class="n">elasticsearch</span><span class="o">-</span><span class="n">index</span><span class="o">-</span><span class="n">prefix</span> <span class="n">ELASTICSEARCH_INDEX_PREFIX</span>
<span class="n">Prefix</span> <span class="n">to</span> <span class="n">add</span> <span class="ow">in</span> <span class="n">front</span> <span class="n">of</span> <span class="n">the</span> <span class="n">dmarc_aggregate</span> <span class="ow">and</span>
<span class="n">dmarc_forensic</span> <span class="n">Elasticsearch</span> <span class="n">index</span> <span class="n">names</span><span class="p">,</span> <span class="n">joined</span> <span class="n">by</span> <span class="n">_</span>
<span class="o">--</span><span class="n">elasticsearch</span><span class="o">-</span><span class="n">index</span><span class="o">-</span><span class="n">suffix</span> <span class="n">ELASTICSEARCH_INDEX_SUFFIX</span>
<span class="n">Append</span> <span class="n">this</span> <span class="n">suffix</span> <span class="n">to</span> <span class="n">the</span> <span class="n">dmarc_aggregate</span> <span class="ow">and</span>
<span class="n">dmarc_forensic</span> <span class="n">Elasticsearch</span> <span class="n">index</span> <span class="n">names</span><span class="p">,</span> <span class="n">joined</span> <span class="n">by</span> <span class="n">_</span>
<span class="o">--</span><span class="n">hec</span> <span class="n">HEC</span> <span class="n">URL</span> <span class="n">to</span> <span class="n">a</span> <span class="n">Splunk</span> <span class="n">HTTP</span> <span class="n">Event</span> <span class="n">Collector</span> <span class="p">(</span><span class="n">HEC</span><span class="p">)</span>
<span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">token</span> <span class="n">HEC_TOKEN</span>
<span class="n">The</span> <span class="n">authorization</span> <span class="n">token</span> <span class="k">for</span> <span class="n">a</span> <span class="n">Splunk</span> <span class="n">HTTP</span> <span class="n">Event</span>
<span class="n">Collector</span> <span class="p">(</span><span class="n">HEC</span><span class="p">)</span>
<span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">index</span> <span class="n">HEC_INDEX</span>
<span class="n">The</span> <span class="n">index</span> <span class="n">to</span> <span class="n">use</span> <span class="n">when</span> <span class="n">sending</span> <span class="n">events</span> <span class="n">to</span> <span class="n">the</span> <span class="n">Splunk</span>
<span class="n">HTTP</span> <span class="n">Event</span> <span class="n">Collector</span> <span class="p">(</span><span class="n">HEC</span><span class="p">)</span>
<span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">skip</span><span class="o">-</span><span class="n">certificate</span><span class="o">-</span><span class="n">verification</span>
<span class="n">Skip</span> <span class="n">certificate</span> <span class="n">verification</span> <span class="k">for</span> <span class="n">Splunk</span> <span class="n">HEC</span>
<span class="o">-</span><span class="n">K</span> <span class="p">[</span><span class="n">KAFKA_HOSTS</span> <span class="p">[</span><span class="n">KAFKA_HOSTS</span> <span class="o">...</span><span class="p">]],</span> <span class="o">--</span><span class="n">kafka</span><span class="o">-</span><span class="n">hosts</span> <span class="p">[</span><span class="n">KAFKA_HOSTS</span> <span class="p">[</span><span class="n">KAFKA_HOSTS</span> <span class="o">...</span><span class="p">]]</span>
<span class="n">A</span> <span class="nb">list</span> <span class="n">of</span> <span class="n">one</span> <span class="ow">or</span> <span class="n">more</span> <span class="n">Kafka</span> <span class="n">hostnames</span> <span class="ow">or</span> <span class="n">URLs</span>
<span class="o">--</span><span class="n">kafka</span><span class="o">-</span><span class="n">aggregate</span><span class="o">-</span><span class="n">topic</span> <span class="n">KAFKA_AGGREGATE_TOPIC</span>
<span class="n">The</span> <span class="n">Kafka</span> <span class="n">topic</span> <span class="n">to</span> <span class="n">publish</span> <span class="n">aggregate</span> <span class="n">reports</span> <span class="n">to</span>
<span class="p">(</span><span class="n">Default</span><span class="p">:</span> <span class="n">dmarc_aggregate</span><span class="p">)</span>
<span class="o">--</span><span class="n">kafka</span><span class="o">-</span><span class="n">forensic_topic</span> <span class="n">KAFKA_FORENSIC_TOPIC</span>
<span class="n">The</span> <span class="n">Kafka</span> <span class="n">topic</span> <span class="n">to</span> <span class="n">publish</span> <span class="n">forensic</span> <span class="n">reports</span> <span class="n">to</span>
<span class="p">(</span><span class="n">Default</span><span class="p">:</span> <span class="n">dmarc_forensic</span><span class="p">)</span>
<span class="o">--</span><span class="n">save</span><span class="o">-</span><span class="n">aggregate</span> <span class="n">Save</span> <span class="n">aggregate</span> <span class="n">reports</span> <span class="n">to</span> <span class="n">search</span> <span class="n">indexes</span>
<span class="o">--</span><span class="n">save</span><span class="o">-</span><span class="n">forensic</span> <span class="n">Save</span> <span class="n">forensic</span> <span class="n">reports</span> <span class="n">to</span> <span class="n">search</span> <span class="n">indexes</span>
<span class="o">-</span><span class="n">O</span> <span class="n">OUTGOING_HOST</span><span class="p">,</span> <span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">host</span> <span class="n">OUTGOING_HOST</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">using</span> <span class="n">this</span> <span class="n">host</span>
<span class="o">-</span><span class="n">U</span> <span class="n">OUTGOING_USER</span><span class="p">,</span> <span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">user</span> <span class="n">OUTGOING_USER</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">using</span> <span class="n">this</span> <span class="n">user</span>
<span class="o">-</span><span class="n">P</span> <span class="n">OUTGOING_PASSWORD</span><span class="p">,</span> <span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">password</span> <span class="n">OUTGOING_PASSWORD</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">using</span> <span class="n">this</span> <span class="n">password</span>
<span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">port</span> <span class="n">OUTGOING_PORT</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">using</span> <span class="n">this</span> <span class="n">port</span>
<span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">ssl</span> <span class="n">OUTGOING_SSL</span>
<span class="n">Use</span> <span class="n">SSL</span><span class="o">/</span><span class="n">TLS</span> <span class="n">instead</span> <span class="n">of</span> <span class="n">STARTTLS</span> <span class="p">(</span><span class="n">more</span> <span class="n">secure</span><span class="p">,</span> <span class="ow">and</span>
<span class="n">required</span> <span class="n">by</span> <span class="n">some</span> <span class="n">providers</span><span class="p">,</span> <span class="n">like</span> <span class="n">Gmail</span><span class="p">)</span>
<span class="o">-</span><span class="n">F</span> <span class="n">OUTGOING_FROM</span><span class="p">,</span> <span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="kn">from</span> <span class="nn">OUTGOING_FROM</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">using</span> <span class="n">this</span> <span class="kn">from</span> <span class="nn">address</span>
<span class="o">-</span><span class="n">T</span> <span class="n">OUTGOING_TO</span> <span class="p">[</span><span class="n">OUTGOING_TO</span> <span class="o">...</span><span class="p">],</span> <span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">to</span> <span class="n">OUTGOING_TO</span> <span class="p">[</span><span class="n">OUTGOING_TO</span> <span class="o">...</span><span class="p">]</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">to</span> <span class="n">these</span> <span class="n">addresses</span>
<span class="o">-</span><span class="n">S</span> <span class="n">OUTGOING_SUBJECT</span><span class="p">,</span> <span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">subject</span> <span class="n">OUTGOING_SUBJECT</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">using</span> <span class="n">this</span> <span class="n">subject</span>
<span class="o">-</span><span class="n">A</span> <span class="n">OUTGOING_ATTACHMENT</span><span class="p">,</span> <span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">attachment</span> <span class="n">OUTGOING_ATTACHMENT</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">using</span> <span class="n">this</span> <span class="n">filename</span>
<span class="o">-</span><span class="n">M</span> <span class="n">OUTGOING_MESSAGE</span><span class="p">,</span> <span class="o">--</span><span class="n">outgoing</span><span class="o">-</span><span class="n">message</span> <span class="n">OUTGOING_MESSAGE</span>
<span class="n">Email</span> <span class="n">the</span> <span class="n">results</span> <span class="n">using</span> <span class="n">this</span> <span class="n">message</span>
<span class="o">-</span><span class="n">w</span><span class="p">,</span> <span class="o">--</span><span class="n">watch</span> <span class="n">Use</span> <span class="n">an</span> <span class="n">IMAP</span> <span class="n">IDLE</span> <span class="n">connection</span> <span class="n">to</span> <span class="n">process</span> <span class="n">reports</span> <span class="k">as</span> <span class="n">they</span>
<span class="n">arrive</span> <span class="ow">in</span> <span class="n">the</span> <span class="n">inbox</span>
<span class="o">--</span><span class="n">test</span> <span class="n">Do</span> <span class="ow">not</span> <span class="n">move</span> <span class="ow">or</span> <span class="n">delete</span> <span class="n">IMAP</span> <span class="n">messages</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">debug</span> <span class="n">Print</span> <span class="n">debugging</span> <span class="n">information</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">&#39;s version number and exit</span>
</pre></div>
</div>
</div>
<div class="section" id="sample-aggregate-report-output">
<h2>Sample aggregate report output<a class="headerlink" href="#sample-aggregate-report-output" title="Permalink to this headline"></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. Its 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>
<div class="section" id="json">
<h3>JSON<a class="headerlink" href="#json" title="Permalink to this headline"></a></h3>
<div class="highlight-json notranslate"><div class="highlight"><pre><span></span><span class="p">{</span>
<span class="nt">&quot;xml_schema&quot;</span><span class="p">:</span> <span class="s2">&quot;draft&quot;</span><span class="p">,</span>
<span class="nt">&quot;report_metadata&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;org_name&quot;</span><span class="p">:</span> <span class="s2">&quot;acme.com&quot;</span><span class="p">,</span>
<span class="nt">&quot;org_email&quot;</span><span class="p">:</span> <span class="s2">&quot;noreply-dmarc-support@acme.com&quot;</span><span class="p">,</span>
<span class="nt">&quot;org_extra_contact_info&quot;</span><span class="p">:</span> <span class="s2">&quot;http://acme.com/dmarc/support&quot;</span><span class="p">,</span>
<span class="nt">&quot;report_id&quot;</span><span class="p">:</span> <span class="s2">&quot;9391651994964116463&quot;</span><span class="p">,</span>
<span class="nt">&quot;begin_date&quot;</span><span class="p">:</span> <span class="s2">&quot;2012-04-27 20:00:00&quot;</span><span class="p">,</span>
<span class="nt">&quot;end_date&quot;</span><span class="p">:</span> <span class="s2">&quot;2012-04-28 19:59:59&quot;</span><span class="p">,</span>
<span class="nt">&quot;errors&quot;</span><span class="p">:</span> <span class="p">[]</span>
<span class="p">},</span>
<span class="nt">&quot;policy_published&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;domain&quot;</span><span class="p">:</span> <span class="s2">&quot;example.com&quot;</span><span class="p">,</span>
<span class="nt">&quot;adkim&quot;</span><span class="p">:</span> <span class="s2">&quot;r&quot;</span><span class="p">,</span>
<span class="nt">&quot;aspf&quot;</span><span class="p">:</span> <span class="s2">&quot;r&quot;</span><span class="p">,</span>
<span class="nt">&quot;p&quot;</span><span class="p">:</span> <span class="s2">&quot;none&quot;</span><span class="p">,</span>
<span class="nt">&quot;sp&quot;</span><span class="p">:</span> <span class="s2">&quot;none&quot;</span><span class="p">,</span>
<span class="nt">&quot;pct&quot;</span><span class="p">:</span> <span class="s2">&quot;100&quot;</span><span class="p">,</span>
<span class="nt">&quot;fo&quot;</span><span class="p">:</span> <span class="s2">&quot;0&quot;</span>
<span class="p">},</span>
<span class="nt">&quot;records&quot;</span><span class="p">:</span> <span class="p">[</span>
<span class="p">{</span>
<span class="nt">&quot;source&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;ip_address&quot;</span><span class="p">:</span> <span class="s2">&quot;72.150.241.94&quot;</span><span class="p">,</span>
<span class="nt">&quot;country&quot;</span><span class="p">:</span> <span class="s2">&quot;US&quot;</span><span class="p">,</span>
<span class="nt">&quot;reverse_dns&quot;</span><span class="p">:</span> <span class="s2">&quot;adsl-72-150-241-94.shv.bellsouth.net&quot;</span><span class="p">,</span>
<span class="nt">&quot;base_domain&quot;</span><span class="p">:</span> <span class="s2">&quot;bellsouth.net&quot;</span>
<span class="p">},</span>
<span class="nt">&quot;count&quot;</span><span class="p">:</span> <span class="mi">2</span><span class="p">,</span>
<span class="nt">&quot;alignment&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;spf&quot;</span><span class="p">:</span> <span class="kc">true</span><span class="p">,</span>
<span class="nt">&quot;dkim&quot;</span><span class="p">:</span> <span class="kc">false</span><span class="p">,</span>
<span class="nt">&quot;dmarc&quot;</span><span class="p">:</span> <span class="kc">true</span>
<span class="p">},</span>
<span class="nt">&quot;policy_evaluated&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;disposition&quot;</span><span class="p">:</span> <span class="s2">&quot;none&quot;</span><span class="p">,</span>
<span class="nt">&quot;dkim&quot;</span><span class="p">:</span> <span class="s2">&quot;fail&quot;</span><span class="p">,</span>
<span class="nt">&quot;spf&quot;</span><span class="p">:</span> <span class="s2">&quot;pass&quot;</span><span class="p">,</span>
<span class="nt">&quot;policy_override_reasons&quot;</span><span class="p">:</span> <span class="p">[]</span>
<span class="p">},</span>
<span class="nt">&quot;identifiers&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;header_from&quot;</span><span class="p">:</span> <span class="s2">&quot;example.com&quot;</span><span class="p">,</span>
<span class="nt">&quot;envelope_from&quot;</span><span class="p">:</span> <span class="s2">&quot;example.com&quot;</span><span class="p">,</span>
<span class="nt">&quot;envelope_to&quot;</span><span class="p">:</span> <span class="kc">null</span>
<span class="p">},</span>
<span class="nt">&quot;auth_results&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;dkim&quot;</span><span class="p">:</span> <span class="p">[</span>
<span class="p">{</span>
<span class="nt">&quot;domain&quot;</span><span class="p">:</span> <span class="s2">&quot;example.com&quot;</span><span class="p">,</span>
<span class="nt">&quot;selector&quot;</span><span class="p">:</span> <span class="s2">&quot;none&quot;</span><span class="p">,</span>
<span class="nt">&quot;result&quot;</span><span class="p">:</span> <span class="s2">&quot;fail&quot;</span>
<span class="p">}</span>
<span class="p">],</span>
<span class="nt">&quot;spf&quot;</span><span class="p">:</span> <span class="p">[</span>
<span class="p">{</span>
<span class="nt">&quot;domain&quot;</span><span class="p">:</span> <span class="s2">&quot;example.com&quot;</span><span class="p">,</span>
<span class="nt">&quot;scope&quot;</span><span class="p">:</span> <span class="s2">&quot;mfrom&quot;</span><span class="p">,</span>
<span class="nt">&quot;result&quot;</span><span class="p">:</span> <span class="s2">&quot;pass&quot;</span>
<span class="p">}</span>
<span class="p">]</span>
<span class="p">}</span>
<span class="p">}</span>
<span class="p">]</span>
<span class="p">}</span>
</pre></div>
</div>
</div>
<div class="section" id="csv">
<h3>CSV<a class="headerlink" href="#csv" title="Permalink to this headline"></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">disposition</span><span class="p">,</span><span class="n">dkim_alignment</span><span class="p">,</span><span class="n">spf_alignment</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</span><span class="o">.</span><span class="mf">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="n">none</span><span class="p">,</span><span class="n">fail</span><span class="p">,</span><span class="k">pass</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>
</pre></div>
</div>
</div>
</div>
<div class="section" id="sample-forensic-report-output">
<h2>Sample forensic report output<a class="headerlink" href="#sample-forensic-report-output" title="Permalink to this headline"></a></h2>
<p>Thanks to Github user <a class="reference external" href="https://github.com/xennn">xennn</a> for the anonymized
<a class="reference external" href="https://github.com/domainaware/parsedmarc/raw/master/samples/forensic/DMARC%20Failure%20Report%20for%20domain.de%20(mail-from%3Dsharepoint%40domain.de%2C%20ip%3D10.10.10.10).eml">forensic report email sample</a>.</p>
<div class="section" id="id1">
<h3>JSON<a class="headerlink" href="#id1" title="Permalink to this headline"></a></h3>
<div class="highlight-json notranslate"><div class="highlight"><pre><span></span><span class="p">{</span>
<span class="nt">&quot;feedback_type&quot;</span><span class="p">:</span> <span class="s2">&quot;auth-failure&quot;</span><span class="p">,</span>
<span class="nt">&quot;user_agent&quot;</span><span class="p">:</span> <span class="s2">&quot;Lua/1.0&quot;</span><span class="p">,</span>
<span class="nt">&quot;version&quot;</span><span class="p">:</span> <span class="s2">&quot;1.0&quot;</span><span class="p">,</span>
<span class="nt">&quot;original_mail_from&quot;</span><span class="p">:</span> <span class="s2">&quot;sharepoint@domain.de&quot;</span><span class="p">,</span>
<span class="nt">&quot;original_rcpt_to&quot;</span><span class="p">:</span> <span class="s2">&quot;peter.pan@domain.de&quot;</span><span class="p">,</span>
<span class="nt">&quot;arrival_date&quot;</span><span class="p">:</span> <span class="s2">&quot;Mon, 01 Oct 2018 11:20:27 +0200&quot;</span><span class="p">,</span>
<span class="nt">&quot;message_id&quot;</span><span class="p">:</span> <span class="s2">&quot;&lt;38.E7.30937.BD6E1BB5@ mailrelay.de&gt;&quot;</span><span class="p">,</span>
<span class="nt">&quot;authentication_results&quot;</span><span class="p">:</span> <span class="s2">&quot;dmarc=fail (p=none, dis=none) header.from=domain.de&quot;</span><span class="p">,</span>
<span class="nt">&quot;delivery_result&quot;</span><span class="p">:</span> <span class="s2">&quot;smg-policy-action&quot;</span><span class="p">,</span>
<span class="nt">&quot;auth_failure&quot;</span><span class="p">:</span> <span class="p">[</span>
<span class="s2">&quot;dmarc&quot;</span>
<span class="p">],</span>
<span class="nt">&quot;reported_domain&quot;</span><span class="p">:</span> <span class="s2">&quot;domain.de&quot;</span><span class="p">,</span>
<span class="nt">&quot;arrival_date_utc&quot;</span><span class="p">:</span> <span class="s2">&quot;2018-10-01 09:20:27&quot;</span><span class="p">,</span>
<span class="nt">&quot;source&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;ip_address&quot;</span><span class="p">:</span> <span class="s2">&quot;10.10.10.10&quot;</span><span class="p">,</span>
<span class="nt">&quot;country&quot;</span><span class="p">:</span> <span class="kc">null</span><span class="p">,</span>
<span class="nt">&quot;reverse_dns&quot;</span><span class="p">:</span> <span class="kc">null</span><span class="p">,</span>
<span class="nt">&quot;base_domain&quot;</span><span class="p">:</span> <span class="kc">null</span>
<span class="p">},</span>
<span class="nt">&quot;authentication_mechanisms&quot;</span><span class="p">:</span> <span class="p">[],</span>
<span class="nt">&quot;original_envelope_id&quot;</span><span class="p">:</span> <span class="kc">null</span><span class="p">,</span>
<span class="nt">&quot;dkim_domain&quot;</span><span class="p">:</span> <span class="kc">null</span><span class="p">,</span>
<span class="nt">&quot;sample_headers_only&quot;</span><span class="p">:</span> <span class="kc">false</span><span class="p">,</span>
<span class="nt">&quot;sample&quot;</span><span class="p">:</span> <span class="s2">&quot;Content-Type: message/rfc822\nContent-Disposition: inline\nReceived: from Servernameone.domain.local (Servernameone.domain.local [10.10.10.10])\n by mailrelay.de (mail.DOMAIN.de) with SMTP id 38.E7.30937.BD6E1BB5; Mon, 1 Oct 2018 11:20:27 +0200 (CEST)\nDate: 01 Oct 2018 11:20:27 +0200\nMessage-ID: &lt;38.E7.30937.BD6E1BB5@ mailrelay.de&gt;\nTo: &lt;peter.pan@domain.de&gt;\nfrom: \&quot;=?utf-8?B?SW50ZXJha3RpdmUgV2V0dGJld2VyYmVyLcOcYmVyc2ljaHQ=?=\&quot; &lt;sharepoint@domain.de&gt;\nSubject: Subject\nMIME-Version: 1.0\nX-Mailer: Microsoft SharePoint Foundation 2010\nContent-Type: text/html; charset=utf-8\nContent-Transfer-Encoding: quoted-printable\n\n\n&lt;html&gt;&lt;head&gt;&lt;base href=3D&#39;\nwettbewerb&#39; /&gt;&lt;/head&gt;&lt;body&gt;&lt;!DOCTYPE HTML PUBLIC \&quot;-//W3C//DTD HTML 3.2//EN\&quot;=\n&gt;&lt;HTML&gt;&lt;HEAD&gt;&lt;META NAME=3D\&quot;Generator\&quot; CONTENT=3D\&quot;MS Exchange Server version=\n 08.01.0240.003\&quot;&gt;&lt;/html&gt;\n &quot;</span><span class="p">,</span>
<span class="nt">&quot;parsed_sample&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;content-transfer-encoding&quot;</span><span class="p">:</span> <span class="s2">&quot;quoted-printable&quot;</span><span class="p">,</span>
<span class="nt">&quot;x-mailer&quot;</span><span class="p">:</span> <span class="s2">&quot;Microsoft SharePoint Foundation 2010&quot;</span><span class="p">,</span>
<span class="nt">&quot;message-id&quot;</span><span class="p">:</span> <span class="s2">&quot;&lt;38.E7.30937.BD6E1BB5@ mailrelay.de&gt;&quot;</span><span class="p">,</span>
<span class="nt">&quot;body&quot;</span><span class="p">:</span> <span class="s2">&quot;&lt;html&gt;&lt;head&gt;&lt;base href=3D&#39;\nwettbewerb&#39; /&gt;&lt;/head&gt;&lt;body&gt;&lt;!DOCTYPE HTML PUBLIC \&quot;-//W3C//DTD HTML 3.2//EN\&quot;=\n&gt;&lt;HTML&gt;&lt;HEAD&gt;&lt;META NAME=3D\&quot;Generator\&quot; CONTENT=3D\&quot;MS Exchange Server version=\n 08.01.0240.003\&quot;&gt;&lt;/html&gt;&quot;</span><span class="p">,</span>
<span class="nt">&quot;to&quot;</span><span class="p">:</span> <span class="p">[</span>
<span class="p">{</span>
<span class="nt">&quot;display_name&quot;</span><span class="p">:</span> <span class="kc">null</span><span class="p">,</span>
<span class="nt">&quot;address&quot;</span><span class="p">:</span> <span class="s2">&quot;peter.pan@domain.de&quot;</span><span class="p">,</span>
<span class="nt">&quot;local&quot;</span><span class="p">:</span> <span class="s2">&quot;peter.pan&quot;</span><span class="p">,</span>
<span class="nt">&quot;domain&quot;</span><span class="p">:</span> <span class="s2">&quot;domain.de&quot;</span>
<span class="p">}</span>
<span class="p">],</span>
<span class="nt">&quot;date&quot;</span><span class="p">:</span> <span class="s2">&quot;2018-10-01 09:20:27&quot;</span><span class="p">,</span>
<span class="nt">&quot;to_domains&quot;</span><span class="p">:</span> <span class="p">[</span>
<span class="s2">&quot;domain.de&quot;</span>
<span class="p">],</span>
<span class="nt">&quot;received&quot;</span><span class="p">:</span> <span class="p">[</span>
<span class="p">{</span>
<span class="nt">&quot;from&quot;</span><span class="p">:</span> <span class="s2">&quot;Servernameone.domain.local Servernameone.domain.local 10.10.10.10&quot;</span><span class="p">,</span>
<span class="nt">&quot;by&quot;</span><span class="p">:</span> <span class="s2">&quot;mailrelay.de mail.DOMAIN.de&quot;</span><span class="p">,</span>
<span class="nt">&quot;with&quot;</span><span class="p">:</span> <span class="s2">&quot;SMTP id 38.E7.30937.BD6E1BB5&quot;</span><span class="p">,</span>
<span class="nt">&quot;date&quot;</span><span class="p">:</span> <span class="s2">&quot;Mon, 1 Oct 2018 11:20:27 +0200 CEST&quot;</span><span class="p">,</span>
<span class="nt">&quot;hop&quot;</span><span class="p">:</span> <span class="mi">1</span><span class="p">,</span>
<span class="nt">&quot;date_utc&quot;</span><span class="p">:</span> <span class="s2">&quot;2018-10-01 09:20:27&quot;</span><span class="p">,</span>
<span class="nt">&quot;delay&quot;</span><span class="p">:</span> <span class="mi">0</span>
<span class="p">}</span>
<span class="p">],</span>
<span class="nt">&quot;content-disposition&quot;</span><span class="p">:</span> <span class="s2">&quot;inline&quot;</span><span class="p">,</span>
<span class="nt">&quot;mime-version&quot;</span><span class="p">:</span> <span class="s2">&quot;1.0&quot;</span><span class="p">,</span>
<span class="nt">&quot;subject&quot;</span><span class="p">:</span> <span class="s2">&quot;Subject&quot;</span><span class="p">,</span>
<span class="nt">&quot;timezone&quot;</span><span class="p">:</span> <span class="s2">&quot;+2&quot;</span><span class="p">,</span>
<span class="nt">&quot;from&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;display_name&quot;</span><span class="p">:</span> <span class="s2">&quot;Interaktive Wettbewerber-Übersicht&quot;</span><span class="p">,</span>
<span class="nt">&quot;address&quot;</span><span class="p">:</span> <span class="s2">&quot;sharepoint@domain.de&quot;</span><span class="p">,</span>
<span class="nt">&quot;local&quot;</span><span class="p">:</span> <span class="s2">&quot;sharepoint&quot;</span><span class="p">,</span>
<span class="nt">&quot;domain&quot;</span><span class="p">:</span> <span class="s2">&quot;domain.de&quot;</span>
<span class="p">},</span>
<span class="nt">&quot;content-type&quot;</span><span class="p">:</span> <span class="s2">&quot;message/rfc822&quot;</span><span class="p">,</span>
<span class="nt">&quot;has_defects&quot;</span><span class="p">:</span> <span class="kc">false</span><span class="p">,</span>
<span class="nt">&quot;headers&quot;</span><span class="p">:</span> <span class="p">{</span>
<span class="nt">&quot;Content-Type&quot;</span><span class="p">:</span> <span class="s2">&quot;text/html; charset=utf-8&quot;</span><span class="p">,</span>
<span class="nt">&quot;Content-Disposition&quot;</span><span class="p">:</span> <span class="s2">&quot;inline&quot;</span><span class="p">,</span>
<span class="nt">&quot;Received&quot;</span><span class="p">:</span> <span class="s2">&quot;from Servernameone.domain.local (Servernameone.domain.local [10.10.10.10])\n by mailrelay.de (mail.DOMAIN.de) with SMTP id 38.E7.30937.BD6E1BB5; Mon, 1 Oct 2018 11:20:27 +0200 (CEST)&quot;</span><span class="p">,</span>
<span class="nt">&quot;Date&quot;</span><span class="p">:</span> <span class="s2">&quot;01 Oct 2018 11:20:27 +0200&quot;</span><span class="p">,</span>
<span class="nt">&quot;Message-ID&quot;</span><span class="p">:</span> <span class="s2">&quot;&lt;38.E7.30937.BD6E1BB5@ mailrelay.de&gt;&quot;</span><span class="p">,</span>
<span class="nt">&quot;To&quot;</span><span class="p">:</span> <span class="s2">&quot;&lt;peter.pan@domain.de&gt;&quot;</span><span class="p">,</span>
<span class="nt">&quot;from&quot;</span><span class="p">:</span> <span class="s2">&quot;\&quot;Interaktive Wettbewerber-Übersicht\&quot; &lt;sharepoint@domain.de&gt;&quot;</span><span class="p">,</span>
<span class="nt">&quot;Subject&quot;</span><span class="p">:</span> <span class="s2">&quot;Subject&quot;</span><span class="p">,</span>
<span class="nt">&quot;MIME-Version&quot;</span><span class="p">:</span> <span class="s2">&quot;1.0&quot;</span><span class="p">,</span>
<span class="nt">&quot;X-Mailer&quot;</span><span class="p">:</span> <span class="s2">&quot;Microsoft SharePoint Foundation 2010&quot;</span><span class="p">,</span>
<span class="nt">&quot;Content-Transfer-Encoding&quot;</span><span class="p">:</span> <span class="s2">&quot;quoted-printable&quot;</span>
<span class="p">},</span>
<span class="nt">&quot;reply_to&quot;</span><span class="p">:</span> <span class="p">[],</span>
<span class="nt">&quot;cc&quot;</span><span class="p">:</span> <span class="p">[],</span>
<span class="nt">&quot;bcc&quot;</span><span class="p">:</span> <span class="p">[],</span>
<span class="nt">&quot;attachments&quot;</span><span class="p">:</span> <span class="p">[],</span>
<span class="nt">&quot;filename_safe_subject&quot;</span><span class="p">:</span> <span class="s2">&quot;Subject&quot;</span>
<span class="p">}</span>
<span class="p">}</span>
</pre></div>
</div>
</div>
<div class="section" id="id2">
<h3>CSV<a class="headerlink" href="#id2" title="Permalink to this headline"></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">&quot;Mon, 01 Oct 2018 11:20:27 +0200&quot;</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">&lt;</span><span class="mf">38.E7</span><span class="o">.</span><span class="mf">30937.</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">&gt;</span><span class="p">,</span><span class="s2">&quot;dmarc=fail (p=none, dis=none) header.from=domain.de&quot;</span><span class="p">,,</span><span class="mf">10.10</span><span class="o">.</span><span class="mf">10.10</span><span class="p">,,,,</span><span class="n">smg</span><span class="o">-</span><span class="n">policy</span><span class="o">-</span><span class="n">action</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>
</pre></div>
</div>
</div>
</div>
<div class="section" id="bug-reports">
<h2>Bug reports<a class="headerlink" href="#bug-reports" title="Permalink to this headline"></a></h2>
<p>Please report bugs on the GitHub issue tracker</p>
<p><a class="reference external" href="https://github.com/domainaware/parsedmarc/issues">https://github.com/domainaware/parsedmarc/issues</a></p>
</div>
<div class="section" id="installation">
<h2>Installation<a class="headerlink" href="#installation" title="Permalink to this headline"></a></h2>
<p><code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> works with Python 3 only.</p>
<p>On Debian or Ubuntu systems, run:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo apt-get install python3-pip
</pre></div>
</div>
<p>Python 3 installers for Windows and macOS can be found at
<a class="reference external" href="https://www.python.org/downloads/">https://www.python.org/downloads/</a></p>
<p>To install or upgrade to the latest stable release of <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> on
macOS or Linux, run</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo -H pip3 install -U parsedmarc
</pre></div>
</div>
<p>Or, install the latest development release directly from GitHub:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo -H pip3 install -U git+https://github.com/domainaware/parsedmarc.git
</pre></div>
</div>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">On Windows, <code class="docutils literal notranslate"><span class="pre">pip3</span></code> is <code class="docutils literal notranslate"><span class="pre">pip</span></code>, even with Python 3. So on Windows,
substitute <code class="docutils literal notranslate"><span class="pre">pip</span></code> as an administrator in place of <code class="docutils literal notranslate"><span class="pre">sudo</span> <span class="pre">pip3</span></code>, in the
above commands.</p>
</div>
<div class="section" id="installation-using-pypy3">
<h3>Installation using pypy3<a class="headerlink" href="#installation-using-pypy3" title="Permalink to this headline"></a></h3>
<p>For the best possible processing speed, consider using <cite>parsedmarc</cite> inside a <code class="docutils literal notranslate"><span class="pre">pypy3</span></code>
virtualenv. First, <a class="reference external" href="https://pypy.org/download.html#default-with-a-jit-compiler">download the latest version of pypy3</a>. Extract it to
<code class="docutils literal notranslate"><span class="pre">/opt/pypy3</span></code> (<code class="docutils literal notranslate"><span class="pre">sudo</span> <span class="pre">mkdir</span> <span class="pre">/opt</span></code> if <code class="docutils literal notranslate"><span class="pre">/opt</span></code> does not exist), then create a
symlink:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo ln -s /opt/pypy3/bin/pypy3 /usr/local/bin/pypy3
</pre></div>
</div>
<p>Install <code class="docutils literal notranslate"><span class="pre">virtualenv</span></code> on your system:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo apt-get install python3-pip
$ sudo -H pip3 install -U virtualenv
</pre></div>
</div>
<p>Uninstall any instance of <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> that you may have installed globally</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo -H pip3 uninstall -y parsedmarc
</pre></div>
</div>
<p>Next, create a <code class="docutils literal notranslate"><span class="pre">pypy3</span></code> virtualenv for parsedmarc</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo mkdir /opt/venvs
$ <span class="nb">cd</span> /opt/venvs
$ sudo -H pip3 install -U virtualenv
$ sudo virtualenv --download -p /usr/local/bin/pypy3 parsedmarc
$ sudo -H /opt/venvs/parsedmarc/bin/pip3 install -U parsedmarc
$ sudo ln -s /opt/venvs/parsedmarc/bin/parsedmarc /usr/local/bin/parsedmarc
</pre></div>
</div>
<p>To upgrade <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> inside the virtualenv, run:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo -H /opt/venvs/parsedmarc/bin/pip3 install -U parsedmarc
</pre></div>
</div>
<p>Or, install the latest development release directly from GitHub:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo -H /opt/venvs/parsedmarc/bin/pip3 install -U git+https://github.com/domainaware/parsedmarc.git
</pre></div>
</div>
</div>
<div class="section" id="optional-dependencies">
<h3>Optional dependencies<a class="headerlink" href="#optional-dependencies" title="Permalink to this headline"></a></h3>
<p>If you would like to be able to parse emails saved from Microsoft Outlook
(i.e. OLE .msg files), install <code class="docutils literal notranslate"><span class="pre">msgconvert</span></code>:</p>
<p>On Debian or Ubuntu systems, run:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>$ sudo apt-get install libemail-outlook-message-perl
</pre></div>
</div>
</div>
<div class="section" id="dns-performance">
<h3>DNS performance<a class="headerlink" href="#dns-performance" title="Permalink to this headline"></a></h3>
<p>You can often improve performance by providing one or more local nameservers
to the CLI or function calls, as long as those nameservers return the same
records as the public DNS.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p>If you do not specify any nameservers, Cloudflares public nameservers are
used by default, <strong>not the systems default nameservers</strong>.</p>
<p class="last">This is done to avoid a situation where records in a local nameserver do
not match records in the public DNS.</p>
</div>
</div>
<div class="section" id="testing-multiple-report-analyzers">
<h3>Testing multiple report analyzers<a class="headerlink" href="#testing-multiple-report-analyzers" title="Permalink to this headline"></a></h3>
<p>If you would like to test parsedmarc and another report processing solution
at the same time, you can have up to two mailto URIs each in the rua and ruf
tags in your DMARC record, separated by commas.</p>
</div>
<div class="section" id="elasticsearch-and-kibana">
<h3>Elasticsearch and Kibana<a class="headerlink" href="#elasticsearch-and-kibana" title="Permalink to this headline"></a></h3>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">Splunk is also supported starting with <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> 4.3.0</p>
</div>
<p>To set up visual dashboards of DMARC data, install Elasticsearch and Kibana.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">Elasticsearch and Kibana 6 or later are required</p>
</div>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo apt-get install -y openjdk-8-jre apt-transport-https
wget -qO - https://artifacts.elastic.co/GPG-KEY-elasticsearch <span class="p">|</span> sudo apt-key add -
<span class="nb">echo</span> <span class="s2">&quot;deb https://artifacts.elastic.co/packages/6.x/apt stable main&quot;</span> <span class="p">|</span> sudo tee -a /etc/apt/sources.list.d/elastic-6.x.list
sudo apt-get update
sudo apt-get install -y default-jre-headless elasticsearch kibana
sudo systemctl daemon-reload
sudo systemctl <span class="nb">enable</span> elasticsearch.service
sudo systemctl <span class="nb">enable</span> kibana.service
sudo service start elasticsearch
sudo service start kibana
</pre></div>
</div>
<p>Without the commercial <a class="reference external" href="https://www.elastic.co/products/x-pack">X-Pack</a>, 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
</pre></div>
</div>
<p>Create a directory to store the certificates and keys:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>mkdir ~/ssl
<span class="nb">cd</span> ~/ssl
</pre></div>
</div>
<p>To create a self-signed certificate, run:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>openssl req -x509 -nodes -days <span class="m">365</span> -newkey rsa:4096 -keyout kibana.key -out kibana.crt
</pre></div>
</div>
<p>Or, to create a Certificate Signing Request (CSR) for a CA, run:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>openssl req -newkey rsa:4096-nodes -keyout kibana.key -out kibana.csr
</pre></div>
</div>
<p>Fill in the prompts. Watch out for Common Name (e.g. server FQDN or YOUR
domain name), which is the IP address or domain name that you will be hosting
Kibana on. it is the most important field.</p>
<p>If you generated a CSR, remove the CSR after you have your certs</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>rm -f kibana.csr
</pre></div>
</div>
<p>Move the keys into place and secure them:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span><span class="nb">cd</span>
sudo mv ssl /etc/nginx
sudo chown -R root:www-data /etc/nginx/ssl
sudo chmod -R <span class="nv">u</span><span class="o">=</span>rX,g<span class="o">=</span>rX,o<span class="o">=</span> /etc/nginx/ssl
</pre></div>
</div>
<p>Disable the default nginx configuration:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo rm /etc/nginx/sites-enabled/default
</pre></div>
</div>
<p>Create the web server configuration</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo nano /etc/nginx/sites-available/kibana
</pre></div>
</div>
<div class="highlight-nginx notranslate"><div class="highlight"><pre><span></span><span class="k">server</span> <span class="p">{</span>
<span class="kn">listen</span> <span class="mi">443</span> <span class="s">ssl</span> <span class="s">http2</span><span class="p">;</span>
<span class="kn">ssl_certificate</span> <span class="s">/etc/nginx/ssl/kibana.crt</span><span class="p">;</span>
<span class="kn">ssl_certificate_key</span> <span class="s">/etc/nginx/ssl/kibana.key</span><span class="p">;</span>
<span class="kn">ssl_session_timeout</span> <span class="s">1d</span><span class="p">;</span>
<span class="kn">ssl_session_cache</span> <span class="s">shared:SSL:50m</span><span class="p">;</span>
<span class="kn">ssl_session_tickets</span> <span class="no">off</span><span class="p">;</span>
<span class="c1"># modern configuration. tweak to your needs.</span>
<span class="kn">ssl_protocols</span> <span class="s">TLSv1.2</span><span class="p">;</span>
<span class="kn">ssl_ciphers</span> <span class="s">&#39;ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256&#39;</span><span class="p">;</span>
<span class="kn">ssl_prefer_server_ciphers</span> <span class="no">on</span><span class="p">;</span>
<span class="c1"># Uncomment this next line if you are using a signed, trusted cert</span>
<span class="c1">#add_header Strict-Transport-Security &quot;max-age=63072000; includeSubdomains; preload&quot;;</span>
<span class="kn">add_header</span> <span class="s">X-Frame-Options</span> <span class="s">SAMEORIGIN</span><span class="p">;</span>
<span class="kn">add_header</span> <span class="s">X-Content-Type-Options</span> <span class="s">nosniff</span><span class="p">;</span>
<span class="kn">auth_basic</span> <span class="s">&quot;Login</span> <span class="s">required&quot;</span><span class="p">;</span>
<span class="kn">auth_basic_user_file</span> <span class="s">/etc/nginx/htpasswd</span><span class="p">;</span>
<span class="kn">location</span> <span class="s">/</span> <span class="p">{</span>
<span class="kn">proxy_pass</span> <span class="s">http://127.0.0.1:5601</span><span class="p">;</span>
<span class="kn">proxy_set_header</span> <span class="s">Host</span> <span class="nv">$host</span><span class="p">;</span>
<span class="kn">proxy_set_header</span> <span class="s">X-Real-IP</span> <span class="nv">$remote_addr</span><span class="p">;</span>
<span class="kn">proxy_set_header</span> <span class="s">X-Forwarded-For</span> <span class="nv">$proxy_add_x_forwarded_for</span><span class="p">;</span>
<span class="p">}</span>
<span class="p">}</span>
<span class="k">server</span> <span class="p">{</span>
<span class="kn">listen</span> <span class="mi">80</span><span class="p">;</span>
<span class="kn">return</span> <span class="mi">301</span> <span class="s">https://</span><span class="nv">$host$request_uri</span><span class="p">;</span>
<span class="p">}</span>
</pre></div>
</div>
<p>Enable the nginx configuration for Kibana:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo ln -s /etc/nginx/sites-available/kibana /etc/nginx/sites-enabled/kibana
</pre></div>
</div>
<p>Add a user to basic authentication:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo htpasswd -c /etc/nginx/htpasswd exampleuser
</pre></div>
</div>
<p>Where <code class="docutils literal notranslate"><span class="pre">exampleuser</span></code> is the name of the user you want to add.</p>
<p>Secure the permissions of the httpasswd file:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo chown root:www-data /etc/nginx/htpasswd
sudo chmod <span class="nv">u</span><span class="o">=</span>rw,g<span class="o">=</span>r,o<span class="o">=</span> /etc/nginx/htpasswd
</pre></div>
</div>
<p>Restart nginx:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo service nginx restart
</pre></div>
</div>
<p>Now that Elasticsearch is up and running, use <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> to send data to
it.</p>
<p>Om the same system as Elasticsearch, pass <code class="docutils literal notranslate"><span class="pre">--save-aggregate</span></code> and/or
<code class="docutils literal notranslate"><span class="pre">--save-forensic</span></code> to <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> save the results in Elasticsearch.</p>
<div class="admonition warning">
<p class="first admonition-title">Warning</p>
<blockquote>
<div><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>
</div></blockquote>
<p class="last">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> <span class="pre">--save-forensic</span></code> manually on a
separate IMAP folder (using the <code class="docutils literal notranslate"><span class="pre">-r</span></code> option), after you have manually
moved known samples you want to save to that folder (e.g. malicious
samples non-sensitive legitimate samples).</p>
</div>
<p>When you first visit Kibana, it will prompt you to create an index pattern.
Start by creating the index pattern <code class="docutils literal notranslate"><span class="pre">dmarc_aggregate</span></code> (without an <code class="docutils literal notranslate"><span class="pre">*</span></code>),
and select <code class="docutils literal notranslate"><span class="pre">date_range</span></code> as the time field. Once the <code class="docutils literal notranslate"><span class="pre">dmarc_aggregate</span></code>
index pattern <code class="docutils literal notranslate"><span class="pre">dmarc_aggregate</span></code> has been saved, create a <code class="docutils literal notranslate"><span class="pre">dmarc_forensic</span></code>
index pattern, with <code class="docutils literal notranslate"><span class="pre">arrival_date</span></code> as the time field.</p>
<a class="reference external image-reference" href="_static/screenshots/define-dmarc-aggregate.png"><img alt="A screenshot of defining the dmarc_aggregate index pattern" class="align-center" src="_images/define-dmarc-aggregate.png" /></a>
<a class="reference external image-reference" href="_static/screenshots/dmarc-aggregate-time-field.png"><img alt="A screenshot of setting the time field for the dmarc_aggregate index pattern" class="align-center" src="_images/dmarc-aggregate-time-field.png" /></a>
<a class="reference external image-reference" href="_static/screenshots/define-dmarc-forensic.png"><img alt="A screenshot of defining the dmarc_forensic index pattern" class="align-center" src="_images/define-dmarc-forensic.png" /></a>
<a class="reference external image-reference" href="_static/screenshots/dmarc-forensic-time-field.png"><img alt="A screenshot of setting the time field for the dmarc_forensic index pattern" class="align-center" src="_images/dmarc-forensic-time-field.png" /></a>
<p>Once the index patterns have been created, you can import the dashboards.</p>
<p>Download (right click the link and click save as) <a class="reference external" href="https://raw.githubusercontent.com/domainaware/parsedmarc/master/kibana/kibana_saved_objects.json">kibana_saved_objects.json</a>.</p>
<p>Import <code class="docutils literal notranslate"><span class="pre">kibana_saved_objects.json</span></code> the Saved Objects tab of the management
page of Kibana.</p>
<p>It will give you the option to overwrite existing saved dashboards or
visualizations, which could be used to restore them if you or someone else
breaks them, as there are no permissions/access controls in Kibana without
the commercial <a class="reference external" href="https://www.elastic.co/products/x-pack">X-Pack</a>.</p>
<a class="reference external image-reference" href="_static/screenshots/saved-objects.png"><img alt="A screenshot of setting the Saved Objects management UI in Kibana" class="align-center" src="_images/saved-objects.png" /></a>
<a class="reference external image-reference" href="_static/screenshots/confirm-overwrite.png"><img alt="A screenshot of the overwrite conformation prompt" class="align-center" src="_images/confirm-overwrite.png" /></a>
<p>Kibana will then ask you to match the newly imported objects to your index
patterns. Select <code class="docutils literal notranslate"><span class="pre">dmarc_forensic</span></code> for the set of forensic objects, and
select <code class="docutils literal notranslate"><span class="pre">dmarc_aggregate</span></code> for the other saved objects, as shown below.</p>
<a class="reference external image-reference" href="_static/screenshots/index-pattern-conflicts.png"><img alt="A screenshot showing how to resolve index pattern conflicts after importing saved objects" class="align-center" src="_images/index-pattern-conflicts.png" /></a>
<div class="section" id="records-retention">
<h4>Records retention<a class="headerlink" href="#records-retention" title="Permalink to this headline"></a></h4>
<p>To prevent your indexes from growing too large, or to comply with records
retention regulations such as GDPR, you need to use <a class="reference external" href="https://www.elastic.co/blog/managing-time-based-indices-efficiently">time-based indexes</a>.</p>
</div>
</div>
<div class="section" id="splunk">
<h3>Splunk<a class="headerlink" href="#splunk" title="Permalink to this headline"></a></h3>
<p>Starting in version 4.3.0 <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> supports sending aggregate and/or
forensic DMARC data to a Splunk <a class="reference external" href="http://docs.splunk.com/Documentation/Splunk/latest/Data/AboutHEC">HTTP Event collector (HEC)</a>. Simply use the
following command line options, along with <code class="docutils literal notranslate"><span class="pre">--save-aggregate</span></code> and/or
<code class="docutils literal notranslate"><span class="pre">--save-forensic</span></code>:</p>
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="o">--</span><span class="n">hec</span> <span class="n">HEC</span> <span class="n">URL</span> <span class="n">to</span> <span class="n">a</span> <span class="n">Splunk</span> <span class="n">HTTP</span> <span class="n">Event</span> <span class="n">Collector</span> <span class="p">(</span><span class="n">HEC</span><span class="p">)</span>
<span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">token</span> <span class="n">HEC_TOKEN</span>
<span class="n">The</span> <span class="n">authorization</span> <span class="n">token</span> <span class="k">for</span> <span class="n">a</span> <span class="n">Splunk</span> <span class="n">HTTP</span> <span class="n">Event</span>
<span class="n">Collector</span> <span class="p">(</span><span class="n">HEC</span><span class="p">)</span>
<span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">index</span> <span class="n">HEC_INDEX</span>
<span class="n">The</span> <span class="n">index</span> <span class="n">to</span> <span class="n">use</span> <span class="n">when</span> <span class="n">sending</span> <span class="n">events</span> <span class="n">to</span> <span class="n">the</span> <span class="n">Splunk</span>
<span class="n">HTTP</span> <span class="n">Event</span> <span class="n">Collector</span> <span class="p">(</span><span class="n">HEC</span><span class="p">)</span>
<span class="o">--</span><span class="n">hec</span><span class="o">-</span><span class="n">skip</span><span class="o">-</span><span class="n">certificate</span><span class="o">-</span><span class="n">verification</span>
<span class="n">Skip</span> <span class="n">certificate</span> <span class="n">verification</span> <span class="k">for</span> <span class="n">Splunk</span> <span class="n">HEC</span>
</pre></div>
</div>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p>To maintain CLI backwards compatibility with previous versions of
<code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code>, if <code class="docutils literal notranslate"><span class="pre">--save-aggregate</span></code> and/or <code class="docutils literal notranslate"><span class="pre">--save-forensic</span></code> are used
without the <code class="docutils literal notranslate"><span class="pre">--hec</span></code> or <code class="docutils literal notranslate"><span class="pre">-E</span></code> options, <code class="docutils literal notranslate"><span class="pre">-E</span> <span class="pre">localhost:9200</span></code> is implied.</p>
<p class="last">It is possible to save data in Elasticsearch and Splunk at the same time by
supplying <code class="docutils literal notranslate"><span class="pre">-E</span></code> and the HEC options, along with <code class="docutils literal notranslate"><span class="pre">--save-aggregate</span></code> and/or
<code class="docutils literal notranslate"><span class="pre">--save-forensic</span></code>.</p>
</div>
<p>The project repository contains <a class="reference external" href="https://github.com/domainaware/parsedmarc/tree/master/splunk">XML files</a> for premade Splunk dashboards for
aggregate and forensic DMARC reports.</p>
<p>Copy and paste the contents of each file into a separate Splunk dashboard XML
editor.</p>
<div class="admonition warning">
<p class="first admonition-title">Warning</p>
<p class="last">Change all occurrences of <code class="docutils literal notranslate"><span class="pre">index=&quot;email&quot;</span></code> in the XML to
match your own index name.</p>
</div>
<p>The Splunk dashboards display the same content and layout as the Kibana
dashboards, although the Kibana dashboards have slightly easier and more
flexible filtering options.</p>
</div>
<div class="section" id="running-parsedmarc-as-a-systemd-service">
<h3>Running parsedmarc as a systemd service<a class="headerlink" href="#running-parsedmarc-as-a-systemd-service" title="Permalink to this headline"></a></h3>
<p>Use systemd to run <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> as a service and process reports as they
arrive.</p>
<p>Create the service configuration file</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo nano /etc/systemd/system/parsedmarc.service
</pre></div>
</div>
<div class="highlight-ini notranslate"><div class="highlight"><pre><span></span><span class="k">[Unit]</span>
<span class="na">Description</span><span class="o">=</span><span class="s">parsedmarc mailbox watcher</span>
<span class="na">Documentation</span><span class="o">=</span><span class="s">https://domainaware.github.io/parsedmarc/</span>
<span class="na">Wants</span><span class="o">=</span><span class="s">network-online.target</span>
<span class="na">After</span><span class="o">=</span><span class="s">network.target network-online.target elasticsearch.service</span>
<span class="k">[Service]</span>
<span class="na">ExecStart</span><span class="o">=</span><span class="s">/usr/local/bin/parsedmarc --watch --silent --save-aggregate --save-forensic -H &quot;outlook.office365.com&quot; -u &quot;dmarc@example.com&quot; -p &quot;FooBar!&quot;</span>
<span class="na">Restart</span><span class="o">=</span><span class="s">always</span>
<span class="na">RestartSec</span><span class="o">=</span><span class="s">5m</span>
<span class="k">[Install]</span>
<span class="na">WantedBy</span><span class="o">=</span><span class="s">multi-user.target</span>
</pre></div>
</div>
<p>Edit the command line options of <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> in the services <code class="docutils literal notranslate"><span class="pre">ExecStart</span></code>
setting to suit your needs.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">Always pass the <code class="docutils literal notranslate"><span class="pre">--watch</span></code> option to <code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code> when running it as a
service. Use <code class="docutils literal notranslate"><span class="pre">--silent</span></code> to only log errors.</p>
</div>
<div class="admonition warning">
<p class="first admonition-title">Warning</p>
<p class="last">As mentioned earlier, forensic/failure reports contain copies of emails
that failed DMARC, including emails that may be legitimate and contain
sensitive customer or business information. For privacy and/or regulatory
reasons, you may not want to use the <code class="docutils literal notranslate"><span class="pre">--save-forensic</span></code> flag included in
the example service configuration <code class="docutils literal notranslate"><span class="pre">ExecStart</span></code> setting, which would save
these samples to Elasticsearch.</p>
</div>
<p>Then, enable the service</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo systemctl daemon-reload
sudo systemctl <span class="nb">enable</span> parsedmarc.service
sudo service parsedmarc restart
</pre></div>
</div>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">You must also run the above commands whenever you edit
<code class="docutils literal notranslate"><span class="pre">parsedmarc.service</span></code>.</p>
</div>
<div class="admonition warning">
<p class="first admonition-title">Warning</p>
<blockquote>
<div>Always restart the service every time you upgrade to a new version of
<code class="docutils literal notranslate"><span class="pre">parsedmarc</span></code>:</div></blockquote>
<div class="last highlight-bash notranslate"><div class="highlight"><pre><span></span>sudo service parsedmarc restart
</pre></div>
</div>
</div>
<p>To check the status of the service, run:</p>
<div class="highlight-bash notranslate"><div class="highlight"><pre><span></span>service parsedmarc status
</pre></div>
</div>
<div class="admonition note">
<p class="first 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
current process. To vew the logs for previous runs as well as the
current process (newest to oldest), run:</p>
<div class="last highlight-bash notranslate"><div class="highlight"><pre><span></span>journalctl -u parsedmarc.service -r
</pre></div>
</div>
</div>
</div>
</div>
<div class="section" id="using-the-kibana-dashboards">
<h2>Using the Kibana dashboards<a class="headerlink" href="#using-the-kibana-dashboards" title="Permalink to this headline"></a></h2>
<p>The Kibana DMARC dashboards are a human-friendly way to understand the results
from incoming DMARC reports.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">The default dashboard is DMARC Summary. To switch between dashboards,
click on the Dashboard link in the left side menu of Kibana.</p>
</div>
<div class="section" id="dmarc-summary">
<h3>DMARC Summary<a class="headerlink" href="#dmarc-summary" title="Permalink to this headline"></a></h3>
<p>As the name suggests, this dashboard is the best place to start reviewing your
aggregate DMARC data.</p>
<p>Across the top of the dashboard, three pie charts display the percentage of
alignment pass/fail for SPF, DKIM, and DMARC. Clicking on any chart segment
will filter for that value.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">Messages should not be considered malicious just because they failed to pass
DMARC; especially if you have just started collecting data. It may be a
legitimate service that needs SPF and DKIM configured correctly.</p>
</div>
<p>Start by filtering the results to only show failed DKIM alignment. While DMARC
passes if a message passes SPF or DKIM alignment, only DKIM alignment remains
valid when a message is forwarded without changing the from address, which is
often caused by a mailbox forwarding rule. This is because DKIM signatures are
part of the message headers, whereas SPF relies on SMTP session headers.</p>
<p>Underneath the pie charts. you can see graphs of DMARC passage and message
disposition over time.</p>
<p>Under the graphs you will find the most useful data tables on the dashboard. On
the left, there is a list of organizations that are sending you DMARC reports.
In the center, there is a list of sending servers grouped by the base domain
in their reverse DNS. On the right, there is a list of email from domains,
sorted by message volume.</p>
<p>By hovering your mouse over a data table value and using the magnifying glass
icons, you can filter on our filter out different values. Start by looking at
the Message Sources by Reverse DNS table. Find a sender that you recognize,
such as an email marketing service, hover over it, and click on the plus (+)
magnifying glass icon, to add a filter that only shows results for that sender.
Now, look at the Message From Header table to the right. That shows you the
domains that a sender is sending as, which might tell you which brand/business
is using a particular service. With that information, you can contact them and
have them set up DKIM.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">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
emails from an old account to a new account, which is why DKIM
authentication is so important, as mentioned earlier. Similar patterns may
be observed with businesses who send from reverse DNS addressees of
parent, subsidiary, and outdated brands.</p>
</div>
<p>Further down the dashboard, you can filter by source country or source IP
address.</p>
<p>Tables showing SPF and DKIM alignment details are located under the IP address
table.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">Previously, the alignment tables were included in a separate dashboard
called DMARC Alignment Failures. That dashboard has been consolidated into
the DMARC Summary dashboard. To view failures only, use the pie chart.</p>
</div>
<p>Any other filters work the same way. You can also add your own custom temporary
filters by clicking on Add Filter at the upper right of the page.</p>
</div>
<div class="section" id="dmarc-forensic-samples">
<h3>DMARC Forensic Samples<a class="headerlink" href="#dmarc-forensic-samples" title="Permalink to this headline"></a></h3>
<p>The DMARC Forensic Samples dashboard contains information on DMARC forensic
reports (also known as failure reports or ruf reports). These reports contain
samples of emails that have failed to pass DMARC.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">Most recipients do not send forensic/failure/ruf reports at all to avoid
privacy leaks. Some recipients (notably Chinese webmail services) will only
supply the headers of sample emails. Very few provide the entire email.</p>
</div>
</div>
</div>
<div class="section" id="dmarc-alignment-guide">
<h2>DMARC Alignment Guide<a class="headerlink" href="#dmarc-alignment-guide" title="Permalink to this headline"></a></h2>
<p>DMARC ensures that SPF and DKM authentication mechanisms actually authenticate
against the same domain that the end user sees.</p>
<p>A message passes a DMARC check by passing DKIM or SPF, <strong>as long as the related
indicators are also in alignment</strong>.</p>
<table border="1" class="docutils">
<colgroup>
<col width="33%" />
<col width="33%" />
<col width="33%" />
</colgroup>
<tbody valign="top">
<tr class="row-odd"><td>&#160;</td>
<td><strong>DKIM</strong></td>
<td><strong>SPF</strong></td>
</tr>
<tr class="row-even"><td><strong>Passing</strong></td>
<td>The signature in the
DKIM header is
validated using a
public key that is
published as a DNS
record of the domain
name specified in the
signature</td>
<td>The mail servers IP
address is listed in
the SPF record of the
domain in the SMTP
envelopes mail from
header</td>
</tr>
<tr class="row-odd"><td><strong>Alignment</strong></td>
<td>The signing domain
aligns with the
domain in the
messages from header</td>
<td>The domain in the
SMTP envelopes mail
from header aligns
with the domain in
the messages from
header</td>
</tr>
</tbody>
</table>
</div>
<div class="section" id="what-if-a-sender-won-t-support-dkim-dmarc">
<h2>What if a sender wont support DKIM/DMARC?<a class="headerlink" href="#what-if-a-sender-won-t-support-dkim-dmarc" title="Permalink to this headline"></a></h2>
<ol class="arabic simple">
<li>Some vendors dont know about DMARC yet; ask about SPF and DKIM/email
authentication.</li>
<li>Check if they can send through your email relays instead of theirs.</li>
<li>Do they really need to spoof your domain? Why not use the display
name instead?</li>
<li>Worst case, have that vendor send email as a specific subdomain of
your domain (e.g. <code class="docutils literal notranslate"><span class="pre">noreply&#64;news.example.com</span></code>), and then create
separate SPF and DMARC records on <code class="docutils literal notranslate"><span class="pre">news.example.com</span></code>, and set
<code class="docutils literal notranslate"><span class="pre">p=none</span></code> in that DMARC record.</li>
</ol>
<blockquote>
<div><div class="admonition warning">
<p class="first admonition-title">Warning</p>
<p class="last">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>
</div>
</div></blockquote>
</div>
<div class="section" id="module-parsedmarc">
<span id="api"></span><h2>API<a class="headerlink" href="#module-parsedmarc" title="Permalink to this headline"></a></h2>
<p>A Python package for parsing DMARC reports</p>
<dl class="exception">
<dt id="parsedmarc.IMAPError">
<em class="property">exception </em><code class="descclassname">parsedmarc.</code><code class="descname">IMAPError</code><a class="reference internal" href="_modules/parsedmarc.html#IMAPError"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.IMAPError" title="Permalink to this definition"></a></dt>
<dd><p>Raised when an IMAP error occurs</p>
</dd></dl>
<dl class="exception">
<dt id="parsedmarc.InvalidAggregateReport">
<em class="property">exception </em><code class="descclassname">parsedmarc.</code><code class="descname">InvalidAggregateReport</code><a class="reference internal" href="_modules/parsedmarc.html#InvalidAggregateReport"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.InvalidAggregateReport" title="Permalink to this definition"></a></dt>
<dd><p>Raised when an invalid DMARC aggregate report is encountered</p>
</dd></dl>
<dl class="exception">
<dt id="parsedmarc.InvalidDMARCReport">
<em class="property">exception </em><code class="descclassname">parsedmarc.</code><code class="descname">InvalidDMARCReport</code><a class="reference internal" href="_modules/parsedmarc.html#InvalidDMARCReport"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.InvalidDMARCReport" title="Permalink to this definition"></a></dt>
<dd><p>Raised when an invalid DMARC report is encountered</p>
</dd></dl>
<dl class="exception">
<dt id="parsedmarc.InvalidForensicReport">
<em class="property">exception </em><code class="descclassname">parsedmarc.</code><code class="descname">InvalidForensicReport</code><a class="reference internal" href="_modules/parsedmarc.html#InvalidForensicReport"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.InvalidForensicReport" title="Permalink to this definition"></a></dt>
<dd><p>Raised when an invalid DMARC forensic report is encountered</p>
</dd></dl>
<dl class="exception">
<dt id="parsedmarc.ParserError">
<em class="property">exception </em><code class="descclassname">parsedmarc.</code><code class="descname">ParserError</code><a class="reference internal" href="_modules/parsedmarc.html#ParserError"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.ParserError" title="Permalink to this definition"></a></dt>
<dd><p>Raised whenever the parser fails for some reason</p>
</dd></dl>
<dl class="exception">
<dt id="parsedmarc.SMTPError">
<em class="property">exception </em><code class="descclassname">parsedmarc.</code><code class="descname">SMTPError</code><a class="reference internal" href="_modules/parsedmarc.html#SMTPError"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.SMTPError" title="Permalink to this definition"></a></dt>
<dd><p>Raised when a SMTP error occurs</p>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.email_results">
<code class="descclassname">parsedmarc.</code><code class="descname">email_results</code><span class="sig-paren">(</span><em>results</em>, <em>host</em>, <em>mail_from</em>, <em>mail_to</em>, <em>port=0</em>, <em>use_ssl=False</em>, <em>user=None</em>, <em>password=None</em>, <em>subject=None</em>, <em>attachment_filename=None</em>, <em>message=None</em>, <em>ssl_context=None</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#email_results"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.email_results" title="Permalink to this definition"></a></dt>
<dd><p>Emails parsing results as a zip file</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first last simple">
<li><strong>results</strong> (<em>OrderedDict</em>) Parsing results</li>
<li><strong>host</strong> Mail server hostname or IP address</li>
<li><strong>mail_from</strong> The value of the message from header</li>
<li><strong>mail_to</strong> A list of addresses to mail to</li>
<li><strong>port</strong> (<em>int</em>) Port to use</li>
<li><strong>use_ssl</strong> (<em>bool</em>) Require a SSL connection from the start</li>
<li><strong>user</strong> An optional username</li>
<li><strong>password</strong> An optional password</li>
<li><strong>subject</strong> Overrides the default message subject</li>
<li><strong>attachment_filename</strong> Override the default attachment filename</li>
<li><strong>message</strong> Override the default plain text body</li>
<li><strong>ssl_context</strong> SSL context options</li>
</ul>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.extract_xml">
<code class="descclassname">parsedmarc.</code><code class="descname">extract_xml</code><span class="sig-paren">(</span><em>input_</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#extract_xml"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.extract_xml" title="Permalink to this definition"></a></dt>
<dd><p>Extracts xml from a zip or gzip file at the given path, file-like object,
or bytes.</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>input</strong> A path to a file, a file like object, or bytes</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">The extracted XML</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">str</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.get_dmarc_reports_from_inbox">
<code class="descclassname">parsedmarc.</code><code class="descname">get_dmarc_reports_from_inbox</code><span class="sig-paren">(</span><em>host=None</em>, <em>user=None</em>, <em>password=None</em>, <em>connection=None</em>, <em>port=None</em>, <em>ssl=True</em>, <em>move_supported=None</em>, <em>reports_folder='INBOX'</em>, <em>archive_folder='Archive'</em>, <em>delete=False</em>, <em>test=False</em>, <em>nameservers=None</em>, <em>dns_timeout=6.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#get_dmarc_reports_from_inbox"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.get_dmarc_reports_from_inbox" title="Permalink to this definition"></a></dt>
<dd><p>Fetches and parses DMARC reports from sn inbox</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>host</strong> The mail server hostname or IP address</li>
<li><strong>user</strong> The mail server user</li>
<li><strong>password</strong> The mail server password</li>
<li><strong>connection</strong> An IMAPCLient connection to reuse</li>
<li><strong>port</strong> The mail server port</li>
<li><strong>ssl</strong> (<em>bool</em>) Use SSL/TLS</li>
<li><strong>move_supported</strong> Indicate if the IMAP server supports the MOVE command</li>
<li><strong>if None</strong><strong>)</strong> (<em>(</em><em>autodetect</em>) </li>
<li><strong>reports_folder</strong> The IMAP folder where reports can be found</li>
<li><strong>archive_folder</strong> The folder to move processed mail to</li>
<li><strong>delete</strong> (<em>bool</em>) Delete messages after processing them</li>
<li><strong>test</strong> (<em>bool</em>) Do not move or delete messages after processing them</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of DNS nameservers to query</li>
<li><strong>dns_timeout</strong> (<em>float</em>) Set the DNS query timeout</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first">Lists of <code class="docutils literal notranslate"><span class="pre">aggregate_reports</span></code> and <code class="docutils literal notranslate"><span class="pre">forensic_reports</span></code></p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">OrderedDict</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.get_imap_capabilities">
<code class="descclassname">parsedmarc.</code><code class="descname">get_imap_capabilities</code><span class="sig-paren">(</span><em>server</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#get_imap_capabilities"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.get_imap_capabilities" title="Permalink to this definition"></a></dt>
<dd><p>Returns a list of an IMAP servers capabilities</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>server</strong> (<em>imapclient.IMAPClient</em>) An instance of imapclient.IMAPClient</td>
</tr>
</tbody>
</table>
<p>Returns (list): A list of capabilities</p>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.get_report_zip">
<code class="descclassname">parsedmarc.</code><code class="descname">get_report_zip</code><span class="sig-paren">(</span><em>results</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#get_report_zip"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.get_report_zip" title="Permalink to this definition"></a></dt>
<dd><p>Creates a zip file of parsed report output</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>results</strong> (<em>OrderedDict</em>) The parsed results</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">zip file bytes</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">bytes</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.parse_aggregate_report_file">
<code class="descclassname">parsedmarc.</code><code class="descname">parse_aggregate_report_file</code><span class="sig-paren">(</span><em>_input</em>, <em>nameservers=None</em>, <em>timeout=2.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#parse_aggregate_report_file"><span class="viewcode-link">[source]</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
aggregate DMARC report</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>_input</strong> A path to a file, a file like object, or bytes</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>public DNS resolvers by default</strong><strong>)</strong> (<em>(</em><em>Cloudflare's</em>) </li>
<li><strong>timeout</strong> (<em>float</em>) Sets the DNS timeout in seconds</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first">The parsed DMARC aggregate report</p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">OrderedDict</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.parse_aggregate_report_xml">
<code class="descclassname">parsedmarc.</code><code class="descname">parse_aggregate_report_xml</code><span class="sig-paren">(</span><em>xml</em>, <em>nameservers=None</em>, <em>timeout=2.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#parse_aggregate_report_xml"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.parse_aggregate_report_xml" title="Permalink to this definition"></a></dt>
<dd><p>Parses a DMARC XML report string and returns a consistent OrderedDict</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>xml</strong> (<em>str</em>) A string of DMARC aggregate report XML</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>public DNS resolvers by default</strong><strong>)</strong> (<em>(</em><em>Cloudflare's</em>) </li>
<li><strong>timeout</strong> (<em>float</em>) Sets the DNS timeout in seconds</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first">The parsed aggregate DMARC report</p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">OrderedDict</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.parse_forensic_report">
<code class="descclassname">parsedmarc.</code><code class="descname">parse_forensic_report</code><span class="sig-paren">(</span><em>feedback_report</em>, <em>sample</em>, <em>msg_date</em>, <em>nameservers=None</em>, <em>timeout=2.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#parse_forensic_report"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.parse_forensic_report" title="Permalink to this definition"></a></dt>
<dd><p>Converts a DMARC forensic report and sample to a <code class="docutils literal notranslate"><span class="pre">OrderedDict</span></code></p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>feedback_report</strong> (<em>str</em>) A messages feedback report as a string</li>
<li><strong>sample</strong> (<em>str</em>) The RFC 822 headers or RFC 822 message sample</li>
<li><strong>msg_date</strong> (<em>str</em>) The messages date header</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>public DNS resolvers by default</strong><strong>)</strong> (<em>(</em><em>Cloudflare's</em>) </li>
<li><strong>timeout</strong> (<em>float</em>) Sets the DNS timeout in seconds</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first">A parsed report and sample</p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">OrderedDict</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.parse_report_email">
<code class="descclassname">parsedmarc.</code><code class="descname">parse_report_email</code><span class="sig-paren">(</span><em>input_</em>, <em>nameservers=None</em>, <em>timeout=2.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#parse_report_email"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.parse_report_email" title="Permalink to this definition"></a></dt>
<dd><p>Parses a DMARC report from an email</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>input</strong> An emailed DMARC report in RFC 822 format, as bytes or a string</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>timeout</strong> (<em>float</em>) Sets the DNS timeout in seconds</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first"><ul class="simple">
<li><code class="docutils literal notranslate"><span class="pre">report_type</span></code>: <code class="docutils literal notranslate"><span class="pre">aggregate</span></code> or <code class="docutils literal notranslate"><span class="pre">forensic</span></code></li>
<li><code class="docutils literal notranslate"><span class="pre">report</span></code>: The parsed report</li>
</ul>
</p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">OrderedDict</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.parse_report_file">
<code class="descclassname">parsedmarc.</code><code class="descname">parse_report_file</code><span class="sig-paren">(</span><em>input_</em>, <em>nameservers=None</em>, <em>timeout=2.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#parse_report_file"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.parse_report_file" title="Permalink to this definition"></a></dt>
<dd><p>Parses a DMARC aggregate or forensic file at the given path, a
file-like object. or bytes</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>input</strong> A path to a file, a file like object, or bytes</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>public DNS resolvers by default</strong><strong>)</strong> (<em>(</em><em>Cloudflare's</em>) </li>
<li><strong>timeout</strong> (<em>float</em>) Sets the DNS timeout in seconds</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first">The parsed DMARC report</p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">OrderedDict</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.parsed_aggregate_reports_to_csv">
<code class="descclassname">parsedmarc.</code><code class="descname">parsed_aggregate_reports_to_csv</code><span class="sig-paren">(</span><em>reports</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#parsed_aggregate_reports_to_csv"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.parsed_aggregate_reports_to_csv" title="Permalink to this definition"></a></dt>
<dd><p>Converts one or more parsed aggregate reports to flat CSV format, including
headers</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>reports</strong> A parsed aggregate report or list of parsed aggregate reports</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">Parsed aggregate report data in flat CSV format, including headers</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">str</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.parsed_forensic_reports_to_csv">
<code class="descclassname">parsedmarc.</code><code class="descname">parsed_forensic_reports_to_csv</code><span class="sig-paren">(</span><em>reports</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#parsed_forensic_reports_to_csv"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.parsed_forensic_reports_to_csv" title="Permalink to this definition"></a></dt>
<dd><p>Converts one or more parsed forensic reports to flat CSV format, including
headers</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>reports</strong> A parsed forensic report or list of parsed forensic reports</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">Parsed forensic report data in flat CSV format, including headers</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">str</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.save_output">
<code class="descclassname">parsedmarc.</code><code class="descname">save_output</code><span class="sig-paren">(</span><em>results</em>, <em>output_directory='output'</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#save_output"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.save_output" title="Permalink to this definition"></a></dt>
<dd><p>Save report data in the given directory</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first last simple">
<li><strong>results</strong> (<em>OrderedDict</em>) Parsing results</li>
<li><strong>output_directory</strong> The patch to the directory to save in</li>
</ul>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.watch_inbox">
<code class="descclassname">parsedmarc.</code><code class="descname">watch_inbox</code><span class="sig-paren">(</span><em>host</em>, <em>username</em>, <em>password</em>, <em>callback</em>, <em>port=None</em>, <em>ssl=True</em>, <em>reports_folder='INBOX'</em>, <em>archive_folder='Archive'</em>, <em>delete=False</em>, <em>test=False</em>, <em>wait=30</em>, <em>nameservers=None</em>, <em>dns_timeout=6.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc.html#watch_inbox"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.watch_inbox" title="Permalink to this definition"></a></dt>
<dd><p>Use an IDLE IMAP connection to parse incoming emails, and pass the results
to a callback function</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first last simple">
<li><strong>host</strong> The mail server hostname or IP address</li>
<li><strong>username</strong> The mail server username</li>
<li><strong>password</strong> The mail server password</li>
<li><strong>callback</strong> The callback function to receive the parsing results</li>
<li><strong>port</strong> The mail server port</li>
<li><strong>ssl</strong> (<em>bool</em>) Use SSL/TLS</li>
<li><strong>reports_folder</strong> The IMAP folder where reports can be found</li>
<li><strong>archive_folder</strong> The folder to move processed mail to</li>
<li><strong>delete</strong> (<em>bool</em>) Delete messages after processing them</li>
<li><strong>test</strong> (<em>bool</em>) Do not move or delete messages after processing them</li>
<li><strong>wait</strong> (<em>int</em>) Number of seconds to wait for a IMAP IDLE response</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>public DNS resolvers by default</strong><strong>)</strong> (<em>(</em><em>Cloudflare's</em>) </li>
<li><strong>dns_timeout</strong> (<em>float</em>) Set the DNS query timeout</li>
</ul>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<div class="section" id="module-parsedmarc.elastic">
<span id="parsedmarc-elastic"></span><h3>parsedmarc.elastic<a class="headerlink" href="#module-parsedmarc.elastic" title="Permalink to this headline"></a></h3>
<dl class="exception">
<dt id="parsedmarc.elastic.AlreadySaved">
<em class="property">exception </em><code class="descclassname">parsedmarc.elastic.</code><code class="descname">AlreadySaved</code><a class="reference internal" href="_modules/parsedmarc/elastic.html#AlreadySaved"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.elastic.AlreadySaved" title="Permalink to this definition"></a></dt>
<dd><p>Raised when a report to be saved matches an existing report</p>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.elastic.create_indexes">
<code class="descclassname">parsedmarc.elastic.</code><code class="descname">create_indexes</code><span class="sig-paren">(</span><em>names=None</em>, <em>settings=None</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/elastic.html#create_indexes"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.elastic.create_indexes" title="Permalink to this definition"></a></dt>
<dd><p>Create Elasticsearch indexes</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first last simple">
<li><strong>names</strong> (<em>list</em>) A list of index names</li>
<li><strong>&quot;dmarc_forensic&quot;</strong><strong>] </strong><strong>by default</strong> (<em>[</em><em>&quot;dmarc_aggregate&quot;</em><em>,</em>) </li>
<li><strong>settings</strong> (<em>dict</em>) Index settings</li>
</ul>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.elastic.save_aggregate_report_to_elasticsearch">
<code class="descclassname">parsedmarc.elastic.</code><code class="descname">save_aggregate_report_to_elasticsearch</code><span class="sig-paren">(</span><em>aggregate_report</em>, <em>index='dmarc_aggregate'</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/elastic.html#save_aggregate_report_to_elasticsearch"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.elastic.save_aggregate_report_to_elasticsearch" title="Permalink to this definition"></a></dt>
<dd><p>Saves a parsed DMARC aggregate report to ElasticSearch</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>aggregate_report</strong> (<em>OrderedDict</em>) A parsed forensic report</li>
<li><strong>index</strong> (<em>str</em>) The name of the index to save to</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Raises:</th><td class="field-body"><p class="first last"><a class="reference internal" href="#parsedmarc.elastic.AlreadySaved" title="parsedmarc.elastic.AlreadySaved"><code class="xref py py-exc docutils literal notranslate"><span class="pre">AlreadySaved</span></code></a></p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.elastic.save_forensic_report_to_elasticsearch">
<code class="descclassname">parsedmarc.elastic.</code><code class="descname">save_forensic_report_to_elasticsearch</code><span class="sig-paren">(</span><em>forensic_report</em>, <em>index='dmarc_forensic'</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/elastic.html#save_forensic_report_to_elasticsearch"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.elastic.save_forensic_report_to_elasticsearch" title="Permalink to this definition"></a></dt>
<dd><p>Saves a parsed DMARC forensic report to ElasticSearch</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>forensic_report</strong> (<em>OrderedDict</em>) A parsed forensic report</li>
<li><strong>index</strong> (<em>str</em>) The name of the index to save to</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Raises:</th><td class="field-body"><p class="first last"><a class="reference internal" href="#parsedmarc.elastic.AlreadySaved" title="parsedmarc.elastic.AlreadySaved"><code class="xref py py-exc docutils literal notranslate"><span class="pre">AlreadySaved</span></code></a></p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.elastic.set_hosts">
<code class="descclassname">parsedmarc.elastic.</code><code class="descname">set_hosts</code><span class="sig-paren">(</span><em>hosts</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/elastic.html#set_hosts"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.elastic.set_hosts" title="Permalink to this definition"></a></dt>
<dd><p>Sets the Elasticsearch hosts to use</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>hosts</strong> A single hostname or URL, or list of hostnames or URLs</td>
</tr>
</tbody>
</table>
</dd></dl>
<div class="toctree-wrapper compound">
</div>
<span class="target" id="module-parsedmarc.splunk"></span><dl class="class">
<dt id="parsedmarc.splunk.HECClient">
<em class="property">class </em><code class="descclassname">parsedmarc.splunk.</code><code class="descname">HECClient</code><span class="sig-paren">(</span><em>url</em>, <em>access_token</em>, <em>index</em>, <em>source='parsedmarc'</em>, <em>verify=True</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/splunk.html#HECClient"><span class="viewcode-link">[source]</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>
<dl class="method">
<dt id="parsedmarc.splunk.HECClient.save_aggregate_reports_to_splunk">
<code class="descname">save_aggregate_reports_to_splunk</code><span class="sig-paren">(</span><em>aggregate_reports</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">[source]</span></a><a class="headerlink" href="#parsedmarc.splunk.HECClient.save_aggregate_reports_to_splunk" title="Permalink to this definition"></a></dt>
<dd><p>Saves aggregate DMARC reports to Splunk</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first last simple">
<li><strong>aggregate_reports</strong> A list of aggregate report dictionaries</li>
<li><strong>save in Splunk</strong> (<em>to</em>) </li>
</ul>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="method">
<dt id="parsedmarc.splunk.HECClient.save_forensic_reports_to_splunk">
<code class="descname">save_forensic_reports_to_splunk</code><span class="sig-paren">(</span><em>forensic_reports</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/splunk.html#HECClient.save_forensic_reports_to_splunk"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.splunk.HECClient.save_forensic_reports_to_splunk" title="Permalink to this definition"></a></dt>
<dd><p>Saves forensic DMARC reports to Splunk</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first last simple">
<li><strong>forensic_reports</strong> (<em>list</em>) A list of forensic report dictionaries</li>
<li><strong>save in Splunk</strong> (<em>to</em>) </li>
</ul>
</td>
</tr>
</tbody>
</table>
</dd></dl>
</dd></dl>
<dl class="exception">
<dt id="parsedmarc.splunk.SplunkError">
<em class="property">exception </em><code class="descclassname">parsedmarc.splunk.</code><code class="descname">SplunkError</code><a class="reference internal" href="_modules/parsedmarc/splunk.html#SplunkError"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.splunk.SplunkError" title="Permalink to this definition"></a></dt>
<dd><p>Raised when a Splunk API error occurs</p>
</dd></dl>
<div class="toctree-wrapper compound">
</div>
<span class="target" id="module-parsedmarc.utils"></span><p>Utility functions that might be useful for other projects</p>
<dl class="exception">
<dt id="parsedmarc.utils.EmailParserError">
<em class="property">exception </em><code class="descclassname">parsedmarc.utils.</code><code class="descname">EmailParserError</code><a class="reference internal" href="_modules/parsedmarc/utils.html#EmailParserError"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.EmailParserError" title="Permalink to this definition"></a></dt>
<dd><p>Raised when an error parsing the email occurs</p>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.convert_outlook_msg">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">convert_outlook_msg</code><span class="sig-paren">(</span><em>msg_bytes</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#convert_outlook_msg"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.convert_outlook_msg" title="Permalink to this definition"></a></dt>
<dd><p>Uses the <code class="docutils literal notranslate"><span class="pre">msgconvert</span></code> Perl utility to convert an Outlook MS file to
standard RFC 822 format</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>msg_bytes</strong> (<em>bytes</em>) the content of the .msg file</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">A RFC 822 string</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.get_base_domain">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">get_base_domain</code><span class="sig-paren">(</span><em>domain</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#get_base_domain"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.get_base_domain" title="Permalink to this definition"></a></dt>
<dd><p>Gets the base domain name for the given domain</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p>Results are based on a list of public domain suffixes at
<a class="reference external" href="https://publicsuffix.org/list/public_suffix_list.dat">https://publicsuffix.org/list/public_suffix_list.dat</a>.</p>
<p class="last">This file is saved to the current working directory,
where it is used as a cache file for 24 hours.</p>
</div>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>domain</strong> (<em>str</em>) A domain or subdomain</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">The base domain of the given domain</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">str</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.get_filename_safe_string">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">get_filename_safe_string</code><span class="sig-paren">(</span><em>string</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#get_filename_safe_string"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.get_filename_safe_string" title="Permalink to this definition"></a></dt>
<dd><p>Converts a string to a string that is safe for a filename
:param string: A string to make safe for a filename
:type string: str</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Returns:</th><td class="field-body">A string safe for a filename</td>
</tr>
<tr class="field-even field"><th class="field-name">Return type:</th><td class="field-body">str</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.get_ip_address_country">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">get_ip_address_country</code><span class="sig-paren">(</span><em>ip_address</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#get_ip_address_country"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.get_ip_address_country" title="Permalink to this definition"></a></dt>
<dd><p>Uses the MaxMind Geolite2 Country database to return the ISO code for the
country associated with the given IPv4 or IPv6 address</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>ip_address</strong> (<em>str</em>) The IP address to query for</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">And ISO country code associated with the given IP address</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">str</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.get_ip_address_info">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">get_ip_address_info</code><span class="sig-paren">(</span><em>ip_address</em>, <em>nameservers=None</em>, <em>timeout=2.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#get_ip_address_info"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.get_ip_address_info" title="Permalink to this definition"></a></dt>
<dd><p>Returns reverse DNS and country information for the given IP address</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>ip_address</strong> (<em>str</em>) The IP address to check</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>public DNS resolvers by default</strong><strong>)</strong> (<em>(</em><em>Cloudflare's</em>) </li>
<li><strong>timeout</strong> (<em>float</em>) Sets the DNS timeout in seconds</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first"><code class="docutils literal notranslate"><span class="pre">ip_address</span></code>, <code class="docutils literal notranslate"><span class="pre">reverse_dns</span></code></p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">OrderedDict</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.get_reverse_dns">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">get_reverse_dns</code><span class="sig-paren">(</span><em>ip_address</em>, <em>nameservers=None</em>, <em>timeout=2.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#get_reverse_dns"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.get_reverse_dns" title="Permalink to this definition"></a></dt>
<dd><p>Resolves an IP address to a hostname using a reverse DNS query</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>ip_address</strong> (<em>str</em>) The IP address to resolve</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>public DNS resolvers by default</strong><strong>)</strong> (<em>(</em><em>Cloudflare's</em>) </li>
<li><strong>timeout</strong> (<em>float</em>) Sets the DNS query timeout in seconds</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first">The reverse DNS hostname (if any)</p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">str</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.human_timestamp_to_datetime">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">human_timestamp_to_datetime</code><span class="sig-paren">(</span><em>human_timestamp</em>, <em>to_utc=False</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#human_timestamp_to_datetime"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.human_timestamp_to_datetime" title="Permalink to this definition"></a></dt>
<dd><p>Converts a human-readable timestamp into a Python <code class="docutils literal notranslate"><span class="pre">DateTime</span></code> object</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>human_timestamp</strong> (<em>str</em>) A timestamp string</li>
<li><strong>to_utc</strong> (<em>bool</em>) Convert the timestamp to UTC</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first">The converted timestamp</p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">DateTime</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.human_timestamp_to_timestamp">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">human_timestamp_to_timestamp</code><span class="sig-paren">(</span><em>human_timestamp</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#human_timestamp_to_timestamp"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.human_timestamp_to_timestamp" title="Permalink to this definition"></a></dt>
<dd><p>Converts a human-readable timestamp into a into a UNIX timestamp</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>human_timestamp</strong> (<em>str</em>) A timestamp in <cite>YYYY-MM-DD HH:MM:SS`</cite> format</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">The converted timestamp</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">float</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.is_outlook_msg">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">is_outlook_msg</code><span class="sig-paren">(</span><em>content</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#is_outlook_msg"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.is_outlook_msg" title="Permalink to this definition"></a></dt>
<dd><p>Checks if the given content is a Outlook msg OLE file</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>content</strong> Content to check</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">A flag the indicates if a file is a Outlook MSG file</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">bool</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.parse_email">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">parse_email</code><span class="sig-paren">(</span><em>data</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#parse_email"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.parse_email" title="Permalink to this definition"></a></dt>
<dd><p>A simplified email parser</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>data</strong> The RFC 822 message string, or MSG binary</td>
</tr>
</tbody>
</table>
<p>Returns (dict): Parsed email data</p>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.query_dns">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">query_dns</code><span class="sig-paren">(</span><em>domain</em>, <em>record_type</em>, <em>nameservers=None</em>, <em>timeout=2.0</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#query_dns"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.query_dns" title="Permalink to this definition"></a></dt>
<dd><p>Queries DNS</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><ul class="first simple">
<li><strong>domain</strong> (<em>str</em>) The domain or subdomain to query about</li>
<li><strong>record_type</strong> (<em>str</em>) The record type to query for</li>
<li><strong>nameservers</strong> (<em>list</em>) A list of one or more nameservers to use</li>
<li><strong>public DNS resolvers by default</strong><strong>)</strong> (<em>(</em><em>Cloudflare's</em>) </li>
<li><strong>timeout</strong> (<em>float</em>) Sets the DNS timeout in seconds</li>
</ul>
</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body"><p class="first">A list of answers</p>
</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body"><p class="first last">list</p>
</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.timestamp_to_datetime">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">timestamp_to_datetime</code><span class="sig-paren">(</span><em>timestamp</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#timestamp_to_datetime"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.timestamp_to_datetime" title="Permalink to this definition"></a></dt>
<dd><p>Converts a UNIX/DMARC timestamp to a Python <code class="docutils literal notranslate"><span class="pre">DateTime</span></code> object</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>timestamp</strong> (<em>int</em>) The timestamp</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">The converted timestamp as a Python <code class="docutils literal notranslate"><span class="pre">DateTime</span></code> object</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">DateTime</td>
</tr>
</tbody>
</table>
</dd></dl>
<dl class="function">
<dt id="parsedmarc.utils.timestamp_to_human">
<code class="descclassname">parsedmarc.utils.</code><code class="descname">timestamp_to_human</code><span class="sig-paren">(</span><em>timestamp</em><span class="sig-paren">)</span><a class="reference internal" href="_modules/parsedmarc/utils.html#timestamp_to_human"><span class="viewcode-link">[source]</span></a><a class="headerlink" href="#parsedmarc.utils.timestamp_to_human" title="Permalink to this definition"></a></dt>
<dd><p>Converts a UNIX/DMARC timestamp to a human-readable string</p>
<table class="docutils field-list" frame="void" rules="none">
<col class="field-name" />
<col class="field-body" />
<tbody valign="top">
<tr class="field-odd field"><th class="field-name">Parameters:</th><td class="field-body"><strong>timestamp</strong> The timestamp</td>
</tr>
<tr class="field-even field"><th class="field-name">Returns:</th><td class="field-body">The converted timestamp in <code class="docutils literal notranslate"><span class="pre">YYYY-MM-DD</span> <span class="pre">HH:MM:SS</span></code> format</td>
</tr>
<tr class="field-odd field"><th class="field-name">Return type:</th><td class="field-body">str</td>
</tr>
</tbody>
</table>
</dd></dl>
<div class="toctree-wrapper compound">
</div>
<div class="toctree-wrapper compound">
</div>
</div>
</div>
<div class="section" id="indices-and-tables">
<h2>Indices and tables<a class="headerlink" href="#indices-and-tables" title="Permalink to this headline"></a></h2>
<ul class="simple">
<li><a class="reference internal" href="genindex.html"><span class="std std-ref">Index</span></a></li>
<li><a class="reference internal" href="py-modindex.html"><span class="std std-ref">Module Index</span></a></li>
<li><a class="reference internal" href="search.html"><span class="std std-ref">Search Page</span></a></li>
</ul>
</div>
</div>
</div>
</div>
<footer>
<hr/>
<div role="contentinfo">
<p>
&copy; Copyright 2018, Sean Whalen
</p>
</div>
Built with <a href="http://sphinx-doc.org/">Sphinx</a> using a <a href="https://github.com/rtfd/sphinx_rtd_theme">theme</a> provided by <a href="https://readthedocs.org">Read the Docs</a>.
</footer>
</div>
</div>
</section>
</div>
<script type="text/javascript">
var DOCUMENTATION_OPTIONS = {
URL_ROOT:'./',
VERSION:'4.3.0',
LANGUAGE:'None',
COLLAPSE_INDEX:false,
FILE_SUFFIX:'.html',
HAS_SOURCE: true,
SOURCELINK_SUFFIX: '.txt'
};
</script>
<script type="text/javascript" src="_static/jquery.js"></script>
<script type="text/javascript" src="_static/underscore.js"></script>
<script type="text/javascript" src="_static/doctools.js"></script>
<script type="text/javascript" src="_static/js/theme.js"></script>
<script type="text/javascript">
jQuery(function () {
SphinxRtdTheme.Navigation.enable(true);
});
</script>
</body>
</html>