0

Assume the following enumeration type is defined somewhere in my Rust library:

#[derive(Debug)]
pub enum Color {
    Red,
    Green,
    Blue,
}

Is it considered a breaking change when I add a fourth variant Color::Yellow to the enum? If it is a breaking change (I guess so because of the match statement), is there a way to indicate to API users that this type might be extended in the future?

blerontin
  • 2,892
  • 5
  • 34
  • 60
  • Since it will break all `match` statements, sure. – Sven Marnach Mar 09 '23 at 10:05
  • 1
    Does this answer your question? [What exactly is considered a breaking change to a library crate?](https://stackoverflow.com/questions/41185023/what-exactly-is-considered-a-breaking-change-to-a-library-crate/41195476#41195476). You can annotate your enum with the [`#[non_exhaustive]`](https://doc.rust-lang.org/reference/attributes/type_system.html#the-non_exhaustive-attribute) attribute to mitigate the breaking change (it forbids your users to non-exhaustively match against your enum). – Jonas Fassbender Mar 09 '23 at 10:06
  • @JonasFassbender: Yes, this linked answer covers my question, too. Thanks for the attribute hint. If you turn your comment into an answer I will mark it as accepted. – blerontin Mar 09 '23 at 10:13

1 Answers1

2

Yes, adding an enum variant is considered a breaking change. Read more about it in the Rust RFC 1105 - API evolution here.

You can add the #[non_exhaustive] attribute to your enum to warn your users that you may extend your enum with further variants in the future, so adding a new variant won't be considered a breaking change:

#[non_exhaustive]
#[derive(Debug)]
pub enum Color {
    Red,
    Green,
    Blue,
}

This disallows projects that import your enum to non-exhaustively match it. I.e.:

match color {
    Color::Red => (),
    Color::Green => (),
    Color::Blue => (),
}

throws an error, while

match color {
    Color::Red => (),
    Color::Green => (),
    Color::Blue => (),
    _ => (),
}

won't.

Jonas Fassbender
  • 2,371
  • 1
  • 3
  • 19
  • 1
    IMHO, it is sometimes better to broke users code with new enum variant than to make non-exhastive enums. Compiler would notify users about places where users need add new match arms when they make major update of a library. Inabilitiy to miss handler for enum variant is one of major pros of Rusts match expression after all. – Angelicos Phosphoros Mar 09 '23 at 15:50