Radish alpha
h
Radicle Heartwood Protocol & Stack
Radicle
Git (anonymous pull)
Log in to clone via SSH
Replace `quickcheck` with `qcheck`
Alexis Sellier committed 3 years ago
commit f9c81ab3829724cf1ebe346d07dc2ccda44c958d
parent cc246992324f85d25ec229c713618f281d7ed563
31 files changed +118 -177
modified Cargo.lock
@@ -768,16 +768,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a357d28ed41a50f9c765dbfe56cbc04a64e53e5fc58ba79fbc34c10ef3df831f"

[[package]]
-
name = "env_logger"
-
version = "0.8.4"
-
source = "registry+https://github.com/rust-lang/crates.io-index"
-
checksum = "a19187fea3ac7e84da7dacf48de0c45d63c6a76f9490dae389aead16c243fce3"
-
dependencies = [
-
 "log",
-
 "regex",
-
]
-

-
[[package]]
name = "errno"
version = "0.2.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -2131,21 +2121,19 @@ dependencies = [
]

[[package]]
-
name = "quickcheck"
-
version = "1.0.3"
+
name = "qcheck"
+
version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-
checksum = "588f6378e4dd99458b60ec275b4477add41ce4fa9f64dcba6f15adccb19b50d6"
+
checksum = "b439bd4242da51d62d18c95e6a6add749346756b0d1a587dfd0cc22fa6b5f3f0"
dependencies = [
-
 "env_logger",
-
 "log",
 "rand 0.8.5",
]

