Variable used after move in lambda

use std::fmt::Error;

#[derive(Debug)]
struct ErrorStruct {}
struct SuccessStruct {
    number: i8
}

struct Something {}

impl Something {
    fn do_something(&self) -> Result<i8, Error> {
        Ok(1)
    }

    fn into_err_struct(self) -> ErrorStruct {
        ErrorStruct {  }
    }

    fn into_success_struct(self, number: i8) -> SuccessStruct {
        SuccessStruct { number }
    }
}

fn do_the_thing() -> Result<SuccessStruct, ErrorStruct> {
    let sth = Something{};
    sth.do_something().map_err(|_| sth.into_err_struct())
        .map(|number| sth.into_success_struct(number))
}

In this case we have a variable which we want to convert into different types depending on success or error. For a human, it’s obvious that into_err_struct and into_success_struct are mutually exclusive, but rust will give the following error:

fn do_the_thing() -> Result<SuccessStruct, ErrorStruct> {
    let sth = Something{};                                // move occurs because `sth` has type `Something`, which does not implement the `Copy` trait
    sth.do_something().map_err(|_| sth.into_err_struct()) // variable moved due to use in closure
        .map(|number| sth.into_success_struct(number))    // use occurs due to use in closure
}

It seems that in order to make rustc understand the flow, you need to switch to using match and early return.

fn do_the_thing() -> Result<SuccessStruct, ErrorStruct> {
    let sth = Something{};
    let number = match sth.do_something() {
        Ok(number) => number,
        Err(_) => return Err(sth.into_err_struct()),
    };
    Ok(sth.into_success_struct(number))
}

In this case we can slim it down a bit, but that might not be applicable in all cases

fn do_the_thing() -> Result<SuccessStruct, ErrorStruct> {
    let sth = Something{};
    match sth.do_something() {
        Ok(number) => Ok(sth.into_success_struct(number)),
        Err(_) => Err(sth.into_err_struct()),
    }
}

To sum it up, it seems like rust requires use of match for branching paths who both move a variable.