use std::fmt;
use serde::{Deserialize, Serialize};
use crate::generator::{MAX_TIMESTAMP, SEQUENCE_BITS, WORKER_BITS};
const WORKER_MASK: u64 = (1_u64 << WORKER_BITS) - 1;
const SEQUENCE_MASK: u64 = (1_u64 << SEQUENCE_BITS) - 1;
const SEQUENCE_SHIFT: u32 = WORKER_BITS;
const TIMESTAMP_SHIFT: u32 = WORKER_BITS + SEQUENCE_BITS;
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, PartialOrd, Ord, Serialize, Deserialize)]
pub struct BeakId(i64);
impl BeakId {
#[must_use]
pub const fn new(value: i64) -> Self {
Self(value)
}
#[must_use]
pub const fn as_i64(self) -> i64 {
self.0
}
#[must_use]
pub const fn timestamp_window(self) -> u64 {
((self.0 as u64) >> TIMESTAMP_SHIFT) & MAX_TIMESTAMP
}
#[must_use]
pub const fn sequence(self) -> u64 {
((self.0 as u64) >> SEQUENCE_SHIFT) & SEQUENCE_MASK
}
#[must_use]
pub const fn worker_id(self) -> u16 {
(self.0 as u64 & WORKER_MASK) as u16
}
#[must_use]
pub const fn parts(self) -> (u64, u64, u16) {
(self.timestamp_window(), self.sequence(), self.worker_id())
}
}
impl From<i64> for BeakId {
fn from(value: i64) -> Self {
Self::new(value)
}
}
impl From<BeakId> for i64 {
fn from(id: BeakId) -> Self {
id.as_i64()
}
}
impl fmt::Display for BeakId {
fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
self.0.fmt(formatter)
}
}