[[package]]
-
name = "quickcheck_macros"
+
name = "qcheck-macros"
version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-
checksum = "b22a693222d716a9587786f37ac3f6b4faedb5b80c23914e7303ff5a1d8016e9"
+
checksum = "2742b9af5a690615904b18f11983f4db9ea7ad1c7e6ed3fb4b2402cdaaf5b1b5"
dependencies = [
 "proc-macro2",
 "quote",
@@ -2180,8 +2168,8 @@ dependencies = [
 "olpc-cjson",
 "once_cell",
 "pretty_assertions",
-
 "quickcheck",
-
 "quickcheck_macros",
+
 "qcheck",
+
 "qcheck-macros",
 "radicle-cob",
 "radicle-crdt",
 "radicle-crypto",
@@ -2233,8 +2221,8 @@ dependencies = [
 "git2",
 "log",
 "petgraph",
-
 "quickcheck",
-
 "quickcheck_macros",
+
 "qcheck",
+
 "qcheck-macros",
 "radicle-crypto",
 "radicle-git-ext",
 "serde",
@@ -2249,8 +2237,8 @@ version = "0.1.0"
dependencies = [
 "fastrand",
 "num-traits",
-
 "quickcheck",
-
 "quickcheck_macros",
+
 "qcheck",
+
 "qcheck-macros",
 "radicle-crypto",
 "serde",
 "tempfile",
@@ -2266,8 +2254,8 @@ dependencies = [
 "fastrand",
 "git-ref-format 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
 "multibase",
-
 "quickcheck",
-
 "quickcheck_macros",
+
 "qcheck",
+
 "qcheck-macros",
 "radicle-ssh",
 "serde",
 "sha2 0.10.6",
@@ -2335,8 +2323,8 @@ dependencies = [
 "nakamoto-net",
 "nakamoto-net-poll",
 "nonempty 0.8.0",
-
 "quickcheck",
-
 "quickcheck_macros",
+
 "qcheck",
+
 "qcheck-macros",
 "radicle",
 "radicle-crypto",
 "scrypt",
modified radicle-cob/Cargo.toml
@@ -41,8 +41,8 @@ ed25519-compact = { version = "2.0.2", features = ["pem"] }
fastrand = { version = "1.8.0", default-features = false }
git-ref-format = { version = "0.1", features = ["macro"] }
tempfile = { version = "3" }
-
quickcheck = { version = "1", default-features = false }
-
quickcheck_macros = { version = "1", default-features = false }
+
qcheck = { version = "1", default-features = false }
+
qcheck-macros = { version = "1", default-features = false }

[dev-dependencies.radicle-crypto]
path = "../radicle-crypto"
modified radicle-cob/src/lib.rs
@@ -72,10 +72,10 @@
//! [RFC-0662]: https://github.com/radicle-dev/radicle-link/blob/master/docs/rfc/0662-collaborative-objects.adoc

#[cfg(test)]
-
extern crate quickcheck;
+
extern crate qcheck;
#[cfg(test)]
#[macro_use(quickcheck)]
-
extern crate quickcheck_macros;
+
extern crate qcheck_macros;

extern crate radicle_crypto as crypto;
extern crate radicle_git_ext as git_ext;
modified radicle-cob/src/test/arbitrary.rs
@@ -1,6 +1,6 @@
use std::{iter, marker::PhantomData};

-
use quickcheck::Arbitrary;
+
use qcheck::Arbitrary;

use crate::{ObjectId, TypeName};

@@ -11,7 +11,7 @@ pub struct Invalid<T> {
}

impl Arbitrary for TypeName {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let rng = fastrand::Rng::with_seed(u64::arbitrary(g));
        let mut name: Vec<String> = Vec::new();
        for _ in 0..rng.usize(1..5) {
@@ -28,7 +28,7 @@ impl Arbitrary for TypeName {
}

impl Arbitrary for ObjectId {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let rng = fastrand::Rng::with_seed(u64::arbitrary(g));
        let bytes = iter::repeat_with(|| rng.u8(..))
            .take(20)
@@ -38,7 +38,7 @@ impl Arbitrary for ObjectId {
}

impl Arbitrary for Invalid<ObjectId> {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let rng = fastrand::Rng::with_seed(u64::arbitrary(g));
        let value = iter::repeat_with(|| rng.alphanumeric())
            .take(rng.usize(21..50))
modified radicle-cob/src/tests.rs
@@ -2,7 +2,7 @@ use std::ops::ControlFlow;

use crypto::test::signer::MockSigner;
use git_ref_format::{refname, Component, RefString};
-
use quickcheck::Arbitrary;
+
use qcheck::Arbitrary;
use radicle_crypto::Signer;

use crate::{
@@ -280,7 +280,7 @@ fn invalid_parse_refstr(oid: Invalid<ObjectId>, typename: TypeName) {
}

fn gen<T: Arbitrary>(size: usize) -> T {
-
    let mut gen = quickcheck::Gen::new(size);
+
    let mut gen = qcheck::Gen::new(size);

    T::arbitrary(&mut gen)
}
modified radicle-crdt/Cargo.toml
@@ -4,12 +4,12 @@ version = "0.1.0"
edition = "2021"

[features]
-
test = ["fastrand", "quickcheck"]
+
test = ["fastrand", "qcheck"]

[dependencies]
fastrand = { version = "1.8.0", optional = true }
num-traits = { version = "0.2.15", default-features = false, features = ["std"] }
-
quickcheck = { version = "1", optional = true }
+
qcheck = { version = "1", optional = true }
serde = { version = "1" }

[dependencies.radicle-crypto]
@@ -19,7 +19,7 @@ features = []

[dev-dependencies]
fastrand = { version = "1.8.0" }
-
quickcheck = { version = "1" }
-
quickcheck_macros = { version = "1" }
+
qcheck = { version = "1" }
+
qcheck-macros = { version = "1" }
radicle-crypto = { path = "../radicle-crypto", features = ["test"] }
tempfile = { version = "3" }
modified radicle-crdt/src/gmap.rs
@@ -88,7 +88,7 @@ impl<K, V> Deref for GMap<K, V> {

#[cfg(test)]
mod tests {
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    use super::*;
    use crate::ord::Max;
modified radicle-crdt/src/lib.rs
@@ -116,7 +116,7 @@ where
#[cfg(test)]
mod tests {
    use crate::{test, Max, Min, Semilattice};
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    #[quickcheck]
    fn prop_option_laws(a: Max<u8>, b: Max<u8>, c: Max<u8>) {
modified radicle-crdt/src/lwwmap.rs
@@ -96,7 +96,7 @@ where

#[cfg(test)]
mod tests {
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    use super::*;
    use crate::ord::Max;
modified radicle-crdt/src/lwwreg.rs
@@ -76,7 +76,7 @@ where

#[cfg(test)]
mod tests {
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    use super::*;
    use crate::Min;
modified radicle-crdt/src/lwwset.rs
@@ -77,7 +77,7 @@ where
#[cfg(test)]
mod tests {
    use super::*;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    #[quickcheck]
    fn prop_semilattice(
modified radicle-crdt/src/ord.rs
@@ -115,14 +115,14 @@ impl<T: PartialOrd> Semilattice for Min<T> {
mod arbitrary {
    use super::*;

-
    impl<T: quickcheck::Arbitrary> quickcheck::Arbitrary for Max<T> {
-
        fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    impl<T: qcheck::Arbitrary> qcheck::Arbitrary for Max<T> {
+
        fn arbitrary(g: &mut qcheck::Gen) -> Self {
            Self::from(T::arbitrary(g))
        }
    }

-
    impl<T: quickcheck::Arbitrary> quickcheck::Arbitrary for Min<T> {
-
        fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    impl<T: qcheck::Arbitrary> qcheck::Arbitrary for Min<T> {
+
        fn arbitrary(g: &mut qcheck::Gen) -> Self {
            Self::from(T::arbitrary(g))
        }
    }
modified radicle-crdt/src/redactable.rs
@@ -69,7 +69,7 @@ impl<T: PartialEq> Semilattice for Redactable<T> {

#[cfg(test)]
mod test {
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    use super::*;
    use crate::test;
modified radicle-crypto/Cargo.toml
@@ -9,7 +9,7 @@ authors = [
edition = "2021"

[features]
-
test = ["fastrand", "quickcheck"]
+
test = ["fastrand", "qcheck"]
ssh = ["base64", "radicle-ssh", "ssh-key"]

[dependencies]
@@ -37,7 +37,7 @@ default-features = false
features = ["std", "encryption", "rand_core", "getrandom"]
optional = true

-
[dependencies.quickcheck]
+
[dependencies.qcheck]
version = "1"
default-features = false
optional = true
@@ -54,6 +54,6 @@ optional = true

[dev-dependencies]
fastrand = { version = "1.8.0", default-features = false }
-
quickcheck_macros = { version = "1", default-features = false }
-
quickcheck = { version = "1", default-features = false }
+
qcheck-macros = { version = "1", default-features = false }
+
qcheck = { version = "1", default-features = false }
tempfile = { version = "3.3.0" }
modified radicle-crypto/src/lib.rs
@@ -395,7 +395,7 @@ pub mod keypair {
#[cfg(test)]
mod tests {
    use crate::PublicKey;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;
    use std::str::FromStr;

    #[quickcheck]
modified radicle-crypto/src/ssh.rs
@@ -322,11 +322,10 @@ impl ExtendedSignature {
mod test {
    use std::sync::{Arc, Mutex};

-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    use super::{fmt, ExtendedSignature};
    use crate as crypto;
-
    use crate::test::arbitrary::ByteArray;
    use crate::{PublicKey, SecretKey};
    use radicle_ssh::agent::client::{AgentClient, ClientStream, Error};
    use radicle_ssh::encoding::*;
@@ -352,9 +351,9 @@ mod test {
    }

    #[quickcheck]
-
    fn prop_encode_decode_sk(input: ByteArray<64>) {
+
    fn prop_encode_decode_sk(input: [u8; 64]) {
        let mut buf = Buffer::default();
-
        let sk = crypto::SecretKey::from(input.into_inner());
+
        let sk = crypto::SecretKey::from(input);
        sk.write(&mut buf);

        let mut cursor = buf.reader(0);
modified radicle-crypto/src/test/arbitrary.rs
@@ -1,11 +1,11 @@
-
use quickcheck::Arbitrary;
+
use qcheck::Arbitrary;

use crate::{hash, test::signer::MockSigner, KeyPair, PublicKey, SecretKey, Seed};

impl Arbitrary for MockSigner {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
-
        let bytes: ByteArray<32> = Arbitrary::arbitrary(g);
-
        let seed = Seed::new(bytes.into_inner());
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
+
        let bytes: [u8; 32] = Arbitrary::arbitrary(g);
+
        let seed = Seed::new(bytes);
        let sk = KeyPair::from_seed(seed).sk;

        MockSigner::from(SecretKey::from(sk))
@@ -13,9 +13,9 @@ impl Arbitrary for MockSigner {
}

impl Arbitrary for PublicKey {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
-
        let bytes: ByteArray<32> = Arbitrary::arbitrary(g);
-
        let seed = Seed::new(bytes.into_inner());
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
+
        let bytes: [u8; 32] = Arbitrary::arbitrary(g);
+
        let seed = Seed::new(bytes);
        let keypair = KeyPair::from_seed(seed);

        PublicKey(keypair.pk)
@@ -23,31 +23,8 @@ impl Arbitrary for PublicKey {
}

impl Arbitrary for hash::Digest {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let bytes: Vec<u8> = Arbitrary::arbitrary(g);
        hash::Digest::new(&bytes)
    }
}
-

-
#[derive(Clone, Debug)]
-
pub struct ByteArray<const N: usize>([u8; N]);
-

-
impl<const N: usize> ByteArray<N> {
-
    pub fn into_inner(self) -> [u8; N] {
-
        self.0
-
    }
-

-
    pub fn as_slice(&self) -> &[u8] {
-
        self.0.as_slice()
-
    }
-
}
-

-
impl<const N: usize> Arbitrary for ByteArray<N> {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
-
        let mut bytes: [u8; N] = [0; N];
-
        for byte in &mut bytes {
-
            *byte = u8::arbitrary(g);
-
        }
-
        Self(bytes)
-
    }
-
}
modified radicle-node/Cargo.toml
@@ -6,7 +6,7 @@ authors = ["Alexis Sellier <alexis@radicle.xyz>"]
edition = "2021"

[features]
-
test = ["radicle/test", "radicle-crypto/test", "quickcheck"]
+
test = ["radicle/test", "radicle-crypto/test", "qcheck"]

[dependencies]
anyhow = { version = "1" }
@@ -22,7 +22,7 @@ log = { version = "0.4.17", features = ["std"] }
nakamoto-net = { version = "0.3.0" }
nakamoto-net-poll = { version = "0.3.0" }
nonempty = { version = "0.8.0", features = ["serialize"] }
-
quickcheck = { version = "1", default-features = false, optional = true }
+
qcheck = { version = "1", default-features = false, optional = true }
sqlite = { version = "0.28.1" }
sqlite3-src = { version = "0.4.0", features = ["bundled"] } # Ensures static linking
scrypt = { version = "0.10.0", default-features = false }
@@ -39,5 +39,5 @@ features = ["sql"]
[dev-dependencies]
radicle = { path = "../radicle", version = "*", features = ["test"] }
radicle-crypto = { path = "../radicle-crypto", version = "*", features = ["test"] }
-
quickcheck = { version = "1", default-features = false }
-
quickcheck_macros = { version = "1", default-features = false }
+
qcheck = { version = "1", default-features = false }
+
qcheck-macros = { version = "1", default-features = false }
modified radicle-node/src/deserializer.rs
@@ -76,7 +76,7 @@ impl<D: wire::Decode> Iterator for Deserializer<D> {
#[cfg(test)]
mod test {
    use super::*;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    const MSG_HELLO: &[u8] = &[5, b'h', b'e', b'l', b'l', b'o'];
    const MSG_BYE: &[u8] = &[3, b'b', b'y', b'e'];
modified radicle-node/src/service/message.rs
@@ -508,7 +508,7 @@ mod tests {

    use crate::crypto::test::signer::MockSigner;
    use crate::test::arbitrary;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    #[test]
    fn test_inventory_limit() {
modified radicle-node/src/test/arbitrary.rs
@@ -1,7 +1,7 @@
use std::net;

use bloomy::BloomFilter;
-
use quickcheck::Arbitrary;
+
use qcheck::Arbitrary;

use crate::crypto;
use crate::prelude::{BoundedVec, Id, NodeId, Refs, Timestamp};
@@ -15,7 +15,7 @@ use crate::wire::message::MessageType;
pub use radicle::test::arbitrary::*;

impl Arbitrary for Filter {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let size = *g
            .choose(&[FILTER_SIZE_S, FILTER_SIZE_M, FILTER_SIZE_L])
            .unwrap();
@@ -29,7 +29,7 @@ impl Arbitrary for Filter {
}

impl Arbitrary for Message {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let type_id = g
            .choose(&[
                MessageType::InventoryAnnouncement,
@@ -49,7 +49,7 @@ impl Arbitrary for Message {
                    timestamp: Timestamp::arbitrary(g),
                }
                .into(),
-
                signature: crypto::Signature::from(ByteArray::<64>::arbitrary(g).into_inner()),
+
                signature: crypto::Signature::from(<[u8; 64]>::arbitrary(g)),
            }
            .into(),
            MessageType::RefsAnnouncement => Announcement {
@@ -60,20 +60,20 @@ impl Arbitrary for Message {
                    timestamp: Timestamp::arbitrary(g),
                }
                .into(),
-
                signature: crypto::Signature::from(ByteArray::<64>::arbitrary(g).into_inner()),
+
                signature: crypto::Signature::from(<[u8; 64]>::arbitrary(g)),
            }
            .into(),
            MessageType::NodeAnnouncement => {
                let message = NodeAnnouncement {
                    features: u64::arbitrary(g).into(),
                    timestamp: Timestamp::arbitrary(g),
-
                    alias: ByteArray::<32>::arbitrary(g).into_inner(),
+
                    alias: <[u8; 32]>::arbitrary(g),
                    addresses: Arbitrary::arbitrary(g),
                    nonce: u64::arbitrary(g),
                }
                .into();
-
                let bytes: ByteArray<64> = Arbitrary::arbitrary(g);
-
                let signature = crypto::Signature::from(bytes.into_inner());
+
                let bytes: [u8; 64] = Arbitrary::arbitrary(g);
+
                let signature = crypto::Signature::from(bytes);

                Announcement {
                    node: NodeId::arbitrary(g),
@@ -101,14 +101,14 @@ impl Arbitrary for Message {
}

impl Arbitrary for Address {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        if bool::arbitrary(g) {
            Address::Ipv4 {
                ip: net::Ipv4Addr::from(u32::arbitrary(g)),
                port: u16::arbitrary(g),
            }
        } else {
-
            let octets: [u8; 16] = ByteArray::<16>::arbitrary(g).into_inner();
+
            let octets: [u8; 16] = Arbitrary::arbitrary(g);

            Address::Ipv6 {
                ip: net::Ipv6Addr::from(octets),
@@ -119,7 +119,7 @@ impl Arbitrary for Address {
}

impl Arbitrary for ZeroBytes {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        ZeroBytes::new(u16::arbitrary(g))
    }
}
@@ -128,7 +128,7 @@ impl<T, const N: usize> Arbitrary for BoundedVec<T, N>
where
    T: Arbitrary + Eq,
{
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let mut v: Vec<T> = Arbitrary::arbitrary(g);
        v.truncate(N);
        v.try_into().expect("size within bounds")
modified radicle-node/src/tests.rs
@@ -973,7 +973,7 @@ fn prop_inventory_exchange_dense() {
            }
        }
    }
-
    quickcheck::QuickCheck::new()
-
        .gen(quickcheck::Gen::new(8))
+
    qcheck::QuickCheck::new()
+
        .gen(qcheck::Gen::new(8))
        .quickcheck(property as fn(MockStorage, MockStorage, MockStorage));
}
modified radicle-node/src/wire.rs
@@ -628,11 +628,11 @@ impl<R, S, W, G, H: Handshake> Iterator for Wire<R, S, W, G, H> {
#[cfg(test)]
mod tests {
    use super::*;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    use crate::crypto::Unverified;
    use crate::storage::refs::SignedRefs;
-
    use crate::test::{arbitrary, assert_matches};
+
    use crate::test::assert_matches;

    #[quickcheck]
    fn prop_u8(input: u8) {
@@ -655,13 +655,13 @@ mod tests {
    }

    #[quickcheck]
-
    fn prop_string(input: String) -> quickcheck::TestResult {
+
    fn prop_string(input: String) -> qcheck::TestResult {
        if input.len() > u8::MAX as usize {
-
            return quickcheck::TestResult::discard();
+
            return qcheck::TestResult::discard();
        }
        assert_eq!(deserialize::<String>(&serialize(&input)).unwrap(), input);

-
        quickcheck::TestResult::passed()
+
        qcheck::TestResult::passed()
    }

    #[quickcheck]
@@ -701,8 +701,8 @@ mod tests {
    }

    #[quickcheck]
-
    fn prop_signature(input: arbitrary::ByteArray<64>) {
-
        let signature = Signature::from(input.into_inner());
+
    fn prop_signature(input: [u8; 64]) {
+
        let signature = Signature::from(input);

        assert_eq!(
            deserialize::<Signature>(&serialize(&signature)).unwrap(),
@@ -711,8 +711,8 @@ mod tests {
    }

    #[quickcheck]
-
    fn prop_oid(input: arbitrary::ByteArray<20>) {
-
        let oid = git::Oid::try_from(input.into_inner().as_slice()).unwrap();
+
    fn prop_oid(input: [u8; 20]) {
+
        let oid = git::Oid::try_from(input.as_slice()).unwrap();

        assert_eq!(deserialize::<git::Oid>(&serialize(&oid)).unwrap(), oid);
    }
modified radicle-node/src/wire/message.rs
@@ -359,7 +359,7 @@ impl wire::Decode for ZeroBytes {
#[cfg(test)]
mod tests {
    use super::*;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    use crate::deserializer::Deserializer;
    use crate::wire::{self, Encode};
@@ -423,8 +423,8 @@ mod tests {
            }
        }

-
        quickcheck::QuickCheck::new()
-
            .gen(quickcheck::Gen::new(16))
+
        qcheck::QuickCheck::new()
+
            .gen(qcheck::Gen::new(16))
            .quickcheck(property as fn(items: Vec<Message>));
    }

modified radicle/Cargo.toml
@@ -7,7 +7,7 @@ edition = "2021"

[features]
default = []
-
test = ["quickcheck", "radicle-crypto/test"]
+
test = ["qcheck", "radicle-crypto/test"]
sql = ["sqlite"]

[dependencies]
@@ -56,15 +56,15 @@ path = "../radicle-ssh"
version = "0"
default-features = false

-
[dependencies.quickcheck]
+
[dependencies.qcheck]
version = "1"
default-features = false
optional = true

[dev-dependencies]
pretty_assertions = { version = "1.3.0" }
-
quickcheck_macros = { version = "1", default-features = false }
-
quickcheck = { version = "1", default-features = false }
+
qcheck-macros = { version = "1", default-features = false }
+
qcheck = { version = "1", default-features = false }

[dev-dependencies.radicle-crypto]
path = "../radicle-crypto"
modified radicle/src/cob/patch.rs
@@ -778,7 +778,7 @@ mod test {
    use radicle_crdt::test::{assert_laws, WeightedGenerator};

    use pretty_assertions::assert_eq;
-
    use quickcheck::{Arbitrary, TestResult};
+
    use qcheck::{Arbitrary, TestResult};

    use super::*;
    use crate::cob::op::{Actor, ActorId};
@@ -804,7 +804,7 @@ mod test {
    }

    impl<const N: usize> Arbitrary for Changes<N> {
-
        fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
        fn arbitrary(g: &mut qcheck::Gen) -> Self {
            type State = (clock::Lamport, Vec<OpId>, Vec<Tag>);

            let author = ActorId::from([0; 32]);
@@ -927,9 +927,9 @@ mod test {
            TestResult::passed()
        }

-
        quickcheck::QuickCheck::new()
+
        qcheck::QuickCheck::new()
            .min_tests_passed(100)
-
            .gen(quickcheck::Gen::new(8))
+
            .gen(qcheck::Gen::new(8))
            .quickcheck(property as fn(Changes<3>) -> TestResult);
    }

modified radicle/src/cob/thread.rs
@@ -290,8 +290,8 @@ mod tests {

    use crate::crypto::test::signer::MockSigner;
    use pretty_assertions::assert_eq;
-
    use quickcheck::Arbitrary;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck::Arbitrary;
+
    use qcheck_macros::quickcheck;

    use super::*;
    use crate as radicle;
@@ -316,7 +316,7 @@ mod tests {
    }

    impl<const N: usize> Arbitrary for Changes<N> {
-
        fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
        fn arbitrary(g: &mut qcheck::Gen) -> Self {
            let author = ActorId::from([0; 32]);
            let rng = fastrand::Rng::with_seed(u64::arbitrary(g));
            let gen =
modified radicle/src/identity.rs
@@ -83,7 +83,7 @@ impl Deref for Did {
mod test {
    use super::*;
    use crate::crypto::PublicKey;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;
    use std::collections::HashSet;

    #[quickcheck]
modified radicle/src/identity/project.rs
@@ -504,7 +504,7 @@ mod test {
    use crate::test::fixtures;

    use super::*;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    #[test]
    fn test_not_found() {
modified radicle/src/storage/refs.rs
@@ -367,7 +367,7 @@ pub mod canonical {
#[cfg(test)]
mod tests {
    use super::*;
-
    use quickcheck_macros::quickcheck;
+
    use qcheck_macros::quickcheck;

    #[quickcheck]
    fn prop_canonical_roundtrip(refs: Refs) {
modified radicle/src/test/arbitrary.rs
@@ -6,7 +6,7 @@ use std::ops::RangeBounds;
use crypto::test::signer::MockSigner;
use crypto::{PublicKey, Signer, Unverified, Verified};
use nonempty::NonEmpty;
-
use quickcheck::Arbitrary;
+
use qcheck::Arbitrary;

use crate::collections::HashMap;
use crate::git;
@@ -18,7 +18,7 @@ use crate::test::storage::MockStorage;
pub fn set<T: Eq + Hash + Arbitrary>(range: impl RangeBounds<usize>) -> HashSet<T> {
    let size = fastrand::usize(range);
    let mut set = HashSet::with_capacity(size);
-
    let mut g = quickcheck::Gen::new(size);
+
    let mut g = qcheck::Gen::new(size);

    while set.len() < size {
        set.insert(T::arbitrary(&mut g));
@@ -28,7 +28,7 @@ pub fn set<T: Eq + Hash + Arbitrary>(range: impl RangeBounds<usize>) -> HashSet<

pub fn vec<T: Eq + Arbitrary>(size: usize) -> Vec<T> {
    let mut vec = Vec::with_capacity(size);
-
    let mut g = quickcheck::Gen::new(size);
+
    let mut g = qcheck::Gen::new(size);

    for _ in 0..vec.capacity() {
        vec.push(T::arbitrary(&mut g));
@@ -37,36 +37,13 @@ pub fn vec<T: Eq + Arbitrary>(size: usize) -> Vec<T> {
}

pub fn gen<T: Arbitrary>(size: usize) -> T {
-
    let mut gen = quickcheck::Gen::new(size);
+
    let mut gen = qcheck::Gen::new(size);

    T::arbitrary(&mut gen)
}

-
#[derive(Clone, Debug)]
-
pub struct ByteArray<const N: usize>([u8; N]);
-

-
impl<const N: usize> ByteArray<N> {
-
    pub fn into_inner(self) -> [u8; N] {
-
        self.0
-
    }
-

-
    pub fn as_slice(&self) -> &[u8] {
-
        self.0.as_slice()
-
    }
-
}
-

-
impl<const N: usize> Arbitrary for ByteArray<N> {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
-
        let mut bytes: [u8; N] = [0; N];
-
        for byte in &mut bytes {
-
            *byte = u8::arbitrary(g);
-
        }
-
        Self(bytes)
-
    }
-
}
-

impl Arbitrary for storage::Remotes<crypto::Verified> {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let remotes: HashMap<storage::RemoteId, storage::Remote<crypto::Verified>> =
            Arbitrary::arbitrary(g);

@@ -75,13 +52,13 @@ impl Arbitrary for storage::Remotes<crypto::Verified> {
}

impl Arbitrary for Did {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        Self::from(PublicKey::arbitrary(g))
    }
}

impl Arbitrary for Delegate {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        Self {
            name: String::arbitrary(g),
            id: Did::arbitrary(g),
@@ -90,7 +67,7 @@ impl Arbitrary for Delegate {
}

impl Arbitrary for Doc<Unverified> {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let name = String::arbitrary(g);
        let description = String::arbitrary(g);
        let default_branch = git::RefString::try_from(String::arbitrary(g)).unwrap();
@@ -101,7 +78,7 @@ impl Arbitrary for Doc<Unverified> {
}

impl Arbitrary for Doc<Verified> {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let rng = fastrand::Rng::with_seed(u64::arbitrary(g));
        let name = iter::repeat_with(|| rng.alphanumeric())
            .take(rng.usize(1..16))
@@ -133,9 +110,9 @@ impl Arbitrary for Doc<Verified> {
}

impl Arbitrary for SignedRefs<Unverified> {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
-
        let bytes: ByteArray<64> = Arbitrary::arbitrary(g);
-
        let signature = crypto::Signature::from(bytes.into_inner());
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
+
        let bytes: [u8; 64] = Arbitrary::arbitrary(g);
+
        let signature = crypto::Signature::from(bytes);
        let refs = Refs::arbitrary(g);

        Self::new(refs, signature)
@@ -143,7 +120,7 @@ impl Arbitrary for SignedRefs<Unverified> {
}

impl Arbitrary for Refs {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let mut refs: BTreeMap<git::RefString, storage::Oid> = BTreeMap::new();
        let mut bytes: [u8; 20] = [0; 20];
        let names = &[
@@ -173,14 +150,14 @@ impl Arbitrary for Refs {
}

impl Arbitrary for MockStorage {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let inventory = Arbitrary::arbitrary(g);
        MockStorage::new(inventory)
    }
}

impl Arbitrary for storage::Remote<crypto::Verified> {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
        let refs = Refs::arbitrary(g);
        let signer = MockSigner::arbitrary(g);
        let signed = refs.signed(&signer).unwrap();
@@ -190,8 +167,8 @@ impl Arbitrary for storage::Remote<crypto::Verified> {
}

impl Arbitrary for Id {
-
    fn arbitrary(g: &mut quickcheck::Gen) -> Self {
-
        let bytes = ByteArray::<20>::arbitrary(g);
+
    fn arbitrary(g: &mut qcheck::Gen) -> Self {
+
        let bytes = <[u8; 20]>::arbitrary(g);
        let oid = git::Oid::try_from(bytes.as_slice()).unwrap();

        Id::from(oid)