Skip to content

Commit 8a78eb2

Browse files
authored
Merge pull request #2768 from rust-lang/diags
Update diagnostics documentation
2 parents 313c111 + 37905eb commit 8a78eb2

File tree

2 files changed

+56
-134
lines changed

2 files changed

+56
-134
lines changed

src/diagnostics/diagnostic-structs.md

Lines changed: 53 additions & 120 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ customizing the rendering logic, or selecting messages at runtime, you will need
1212
the corresponding trait (`Diagnostic`, `LintDiagnostic`, or `Subdiagnostic`).
1313
This approach provides greater flexibility and is recommended for diagnostics that go beyond simple, static structures.
1414

15-
Diagnostic can be translated into different languages and each has a slug that uniquely identifies the diagnostic.
15+
Diagnostic can be translated into different languages.
1616

1717
## `#[derive(Diagnostic)]` and `#[derive(LintDiagnostic)]`
1818

@@ -21,13 +21,13 @@ shown below:
2121

2222
```rust,ignore
2323
#[derive(Diagnostic)]
24-
#[diag(hir_analysis_field_already_declared, code = E0124)]
24+
#[diag("field `{$field_name}` is already declared", code = E0124)]
2525
pub struct FieldAlreadyDeclared {
2626
pub field_name: Ident,
2727
#[primary_span]
28-
#[label]
28+
#[label("field already declared")]
2929
pub span: Span,
30-
#[label(previous_decl_label)]
30+
#[label("`{$field_name}` first declared here")]
3131
pub prev_span: Span,
3232
}
3333
```
@@ -42,25 +42,10 @@ the `code` sub-attribute. Specifying a `code` isn't mandatory, but if you are
4242
porting a diagnostic that uses `Diag` to use `Diagnostic`
4343
then you should keep the code if there was one.
4444

45-
`#[diag(..)]` must provide a slug as the first positional argument (a path to an
46-
item in `rustc_errors::fluent::*`). A slug uniquely identifies the diagnostic
47-
and is also how the compiler knows what error message to emit (in the default
48-
locale of the compiler, or in the locale requested by the user). See
45+
`#[diag(..)]` must provide a message as the first positional argument.
46+
The message is written in English, but might be translated to the locale requested by the user. See
4947
[translation documentation](./translation.md) to learn more about how
50-
translatable error messages are written and how slug items are generated.
51-
52-
In our example, the Fluent message for the "field already declared" diagnostic
53-
looks like this:
54-
55-
```fluent
56-
hir_analysis_field_already_declared =
57-
field `{$field_name}` is already declared
58-
.label = field already declared
59-
.previous_decl_label = `{$field_name}` first declared here
60-
```
61-
62-
`hir_analysis_field_already_declared` is the slug from our example and is followed
63-
by the diagnostic message.
48+
translatable error messages are written and how they are generated.
6449

6550
Every field of the `Diagnostic` which does not have an annotation is
6651
available in Fluent messages as a variable, like `field_name` in the example
@@ -76,13 +61,7 @@ specified on a `Diagnostic`.
7661

