Skip to main content

reifydb_runtime/
hash.rs

1// SPDX-License-Identifier: AGPL-3.0-or-later
2// Copyright (c) 2025 ReifyDB
3
4//! Hash types and functions for ReifyDB.
5//!
6//! Provides xxHash3 hashing using pure Rust implementation that works
7//! on both native and WASM targets.
8
9use core::hash::{Hash, Hasher};
10
11use serde::{Deserialize, Serialize};
12use xxhash_rust::xxh3;
13
14#[repr(transparent)]
15#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Serialize, Deserialize)]
16#[serde(transparent)]
17pub struct Hash64(pub u64);
18
19impl From<u64> for Hash64 {
20	fn from(value: u64) -> Self {
21		Hash64(value)
22	}
23}
24
25impl From<Hash64> for u64 {
26	fn from(hash: Hash64) -> Self {
27		hash.0
28	}
29}
30
31impl Hash for Hash64 {
32	fn hash<H: Hasher>(&self, state: &mut H) {
33		state.write_u64(self.0)
34	}
35}
36
37#[repr(transparent)]
38#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Serialize, Deserialize)]
39#[serde(transparent)]
40pub struct Hash128(pub u128);
41
42impl From<u128> for Hash128 {
43	fn from(value: u128) -> Self {
44		Hash128(value)
45	}
46}
47
48impl From<Hash128> for u128 {
49	fn from(hash: Hash128) -> Self {
50		hash.0
51	}
52}
53
54impl Hash for Hash128 {
55	fn hash<H: Hasher>(&self, state: &mut H) {
56		state.write_u128(self.0)
57	}
58}
59
60/// Compute xxHash3 64-bit hash of data.
61#[inline]
62pub fn xxh3_64(data: &[u8]) -> Hash64 {
63	Hash64(xxh3::xxh3_64(data))
64}
65
66/// Compute xxHash3 128-bit hash of data.
67#[inline]
68pub fn xxh3_128(data: &[u8]) -> Hash128 {
69	Hash128(xxh3::xxh3_128(data))
70}
71
72#[cfg(test)]
73mod tests {
74	use super::*;
75
76	#[test]
77	fn test_xxh3_64() {
78		let data = b"hello world";
79		let hash = xxh3_64(data);
80		// xxh3_64 should be deterministic
81		assert_eq!(hash, xxh3_64(data));
82		assert_ne!(hash, xxh3_64(b"different data"));
83	}
84
85	#[test]
86	fn test_xxh3_128() {
87		let data = b"hello world";
88		let hash = xxh3_128(data);
89		// xxh3_128 should be deterministic
90		assert_eq!(hash, xxh3_128(data));
91		assert_ne!(hash, xxh3_128(b"different data"));
92	}
93
94	#[test]
95	fn test_hash64_conversions() {
96		let value: u64 = 12345;
97		let hash = Hash64::from(value);
98		assert_eq!(u64::from(hash), value);
99	}
100
101	#[test]
102	fn test_hash128_conversions() {
103		let value: u128 = 123456789;
104		let hash = Hash128::from(value);
105		assert_eq!(u128::from(hash), value);
106	}
107}