Files
GopherGate/target/doc/tokio/task/index.html
2026-02-26 12:00:21 -05:00

188 lines
21 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><html lang="en"><head><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><meta name="generator" content="rustdoc"><meta name="description" content="Asynchronous green-threads."><title>tokio::task - Rust</title><script>if(window.location.protocol!=="file:")document.head.insertAdjacentHTML("beforeend","SourceSerif4-Regular-6b053e98.ttf.woff2,FiraSans-Italic-81dc35de.woff2,FiraSans-Regular-0fe48ade.woff2,FiraSans-MediumItalic-ccf7e434.woff2,FiraSans-Medium-e1aa3f0a.woff2,SourceCodePro-Regular-8badfe75.ttf.woff2,SourceCodePro-Semibold-aa29a496.ttf.woff2".split(",").map(f=>`<link rel="preload" as="font" type="font/woff2"href="../../static.files/${f}">`).join(""))</script><link rel="stylesheet" href="../../static.files/normalize-9960930a.css"><link rel="stylesheet" href="../../static.files/rustdoc-ca0dd0c4.css"><meta name="rustdoc-vars" data-root-path="../../" data-static-root-path="../../static.files/" data-current-crate="tokio" data-themes="" data-resource-suffix="" data-rustdoc-version="1.93.1 (01f6ddf75 2026-02-11) (Arch Linux rust 1:1.93.1-1)" data-channel="1.93.1" data-search-js="search-9e2438ea.js" data-stringdex-js="stringdex-a3946164.js" data-settings-js="settings-c38705f0.js" ><script src="../../static.files/storage-e2aeef58.js"></script><script defer src="../sidebar-items.js"></script><script defer src="../../static.files/main-a410ff4d.js"></script><noscript><link rel="stylesheet" href="../../static.files/noscript-263c88ec.css"></noscript><link rel="alternate icon" type="image/png" href="../../static.files/favicon-32x32-eab170b8.png"><link rel="icon" type="image/svg+xml" href="../../static.files/favicon-044be391.svg"></head><body class="rustdoc mod"><!--[if lte IE 11]><div class="warning">This old browser is unsupported and will most likely display funky things.</div><![endif]--><rustdoc-topbar><h2><a href="#">Module task</a></h2></rustdoc-topbar><nav class="sidebar"><div class="sidebar-crate"><h2><a href="../../tokio/index.html">tokio</a><span class="version">1.49.0</span></h2></div><div class="sidebar-elems"><section id="rustdoc-toc"><h2 class="location"><a href="#">Module task</a></h2><h3><a href="#">Sections</a></h3><ul class="block top-toc"><li><a href="#what-are-tasks" title="What are Tasks?">What are Tasks?</a></li><li><a href="#working-with-tasks" title="Working with Tasks">Working with Tasks</a><ul><li><a href="#spawning" title="Spawning">Spawning</a></li><li><a href="#blocking-and-yielding" title="Blocking and Yielding">Blocking and Yielding</a></li></ul></li></ul><h3><a href="#modules">Module Items</a></h3><ul class="block"><li><a href="#modules" title="Modules">Modules</a></li><li><a href="#structs" title="Structs">Structs</a></li><li><a href="#functions" title="Functions">Functions</a></li></ul></section><div id="rustdoc-modnav"><h2 class="in-crate"><a href="../index.html">In crate tokio</a></h2></div></div></nav><div class="sidebar-resizer" title="Drag to resize sidebar"></div><main><div class="width-limiter"><section id="main-content" class="content"><div class="main-heading"><div class="rustdoc-breadcrumbs"><a href="../index.html">tokio</a></div><h1>Module <span>task</span>&nbsp;<button id="copy-path" title="Copy item path to clipboard">Copy item path</button></h1><rustdoc-toolbar></rustdoc-toolbar><span class="sub-heading"><a class="src" href="../../src/tokio/task/mod.rs.html#1-335">Source</a> </span></div><details class="toggle top-doc" open><summary class="hideme"><span>Expand description</span></summary><div class="docblock"><p>Asynchronous green-threads.</p>
<h3 id="what-are-tasks"><a class="doc-anchor" href="#what-are-tasks">§</a>What are Tasks?</h3>
<p>A <em>task</em> is a light weight, non-blocking unit of execution. A task is similar
to an OS thread, but rather than being managed by the OS scheduler, they are
managed by the <a href="../runtime/index.html" title="mod tokio::runtime">Tokio runtime</a>. Another name for this general pattern is
<a href="https://en.wikipedia.org/wiki/Green_threads">green threads</a>. If you are familiar with <a href="https://tour.golang.org/concurrency/1">Gos goroutines</a>, <a href="https://kotlinlang.org/docs/reference/coroutines-overview.html">Kotlins
coroutines</a>, or <a href="http://erlang.org/doc/getting_started/conc_prog.html#processes">Erlangs processes</a>, you can think of Tokios tasks as
something similar.</p>
<p>Key points about tasks include:</p>
<ul>
<li>
<p>Tasks are <strong>light weight</strong>. Because tasks are scheduled by the Tokio
runtime rather than the operating system, creating new tasks or switching
between tasks does not require a context switch and has fairly low
overhead. Creating, running, and destroying large numbers of tasks is
quite cheap, especially compared to OS threads.</p>
</li>
<li>
<p>Tasks are scheduled <strong>cooperatively</strong>. Most operating systems implement
<em>preemptive multitasking</em>. This is a scheduling technique where the
operating system allows each thread to run for a period of time, and then
<em>preempts</em> it, temporarily pausing that thread and switching to another.
Tasks, on the other hand, implement <em>cooperative multitasking</em>. In
cooperative multitasking, a task is allowed to run until it <em>yields</em>,
indicating to the Tokio runtimes scheduler that it cannot currently
continue executing. When a task yields, the Tokio runtime switches to
executing the next task.</p>
</li>
<li>
<p>Tasks are <strong>non-blocking</strong>. Typically, when an OS thread performs I/O or
must synchronize with another thread, it <em>blocks</em>, allowing the OS to
schedule another thread. When a task cannot continue executing, it must
yield instead, allowing the Tokio runtime to schedule another task. Tasks
should generally not perform system calls or other operations that could
block a thread, as this would prevent other tasks running on the same
thread from executing as well. Instead, this module provides APIs for
running blocking operations in an asynchronous context.</p>
</li>
</ul>
<h3 id="working-with-tasks"><a class="doc-anchor" href="#working-with-tasks">§</a>Working with Tasks</h3>
<p>This module provides the following APIs for working with tasks:</p>
<h4 id="spawning"><a class="doc-anchor" href="#spawning">§</a>Spawning</h4>
<p>Perhaps the most important function in this module is <a href="fn.spawn.html" title="fn tokio::task::spawn"><code>task::spawn</code></a>. This
function can be thought of as an async equivalent to the standard librarys
<a href="https://doc.rust-lang.org/1.93.1/std/thread/functions/fn.spawn.html" title="fn std::thread::functions::spawn"><code>thread::spawn</code></a>. It takes an <code>async</code> block or other
<a href="https://doc.rust-lang.org/1.93.1/core/future/future/trait.Future.html" title="trait core::future::future::Future">future</a>, and creates a new task to run that work concurrently:</p>
<div class="example-wrap"><pre class="rust rust-example-rendered"><code><span class="kw">use </span>tokio::task;
task::spawn(<span class="kw">async </span>{
<span class="comment">// perform some work here...
</span>});</code></pre></div>
<p>Like <a href="https://doc.rust-lang.org/1.93.1/std/thread/functions/fn.spawn.html" title="fn std::thread::functions::spawn"><code>std::thread::spawn</code></a>, <code>task::spawn</code> returns a <a href="struct.JoinHandle.html" title="struct tokio::task::JoinHandle"><code>JoinHandle</code></a> struct.
A <code>JoinHandle</code> is itself a future which may be used to await the output of
the spawned task. For example:</p>
<div class="example-wrap"><pre class="rust rust-example-rendered"><code><span class="kw">use </span>tokio::task;
<span class="kw">let </span>join = task::spawn(<span class="kw">async </span>{
<span class="comment">// ...
</span><span class="string">"hello world!"
</span>});
<span class="comment">// ...
// Await the result of the spawned task.
</span><span class="kw">let </span>result = join.<span class="kw">await</span><span class="question-mark">?</span>;
<span class="macro">assert_eq!</span>(result, <span class="string">"hello world!"</span>);</code></pre></div>
<p>Again, like <code>std::thread</code>s <a href="https://doc.rust-lang.org/1.93.1/std/thread/join_handle/struct.JoinHandle.html" title="struct std::thread::join_handle::JoinHandle"><code>JoinHandle</code> type</a>, if the spawned
task panics, awaiting its <code>JoinHandle</code> will return a <a href="struct.JoinError.html" title="struct tokio::task::JoinError"><code>JoinError</code></a>. For
example:</p>
<div class="example-wrap"><pre class="rust rust-example-rendered"><code><span class="kw">use </span>tokio::task;
<span class="kw">let </span>join = task::spawn(<span class="kw">async </span>{
<span class="macro">panic!</span>(<span class="string">"something bad happened!"</span>)
});
<span class="comment">// The returned result indicates that the task failed.
</span><span class="macro">assert!</span>(join.<span class="kw">await</span>.is_err());</code></pre></div>
<p><code>spawn</code>, <code>JoinHandle</code>, and <code>JoinError</code> are present when the “rt”
feature flag is enabled.</p>
<h5 id="cancellation"><a class="doc-anchor" href="#cancellation">§</a>Cancellation</h5>
<p>Spawned tasks may be cancelled using the <a href="struct.JoinHandle.html#method.abort" title="method tokio::task::JoinHandle::abort"><code>JoinHandle::abort</code></a> or
<a href="struct.AbortHandle.html#method.abort" title="method tokio::task::AbortHandle::abort"><code>AbortHandle::abort</code></a> methods. When one of these methods are called, the
task is signalled to shut down next time it yields at an <code>.await</code> point. If
the task is already idle, then it will be shut down as soon as possible
without running again before being shut down. Additionally, shutting down a
Tokio runtime (e.g. by returning from <code>#[tokio::main]</code>) immediately cancels
all tasks on it.</p>
<p>When tasks are shut down, it will stop running at whichever <code>.await</code> it has
yielded at. All local variables are destroyed by running their destructor.
Once shutdown has completed, awaiting the <a href="struct.JoinHandle.html" title="struct tokio::task::JoinHandle"><code>JoinHandle</code></a> will fail with a
<a href="struct.JoinError.html#method.is_cancelled" title="method tokio::task::JoinError::is_cancelled">cancelled error</a>.</p>
<p>Note that aborting a task does not guarantee that it fails with a cancelled
error, since it may complete normally first. For example, if the task does
not yield to the runtime at any point between the call to <code>abort</code> and the
end of the task, then the <a href="struct.JoinHandle.html" title="struct tokio::task::JoinHandle"><code>JoinHandle</code></a> will instead report that the task
exited normally.</p>
<p>Be aware that tasks spawned using <a href="fn.spawn_blocking.html" title="fn tokio::task::spawn_blocking"><code>spawn_blocking</code></a> cannot be aborted
because they are not async. If you call <code>abort</code> on a <code>spawn_blocking</code>
task, then this <em>will not have any effect</em>, and the task will continue
running normally. The exception is if the task has not started running
yet; in that case, calling <code>abort</code> may prevent the task from starting.</p>
<p>Be aware that calls to <a href="struct.JoinHandle.html#method.abort" title="method tokio::task::JoinHandle::abort"><code>JoinHandle::abort</code></a> just schedule the task for
cancellation, and will return before the cancellation has completed. To wait
for cancellation to complete, wait for the task to finish by awaiting the
<a href="struct.JoinHandle.html" title="struct tokio::task::JoinHandle"><code>JoinHandle</code></a>. Similarly, the <a href="struct.JoinHandle.html#method.is_finished" title="method tokio::task::JoinHandle::is_finished"><code>JoinHandle::is_finished</code></a> method does not
return <code>true</code> until the cancellation has finished.</p>
<p>Calling <a href="struct.JoinHandle.html#method.abort" title="method tokio::task::JoinHandle::abort"><code>JoinHandle::abort</code></a> multiple times has the same effect as calling
it once.</p>
<p>Tokio also provides an <a href="struct.AbortHandle.html" title="struct tokio::task::AbortHandle"><code>AbortHandle</code></a>, which is like the <a href="struct.JoinHandle.html" title="struct tokio::task::JoinHandle"><code>JoinHandle</code></a>,
except that it does not provide a mechanism to wait for the task to finish.
Each task can only have one <a href="struct.JoinHandle.html" title="struct tokio::task::JoinHandle"><code>JoinHandle</code></a>, but it can have more than one
<a href="struct.AbortHandle.html" title="struct tokio::task::AbortHandle"><code>AbortHandle</code></a>.</p>
<h4 id="blocking-and-yielding"><a class="doc-anchor" href="#blocking-and-yielding">§</a>Blocking and Yielding</h4>
<p>As we discussed above, code running in asynchronous tasks should not perform
operations that can block. A blocking operation performed in a task running
on a thread that is also running other tasks would block the entire thread,
preventing other tasks from running.</p>
<p>Instead, Tokio provides two APIs for running blocking operations in an
asynchronous context: <a href="fn.spawn_blocking.html" title="fn tokio::task::spawn_blocking"><code>task::spawn_blocking</code></a> and <a href="fn.block_in_place.html" title="fn tokio::task::block_in_place"><code>task::block_in_place</code></a>.</p>
<p>Be aware that if you call a non-async method from async code, that non-async
method is still inside the asynchronous context, so you should also avoid
blocking operations there. This includes destructors of objects destroyed in
async code.</p>
<h5 id="spawn_blocking"><a class="doc-anchor" href="#spawn_blocking">§</a><code>spawn_blocking</code></h5>
<p>The <code>task::spawn_blocking</code> function is similar to the <code>task::spawn</code> function
discussed in the previous section, but rather than spawning an
<em>non-blocking</em> future on the Tokio runtime, it instead spawns a
<em>blocking</em> function on a dedicated thread pool for blocking tasks. For
example:</p>
<div class="example-wrap"><pre class="rust rust-example-rendered"><code><span class="kw">use </span>tokio::task;
task::spawn_blocking(|| {
<span class="comment">// do some compute-heavy work or call synchronous code
</span>});</code></pre></div>
<p>Just like <code>task::spawn</code>, <code>task::spawn_blocking</code> returns a <code>JoinHandle</code>
which we can use to await the result of the blocking operation:</p>
<div class="example-wrap"><pre class="rust rust-example-rendered"><code><span class="kw">let </span>join = task::spawn_blocking(|| {
<span class="comment">// do some compute-heavy work or call synchronous code
</span><span class="string">"blocking completed"
</span>});
<span class="kw">let </span>result = join.<span class="kw">await</span><span class="question-mark">?</span>;
<span class="macro">assert_eq!</span>(result, <span class="string">"blocking completed"</span>);</code></pre></div><h5 id="block_in_place"><a class="doc-anchor" href="#block_in_place">§</a><code>block_in_place</code></h5>
<p>When using the <a href="../runtime/index.html#threaded-scheduler">multi-threaded runtime</a>, the <a href="fn.block_in_place.html" title="fn tokio::task::block_in_place"><code>task::block_in_place</code></a>
function is also available. Like <code>task::spawn_blocking</code>, this function
allows running a blocking operation from an asynchronous context. Unlike
<code>spawn_blocking</code>, however, <code>block_in_place</code> works by transitioning the
<em>current</em> worker thread to a blocking thread, moving other tasks running on
that thread to another worker thread. This can improve performance by avoiding
context switches.</p>
<p>For example:</p>
<div class="example-wrap"><pre class="rust rust-example-rendered"><code><span class="kw">use </span>tokio::task;
<span class="kw">let </span>result = task::block_in_place(|| {
<span class="comment">// do some compute-heavy work or call synchronous code
</span><span class="string">"blocking completed"
</span>});
<span class="macro">assert_eq!</span>(result, <span class="string">"blocking completed"</span>);</code></pre></div><h5 id="yield_now"><a class="doc-anchor" href="#yield_now">§</a><code>yield_now</code></h5>
<p>In addition, this module provides a <a href="fn.yield_now.html" title="fn tokio::task::yield_now"><code>task::yield_now</code></a> async function
that is analogous to the standard librarys <a href="https://doc.rust-lang.org/1.93.1/std/thread/functions/fn.yield_now.html" title="fn std::thread::functions::yield_now"><code>thread::yield_now</code></a>. Calling
and <code>await</code>ing this function will cause the current task to yield to the
Tokio runtimes scheduler, allowing other tasks to be
scheduled. Eventually, the yielding task will be polled again, allowing it
to execute. For example:</p>
<div class="example-wrap"><pre class="rust rust-example-rendered"><code><span class="kw">use </span>tokio::task;
<span class="kw">async </span>{
task::spawn(<span class="kw">async </span>{
<span class="comment">// ...
</span><span class="macro">println!</span>(<span class="string">"spawned task done!"</span>)
});
<span class="comment">// Yield, allowing the newly-spawned task to execute first.
</span>task::yield_now().<span class="kw">await</span>;
<span class="macro">println!</span>(<span class="string">"main task done!"</span>);
}</code></pre></div></div></details><h2 id="modules" class="section-header">Modules<a href="#modules" class="anchor">§</a></h2><dl class="item-table"><dt><a class="mod" href="coop/index.html" title="mod tokio::task::coop">coop</a></dt><dd>Utilities for improved cooperative scheduling.</dd><dt><a class="mod" href="futures/index.html" title="mod tokio::task::futures">futures</a></dt><dd>Task-related futures.</dd></dl><h2 id="structs" class="section-header">Structs<a href="#structs" class="anchor">§</a></h2><dl class="item-table"><dt><a class="struct" href="struct.AbortHandle.html" title="struct tokio::task::AbortHandle">Abort<wbr>Handle</a></dt><dd>An owned permission to abort a spawned task, without awaiting its completion.</dd><dt><a class="struct" href="struct.Id.html" title="struct tokio::task::Id">Id</a></dt><dd>An opaque ID that uniquely identifies a task relative to all other currently
running tasks.</dd><dt><a class="struct" href="struct.JoinError.html" title="struct tokio::task::JoinError">Join<wbr>Error</a></dt><dd>Task failed to execute to completion.</dd><dt><a class="struct" href="struct.JoinHandle.html" title="struct tokio::task::JoinHandle">Join<wbr>Handle</a></dt><dd>An owned permission to join on a task (await its termination).</dd><dt><a class="struct" href="struct.JoinSet.html" title="struct tokio::task::JoinSet">JoinSet</a></dt><dd>A collection of tasks spawned on a Tokio runtime.</dd><dt><a class="struct" href="struct.LocalEnterGuard.html" title="struct tokio::task::LocalEnterGuard">Local<wbr>Enter<wbr>Guard</a></dt><dd>Context guard for <code>LocalSet</code></dd><dt><a class="struct" href="struct.LocalKey.html" title="struct tokio::task::LocalKey">Local<wbr>Key</a></dt><dd>A key for task-local data.</dd><dt><a class="struct" href="struct.LocalSet.html" title="struct tokio::task::LocalSet">Local<wbr>Set</a></dt><dd>A set of tasks which are executed on the same thread.</dd></dl><h2 id="functions" class="section-header">Functions<a href="#functions" class="anchor">§</a></h2><dl class="item-table"><dt><a class="fn" href="fn.block_in_place.html" title="fn tokio::task::block_in_place">block_<wbr>in_<wbr>place</a></dt><dd>Runs the provided blocking function on the current thread without
blocking the executor.</dd><dt><a class="fn" href="fn.id.html" title="fn tokio::task::id">id</a></dt><dd>Returns the <a href="struct.Id.html" title="struct tokio::task::Id"><code>Id</code></a> of the currently running task.</dd><dt><a class="fn" href="fn.spawn.html" title="fn tokio::task::spawn">spawn</a></dt><dd>Spawns a new asynchronous task, returning a
<a href="struct.JoinHandle.html" title="struct tokio::task::JoinHandle"><code>JoinHandle</code></a> for it.</dd><dt><a class="fn" href="fn.spawn_blocking.html" title="fn tokio::task::spawn_blocking">spawn_<wbr>blocking</a></dt><dd>Runs the provided closure on a thread where blocking is acceptable.</dd><dt><a class="fn" href="fn.spawn_local.html" title="fn tokio::task::spawn_local">spawn_<wbr>local</a></dt><dd>Spawns a <code>!Send</code> future on the current <a href="struct.LocalSet.html" title="struct tokio::task::LocalSet"><code>LocalSet</code></a> or <a href="struct@crate::runtime::LocalRuntime"><code>LocalRuntime</code></a>.</dd><dt><a class="fn" href="fn.try_id.html" title="fn tokio::task::try_id">try_id</a></dt><dd>Returns the <a href="struct.Id.html" title="struct tokio::task::Id"><code>Id</code></a> of the currently running task, or <code>None</code> if called outside
of a task.</dd><dt><a class="fn" href="fn.yield_now.html" title="fn tokio::task::yield_now">yield_<wbr>now</a></dt><dd>Yields execution back to the Tokio runtime.</dd></dl></section></div></main></body></html>