Skip to content

Commit b6bb06c

Browse files
committed
rustdoc: write detailed chapter on search engine
1 parent 0b3c617 commit b6bb06c

File tree

3 files changed

+243
-50
lines changed

3 files changed

+243
-50
lines changed

src/doc/rustdoc/src/SUMMARY.md

+1
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
- [Command-line arguments](command-line-arguments.md)
55
- [How to read rustdoc output](how-to-read-rustdoc.md)
66
- [In-doc settings](read-documentation/in-doc-settings.md)
7+
- [Search](read-documentation/search.md)
78
- [How to write documentation](how-to-write-documentation.md)
89
- [What to include (and exclude)](write-documentation/what-to-include.md)
910
- [The `#[doc]` attribute](write-documentation/the-doc-attribute.md)

src/doc/rustdoc/src/how-to-read-rustdoc.md

+5-50
Original file line numberDiff line numberDiff line change
@@ -59,56 +59,11 @@ or the current item whose documentation is being displayed.
5959
## The Theme Picker and Search Interface
6060

6161
When viewing `rustdoc`'s output in a browser with JavaScript enabled,
62-
a dynamic interface appears at the top of the page composed of the search
63-
interface, help screen, and options.
64-
65-
### The Search Interface
66-
67-
Typing in the search bar instantly searches the available documentation for
68-
the string entered with a fuzzy matching algorithm that is tolerant of minor
69-
typos.
70-
71-
By default, the search results given are "In Names",
72-
meaning that the fuzzy match is made against the names of items.
73-
Matching names are shown on the left, and the first few words of their
74-
descriptions are given on the right.
75-
By clicking an item, you will navigate to its particular documentation.
76-
77-
There are two other sets of results, shown as tabs in the search results pane.
78-
"In Parameters" shows matches for the string in the types of parameters to
79-
functions, and "In Return Types" shows matches in the return types of functions.
80-
Both are very useful when looking for a function whose name you can't quite
81-
bring to mind when you know the type you have or want.
82-
83-
Names in the search interface can be prefixed with an item type followed by a
84-
colon (such as `mod:`) to restrict the results to just that kind of item. Also,
85-
searching for `println!` will search for a macro named `println`, just like
86-
searching for `macro:println` does.
87-
88-
Function signature searches can query generics, wrapped in angle brackets, and
89-
traits are normalized like types in the search engine. For example, a function
90-
with the signature `fn my_function<I: Iterator<Item=u32>>(input: I) -> usize`
91-
can be matched with the following queries:
92-
93-
* `Iterator<u32> -> usize`
94-
* `trait:Iterator<primitive:u32> -> primitive:usize`
95-
* `Iterator -> usize`
96-
97-
Generics and function parameters are order-agnostic, but sensitive to nesting
98-
and number of matches. For example, a function with the signature
99-
`fn read_all(&mut self: impl Read) -> Result<Vec<u8>, Error>`
100-
will match these queries:
101-
102-
* `Read -> Result<Vec<u8>, Error>`
103-
* `Read -> Result<Error, Vec>`
104-
* `Read -> Result<Vec<u8>>`
105-
106-
But it *does not* match `Result<Vec, u8>` or `Result<u8<Vec>>`.
107-
108-
Function signature searches also support arrays and slices. The explicit name
109-
`primitive:slice<u8>` and `primitive:array<u8>` can be used to match a slice
110-
or array of bytes, while square brackets `[u8]` will match either one. Empty
111-
square brackets, `[]`, will match any slice regardless of what it contains.
62+
a dynamic interface appears at the top of the page composed of the [search]
63+
interface, help screen, and [options].
64+
65+
[options]: read-documentation/in-doc-settings.html
66+
[search]: read-documentation/search.md
11267

