678 lines
50 KiB
HTML
678 lines
50 KiB
HTML
|
||
<!DOCTYPE html>
|
||
<html lang="en">
|
||
<head>
|
||
<meta charset="utf-8">
|
||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||
<meta name="color-scheme" content="light dark">
|
||
<title>PEP 3143 – Standard daemon process library | peps.python.org</title>
|
||
<link rel="shortcut icon" href="../_static/py.png">
|
||
<link rel="canonical" href="https://peps.python.org/pep-3143/">
|
||
<link rel="stylesheet" href="../_static/style.css" type="text/css">
|
||
<link rel="stylesheet" href="../_static/mq.css" type="text/css">
|
||
<link rel="stylesheet" href="../_static/pygments.css" type="text/css" media="(prefers-color-scheme: light)" id="pyg-light">
|
||
<link rel="stylesheet" href="../_static/pygments_dark.css" type="text/css" media="(prefers-color-scheme: dark)" id="pyg-dark">
|
||
<link rel="alternate" type="application/rss+xml" title="Latest PEPs" href="https://peps.python.org/peps.rss">
|
||
<meta property="og:title" content='PEP 3143 – Standard daemon process library | peps.python.org'>
|
||
<meta property="og:description" content="Writing a program to become a well-behaved Unix daemon is somewhat complex and tricky to get right, yet the steps are largely similar for any daemon regardless of what else the program may need to do.">
|
||
<meta property="og:type" content="website">
|
||
<meta property="og:url" content="https://peps.python.org/pep-3143/">
|
||
<meta property="og:site_name" content="Python Enhancement Proposals (PEPs)">
|
||
<meta property="og:image" content="https://peps.python.org/_static/og-image.png">
|
||
<meta property="og:image:alt" content="Python PEPs">
|
||
<meta property="og:image:width" content="200">
|
||
<meta property="og:image:height" content="200">
|
||
<meta name="description" content="Writing a program to become a well-behaved Unix daemon is somewhat complex and tricky to get right, yet the steps are largely similar for any daemon regardless of what else the program may need to do.">
|
||
<meta name="theme-color" content="#3776ab">
|
||
</head>
|
||
<body>
|
||
|
||
<svg xmlns="http://www.w3.org/2000/svg" style="display: none;">
|
||
<symbol id="svg-sun-half" viewBox="0 0 24 24" pointer-events="all">
|
||
<title>Following system colour scheme</title>
|
||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none"
|
||
stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||
<circle cx="12" cy="12" r="9"></circle>
|
||
<path d="M12 3v18m0-12l4.65-4.65M12 14.3l7.37-7.37M12 19.6l8.85-8.85"></path>
|
||
</svg>
|
||
</symbol>
|
||
<symbol id="svg-moon" viewBox="0 0 24 24" pointer-events="all">
|
||
<title>Selected dark colour scheme</title>
|
||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none"
|
||
stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||
<path stroke="none" d="M0 0h24v24H0z" fill="none"></path>
|
||
<path d="M12 3c.132 0 .263 0 .393 0a7.5 7.5 0 0 0 7.92 12.446a9 9 0 1 1 -8.313 -12.454z"></path>
|
||
</svg>
|
||
</symbol>
|
||
<symbol id="svg-sun" viewBox="0 0 24 24" pointer-events="all">
|
||
<title>Selected light colour scheme</title>
|
||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none"
|
||
stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||
<circle cx="12" cy="12" r="5"></circle>
|
||
<line x1="12" y1="1" x2="12" y2="3"></line>
|
||
<line x1="12" y1="21" x2="12" y2="23"></line>
|
||
<line x1="4.22" y1="4.22" x2="5.64" y2="5.64"></line>
|
||
<line x1="18.36" y1="18.36" x2="19.78" y2="19.78"></line>
|
||
<line x1="1" y1="12" x2="3" y2="12"></line>
|
||
<line x1="21" y1="12" x2="23" y2="12"></line>
|
||
<line x1="4.22" y1="19.78" x2="5.64" y2="18.36"></line>
|
||
<line x1="18.36" y1="5.64" x2="19.78" y2="4.22"></line>
|
||
</svg>
|
||
</symbol>
|
||
</svg>
|
||
<script>
|
||
|
||
document.documentElement.dataset.colour_scheme = localStorage.getItem("colour_scheme") || "auto"
|
||
</script>
|
||
<section id="pep-page-section">
|
||
<header>
|
||
<h1>Python Enhancement Proposals</h1>
|
||
<ul class="breadcrumbs">
|
||
<li><a href="https://www.python.org/" title="The Python Programming Language">Python</a> » </li>
|
||
<li><a href="../pep-0000/">PEP Index</a> » </li>
|
||
<li>PEP 3143</li>
|
||
</ul>
|
||
<button id="colour-scheme-cycler" onClick="setColourScheme(nextColourScheme())">
|
||
<svg aria-hidden="true" class="colour-scheme-icon-when-auto"><use href="#svg-sun-half"></use></svg>
|
||
<svg aria-hidden="true" class="colour-scheme-icon-when-dark"><use href="#svg-moon"></use></svg>
|
||
<svg aria-hidden="true" class="colour-scheme-icon-when-light"><use href="#svg-sun"></use></svg>
|
||
<span class="visually-hidden">Toggle light / dark / auto colour theme</span>
|
||
</button>
|
||
</header>
|
||
<article>
|
||
<section id="pep-content">
|
||
<h1 class="page-title">PEP 3143 – Standard daemon process library</h1>
|
||
<dl class="rfc2822 field-list simple">
|
||
<dt class="field-odd">Author<span class="colon">:</span></dt>
|
||
<dd class="field-odd">Ben Finney <ben+python at benfinney.id.au></dd>
|
||
<dt class="field-even">Status<span class="colon">:</span></dt>
|
||
<dd class="field-even"><abbr title="Inactive draft that may be taken up again at a later time">Deferred</abbr></dd>
|
||
<dt class="field-odd">Type<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><abbr title="Normative PEP with a new feature for Python, implementation change for CPython or interoperability standard for the ecosystem">Standards Track</abbr></dd>
|
||
<dt class="field-even">Created<span class="colon">:</span></dt>
|
||
<dd class="field-even">26-Jan-2009</dd>
|
||
<dt class="field-odd">Python-Version<span class="colon">:</span></dt>
|
||
<dd class="field-odd">3.x</dd>
|
||
<dt class="field-even">Post-History<span class="colon">:</span></dt>
|
||
<dd class="field-even"><p></p></dd>
|
||
</dl>
|
||
<hr class="docutils" />
|
||
<section id="contents">
|
||
<details><summary>Table of Contents</summary><ul class="simple">
|
||
<li><a class="reference internal" href="#abstract">Abstract</a></li>
|
||
<li><a class="reference internal" href="#pep-deferral">PEP Deferral</a></li>
|
||
<li><a class="reference internal" href="#specification">Specification</a><ul>
|
||
<li><a class="reference internal" href="#example-usage">Example usage</a></li>
|
||
<li><a class="reference internal" href="#interface">Interface</a></li>
|
||
<li><a class="reference internal" href="#daemoncontext-objects"><code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code> objects</a></li>
|
||
</ul>
|
||
</li>
|
||
<li><a class="reference internal" href="#motivation">Motivation</a></li>
|
||
<li><a class="reference internal" href="#rationale">Rationale</a><ul>
|
||
<li><a class="reference internal" href="#correct-daemon-behaviour">Correct daemon behaviour</a></li>
|
||
<li><a class="reference internal" href="#a-daemon-is-not-a-service">A daemon is not a service</a></li>
|
||
</ul>
|
||
</li>
|
||
<li><a class="reference internal" href="#reference-implementation">Reference Implementation</a><ul>
|
||
<li><a class="reference internal" href="#other-daemon-implementations">Other daemon implementations</a></li>
|
||
</ul>
|
||
</li>
|
||
<li><a class="reference internal" href="#references">References</a></li>
|
||
<li><a class="reference internal" href="#copyright">Copyright</a></li>
|
||
</ul>
|
||
</details></section>
|
||
<section id="abstract">
|
||
<h2><a class="toc-backref" href="#abstract" role="doc-backlink">Abstract</a></h2>
|
||
<p>Writing a program to become a well-behaved Unix daemon is somewhat
|
||
complex and tricky to get right, yet the steps are largely similar for
|
||
any daemon regardless of what else the program may need to do.</p>
|
||
<p>This PEP introduces a package to the Python standard library that
|
||
provides a simple interface to the task of becoming a daemon process.</p>
|
||
</section>
|
||
<section id="pep-deferral">
|
||
<h2><a class="toc-backref" href="#pep-deferral" role="doc-backlink">PEP Deferral</a></h2>
|
||
<p>Further exploration of the concepts covered in this PEP has been deferred
|
||
for lack of a current champion interested in promoting the goals of the PEP
|
||
and collecting and incorporating feedback, and with sufficient available
|
||
time to do so effectively.</p>
|
||
</section>
|
||
<section id="specification">
|
||
<h2><a class="toc-backref" href="#specification" role="doc-backlink">Specification</a></h2>
|
||
<section id="example-usage">
|
||
<h3><a class="toc-backref" href="#example-usage" role="doc-backlink">Example usage</a></h3>
|
||
<p>Simple example of direct <code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code> usage:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="kn">import</span> <span class="nn">daemon</span>
|
||
|
||
<span class="kn">from</span> <span class="nn">spam</span> <span class="kn">import</span> <span class="n">do_main_program</span>
|
||
|
||
<span class="k">with</span> <span class="n">daemon</span><span class="o">.</span><span class="n">DaemonContext</span><span class="p">():</span>
|
||
<span class="n">do_main_program</span><span class="p">()</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>More complex example usage:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="kn">import</span> <span class="nn">os</span>
|
||
<span class="kn">import</span> <span class="nn">grp</span>
|
||
<span class="kn">import</span> <span class="nn">signal</span>
|
||
<span class="kn">import</span> <span class="nn">daemon</span>
|
||
<span class="kn">import</span> <span class="nn">lockfile</span>
|
||
|
||
<span class="kn">from</span> <span class="nn">spam</span> <span class="kn">import</span> <span class="p">(</span>
|
||
<span class="n">initial_program_setup</span><span class="p">,</span>
|
||
<span class="n">do_main_program</span><span class="p">,</span>
|
||
<span class="n">program_cleanup</span><span class="p">,</span>
|
||
<span class="n">reload_program_config</span><span class="p">,</span>
|
||
<span class="p">)</span>
|
||
|
||
<span class="n">context</span> <span class="o">=</span> <span class="n">daemon</span><span class="o">.</span><span class="n">DaemonContext</span><span class="p">(</span>
|
||
<span class="n">working_directory</span><span class="o">=</span><span class="s1">'/var/lib/foo'</span><span class="p">,</span>
|
||
<span class="n">umask</span><span class="o">=</span><span class="mo">0o002</span><span class="p">,</span>
|
||
<span class="n">pidfile</span><span class="o">=</span><span class="n">lockfile</span><span class="o">.</span><span class="n">FileLock</span><span class="p">(</span><span class="s1">'/var/run/spam.pid'</span><span class="p">),</span>
|
||
<span class="p">)</span>
|
||
|
||
<span class="n">context</span><span class="o">.</span><span class="n">signal_map</span> <span class="o">=</span> <span class="p">{</span>
|
||
<span class="n">signal</span><span class="o">.</span><span class="n">SIGTERM</span><span class="p">:</span> <span class="n">program_cleanup</span><span class="p">,</span>
|
||
<span class="n">signal</span><span class="o">.</span><span class="n">SIGHUP</span><span class="p">:</span> <span class="s1">'terminate'</span><span class="p">,</span>
|
||
<span class="n">signal</span><span class="o">.</span><span class="n">SIGUSR1</span><span class="p">:</span> <span class="n">reload_program_config</span><span class="p">,</span>
|
||
<span class="p">}</span>
|
||
|
||
<span class="n">mail_gid</span> <span class="o">=</span> <span class="n">grp</span><span class="o">.</span><span class="n">getgrnam</span><span class="p">(</span><span class="s1">'mail'</span><span class="p">)</span><span class="o">.</span><span class="n">gr_gid</span>
|
||
<span class="n">context</span><span class="o">.</span><span class="n">gid</span> <span class="o">=</span> <span class="n">mail_gid</span>
|
||
|
||
<span class="n">important_file</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="s1">'spam.data'</span><span class="p">,</span> <span class="s1">'w'</span><span class="p">)</span>
|
||
<span class="n">interesting_file</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="s1">'eggs.data'</span><span class="p">,</span> <span class="s1">'w'</span><span class="p">)</span>
|
||
<span class="n">context</span><span class="o">.</span><span class="n">files_preserve</span> <span class="o">=</span> <span class="p">[</span><span class="n">important_file</span><span class="p">,</span> <span class="n">interesting_file</span><span class="p">]</span>
|
||
|
||
<span class="n">initial_program_setup</span><span class="p">()</span>
|
||
|
||
<span class="k">with</span> <span class="n">context</span><span class="p">:</span>
|
||
<span class="n">do_main_program</span><span class="p">()</span>
|
||
</pre></div>
|
||
</div>
|
||
</section>
|
||
<section id="interface">
|
||
<h3><a class="toc-backref" href="#interface" role="doc-backlink">Interface</a></h3>
|
||
<p>A new package, <code class="docutils literal notranslate"><span class="pre">daemon</span></code>, is added to the standard library.</p>
|
||
<p>A class, <code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code>, is defined to represent the settings and
|
||
process context for the program running as a daemon process.</p>
|
||
</section>
|
||
<section id="daemoncontext-objects">
|
||
<h3><a class="toc-backref" href="#daemoncontext-objects" role="doc-backlink"><code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code> objects</a></h3>
|
||
<p>A <code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code> instance represents the behaviour settings and
|
||
process context for the program when it becomes a daemon. The
|
||
behaviour and environment is customised by setting options on the
|
||
instance, before calling the <code class="docutils literal notranslate"><span class="pre">open</span></code> method.</p>
|
||
<p>Each option can be passed as a keyword argument to the <code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code>
|
||
constructor, or subsequently altered by assigning to an attribute on
|
||
the instance at any time prior to calling <code class="docutils literal notranslate"><span class="pre">open</span></code>. That is, for
|
||
options named <code class="docutils literal notranslate"><span class="pre">wibble</span></code> and <code class="docutils literal notranslate"><span class="pre">wubble</span></code>, the following invocation:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">foo</span> <span class="o">=</span> <span class="n">daemon</span><span class="o">.</span><span class="n">DaemonContext</span><span class="p">(</span><span class="n">wibble</span><span class="o">=</span><span class="n">bar</span><span class="p">,</span> <span class="n">wubble</span><span class="o">=</span><span class="n">baz</span><span class="p">)</span>
|
||
<span class="n">foo</span><span class="o">.</span><span class="n">open</span><span class="p">()</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>is equivalent to:</p>
|
||
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">foo</span> <span class="o">=</span> <span class="n">daemon</span><span class="o">.</span><span class="n">DaemonContext</span><span class="p">()</span>
|
||
<span class="n">foo</span><span class="o">.</span><span class="n">wibble</span> <span class="o">=</span> <span class="n">bar</span>
|
||
<span class="n">foo</span><span class="o">.</span><span class="n">wubble</span> <span class="o">=</span> <span class="n">baz</span>
|
||
<span class="n">foo</span><span class="o">.</span><span class="n">open</span><span class="p">()</span>
|
||
</pre></div>
|
||
</div>
|
||
<p>The following options are defined.</p>
|
||
<dl>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">files_preserve</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
<p>List of files that should <em>not</em> be closed when starting the
|
||
daemon. If <code class="docutils literal notranslate"><span class="pre">None</span></code>, all open file descriptors will be closed.</p>
|
||
<p>Elements of the list are file descriptors (as returned by a file
|
||
object’s <code class="docutils literal notranslate"><span class="pre">fileno()</span></code> method) or Python <code class="docutils literal notranslate"><span class="pre">file</span></code> objects. Each
|
||
specifies a file that is not to be closed during daemon start.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">chroot_directory</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
<p>Full path to a directory to set as the effective root directory of
|
||
the process. If <code class="docutils literal notranslate"><span class="pre">None</span></code>, specifies that the root directory is not
|
||
to be changed.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">working_directory</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">'/'</span></code></dd>
|
||
</dl>
|
||
<p>Full path of the working directory to which the process should
|
||
change on daemon start.</p>
|
||
<p>Since a filesystem cannot be unmounted if a process has its
|
||
current working directory on that filesystem, this should either
|
||
be left at default or set to a directory that is a sensible “home
|
||
directory” for the daemon while it is running.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">umask</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">0</span></code></dd>
|
||
</dl>
|
||
<p>File access creation mask (“umask”) to set for the process on
|
||
daemon start.</p>
|
||
<p>Since a process inherits its umask from its parent process,
|
||
starting the daemon will reset the umask to this value so that
|
||
files are created by the daemon with access modes as it expects.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">pidfile</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
<p>Context manager for a PID lock file. When the daemon context opens
|
||
and closes, it enters and exits the <code class="docutils literal notranslate"><span class="pre">pidfile</span></code> context manager.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">detach_process</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
<p>If <code class="docutils literal notranslate"><span class="pre">True</span></code>, detach the process context when opening the daemon
|
||
context; if <code class="docutils literal notranslate"><span class="pre">False</span></code>, do not detach.</p>
|
||
<p>If unspecified (<code class="docutils literal notranslate"><span class="pre">None</span></code>) during initialisation of the instance,
|
||
this will be set to <code class="docutils literal notranslate"><span class="pre">True</span></code> by default, and <code class="docutils literal notranslate"><span class="pre">False</span></code> only if
|
||
detaching the process is determined to be redundant; for example,
|
||
in the case when the process was started by <code class="docutils literal notranslate"><span class="pre">init</span></code>, by <code class="docutils literal notranslate"><span class="pre">initd</span></code>, or
|
||
by <code class="docutils literal notranslate"><span class="pre">inetd</span></code>.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">signal_map</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd">system-dependent</dd>
|
||
</dl>
|
||
<p>Mapping from operating system signals to callback actions.</p>
|
||
<p>The mapping is used when the daemon context opens, and determines
|
||
the action for each signal’s signal handler:</p>
|
||
<ul class="simple">
|
||
<li>A value of <code class="docutils literal notranslate"><span class="pre">None</span></code> will ignore the signal (by setting the
|
||
signal action to <code class="docutils literal notranslate"><span class="pre">signal.SIG_IGN</span></code>).</li>
|
||
<li>A string value will be used as the name of an attribute on the
|
||
<code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code> instance. The attribute’s value will be used
|
||
as the action for the signal handler.</li>
|
||
<li>Any other value will be used as the action for the signal
|
||
handler.</li>
|
||
</ul>
|
||
<p>The default value depends on which signals are defined on the
|
||
running system. Each item from the list below whose signal is
|
||
actually defined in the <code class="docutils literal notranslate"><span class="pre">signal</span></code> module will appear in the
|
||
default map:</p>
|
||
<ul class="simple">
|
||
<li><code class="docutils literal notranslate"><span class="pre">signal.SIGTTIN</span></code>: <code class="docutils literal notranslate"><span class="pre">None</span></code></li>
|
||
<li><code class="docutils literal notranslate"><span class="pre">signal.SIGTTOU</span></code>: <code class="docutils literal notranslate"><span class="pre">None</span></code></li>
|
||
<li><code class="docutils literal notranslate"><span class="pre">signal.SIGTSTP</span></code>: <code class="docutils literal notranslate"><span class="pre">None</span></code></li>
|
||
<li><code class="docutils literal notranslate"><span class="pre">signal.SIGTERM</span></code>: <code class="docutils literal notranslate"><span class="pre">'terminate'</span></code></li>
|
||
</ul>
|
||
<p>Depending on how the program will interact with its child
|
||
processes, it may need to specify a signal map that includes the
|
||
<code class="docutils literal notranslate"><span class="pre">signal.SIGCHLD</span></code> signal (received when a child process exits).
|
||
See the specific operating system’s documentation for more detail
|
||
on how to determine what circumstances dictate the need for signal
|
||
handlers.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">uid</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">os.getuid()</span></code></dd>
|
||
</dl>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">gid</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">os.getgid()</span></code></dd>
|
||
</dl>
|
||
<p>The user ID (“UID”) value and group ID (“GID”) value to switch
|
||
the process to on daemon start.</p>
|
||
<p>The default values, the real UID and GID of the process, will
|
||
relinquish any effective privilege elevation inherited by the
|
||
process.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">prevent_core</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">True</span></code></dd>
|
||
</dl>
|
||
<p>If true, prevents the generation of core files, in order to avoid
|
||
leaking sensitive information from daemons run as <code class="docutils literal notranslate"><span class="pre">root</span></code>.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">stdin</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">stdout</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">stderr</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Default<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
<p>Each of <code class="docutils literal notranslate"><span class="pre">stdin</span></code>, <code class="docutils literal notranslate"><span class="pre">stdout</span></code>, and <code class="docutils literal notranslate"><span class="pre">stderr</span></code> is a file-like object
|
||
which will be used as the new file for the standard I/O stream
|
||
<code class="docutils literal notranslate"><span class="pre">sys.stdin</span></code>, <code class="docutils literal notranslate"><span class="pre">sys.stdout</span></code>, and <code class="docutils literal notranslate"><span class="pre">sys.stderr</span></code> respectively. The file
|
||
should therefore be open, with a minimum of mode ‘r’ in the case
|
||
of <code class="docutils literal notranslate"><span class="pre">stdin</span></code>, and mode ‘w+’ in the case of <code class="docutils literal notranslate"><span class="pre">stdout</span></code> and <code class="docutils literal notranslate"><span class="pre">stderr</span></code>.</p>
|
||
<p>If the object has a <code class="docutils literal notranslate"><span class="pre">fileno()</span></code> method that returns a file
|
||
descriptor, the corresponding file will be excluded from being
|
||
closed during daemon start (that is, it will be treated as though
|
||
it were listed in <code class="docutils literal notranslate"><span class="pre">files_preserve</span></code>).</p>
|
||
<p>If <code class="docutils literal notranslate"><span class="pre">None</span></code>, the corresponding system stream is re-bound to the
|
||
file named by <code class="docutils literal notranslate"><span class="pre">os.devnull</span></code>.</p>
|
||
</dd>
|
||
</dl>
|
||
<p>The following methods are defined.</p>
|
||
<dl>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">open()</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Return<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
<p>Open the daemon context, turning the current program into a daemon
|
||
process. This performs the following steps:</p>
|
||
<ul>
|
||
<li>If this instance’s <code class="docutils literal notranslate"><span class="pre">is_open</span></code> property is true, return
|
||
immediately. This makes it safe to call <code class="docutils literal notranslate"><span class="pre">open</span></code> multiple times on
|
||
an instance.</li>
|
||
<li>If the <code class="docutils literal notranslate"><span class="pre">prevent_core</span></code> attribute is true, set the resource limits
|
||
for the process to prevent any core dump from the process.</li>
|
||
<li>If the <code class="docutils literal notranslate"><span class="pre">chroot_directory</span></code> attribute is not <code class="docutils literal notranslate"><span class="pre">None</span></code>, set the
|
||
effective root directory of the process to that directory (via
|
||
<code class="docutils literal notranslate"><span class="pre">os.chroot</span></code>).<p>This allows running the daemon process inside a “chroot gaol”
|
||
as a means of limiting the system’s exposure to rogue behaviour
|
||
by the process. Note that the specified directory needs to
|
||
already be set up for this purpose.</p>
|
||
</li>
|
||
<li>Set the process UID and GID to the <code class="docutils literal notranslate"><span class="pre">uid</span></code> and <code class="docutils literal notranslate"><span class="pre">gid</span></code> attribute
|
||
values.</li>
|
||
<li>Close all open file descriptors. This excludes those listed in
|
||
the <code class="docutils literal notranslate"><span class="pre">files_preserve</span></code> attribute, and those that correspond to the
|
||
<code class="docutils literal notranslate"><span class="pre">stdin</span></code>, <code class="docutils literal notranslate"><span class="pre">stdout</span></code>, or <code class="docutils literal notranslate"><span class="pre">stderr</span></code> attributes.</li>
|
||
<li>Change current working directory to the path specified by the
|
||
<code class="docutils literal notranslate"><span class="pre">working_directory</span></code> attribute.</li>
|
||
<li>Reset the file access creation mask to the value specified by
|
||
the <code class="docutils literal notranslate"><span class="pre">umask</span></code> attribute.</li>
|
||
<li>If the <code class="docutils literal notranslate"><span class="pre">detach_process</span></code> option is true, detach the current
|
||
process into its own process group, and disassociate from any
|
||
controlling terminal.</li>
|
||
<li>Set signal handlers as specified by the <code class="docutils literal notranslate"><span class="pre">signal_map</span></code> attribute.</li>
|
||
<li>If any of the attributes <code class="docutils literal notranslate"><span class="pre">stdin</span></code>, <code class="docutils literal notranslate"><span class="pre">stdout</span></code>, <code class="docutils literal notranslate"><span class="pre">stderr</span></code> are not
|
||
<code class="docutils literal notranslate"><span class="pre">None</span></code>, bind the system streams <code class="docutils literal notranslate"><span class="pre">sys.stdin</span></code>, <code class="docutils literal notranslate"><span class="pre">sys.stdout</span></code>,
|
||
and/or <code class="docutils literal notranslate"><span class="pre">sys.stderr</span></code> to the files represented by the
|
||
corresponding attributes. Where the attribute has a file
|
||
descriptor, the descriptor is duplicated (instead of re-binding
|
||
the name).</li>
|
||
<li>If the <code class="docutils literal notranslate"><span class="pre">pidfile</span></code> attribute is not <code class="docutils literal notranslate"><span class="pre">None</span></code>, enter its context
|
||
manager.</li>
|
||
<li>Mark this instance as open (for the purpose of future <code class="docutils literal notranslate"><span class="pre">open</span></code> and
|
||
<code class="docutils literal notranslate"><span class="pre">close</span></code> calls).</li>
|
||
<li>Register the <code class="docutils literal notranslate"><span class="pre">close</span></code> method to be called during Python’s exit
|
||
processing.</li>
|
||
</ul>
|
||
<p>When the function returns, the running program is a daemon
|
||
process.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">close()</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Return<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
<p>Close the daemon context. This performs the following steps:</p>
|
||
<ul class="simple">
|
||
<li>If this instance’s <code class="docutils literal notranslate"><span class="pre">is_open</span></code> property is false, return
|
||
immediately. This makes it safe to call <code class="docutils literal notranslate"><span class="pre">close</span></code> multiple times
|
||
on an instance.</li>
|
||
<li>If the <code class="docutils literal notranslate"><span class="pre">pidfile</span></code> attribute is not <code class="docutils literal notranslate"><span class="pre">None</span></code>, exit its context
|
||
manager.</li>
|
||
<li>Mark this instance as closed (for the purpose of future <code class="docutils literal notranslate"><span class="pre">open</span></code>
|
||
and <code class="docutils literal notranslate"><span class="pre">close</span></code> calls).</li>
|
||
</ul>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">is_open</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Return<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">True</span></code> if the instance is open, <code class="docutils literal notranslate"><span class="pre">False</span></code> otherwise.</dd>
|
||
</dl>
|
||
<p>This property exposes the state indicating whether the instance is
|
||
currently open. It is <code class="docutils literal notranslate"><span class="pre">True</span></code> if the instance’s <code class="docutils literal notranslate"><span class="pre">open</span></code> method has
|
||
been called and the <code class="docutils literal notranslate"><span class="pre">close</span></code> method has not subsequently been
|
||
called.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">terminate(signal_number,</span> <span class="pre">stack_frame)</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Return<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">None</span></code></dd>
|
||
</dl>
|
||
<p>Signal handler for the <code class="docutils literal notranslate"><span class="pre">signal.SIGTERM</span></code> signal. Performs the
|
||
following step:</p>
|
||
<ul class="simple">
|
||
<li>Raise a <code class="docutils literal notranslate"><span class="pre">SystemExit</span></code> exception explaining the signal.</li>
|
||
</ul>
|
||
</dd>
|
||
</dl>
|
||
<p>The class also implements the context manager protocol via
|
||
<code class="docutils literal notranslate"><span class="pre">__enter__</span></code> and <code class="docutils literal notranslate"><span class="pre">__exit__</span></code> methods.</p>
|
||
<dl>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">__enter__()</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Return<span class="colon">:</span></dt>
|
||
<dd class="field-odd">The <code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code> instance</dd>
|
||
</dl>
|
||
<p>Call the instance’s <code class="docutils literal notranslate"><span class="pre">open()</span></code> method, then return the instance.</p>
|
||
</dd>
|
||
<dt><code class="docutils literal notranslate"><span class="pre">__exit__(exc_type,</span> <span class="pre">exc_value,</span> <span class="pre">exc_traceback)</span></code></dt><dd><dl class="field-list simple">
|
||
<dt class="field-odd">Return<span class="colon">:</span></dt>
|
||
<dd class="field-odd"><code class="docutils literal notranslate"><span class="pre">True</span></code> or <code class="docutils literal notranslate"><span class="pre">False</span></code> as defined by the context manager
|
||
protocol</dd>
|
||
</dl>
|
||
<p>Call the instance’s <code class="docutils literal notranslate"><span class="pre">close()</span></code> method, then return <code class="docutils literal notranslate"><span class="pre">True</span></code> if the
|
||
exception was handled or <code class="docutils literal notranslate"><span class="pre">False</span></code> if it was not.</p>
|
||
</dd>
|
||
</dl>
|
||
</section>
|
||
</section>
|
||
<section id="motivation">
|
||
<h2><a class="toc-backref" href="#motivation" role="doc-backlink">Motivation</a></h2>
|
||
<p>The majority of programs written to be Unix daemons either implement
|
||
behaviour very similar to that in the <a class="reference internal" href="#specification">specification</a>, or are
|
||
poorly-behaved daemons by the <a class="reference internal" href="#correct-daemon-behaviour">correct daemon behaviour</a>.</p>
|
||
<p>Since these steps should be much the same in most implementations but
|
||
are very particular and easy to omit or implement incorrectly, they
|
||
are a prime target for a standard well-tested implementation in the
|
||
standard library.</p>
|
||
</section>
|
||
<section id="rationale">
|
||
<h2><a class="toc-backref" href="#rationale" role="doc-backlink">Rationale</a></h2>
|
||
<section id="correct-daemon-behaviour">
|
||
<h3><a class="toc-backref" href="#correct-daemon-behaviour" role="doc-backlink">Correct daemon behaviour</a></h3>
|
||
<p>According to Stevens in <a class="reference internal" href="#stevens" id="id1"><span>[stevens]</span></a> §2.6, a program should perform the
|
||
following steps to become a Unix daemon process.</p>
|
||
<ul class="simple">
|
||
<li>Close all open file descriptors.</li>
|
||
<li>Change current working directory.</li>
|
||
<li>Reset the file access creation mask.</li>
|
||
<li>Run in the background.</li>
|
||
<li>Disassociate from process group.</li>
|
||
<li>Ignore terminal I/O signals.</li>
|
||
<li>Disassociate from control terminal.</li>
|
||
<li>Don’t reacquire a control terminal.</li>
|
||
<li>Correctly handle the following circumstances:<ul>
|
||
<li>Started by System V <code class="docutils literal notranslate"><span class="pre">init</span></code> process.</li>
|
||
<li>Daemon termination by <code class="docutils literal notranslate"><span class="pre">SIGTERM</span></code> signal.</li>
|
||
<li>Children generate <code class="docutils literal notranslate"><span class="pre">SIGCLD</span></code> signal.</li>
|
||
</ul>
|
||
</li>
|
||
</ul>
|
||
<p>The <code class="docutils literal notranslate"><span class="pre">daemon</span></code> tool <a class="reference internal" href="#slack-daemon" id="id2"><span>[slack-daemon]</span></a> lists (in its summary of features)
|
||
behaviour that should be performed when turning a program into a
|
||
well-behaved Unix daemon process. It differs from this PEP’s intent in
|
||
that it invokes a <em>separate</em> program as a daemon process. The
|
||
following features are appropriate for a daemon that starts itself
|
||
once the program is already running:</p>
|
||
<ul class="simple">
|
||
<li>Sets up the correct process context for a daemon.</li>
|
||
<li>Behaves sensibly when started by <code class="docutils literal notranslate"><span class="pre">initd(8)</span></code> or <code class="docutils literal notranslate"><span class="pre">inetd(8)</span></code>.</li>
|
||
<li>Revokes any suid or sgid privileges to reduce security risks in case
|
||
daemon is incorrectly installed with special privileges.</li>
|
||
<li>Prevents the generation of core files to prevent leaking sensitive
|
||
information from daemons run as root (optional).</li>
|
||
<li>Names the daemon by creating and locking a PID file to guarantee
|
||
that only one daemon with the given name can execute at any given
|
||
time (optional).</li>
|
||
<li>Sets the user and group under which to run the daemon (optional,
|
||
root only).</li>
|
||
<li>Creates a chroot gaol (optional, root only).</li>
|
||
<li>Captures the daemon’s stdout and stderr and directs them to syslog
|
||
(optional).</li>
|
||
</ul>
|
||
</section>
|
||
<section id="a-daemon-is-not-a-service">
|
||
<h3><a class="toc-backref" href="#a-daemon-is-not-a-service" role="doc-backlink">A daemon is not a service</a></h3>
|
||
<p>This PEP addresses only Unix-style daemons, for which the above
|
||
correct behaviour is relevant, as opposed to comparable behaviours on
|
||
other operating systems.</p>
|
||
<p>There is a related concept in many systems, called a “service”. A
|
||
service differs from the model in this PEP, in that rather than having
|
||
the <em>current</em> program continue to run as a daemon process, a service
|
||
starts an <em>additional</em> process to run in the background, and the
|
||
current process communicates with that additional process via some
|
||
defined channels.</p>
|
||
<p>The Unix-style daemon model in this PEP can be used, among other
|
||
things, to implement the background-process part of a service; but
|
||
this PEP does not address the other aspects of setting up and managing
|
||
a service.</p>
|
||
</section>
|
||
</section>
|
||
<section id="reference-implementation">
|
||
<h2><a class="toc-backref" href="#reference-implementation" role="doc-backlink">Reference Implementation</a></h2>
|
||
<p>The <code class="docutils literal notranslate"><span class="pre">python-daemon</span></code> package <a class="reference internal" href="#python-daemon" id="id3"><span>[python-daemon]</span></a>.</p>
|
||
<section id="other-daemon-implementations">
|
||
<h3><a class="toc-backref" href="#other-daemon-implementations" role="doc-backlink">Other daemon implementations</a></h3>
|
||
<p>Prior to this PEP, several existing third-party Python libraries or
|
||
tools implemented some of this PEP’s <a class="reference internal" href="#correct-daemon-behaviour">correct daemon behaviour</a>.</p>
|
||
<p>The <a class="reference internal" href="#reference-implementation">reference implementation</a> is a fairly direct successor from the
|
||
following implementations:</p>
|
||
<ul class="simple">
|
||
<li>Many good ideas were contributed by the community to Python cookbook
|
||
recipes #66012 <a class="reference internal" href="#cookbook-66012" id="id4"><span>[cookbook-66012]</span></a> and #278731 <a class="reference internal" href="#cookbook-278731" id="id5"><span>[cookbook-278731]</span></a>.</li>
|
||
<li>The <code class="docutils literal notranslate"><span class="pre">bda.daemon</span></code> library <a class="reference internal" href="#bda-daemon" id="id6"><span>[bda.daemon]</span></a> is an implementation of
|
||
<a class="reference internal" href="#cookbook-66012" id="id7"><span>[cookbook-66012]</span></a>. It is the predecessor of <a class="reference internal" href="#python-daemon" id="id8"><span>[python-daemon]</span></a>.</li>
|
||
</ul>
|
||
<p>Other Python daemon implementations that differ from this PEP:</p>
|
||
<ul class="simple">
|
||
<li>The <code class="docutils literal notranslate"><span class="pre">zdaemon</span></code> tool <a class="reference internal" href="#zdaemon" id="id9"><span>[zdaemon]</span></a> was written for the Zope project. Like
|
||
<a class="reference internal" href="#slack-daemon" id="id10"><span>[slack-daemon]</span></a>, it differs from this specification because it is
|
||
used to run another program as a daemon process.</li>
|
||
<li>The Python library <code class="docutils literal notranslate"><span class="pre">daemon</span></code> <a class="reference internal" href="#clapper-daemon" id="id11"><span>[clapper-daemon]</span></a> is (according to its
|
||
homepage) no longer maintained. As of version 1.0.1, it implements
|
||
the basic steps from <a class="reference internal" href="#stevens" id="id12"><span>[stevens]</span></a>.</li>
|
||
<li>The <code class="docutils literal notranslate"><span class="pre">daemonize</span></code> library <a class="reference internal" href="#seutter-daemonize" id="id13"><span>[seutter-daemonize]</span></a> also implements the
|
||
basic steps from <a class="reference internal" href="#stevens" id="id14"><span>[stevens]</span></a>.</li>
|
||
<li>Ray Burr’s <code class="docutils literal notranslate"><span class="pre">daemon.py</span></code> module <a class="reference internal" href="#burr-daemon" id="id15"><span>[burr-daemon]</span></a> provides the <a class="reference internal" href="#stevens" id="id16"><span>[stevens]</span></a>
|
||
procedure as well as PID file handling and redirection of output to
|
||
syslog.</li>
|
||
<li>Twisted <a class="reference internal" href="#twisted" id="id17"><span>[twisted]</span></a> includes, perhaps unsurprisingly, an
|
||
implementation of a process daemonisation API that is integrated
|
||
with the rest of the Twisted framework; it differs significantly
|
||
from the API in this PEP.</li>
|
||
<li>The Python <code class="docutils literal notranslate"><span class="pre">initd</span></code> library <a class="reference internal" href="#dagitses-initd" id="id18"><span>[dagitses-initd]</span></a>, which uses
|
||
<a class="reference internal" href="#clapper-daemon" id="id19"><span>[clapper-daemon]</span></a>, implements an equivalent of Unix <code class="docutils literal notranslate"><span class="pre">initd(8)</span></code> for
|
||
controlling a daemon process.</li>
|
||
</ul>
|
||
</section>
|
||
</section>
|
||
<section id="references">
|
||
<h2><a class="toc-backref" href="#references" role="doc-backlink">References</a></h2>
|
||
<div role="list" class="citation-list">
|
||
<div class="citation" id="stevens" role="doc-biblioentry">
|
||
<dt class="label" id="stevens">[stevens]<em> (<a href='#id1'>1</a>, <a href='#id12'>2</a>, <a href='#id14'>3</a>, <a href='#id16'>4</a>) </em></dt>
|
||
<dd><code class="docutils literal notranslate"><span class="pre">Unix</span> <span class="pre">Network</span> <span class="pre">Programming</span></code>, W. Richard Stevens, 1994 Prentice
|
||
Hall.</div>
|
||
<div class="citation" id="slack-daemon" role="doc-biblioentry">
|
||
<dt class="label" id="slack-daemon">[slack-daemon]<em> (<a href='#id2'>1</a>, <a href='#id10'>2</a>) </em></dt>
|
||
<dd>The (non-Python) “libslack” implementation of a <code class="docutils literal notranslate"><span class="pre">daemon</span></code> tool
|
||
<a class="reference external" href="http://www.libslack.org/daemon/">http://www.libslack.org/daemon/</a> by “raf” <<a class="reference external" href="mailto:raf%40raf.org">raf<span>@</span>raf<span>.</span>org</a>>.</div>
|
||
<div class="citation" id="python-daemon" role="doc-biblioentry">
|
||
<dt class="label" id="python-daemon">[python-daemon]<em> (<a href='#id3'>1</a>, <a href='#id8'>2</a>) </em></dt>
|
||
<dd>The <code class="docutils literal notranslate"><span class="pre">python-daemon</span></code> library
|
||
<a class="reference external" href="http://pypi.python.org/pypi/python-daemon/">http://pypi.python.org/pypi/python-daemon/</a> by Ben Finney et
|
||
al.</div>
|
||
<div class="citation" id="cookbook-66012" role="doc-biblioentry">
|
||
<dt class="label" id="cookbook-66012">[cookbook-66012]<em> (<a href='#id4'>1</a>, <a href='#id7'>2</a>) </em></dt>
|
||
<dd>Python Cookbook recipe 66012, “Fork a daemon process on Unix”
|
||
<a class="reference external" href="http://code.activestate.com/recipes/66012/">http://code.activestate.com/recipes/66012/</a>.</div>
|
||
<div class="citation" id="cookbook-278731" role="doc-biblioentry">
|
||
<dt class="label" id="cookbook-278731">[<a href="#id5">cookbook-278731</a>]</dt>
|
||
<dd>Python Cookbook recipe 278731, “Creating a daemon the Python way”
|
||
<a class="reference external" href="http://code.activestate.com/recipes/278731/">http://code.activestate.com/recipes/278731/</a>.</div>
|
||
<div class="citation" id="bda-daemon" role="doc-biblioentry">
|
||
<dt class="label" id="bda-daemon">[<a href="#id6">bda.daemon</a>]</dt>
|
||
<dd>The <code class="docutils literal notranslate"><span class="pre">bda.daemon</span></code> library
|
||
<a class="reference external" href="http://pypi.python.org/pypi/bda.daemon/">http://pypi.python.org/pypi/bda.daemon/</a> by Robert
|
||
Niederreiter et al.</div>
|
||
<div class="citation" id="zdaemon" role="doc-biblioentry">
|
||
<dt class="label" id="zdaemon">[<a href="#id9">zdaemon</a>]</dt>
|
||
<dd>The <code class="docutils literal notranslate"><span class="pre">zdaemon</span></code> tool <a class="reference external" href="http://pypi.python.org/pypi/zdaemon/">http://pypi.python.org/pypi/zdaemon/</a> by
|
||
Guido van Rossum et al.</div>
|
||
<div class="citation" id="clapper-daemon" role="doc-biblioentry">
|
||
<dt class="label" id="clapper-daemon">[clapper-daemon]<em> (<a href='#id11'>1</a>, <a href='#id19'>2</a>) </em></dt>
|
||
<dd>The <code class="docutils literal notranslate"><span class="pre">daemon</span></code> library <a class="reference external" href="http://pypi.python.org/pypi/daemon/">http://pypi.python.org/pypi/daemon/</a> by
|
||
Brian Clapper.</div>
|
||
<div class="citation" id="seutter-daemonize" role="doc-biblioentry">
|
||
<dt class="label" id="seutter-daemonize">[<a href="#id13">seutter-daemonize</a>]</dt>
|
||
<dd>The <code class="docutils literal notranslate"><span class="pre">daemonize</span></code> library <a class="reference external" href="http://daemonize.sourceforge.net/">http://daemonize.sourceforge.net/</a> by
|
||
Jerry Seutter.</div>
|
||
<div class="citation" id="burr-daemon" role="doc-biblioentry">
|
||
<dt class="label" id="burr-daemon">[<a href="#id15">burr-daemon</a>]</dt>
|
||
<dd>The <code class="docutils literal notranslate"><span class="pre">daemon.py</span></code> module
|
||
<a class="reference external" href="http://www.nightmare.com/~ryb/code/daemon.py">http://www.nightmare.com/~ryb/code/daemon.py</a> by Ray Burr.</div>
|
||
<div class="citation" id="twisted" role="doc-biblioentry">
|
||
<dt class="label" id="twisted">[<a href="#id17">twisted</a>]</dt>
|
||
<dd>The <code class="docutils literal notranslate"><span class="pre">Twisted</span></code> application framework
|
||
<a class="reference external" href="http://pypi.python.org/pypi/Twisted/">http://pypi.python.org/pypi/Twisted/</a> by Glyph Lefkowitz et
|
||
al.</div>
|
||
<div class="citation" id="dagitses-initd" role="doc-biblioentry">
|
||
<dt class="label" id="dagitses-initd">[<a href="#id18">dagitses-initd</a>]</dt>
|
||
<dd>The Python <code class="docutils literal notranslate"><span class="pre">initd</span></code> library <a class="reference external" href="http://pypi.python.org/pypi/initd/">http://pypi.python.org/pypi/initd/</a>
|
||
by Michael Andreas Dagitses.</div>
|
||
</div>
|
||
</section>
|
||
<section id="copyright">
|
||
<h2><a class="toc-backref" href="#copyright" role="doc-backlink">Copyright</a></h2>
|
||
<p>This work is hereby placed in the public domain. To the extent that
|
||
placing a work in the public domain is not legally possible, the
|
||
copyright holder hereby grants to all recipients of this work all
|
||
rights and freedoms that would otherwise be restricted by copyright.</p>
|
||
</section>
|
||
</section>
|
||
<hr class="docutils" />
|
||
<p>Source: <a class="reference external" href="https://github.com/python/peps/blob/main/peps/pep-3143.rst">https://github.com/python/peps/blob/main/peps/pep-3143.rst</a></p>
|
||
<p>Last modified: <a class="reference external" href="https://github.com/python/peps/commits/main/peps/pep-3143.rst">2023-09-09 17:39:29 GMT</a></p>
|
||
|
||
</article>
|
||
<nav id="pep-sidebar">
|
||
<h2>Contents</h2>
|
||
<ul>
|
||
<li><a class="reference internal" href="#abstract">Abstract</a></li>
|
||
<li><a class="reference internal" href="#pep-deferral">PEP Deferral</a></li>
|
||
<li><a class="reference internal" href="#specification">Specification</a><ul>
|
||
<li><a class="reference internal" href="#example-usage">Example usage</a></li>
|
||
<li><a class="reference internal" href="#interface">Interface</a></li>
|
||
<li><a class="reference internal" href="#daemoncontext-objects"><code class="docutils literal notranslate"><span class="pre">DaemonContext</span></code> objects</a></li>
|
||
</ul>
|
||
</li>
|
||
<li><a class="reference internal" href="#motivation">Motivation</a></li>
|
||
<li><a class="reference internal" href="#rationale">Rationale</a><ul>
|
||
<li><a class="reference internal" href="#correct-daemon-behaviour">Correct daemon behaviour</a></li>
|
||
<li><a class="reference internal" href="#a-daemon-is-not-a-service">A daemon is not a service</a></li>
|
||
</ul>
|
||
</li>
|
||
<li><a class="reference internal" href="#reference-implementation">Reference Implementation</a><ul>
|
||
<li><a class="reference internal" href="#other-daemon-implementations">Other daemon implementations</a></li>
|
||
</ul>
|
||
</li>
|
||
<li><a class="reference internal" href="#references">References</a></li>
|
||
<li><a class="reference internal" href="#copyright">Copyright</a></li>
|
||
</ul>
|
||
|
||
<br>
|
||
<a id="source" href="https://github.com/python/peps/blob/main/peps/pep-3143.rst">Page Source (GitHub)</a>
|
||
</nav>
|
||
</section>
|
||
<script src="../_static/colour_scheme.js"></script>
|
||
<script src="../_static/wrap_tables.js"></script>
|
||
<script src="../_static/sticky_banner.js"></script>
|
||
</body>
|
||
</html> |