7762
`#[label]`, `#[help]`, `#[warning]` and `#[note]` can all be applied to fields which have the
7863
type `Span`. Applying any of these attributes will create the corresponding
79-
subdiagnostic with that `Span`. These attributes will look for their
80-
diagnostic message in a Fluent attribute attached to the primary Fluent
81-
message. In our example, `#[label]` will look for
82-
`hir_analysis_field_already_declared.label` (which has the message "field already
83-
declared"). If there is more than one subdiagnostic of the same type, then
84-
these attributes can also take a value that is the attribute name to look for
85-
(e.g. `previous_decl_label` in our example).
64+
subdiagnostic with that `Span`. These attributes take a diagnostic message as an argument.
8665

8766
Other types have special behavior when used in a `Diagnostic` derive:
8867

@@ -99,17 +78,17 @@ represent optional `#[note]`/`#[help]`/`#[warning]` subdiagnostics.
9978

10079
Suggestions can be emitted using one of four field attributes:
10180

102-
- `#[suggestion(slug, code = "...", applicability = "...")]`
103-
- `#[suggestion_hidden(slug, code = "...", applicability = "...")]`
104-
- `#[suggestion_short(slug, code = "...", applicability = "...")]`
105-
- `#[suggestion_verbose(slug, code = "...", applicability = "...")]`
81+
- `#[suggestion("message", code = "...", applicability = "...")]`
82+
- `#[suggestion_hidden("message", code = "...", applicability = "...")]`
83+
- `#[suggestion_short("message", code = "...", applicability = "...")]`
84+
- `#[suggestion_verbose("message", code = "...", applicability = "...")]`
10685

10786
Suggestions must be applied on either a `Span` field or a `(Span,
108-
MachineApplicability)` field. Similarly to other field attributes, the slug
109-
specifies the Fluent attribute with the message and defaults to the equivalent
110-
of `.suggestion`. `code` specifies the code that should be suggested as a
87+
MachineApplicability)` field. Similarly to other field attributes, a message
88+
needs to be provided which will be shown to the user.
89+
`code` specifies the code that should be suggested as a
11190
replacement and is a format string (e.g. `{field_name}` would be replaced by
112-
the value of the `field_name` field of the struct), not a Fluent identifier.
91+
the value of the `field_name` field of the struct).
11392
`applicability` can be used to specify the applicability in the attribute, it
11493
cannot be used when the field's type contains an `Applicability`.
11594

@@ -119,15 +98,15 @@ In the end, the `Diagnostic` derive will generate an implementation of
11998
```rust,ignore
12099
impl<'a, G: EmissionGuarantee> Diagnostic<'a> for FieldAlreadyDeclared {
121100
fn into_diag(self, dcx: &'a DiagCtxt, level: Level) -> Diag<'a, G> {
122-
let mut diag = Diag::new(dcx, level, fluent::hir_analysis_field_already_declared);
101+
let mut diag = Diag::new(dcx, level, "field `{$field_name}` is already declared");
123102
diag.set_span(self.span);
124103
diag.span_label(
125104
self.span,
126-
fluent::hir_analysis_label
105+
"field already declared"
127106
);
128107
diag.span_label(
129108
self.prev_span,
130-
fluent::hir_analysis_previous_decl_label
109+
"`{$field_name}` first declared here"
131110
);
132111
diag
133112
}
@@ -150,60 +129,40 @@ tcx.dcx().emit_err(FieldAlreadyDeclared {
150129
`#[derive(Diagnostic)]` and `#[derive(LintDiagnostic)]` support the
151130
following attributes:
152131

153-
- `#[diag(slug, code = "...")]`
132+
- `#[diag("message", code = "...")]`
154133
- _Applied to struct or enum variant._
155134
- _Mandatory_
156135
- Defines the text and error code to be associated with the diagnostic.
157-
- Slug (_Mandatory_)
158-
- Uniquely identifies the diagnostic and corresponds to its Fluent message,
159-
mandatory.
160-
- A path to an item in `rustc_errors::fluent`, e.g.
161-
`rustc_errors::fluent::hir_analysis_field_already_declared`
162-
(`rustc_errors::fluent` is implicit in the attribute, so just
163-
`hir_analysis_field_already_declared`).
136+
- Message (_Mandatory_)
137+
- The diagnostic message which will be shown to the user.
164138
- See [translation documentation](./translation.md).
165139
- `code = "..."` (_Optional_)
166140
- Specifies the error code.
167-
- `#[note]` or `#[note(slug)]` (_Optional_)
141+
- `#[note("message")]` (_Optional_)
168142
- _Applied to struct or struct fields of type `Span`, `Option<()>` or `()`._
169143
- Adds a note subdiagnostic.
170-
- Value is a path to an item in `rustc_errors::fluent` for the note's
171-
message.
172-
- Defaults to equivalent of `.note`.
144+
- Value is the note's message.
173145
- If applied to a `Span` field, creates a spanned note.
174-
- `#[help]` or `#[help(slug)]` (_Optional_)
146+
- `#[help("message")]` (_Optional_)
175147
- _Applied to struct or struct fields of type `Span`, `Option<()>` or `()`._
176148
- Adds a help subdiagnostic.
177-
- Value is a path to an item in `rustc_errors::fluent` for the note's
178-
message.
179-
- Defaults to equivalent of `.help`.
149+
- Value is the help message.
180150
- If applied to a `Span` field, creates a spanned help.
181-
- `#[label]` or `#[label(slug)]` (_Optional_)
151+
- `#[label("message")]` (_Optional_)
182152
- _Applied to `Span` fields._
183153
- Adds a label subdiagnostic.
184-
- Value is a path to an item in `rustc_errors::fluent` for the note's
185-
message.
186-
- Defaults to equivalent of `.label`.
187-
- `#[warning]` or `#[warning(slug)]` (_Optional_)
154+
- Value is the label's message.
155+
- `#[warning("message")]` (_Optional_)
188156
- _Applied to struct or struct fields of type `Span`, `Option<()>` or `()`._
189157
- Adds a warning subdiagnostic.
190-
- Value is a path to an item in `rustc_errors::fluent` for the note's
191-
message.
192-
- Defaults to equivalent of `.warn`.
193-
- `#[suggestion{,_hidden,_short,_verbose}(slug, code = "...", applicability = "...")]`
158+
- Value is the warning's message.
159+
- `#[suggestion{,_hidden,_short,_verbose}("message", code = "...", applicability = "...")]`
194160
(_Optional_)
195161
- _Applied to `(Span, MachineApplicability)` or `Span` fields._
196162
- Adds a suggestion subdiagnostic.
197-
- Slug (_Mandatory_)
198-
- A path to an item in `rustc_errors::fluent`, e.g.
199-
`rustc_errors::fluent::hir_analysis_field_already_declared`
200-
(`rustc_errors::fluent` is implicit in the attribute, so just
201-
`hir_analysis_field_already_declared`). Fluent attributes for all messages
202-
exist as top-level items in that module (so `hir_analysis_message.attr` is just
203-
`attr`).
163+
- Message (_Mandatory_)
164+
- Value is the suggestion message that will be shown to the user.
204165
- See [translation documentation](./translation.md).
205-
- Defaults to `rustc_errors::fluent::_subdiag::suggestion` (or
206-
- `.suggestion` in Fluent).
207166
- `code = "..."`/`code("...", ...)` (_Mandatory_)
208167
- One or multiple format strings indicating the code to be suggested as a
209168
replacement. Multiple values signify multiple possible replacements.
@@ -235,12 +194,12 @@ shown below:
235194
```rust
236195
#[derive(Subdiagnostic)]
237196
pub enum ExpectedReturnTypeLabel<'tcx> {
238-
#[label(hir_analysis_expected_default_return_type)]
197+
#[label("expected `()` because of default return type")]
239198
Unit {
240199
#[primary_span]
241200
span: Span,
242201
},
243-
#[label(hir_analysis_expected_return_type)]
202+
#[label("expected `{$expected}` because of return type")]
244203
Other {
245204
#[primary_span]
246205
span: Span,
@@ -260,21 +219,9 @@ attribute applied to the struct or each variant, one of:
260219
- `#[warning(..)]` for defining a warning
261220
- `#[suggestion{,_hidden,_short,_verbose}(..)]` for defining a suggestion
262221

263-
All of the above must provide a slug as the first positional argument (a path
264-
to an item in `rustc_errors::fluent::*`). A slug uniquely identifies the
265-
diagnostic and is also how the compiler knows what error message to emit (in
266-
the default locale of the compiler, or in the locale requested by the user).
222+
All of the above must provide a diagnostic message as the first positional argument.
267223
See [translation documentation](./translation.md) to learn more about how
268-
translatable error messages are written and how slug items are generated.
269-
270-
In our example, the Fluent message for the "expected return type" label
271-
looks like this:
272-
273-
```fluent
274-
hir_analysis_expected_default_return_type = expected `()` because of default return type
275-
276-
hir_analysis_expected_return_type = expected `{$expected}` because of return type
277-
```
224+
translatable error messages are generated.
278225

279226
Using the `#[primary_span]` attribute on a field (with type `Span`) will denote
280227
the primary span of the subdiagnostic. A primary span is only necessary for a
@@ -289,17 +236,15 @@ Like `Diagnostic`, `Subdiagnostic` supports `Option<T>` and
289236

290237
Suggestions can be emitted using one of four attributes on the type/variant:
291238

292-
- `#[suggestion(..., code = "...", applicability = "...")]`
293-
- `#[suggestion_hidden(..., code = "...", applicability = "...")]`
294-
- `#[suggestion_short(..., code = "...", applicability = "...")]`
295-
- `#[suggestion_verbose(..., code = "...", applicability = "...")]`
239+
- `#[suggestion("...", code = "...", applicability = "...")]`
240+
- `#[suggestion_hidden("...", code = "...", applicability = "...")]`
241+
- `#[suggestion_short("...", code = "...", applicability = "...")]`
242+
- `#[suggestion_verbose("...", code = "...", applicability = "...")]`
296243

297244
Suggestions require `#[primary_span]` be set on a field and can have the
298245
following sub-attributes:
299246

300-
- The first positional argument specifies the path to a item in
301-
`rustc_errors::fluent` corresponding to the Fluent attribute with the message
302-
and defaults to the equivalent of `.suggestion`.
247+
- The first positional argument specifies the message which will be shown to the user.
303248
- `code` specifies the code that should be suggested as a replacement and is a
304249
format string (e.g. `{field_name}` would be replaced by the value of the
305250
`field_name` field of the struct), not a Fluent identifier.
@@ -318,11 +263,11 @@ impl<'tcx> Subdiagnostic for ExpectedReturnTypeLabel<'tcx> {
318263
use rustc_errors::{Applicability, IntoDiagArg};
319264
match self {
320265
ExpectedReturnTypeLabel::Unit { span } => {
321-
diag.span_label(span, rustc_errors::fluent::hir_analysis_expected_default_return_type)
266+
diag.span_label(span, "expected `()` because of default return type")
322267
}
323268
ExpectedReturnTypeLabel::Other { span, expected } => {
324269
diag.set_arg("expected", expected);
325-
diag.span_label(span, rustc_errors::fluent::hir_analysis_expected_return_type)
270+
diag.span_label(span, "expected `{$expected}` because of return type")
326271
}
327272
}
328273
}
@@ -354,7 +299,7 @@ If a subdiagnostic sets a argument with the same name as a arguments already in
354299
it will report an error at runtime unless both have exactly the same value.
355300
It has two benefits:
356301
- preserves the flexibility that arguments in the main diagnostic are allowed to appear in the attributes of the subdiagnostic.
357-
For example, There is an attribute `#[suggestion(code = "{new_vis}")]` in the subdiagnostic, but `new_vis` is the field in the main diagnostic struct.
302+
For example, There is an attribute `#[suggestion("...", code = "{new_vis}")]` in the subdiagnostic, but `new_vis` is the field in the main diagnostic struct.
358303
- prevents accidental overwriting or deletion of arguments required by the main diagnostic or other subdiagnostics.
359304

360305
These rules guarantee that arguments injected by subdiagnostics are strictly scoped to their own rendering.
@@ -364,32 +309,20 @@ Additionally, subdiagnostics can access arguments from the main diagnostic with
364309
### Reference for `#[derive(Subdiagnostic)]`
365310
`#[derive(Subdiagnostic)]` supports the following attributes:
366311

367-
- `#[label(slug)]`, `#[help(slug)]`, `#[warning(slug)]` or `#[note(slug)]`
312+
- `#[label("message")]`, `#[help("message")]`, `#[warning("message")]` or `#[note("message")]`
368313
- _Applied to struct or enum variant. Mutually exclusive with struct/enum variant attributes._
369314
- _Mandatory_
370315
- Defines the type to be representing a label, help or note.
371-
- Slug (_Mandatory_)
372-
- Uniquely identifies the diagnostic and corresponds to its Fluent message,
373-
mandatory.
374-
- A path to an item in `rustc_errors::fluent`, e.g.
375-
`rustc_errors::fluent::hir_analysis_field_already_declared`
376-
(`rustc_errors::fluent` is implicit in the attribute, so just
377-
`hir_analysis_field_already_declared`).
316+
- Message (_Mandatory_)
317+
- The diagnostic message that will be shown to the user.
378318
- See [translation documentation](./translation.md).
379-
- `#[suggestion{,_hidden,_short,_verbose}(slug, code = "...", applicability = "...")]`
319+
- `#[suggestion{,_hidden,_short,_verbose}("message", code = "...", applicability = "...")]`
380320
- _Applied to struct or enum variant. Mutually exclusive with struct/enum variant attributes._
381321
- _Mandatory_
382322
- Defines the type to be representing a suggestion.
383-
- Slug (_Mandatory_)
384-
- A path to an item in `rustc_errors::fluent`, e.g.
385-
`rustc_errors::fluent::hir_analysis_field_already_declared`
386-
(`rustc_errors::fluent` is implicit in the attribute, so just
387-
`hir_analysis::field_already_declared`). Fluent attributes for all messages
388-
exist as top-level items in that module (so `hir_analysis_message.attr` is just
389-
`hir_analysis::attr`).
323+
- Message (_Mandatory_)
324+
- The diagnostic message that will be shown to the user.
390325
- See [translation documentation](./translation.md).
391-
- Defaults to `rustc_errors::fluent::_subdiag::suggestion` (or
392-
- `.suggestion` in Fluent).
393326
- `code = "..."`/`code("...", ...)` (_Mandatory_)
394327
- One or multiple format strings indicating the code to be suggested as a
395328
replacement. Multiple values signify multiple possible replacements.
@@ -401,11 +334,11 @@ Additionally, subdiagnostics can access arguments from the main diagnostic with
401334
- `maybe-incorrect`
402335
- `has-placeholders`
403336
- `unspecified`
404-
- `#[multipart_suggestion{,_hidden,_short,_verbose}(slug, applicability = "...")]`
337+
- `#[multipart_suggestion{,_hidden,_short,_verbose}("message", applicability = "...")]`
405338
- _Applied to struct or enum variant. Mutually exclusive with struct/enum variant attributes._
406339
- _Mandatory_
407340
- Defines the type to be representing a multipart suggestion.
408-
- Slug (_Mandatory_): see `#[suggestion]`
341+
- Message (_Mandatory_): see `#[suggestion]`
409342
- `applicability = "..."` (_Optional_): see `#[suggestion]`
410343
- `#[primary_span]` (_Mandatory_ for labels and suggestions; _optional_ otherwise; not applicable
411344
to multipart suggestions)

src/diagnostics/translation.md

Lines changed: 3 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,7 @@ active redesign proposals (as of
1313
Please see the tracking issue <https://github.com/rust-lang/rust/issues/132181>
1414
for status updates.
1515

16-
We have downgraded the internal lints `untranslatable_diagnostic` and
17-
`diagnostic_outside_of_impl`. Those internal lints previously required new code
18-
to use the current translation infrastructure. However, because the translation
19-
infra is waiting for a yet-to-be-proposed redesign and thus rework, we are not
16+
The translation infra is waiting for a yet-to-be-proposed redesign and thus rework, we are not
2017
mandating usage of current translation infra. Use the infra if you *want to* or
2118
otherwise makes the code cleaner, but otherwise sidestep the translation infra
2219
if you need more flexibility.
@@ -40,11 +37,6 @@ There are two ways of writing translatable diagnostics:
4037
When adding or changing a translatable diagnostic,
4138
you don't need to worry about the translations.
4239
Only updating the original English message is required.
43-
Currently,
44-
each crate which defines translatable diagnostics has its own Fluent resource,
45-
which is a file named `messages.ftl`,
46-
located in the root of the crate
47-
(such as`compiler/rustc_expand/messages.ftl`).
4840

4941
## Fluent
5042

@@ -118,11 +110,8 @@ information that needs to be provided by the code to do so.
118110

119111
### Compile-time validation and typed identifiers
120112

121-
rustc's `fluent_messages` macro performs compile-time validation of Fluent
122-
resources and generates code to make it easier to refer to Fluent messages in
123-
diagnostics.
124-
125-
Compile-time validation of Fluent resources will emit any parsing errors
113+
rustc's `#[derive(Diagnostic)]` macro performs compile-time validation of Fluent
114+
messages. Compile-time validation of Fluent resources will emit any parsing errors
126115
from Fluent resources while building the compiler, preventing invalid Fluent
127116
resources from causing panics in the compiler. Compile-time validation also
128117
emits an error if multiple Fluent messages have the same identifier.

0 commit comments

Comments
 (0)