11368
Paths are supported as well, you can look for `Vec::new` or `Option::Some` or
11469
even `module::module_child::another_child::struct::field`. Whitespace characters
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,237 @@
1+
# Rustdoc search
2+
3+
Typing in the search bar instantly searches the available documentation,
4+
matching either the name and path of an item, or a function's approximate
5+
type signature.
6+
7+
## Search By Name
8+
9+
To search by the name of an item (items include modules, types, traits,
10+
functions, and macros), write its name or path. As a special case, the parts
11+
of a path that normally get divided by `::` double colons can instead be
12+
separated by spaces. For example:
13+
14+
* [`vec new`] and [`vec::new`] both show the function `std::vec::Vec::new`
15+
as a result.
16+
* [`vec`], [`vec vec`], [`std::vec`], and [`std::vec::Vec`] all include the struct
17+
`std::vec::Vec` itself in the results (and all but the last one also
18+
include the module in the results).
19+
20+
[`vec new`]: ../../std/vec/struct.Vec.html?search=vec%20new&filter-crate=std
21+
[`vec::new`]: ../../std/vec/struct.Vec.html?search=vec::new&filter-crate=std
22+
[`vec`]: ../../std/vec/struct.Vec.html?search=vec&filter-crate=std
23+
[`vec vec`]: ../../std/vec/struct.Vec.html?search=vec%20vec&filter-crate=std
24+
[`std::vec`]: ../../std/vec/struct.Vec.html?search=std::vec&filter-crate=std
25+
[`std::vec::Vec`]: ../../std/vec/struct.Vec.html?search=std::vec::Vec&filter-crate=std
26+
[`std::vec::Vec`]: ../../std/vec/struct.Vec.html?search=std::vec::Vec&filter-crate=std
27+
28+
As a quick way to trim down the list of results, there's a drop-down selector
29+
below the search input, labeled "Results in \[std\]". Clicking it can change
30+
which crate is being searched.
31+
32+
Rustdoc uses a fuzzy matching function that can tolerate typos for this,
33+
though it's based on the length of the name that's typed in, so a good example
34+
of how this works would be [`HahsMap`]. To avoid this, wrap the item in quotes,
35+
searching for `"HahsMap"` (in this example, no results will be returned).
36+
37+
[`HahsMap`]: ../../std/collections/struct.HashMap.html?search=HahsMap&filter-crate=std
38+
39+
### Tabs in the Search By Name interface
40+
41+
In fact, using [`HahsMap`] again as the example, it tells you that you're
42+
using "In Names" by default, but also lists two other tabs below the crate
43+
drop-down: "In Parameters" and "In Return Types".
44+
45+
These two tabs are lists of functions, defined on the closest matching type
46+
to the search (for `HahsMap`, it loudly auto-corrects to `hashmap`). This
47+
auto-correct only kicks in if nothing is found that matches the literal.
48+
49+
These tabs are not just methods. For example, searching the alloc crate for
50+
[`Layout`] also lists functions that accept layouts even though they're
51+
methods on the allocator or free functions.
52+
53+
[`Layout`]: ../../alloc/index.html?search=Layout&filter-crate=alloc
54+
55+
## Searching By Type Signature for functions
56+
57+
If you know more specifically what the function you want to look at does,
58+
Rustdoc can search by more than one type at once in the parameters and return
59+
value. Multiple parameters are separated by `,` commas, and the return value
60+
is written with after a `->` arrow.
61+
62+
Before describing the syntax in more detail, here's a few sample searches of
63+
the standard library and functions that are included in the results list:
64+
65+
| Query | Results |
66+
|-------|--------|
67+
| [`usize -> vec`][] | `slice::repeat` and `Vec::with_capacity` |
68+
| [`vec, vec -> bool`][] | `Vec::eq` |
69+
| [`option<T>, fnonce -> option<U>`][] | `Option::map` and `Option::and_then` |
70+
| [`option<T>, fnonce -> option<T>`][] | `Option::filter` and `Option::inspect` |
71+
| [`option -> default`][] | `Option::unwrap_or_default` |
72+
| [`stdout, [u8]`][stdoutu8] | `Stdout::write` |
73+
| [`any -> !`][] | `panic::panic_any` |
74+
75+
[`usize -> vec`]: ../../std/vec/struct.Vec.html?search=usize%20-%3E%20vec&filter-crate=std
76+
[`vec, vec -> bool`]: ../../std/vec/struct.Vec.html?search=vec,%20vec%20-%3E%20bool&filter-crate=std
77+
[`option<T>, fnonce -> option<U>`]: ../../std/vec/struct.Vec.html?search=option<T>%2C%20fnonce%20->%20option<U>&filter-crate=std
78+
[`option<T>, fnonce -> option<T>`]: ../../std/vec/struct.Vec.html?search=option<T>%2C%20fnonce%20->%20option<T>&filter-crate=std
79+
[`option -> default`]: ../../std/vec/struct.Vec.html?search=option%20-%3E%20default&filter-crate=std
80+
[`any -> !`]: ../../std/vec/struct.Vec.html?search=any%20-%3E%20!&filter-crate=std
81+
[stdoutu8]: ../../std/vec/struct.Vec.html?search=stdout%2C%20[u8]&filter-crate=std
82+
83+
### How type-based search works
84+
85+
In a complex type-based search, Rustdoc always treats every item as literal.
86+
If a name is used and nothing in the docs matches the individual item, such as
87+
a typo-ed [`uize -> vec`][] search, the item `uize` is treated as a generic
88+
type parameter (resulting in `vec::from` and other generic vec constructors).
89+
90+
[`uize -> vec`]: ../../std/vec/struct.Vec.html?search=uize%20-%3E%20vec&filter-crate=std
91+
92+
After deciding which items are type parameters and which are actual types, it
93+
then searches by matching up the function parameters (written before the `->`)
94+
and the return types (written after the `->`). Type matching is order-agnostic,
95+
and allows items to be left out of the query, but items that are present in the
96+
query must be present in the function for it to match.
97+
98+
Function signature searches can query generics, wrapped in angle brackets, and
99+
traits will be normalized like types in the search engine if no type parameters
100+
match them. For example, a function with the signature
101+
`fn my_function<I: Iterator<Item=u32>>(input: I) -> usize`
102+
can be matched with the following queries:
103+
104+
* `Iterator<u32> -> usize`
105+
* `Iterator -> usize`
106+
107+
Generics and function parameters are order-agnostic, but sensitive to nesting
108+
and number of matches. For example, a function with the signature
109+
`fn read_all(&mut self: impl Read) -> Result<Vec<u8>, Error>`
110+
will match these queries:
111+
112+
* `Read -> Result<Vec<u8>, Error>`
113+
* `Read -> Result<Error, Vec>`
114+
* `Read -> Result<Vec<u8>>`
115+
116+
But it *does not* match `Result<Vec, u8>` or `Result<u8<Vec>>`.
117+
118+
Function signature searches also support arrays and slices. The explicit name
119+
`primitive:slice<u8>` and `primitive:array<u8>` can be used to match a slice
120+
or array of bytes, while square brackets `[u8]` will match either one. Empty
121+
square brackets, `[]`, will match any slice or array regardless of what
122+
it contains, while a slice with a type parameter, like `[T]`, will only match
123+
functions that actually operate on generic slices.
124+
125+
### Limitations and quirks of type-based search
126+
127+
Type-based search is still a buggy, experimental, work-in-progress feature.
128+
Most of these limitations should be addressed in future version of Rustdoc.
129+
130+
* There's no way to write trait constraints on generic parameters.
131+
You can name traits directly, and if there's a type parameter
132+
with that bound, it'll match, but `option<T> -> T where T: Default`
133+
cannot be precisely searched for (use `option<Default> -> Default`).
134+
135+
* Type parameters match type parameters, such that `Option<A>` matches
136+
`Option<T>`, but never match concrete types in function signatures.
137+
A trait named as if it were a type, such as `Option<Read>`, will match
138+
a type parameter constrained by that trait, such as
139+
`Option<T> where T: Read`, as well as matching `dyn Trait` and
140+
`impl Trait`.
141+
142+
* `impl Trait` in argument position is treated exactly like a type
143+
parameter, but in return position it will not match type parameters.
144+
145+
* Any type named in a complex type-based search will be assumed to be a
146+
type parameter if nothing matching the name exactly is found. If you
147+
want to force a type parameter, write `generic:T` and it will be used
148+
as a type parameter even if a matching name is found. If you know
149+
that you don't want a type parameter, you can force it to match
150+
something else by giving it a different prefix like `struct:T`.
151+
152+
* It's impossible to search for references, pointers, or tuples. The
153+
wrapped types can be searched for, so a function that takes `&File` can
154+
be found with `File`, but you'll get a parse error when typing an `&`
155+
into the search field. Similarly, `Option<(T, U)>` can be matched with
156+
`Option<T, U>`, but `(` will give a parse error.
157+
158+
* Path searches, like `hash_map::Entry`, don't work in type-based search.
159+
160+
* Searching for lifetimes is not supported.
161+
162+
* It's impossible to search for closures based on their parameters or
163+
return values.
164+
165+
* It's impossible to search based on the length of an array.
166+
167+
## Item filtering
168+
169+
Names in the search interface can be prefixed with an item type followed by a
170+
colon (such as `mod:`) to restrict the results to just that kind of item. Also,
171+
searching for `println!` will search for a macro named `println`, just like
172+
searching for `macro:println` does. The complete list of available filters is
173+
given under the <kbd>?</kbd> Help area, and in the detailed syntax below.
174+
175+
Item filters can be used in both name-based and type signature-based searches.
176+
177+
## Search query syntax
178+
179+
```text
180+
ident = *(ALPHA / DIGIT / "_")
181+
path = ident *(DOUBLE-COLON ident) [!]
182+
slice = OPEN-SQUARE-BRACKET [ nonempty-arg-list ] CLOSE-SQUARE-BRACKET
183+
arg = [type-filter *WS COLON *WS] (path [generics] / slice / [!])
184+
type-sep = COMMA/WS *(COMMA/WS)
185+
nonempty-arg-list = *(type-sep) arg *(type-sep arg) *(type-sep)
186+
generics = OPEN-ANGLE-BRACKET [ nonempty-arg-list ] *(type-sep)
187+
CLOSE-ANGLE-BRACKET
188+
return-args = RETURN-ARROW *(type-sep) nonempty-arg-list
189+
190+
exact-search = [type-filter *WS COLON] [ RETURN-ARROW ] *WS QUOTE ident QUOTE [ generics ]
191+
type-search = [ nonempty-arg-list ] [ return-args ]
192+
193+
query = *WS (exact-search / type-search) *WS
194+
195+
type-filter = (
196+
"mod" /
197+
"externcrate" /
198+
"import" /
199+
"struct" /
200+
"enum" /
201+
"fn" /
202+
"type" /
203+
"static" /
204+
"trait" /
205+
"impl" /
206+
"tymethod" /
207+
"method" /
208+
"structfield" /
209+
"variant" /
210+
"macro" /
211+
"primitive" /
212+
"associatedtype" /
213+
"constant" /
214+
"associatedconstant" /
215+
"union" /
216+
"foreigntype" /
217+
"keyword" /
218+
"existential" /
219+
"attr" /
220+
"derive" /
221+
"traitalias" /
222+
"generic")
223+
224+
OPEN-ANGLE-BRACKET = "<"
225+
CLOSE-ANGLE-BRACKET = ">"
226+
OPEN-SQUARE-BRACKET = "["
227+
CLOSE-SQUARE-BRACKET = "]"
228+
COLON = ":"
229+
DOUBLE-COLON = "::"
230+
QUOTE = %x22
231+
COMMA = ","
232+
RETURN-ARROW = "->"
233+
234+
ALPHA = %x41-5A / %x61-7A ; A-Z / a-z
235+
DIGIT = %x30-39
236+
WS = %x09 / " "
237+
```

0 commit comments

Comments
 (0)