usecrate::{abort_now, check_correctness, sealed::Sealed, SpanRange}; use proc_macro2::Span; use proc_macro2::TokenStream;
use quote::{quote_spanned, ToTokens};
/// Represents a diagnostic level /// /// # Warnings /// /// Warnings are ignored on stable/beta #[derive(Debug, PartialEq)] #[non_exhaustive] pubenum Level {
Error,
Warning,
}
/// Represents a single diagnostic message #[derive(Debug)] #[must_use = "A diagnostic does nothing unless emitted"] pubstruct Diagnostic { pub(crate) level: Level, pub(crate) span_range: SpanRange, pub(crate) msg: String, pub(crate) suggestions: Vec<(SuggestionKind, String, Option<SpanRange>)>, pub(crate) children: Vec<(SpanRange, String)>,
}
/// A collection of methods that do not exist in `proc_macro::Diagnostic` /// but still useful to have around. /// /// This trait is sealed and cannot be implemented outside of `proc_macro_error`. pubtrait DiagnosticExt: Sealed { /// Create a new diagnostic message that points to the `span_range`. /// /// This function is the same as `Diagnostic::spanned` but produces considerably /// better error messages for multi-token spans on stable. fn spanned_range(span_range: SpanRange, level: Level, message: String) -> Self;
/// Add another error message to self such that it will be emitted right after /// the main message. /// /// This function is the same as `Diagnostic::span_error` but produces considerably /// better error messages for multi-token spans on stable. #[must_use] fn span_range_error(self, span_range: SpanRange, msg: String) -> Self;
/// Attach a "help" note to your main message, the note will have it's own span on nightly. /// /// This function is the same as `Diagnostic::span_help` but produces considerably /// better error messages for multi-token spans on stable. /// /// # Span /// /// The span is ignored on stable, the note effectively inherits its parent's (main message) span #[must_use] fn span_range_help(self, span_range: SpanRange, msg: String) -> Self;
/// Attach a note to your main message, the note will have it's own span on nightly. /// /// This function is the same as `Diagnostic::span_note` but produces considerably /// better error messages for multi-token spans on stable. /// /// # Span /// /// The span is ignored on stable, the note effectively inherits its parent's (main message) span #[must_use] fn span_range_note(self, span_range: SpanRange, msg: String) -> Self;
}
impl Diagnostic { /// Create a new diagnostic message that points to `Span::call_site()` pubfn new(level: Level, message: String) -> Self {
Diagnostic::spanned(Span::call_site(), level, message)
}
/// Create a new diagnostic message that points to the `span` pubfn spanned(span: Span, level: Level, message: String) -> Self {
Diagnostic::spanned_range(
SpanRange {
first: span,
last: span,
},
level,
message,
)
}
/// Add another error message to self such that it will be emitted right after /// the main message. pubfn span_error(self, span: Span, msg: String) -> Self { self.span_range_error(
SpanRange {
first: span,
last: span,
},
msg,
)
}
/// Attach a "help" note to your main message, the note will have it's own span on nightly. /// /// # Span /// /// The span is ignored on stable, the note effectively inherits its parent's (main message) span pubfn span_help(self, span: Span, msg: String) -> Self { self.span_range_help(
SpanRange {
first: span,
last: span,
},
msg,
)
}
/// Attach a "help" note to your main message. pubfn help(mutself, msg: String) -> Self { self.suggestions.push((SuggestionKind::Help, msg, None)); self
}
/// Attach a note to your main message, the note will have it's own span on nightly. /// /// # Span /// /// The span is ignored on stable, the note effectively inherits its parent's (main message) span pubfn span_note(self, span: Span, msg: String) -> Self { self.span_range_note(
SpanRange {
first: span,
last: span,
},
msg,
)
}
/// Attach a note to your main message pubfn note(mutself, msg: String) -> Self { self.suggestions.push((SuggestionKind::Note, msg, None)); self
}
/// The message of main warning/error (no notes attached) #[must_use] pubfn message(&self) -> &str {
&self.msg
}
/// Abort the proc-macro's execution and display the diagnostic. /// /// # Warnings /// /// Warnings are not emitted on stable and beta, but this function will abort anyway. pubfn abort(self) -> ! { self.emit();
abort_now()
}
/// Display the diagnostic while not aborting macro execution. /// /// # Warnings /// /// Warnings are ignored on stable/beta pubfn emit(self) {
check_correctness(); crate::imp::emit_diagnostic(self);
}
}
/// **NOT PUBLIC API! NOTHING TO SEE HERE!!!** #[doc(hidden)] impl Diagnostic { pubfn span_suggestion(self, span: Span, suggestion: &str, msg: String) -> Self { match suggestion { "help" | "hint" => self.span_help(span, msg),
_ => self.span_note(span, msg),
}
}
let lit = match ts.next().unwrap() {
TokenTree::Group(group) => { // Currently `syn` builds `compile_error!` invocations // exclusively in `ident{"..."}` (braced) form which is not // followed by `;` (semicolon). // // But if it changes to `ident("...");` (parenthesized) // or `ident["..."];` (bracketed) form, // we will need to skip the `;` as well. // Highly unlikely, but better safe than sorry.
¤ Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.0.19Bemerkung:
(vorverarbeitet am 2026-10-04)
¤
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.