use std::fmt::Display;
const OK: u32 = 0;
const CANCELLED: u32 = 1;
const UNKNOWN: u32 = 2;
const INVALID_ARGUMENT: u32 = 3;
const DEADLINE_EXCEEDED: u32 = 4;
const NOT_FOUND: u32 = 5;
const ALREADY_EXISTS: u32 = 6;
const PERMISSION_DENIED: u32 = 7;
const RESOURCE_EXHAUSTED: u32 = 8;
const FAILED_PRECONDITION: u32 = 9;
const ABORTED: u32 = 10;
const OUT_OF_RANGE: u32 = 11;
const UNIMPLEMENTED: u32 = 12;
const INTERNAL: u32 = 13;
const UNAVAILABLE: u32 = 14;
const DATA_LOSS: u32 = 15;
const UNAUTHENTICATED: u32 = 16;
#[derive(Clone, Copy, PartialEq, Eq, Debug, Hash)]
#[repr(u32)]
pub enum GrpcStatusCode {
Ok = OK,
Cancelled = CANCELLED,
Unknown = UNKNOWN,
InvalidArgument = INVALID_ARGUMENT,
DeadlineExceeded = DEADLINE_EXCEEDED,
NotFound = NOT_FOUND,
AlreadyExists = ALREADY_EXISTS,
PermissionDenied = PERMISSION_DENIED,
ResourceExhausted = RESOURCE_EXHAUSTED,
FailedPrecondition = FAILED_PRECONDITION,
Aborted = ABORTED,
OutOfRange = OUT_OF_RANGE,
Unimplemented = UNIMPLEMENTED,
Internal = INTERNAL,
Unavailable = UNAVAILABLE,
DataLoss = DATA_LOSS,
Unauthenticated = UNAUTHENTICATED,
}
impl GrpcStatusCode {
pub(super) fn from_u32(code: u32) -> Self {
match code {
OK => Self::Ok,
CANCELLED => Self::Cancelled,
UNKNOWN => Self::Unknown,
INVALID_ARGUMENT => Self::InvalidArgument,
DEADLINE_EXCEEDED => Self::DeadlineExceeded,
NOT_FOUND => Self::NotFound,
ALREADY_EXISTS => Self::AlreadyExists,
PERMISSION_DENIED => Self::PermissionDenied,
RESOURCE_EXHAUSTED => Self::ResourceExhausted,
FAILED_PRECONDITION => Self::FailedPrecondition,
ABORTED => Self::Aborted,
OUT_OF_RANGE => Self::OutOfRange,
UNIMPLEMENTED => Self::Unimplemented,
INTERNAL => Self::Internal,
UNAVAILABLE => Self::Unavailable,
DATA_LOSS => Self::DataLoss,
UNAUTHENTICATED => Self::Unauthenticated,
_ => Self::Unknown,
}
}
pub fn code(&self) -> u32 {
*self as u32
}
pub fn label(&self) -> &'static str {
match *self {
GrpcStatusCode::Ok => "OK",
GrpcStatusCode::Cancelled => "CANCELLED",
GrpcStatusCode::Unknown => "UNKNOWN",
GrpcStatusCode::InvalidArgument => "INVALID_ARGUMENT",
GrpcStatusCode::DeadlineExceeded => "DEADLINE_EXCEEDED",
GrpcStatusCode::NotFound => "NOT_FOUND",
GrpcStatusCode::AlreadyExists => "ALREADY_EXISTS",
GrpcStatusCode::PermissionDenied => "PERMISSION_DENIED",
GrpcStatusCode::ResourceExhausted => "RESOURCE_EXHAUSTED",
GrpcStatusCode::FailedPrecondition => "FAILED_PRECONDITION",
GrpcStatusCode::Aborted => "ABORTED",
GrpcStatusCode::OutOfRange => "OUT_OF_RANGE",
GrpcStatusCode::Unimplemented => "UNIMPLEMENTED",
GrpcStatusCode::Internal => "INTERNAL",
GrpcStatusCode::Unavailable => "UNAVAILABLE",
GrpcStatusCode::DataLoss => "DATA_LOSS",
GrpcStatusCode::Unauthenticated => "UNAUTHENTICATED",
}
}
}
#[derive(Debug)]
pub struct GrpcStatus {
code: GrpcStatusCode,
message: Option<String>,
}
impl GrpcStatus {
pub fn new(status: GrpcStatusCode, message: Option<String>) -> Self {
Self {
code: status,
message,
}
}
pub fn from_code(status: GrpcStatusCode) -> Self {
Self {
code: status,
message: None,
}
}
pub fn code(&self) -> GrpcStatusCode {
self.code
}
pub fn message(&self) -> Option<&str> {
self.message.as_deref()
}
}
impl Display for GrpcStatus {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
let code = self.code.label();
if let Some(message) = self.message.as_deref() {
write!(f, "[{code}] {message}")
} else {
write!(f, "{code}")
}
}
}