Convert enum to string with impl fmt::Display

Viewed 804

Using Rust, I am trying to create an error code enum.

pub enum ErrorCode {
    InvalidUsername,
    InvalidPassword,
}

I want this enum to be used in a JSON response using actix_web, so I need to convert the enum to a string.

To do this, I tried to implement fmt::Display on the ErrorCode enum:

#[derive(Debug)]
pub enum ErrorCode {
    InvalidUsername,
    InvalidPassword,
}

impl fmt::Display for ErrorCode {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{}", *self)
     }
}

But the program crashes with an infinite loop whenever I try to run .to_string() on ErrorCode.

thread 'actix-rt:worker:0' has overflowed its stack
fatal runtime error: stack overflow
[1]    85991 abort      ./target/debug/app

I would like to have the enum as a string, and be able to mutate the string in the impl fmt::Display so I can do things such as convert it to snake_case.

1 Answers

You cannot call write!() inside the fmt() function to substitute {} with self, as this macro calls exact same function, thus creating the infinite loop.

Instead, you should use the parameter of the function f: &mut fmt::Formatter to write the result you want.

match self {
  ErrorCode::InvalidUsername => f.write_str("Invalid user name"),
  ...
}

There are also libraries that help you to reduce the boilerplate code in this case. One is strum as EvilTak suggested.

Related