# Rust Thrift library

## Overview

This crate implements the components required to build a working Thrift server
and client. It is divided into the following modules:

 1. errors
 2. protocol
 3. transport
 4. server
 5. autogen

The modules are layered as shown. The `generated` layer is code generated by the
Thrift compiler's Rust plugin. It uses the components defined in this crate to
serialize and deserialize types and implement RPC. Users interact with these
types and services by writing their own code on top.

 ```text
 +-----------+
 |  app dev  |
 +-----------+
 | generated | <-> errors/results
 +-----------+
 |  protocol |
 +-----------+
 | transport |
 +-----------+
 ```

## Using this crate

Add `thrift = "x.y.z"` to your `Cargo.toml`, where `x.y.z` is the version of the
Thrift compiler you're using.

## API Documentation

Full [Rustdoc](https://docs.rs/thrift/)

## Compatibility

The Rust library and auto-generated code targets Rust versions 1.28+.
It does not currently use any Rust 2021 features.

### Breaking Changes

Breaking changes are minimized. When they are made they will be outlined below with transition guidelines.

##### Thrift 0.15.0

* **[THRIFT-5360]** - No longer define OR generate `description()` methods for `Error` types.

  `Error.description()` was soft-deprecated in 1.27, and deprecated as of 1.41.
  Library error types also do not implement `Error.description()`. Also, as a result of this change
  the generated Rust representation of an Error no longer implements the `Error.description()` method.
  Instead, it generates a `Display` impl with the same information.

  For example:

  ```thrift
  exception Xception {
    1: i32 errorCode,
    2: string message
  }
  ```

  used to generate:

  ```rust
  use std::error::Error;
  use std::fmt;
  use std::fmt::{Display, Formatter};

  // auto-generated by the Thrift compiler
  #[derive(Clone, Debug, Eq, Ord, PartialEq, PartialOrd)]
  pub struct Xception {
    pub error_code: Option<i32>,
    pub message: Option<String>,
  }

  // auto-generated by the Thrift compiler
  impl Error for Xception {
    fn description(&self) -> &str {
      "remote service threw Xception"
    }
  }

  // auto-generated by the Thrift compiler
  impl From<Xception> for thrift::Error {
    fn from(e: Xception) -> Self {
      thrift::Error::User(Box::new(e))
    }
  }

  // auto-generated by the Thrift compiler
  impl Display for Xception {
    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
      self.description().format(f)
    }
  }
  ```

  It *now* generates:

  ```rust
  use std::error::Error;
  use std::fmt;
  use std::fmt::{Display, Formatter};

  // auto-generated by the Thrift compiler
  #[derive(Clone, Debug, Eq, Ord, PartialEq, PartialOrd)]
  pub struct Xception {
    pub error_code: Option<i32>,
    pub message: Option<String>,
  }

  // auto-generated by the Thrift compiler
  impl Error for Xception { }

  // auto-generated by the Thrift compiler
  impl From<Xception> for thrift::Error {
    fn from(e: Xception) -> Self {
      thrift::Error::User(Box::new(e))
    }
  }

  // auto-generated by the Thrift compiler
  impl Display for Xception {
    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
      write!(f, "remote service threw Xception")
    }
  }
  ```

* **[THRIFT-5314]** - Generate enums implementations that are forward compatible (i.e. don't error on unknown values)

  As a result of this change the Rust representation of an enum changes from a standard
  Rust enum into a newtype struct with associated constants.

  For example:

  ```thrift
    // THRIFT
    enum Operation {
      ADD,
      SUBTRACT,
      MULTIPLY,
      DIVIDE,
    }
  ```

  used to generate:

  ```rust
    // OLD AUTO-GENERATED RUST
    pub enum Operation {
       Add,
       Subtract,
       Multiply,
       Divide,
     }
  ```

  It *now* generates:

  ```rust
    // NEW AUTO-GENERATED RUST
    pub struct Operation(pub i32);

    impl Operation {
      pub const ADD: Operation = Operation(0);
      pub const SUBTRACT: Operation = Operation(1);
      pub const MULTIPLY: Operation = Operation(2);
      pub const DIVIDE: Operation = Operation(3);
    }
  ```

##### Thrift 0.14.0

* **[THRIFT-5158]** - Rust library and generator now support Rust 2021 only. Required rust 1.65.0 or higher

    The Rust `thrift` library was updated to Rust 2021 via `cargo fix --edition`.
    All test code in the repo was updated as well. The code generator was also updated
    to support Rust 2021 only.

##### Thrift 0.13.0

* **[THRIFT-4536]** - Use TryFrom from std, required rust 1.34.0 or higher

    Previously TryFrom was from try_from crate, it is now from the std library,
    but this functionality is only available in rust 1.34.0. Additionally,
    ordered-float is now re-exported under the thrift module to reduce
    possible dependency mismatches.

##### Thrift 0.12.0

* **[THRIFT-4529]** - Rust enum variants are now camel-cased instead of uppercased to conform to Rust naming conventions

    Previously, enum variants were uppercased in the auto-generated code.
    For example, the following thrift enum:

    ```thrift
    // THRIFT
    enum Operation {
      ADD,
      SUBTRACT,
      MULTIPLY,
      DIVIDE,
    }
    ```

    used to generate:

    ```rust
    // OLD AUTO-GENERATED RUST
    pub enum Operation {
       ADD,
       SUBTRACT,
       MULTIPLY,
       DIVIDE,
     }
    ```

    It *now* generates:

    ```rust
    // NEW AUTO-GENERATED RUST
    pub enum Operation {
       Add,
       Subtract,
       Multiply,
       Divide,
     }
    ```

    You will have to change all enum variants in your code to use camel-cased names.
    This should be a search and replace.

## Contributing

Bug reports and PRs are always welcome! Please see the
[Thrift website](https://thrift.apache.org/) for more details.

Thrift Rust support requires code in several directories:

* `compiler/cpp/src/thrift/generate/t_rs_generator.cc`: binding code generator
* `lib/rs`: runtime library
* `lib/rs/test`: supplemental tests
* `tutorial/rs`: tutorial client and server
* `test/rs`: cross-language test client and server

All library code, test code and auto-generated code compiles and passes clippy
without warnings. All new code must do the same! When making changes ensure that:

* `rustc` does does output any warnings
* `clippy` with default settings does not output any warnings (includes auto-generated code)
* `cargo test` is successful
* `make precross` and `make check` are successful
* `tutorial/bin/tutorial_client` and `tutorial/bin/tutorial_server` communicate
