Skip to main content

ide_diagnostics/handlers/
non_exhaustive_record_pat.rs

1use crate::{Diagnostic, DiagnosticCode, DiagnosticsContext};
2
3// Diagnostic: non-exhaustive-record-pat
4//
5// This diagnostic is triggered if a record pattern destructures a `#[non_exhaustive]`
6// struct or enum variant from another crate without `..`.
7pub(crate) fn non_exhaustive_record_pat(
8    ctx: &DiagnosticsContext<'_, '_>,
9    d: &hir::NonExhaustiveRecordPat,
10) -> Diagnostic {
11    let item = match d.variant {
12        hir::Variant::Struct(_) => "struct",
13        hir::Variant::Union(_) => "union",
14        hir::Variant::EnumVariant(_) => "variant",
15    };
16
17    Diagnostic::new_with_syntax_node_ptr(
18        ctx,
19        DiagnosticCode::RustcHardError("E0638"),
20        format!("`..` required with {item} marked as non-exhaustive"),
21        d.pat.map(Into::into),
22    )
23    .stable()
24}
25
26#[cfg(test)]
27mod tests {
28    use crate::tests::check_diagnostics;
29
30    #[test]
31    fn reports_external_non_exhaustive_struct_pattern_without_rest() {
32        check_diagnostics(
33            r#"
34//- /lib.rs crate:lib
35#[non_exhaustive]
36pub struct S {
37    pub field: u32,
38}
39
40fn local_ok(s: S) {
41    let S { field } = s;
42    let _ = field;
43}
44
45//- /main.rs crate:main deps:lib
46fn main(s: lib::S) {
47    let lib::S { field } = s;
48      //^^^^^^^^^^^^^^^^ error: `..` required with struct marked as non-exhaustive
49    let _ = field;
50}
51"#,
52        );
53    }
54
55    #[test]
56    fn reports_external_non_exhaustive_variant_pattern_without_rest() {
57        check_diagnostics(
58            r#"
59//- /lib.rs crate:lib
60pub enum E {
61    #[non_exhaustive]
62    V { field: u32 },
63}
64
65fn local_ok(e: E) {
66    let E::V { field } = e;
67    let _ = field;
68}
69
70//- /main.rs crate:main deps:lib
71fn main(e: lib::E) {
72    let lib::E::V { field } = e;
73      //^^^^^^^^^^^^^^^^^^^ error: `..` required with variant marked as non-exhaustive
74    let _ = field;
75}
76"#,
77        );
78    }
79}