From 7ea813fdf15b4086c023166f035e2c057aca1e07 Mon Sep 17 00:00:00 2001 From: Datawav Date: Tue, 30 Jun 2026 06:10:02 +0000 Subject: [PATCH 1/2] Grow default profile pseudonym pool to 128x128 Expand DEFAULT_PROFILE_ADJECTIVES and DEFAULT_PROFILE_NOUNS from 32 to 128 entries each. Pool grows from 1,024 to 16,384 combinations. At 32 nouns the birthday-paradox 50% collision threshold sits at ~7 rolls, which is why users see the same animals repeating almost immediately at signup. At 128 nouns the same threshold moves to ~14. No logic changes. Existing 32 entries preserved; lists stay alphabetical. Existing assert_two_word_pseudonym shape test continues to pass. Word lists are byte-identical to the client-side mirror in marmot-protocol/whitenoise-android. Refs #764 --- crates/marmot-app/src/lib.rs | 38 ++++++++++++++++++++++++++++-------- 1 file changed, 30 insertions(+), 8 deletions(-) diff --git a/crates/marmot-app/src/lib.rs b/crates/marmot-app/src/lib.rs index a73cab0c..44bf69af 100644 --- a/crates/marmot-app/src/lib.rs +++ b/crates/marmot-app/src/lib.rs @@ -229,16 +229,38 @@ pub(crate) const MAX_SEEN_EVENT_IDS: usize = 16_384; const KIND_NOSTR_METADATA: u64 = 0; const KIND_NOSTR_CONTACT_LIST: u64 = 3; const DEFAULT_PROFILE_ADJECTIVES: &[&str] = &[ - "Agile", "Angry", "Brave", "Bright", "Calm", "Clever", "Cosmic", "Daring", "Electric", - "Gentle", "Golden", "Happy", "Hidden", "Jolly", "Kind", "Lucky", "Majestic", "Mellow", - "Mighty", "Nimble", "Noble", "Quiet", "Rapid", "Sage", "Silver", "Sunny", "Swift", "Vivid", - "Witty", "Wondrous", "Young", "Zesty", + "Agile", "Amber", "Angry", "Balanced", "Bold", "Brave", "Breezy", "Bright", "Brisk", + "Bubbly", "Calm", "Caring", "Cheerful", "Clear", "Clever", "Coral", "Cosmic", "Cozy", + "Crimson", "Crisp", "Curious", "Daring", "Dawn", "Deep", "Diamond", "Dreamy", "Eager", + "Earnest", "Easy", "Electric", "Emerald", "Festive", "Fiery", "Fleet", "Forest", "Fresh", + "Frosty", "Gentle", "Glad", "Golden", "Graceful", "Grand", "Grateful", "Green", "Happy", + "Hardy", "Hearty", "Hidden", "Honest", "Hopeful", "Humble", "Indigo", "Ivory", "Jade", + "Jolly", "Kind", "Lively", "Loyal", "Lucky", "Majestic", "Maple", "Mellow", "Merry", + "Mighty", "Mindful", "Misty", "Modest", "Mossy", "Neat", "Nifty", "Nimble", "Noble", + "Olive", "Open", "Patient", "Peaceful", "Plum", "Polar", "Proud", "Quiet", "Radiant", + "Rapid", "Ready", "Restful", "Rosy", "Ruby", "Rustic", "Sage", "Scarlet", "Serene", + "Sharp", "Shiny", "Silver", "Sincere", "Sky", "Smooth", "Solar", "Solid", "Spirited", + "Spry", "Steady", "Stellar", "Stormy", "Sturdy", "Sunlit", "Sunny", "Swift", "Tame", + "Tangy", "Tender", "Tidy", "Topaz", "Tranquil", "Trusty", "Twilight", "Upbeat", "Valiant", + "Verdant", "Vivid", "Warm", "Willing", "Winsome", "Wise", "Witty", "Wondrous", "Woodland", + "Young", "Zesty", ]; const DEFAULT_PROFILE_NOUNS: &[&str] = &[ - "Antelope", "Badger", "Bear", "Beaver", "Bison", "Bobcat", "Cougar", "Dolphin", "Eagle", - "Falcon", "Finch", "Fox", "Gecko", "Heron", "Jaguar", "Koala", "Llama", "Lynx", "Moose", - "Narwhal", "Otter", "Owl", "Panda", "Puffin", "Raven", "Robin", "Seal", "Swan", "Tiger", - "Turtle", "Wolf", "Yak", + "Albatross", "Alpaca", "Ant", "Antelope", "Armadillo", "Badger", "Bat", "Bear", "Beaver", + "Bee", "Bison", "Bluebird", "Bobcat", "Bullfrog", "Bumblebee", "Butterfly", "Camel", "Caribou", + "Cat", "Caterpillar", "Cheetah", "Chickadee", "Chinchilla", "Chipmunk", "Cobra", "Condor", + "Cougar", "Crab", "Crane", "Cricket", "Crow", "Deer", "Dingo", "Dolphin", "Dove", "Dragonfly", + "Duck", "Eagle", "Egret", "Elephant", "Elk", "Falcon", "Fawn", "Ferret", "Finch", "Firefly", + "Flamingo", "Flounder", "Fox", "Gazelle", "Gecko", "Giraffe", "Goat", "Goose", "Gopher", + "Grouse", "Hare", "Hawk", "Hedgehog", "Heron", "Hippo", "Hornet", "Horse", "Hummingbird", + "Ibex", "Iguana", "Jackal", "Jaguar", "Jay", "Kestrel", "Kingfisher", "Kiwi", "Koala", + "Ladybug", "Lark", "Leopard", "Lion", "Llama", "Lynx", "Macaw", "Magpie", "Mallard", + "Manatee", "Marmot", "Meerkat", "Mink", "Mole", "Mongoose", "Monkey", "Moose", "Mouse", + "Narwhal", "Newt", "Nightingale", "Octopus", "Opossum", "Orca", "Oriole", "Ostrich", "Otter", + "Owl", "Panda", "Parrot", "Peacock", "Pelican", "Penguin", "Pheasant", "Pigeon", "Pony", + "Porcupine", "Puffin", "Quail", "Rabbit", "Raccoon", "Ram", "Raven", "Reindeer", "Rhino", + "Roadrunner", "Robin", "Salamander", "Salmon", "Seal", "Swan", "Tiger", "Turtle", "Wolf", + "Yak", ]; type AppRuntime = AccountDeviceRuntime< From 352c09c49ca472b29cacf6397b88ae1192596bd8 Mon Sep 17 00:00:00 2001 From: Jeff Gardner <202880+erskingardner@users.noreply.github.com> Date: Wed, 1 Jul 2026 17:43:58 -0400 Subject: [PATCH 2/2] Fix pseudonym pool formatting and invariants --- crates/marmot-app/src/lib.rs | 170 +++++++++++++++++++++++++++------ crates/marmot-app/src/tests.rs | 34 +++++++ 2 files changed, 175 insertions(+), 29 deletions(-) diff --git a/crates/marmot-app/src/lib.rs b/crates/marmot-app/src/lib.rs index 44bf69af..a0c1ca97 100644 --- a/crates/marmot-app/src/lib.rs +++ b/crates/marmot-app/src/lib.rs @@ -229,37 +229,149 @@ pub(crate) const MAX_SEEN_EVENT_IDS: usize = 16_384; const KIND_NOSTR_METADATA: u64 = 0; const KIND_NOSTR_CONTACT_LIST: u64 = 3; const DEFAULT_PROFILE_ADJECTIVES: &[&str] = &[ - "Agile", "Amber", "Angry", "Balanced", "Bold", "Brave", "Breezy", "Bright", "Brisk", - "Bubbly", "Calm", "Caring", "Cheerful", "Clear", "Clever", "Coral", "Cosmic", "Cozy", - "Crimson", "Crisp", "Curious", "Daring", "Dawn", "Deep", "Diamond", "Dreamy", "Eager", - "Earnest", "Easy", "Electric", "Emerald", "Festive", "Fiery", "Fleet", "Forest", "Fresh", - "Frosty", "Gentle", "Glad", "Golden", "Graceful", "Grand", "Grateful", "Green", "Happy", - "Hardy", "Hearty", "Hidden", "Honest", "Hopeful", "Humble", "Indigo", "Ivory", "Jade", - "Jolly", "Kind", "Lively", "Loyal", "Lucky", "Majestic", "Maple", "Mellow", "Merry", - "Mighty", "Mindful", "Misty", "Modest", "Mossy", "Neat", "Nifty", "Nimble", "Noble", - "Olive", "Open", "Patient", "Peaceful", "Plum", "Polar", "Proud", "Quiet", "Radiant", - "Rapid", "Ready", "Restful", "Rosy", "Ruby", "Rustic", "Sage", "Scarlet", "Serene", - "Sharp", "Shiny", "Silver", "Sincere", "Sky", "Smooth", "Solar", "Solid", "Spirited", - "Spry", "Steady", "Stellar", "Stormy", "Sturdy", "Sunlit", "Sunny", "Swift", "Tame", - "Tangy", "Tender", "Tidy", "Topaz", "Tranquil", "Trusty", "Twilight", "Upbeat", "Valiant", - "Verdant", "Vivid", "Warm", "Willing", "Winsome", "Wise", "Witty", "Wondrous", "Woodland", - "Young", "Zesty", + "Agile", "Amber", "Angry", "Balanced", "Bold", "Brave", "Breezy", "Bright", "Brisk", "Bubbly", + "Calm", "Caring", "Cheerful", "Clear", "Clever", "Coral", "Cosmic", "Cozy", "Crimson", "Crisp", + "Curious", "Daring", "Dawn", "Deep", "Diamond", "Dreamy", "Eager", "Earnest", "Easy", + "Electric", "Emerald", "Festive", "Fiery", "Fleet", "Forest", "Fresh", "Frosty", "Gentle", + "Glad", "Golden", "Graceful", "Grand", "Grateful", "Green", "Happy", "Hardy", "Hearty", + "Hidden", "Honest", "Hopeful", "Humble", "Indigo", "Ivory", "Jade", "Jolly", "Kind", "Lively", + "Loyal", "Lucky", "Majestic", "Maple", "Mellow", "Merry", "Mighty", "Mindful", "Misty", + "Modest", "Mossy", "Neat", "Nifty", "Nimble", "Noble", "Olive", "Open", "Patient", "Peaceful", + "Plum", "Polar", "Proud", "Quiet", "Radiant", "Rapid", "Ready", "Restful", "Rosy", "Ruby", + "Rustic", "Sage", "Scarlet", "Serene", "Sharp", "Shiny", "Silver", "Sincere", "Sky", "Smooth", + "Solar", "Solid", "Spirited", "Spry", "Steady", "Stellar", "Stormy", "Sturdy", "Sunlit", + "Sunny", "Swift", "Tame", "Tangy", "Tender", "Tidy", "Topaz", "Tranquil", "Trusty", "Twilight", + "Upbeat", "Valiant", "Verdant", "Vivid", "Warm", "Willing", "Winsome", "Wise", "Witty", + "Wondrous", "Woodland", "Young", "Zesty", ]; const DEFAULT_PROFILE_NOUNS: &[&str] = &[ - "Albatross", "Alpaca", "Ant", "Antelope", "Armadillo", "Badger", "Bat", "Bear", "Beaver", - "Bee", "Bison", "Bluebird", "Bobcat", "Bullfrog", "Bumblebee", "Butterfly", "Camel", "Caribou", - "Cat", "Caterpillar", "Cheetah", "Chickadee", "Chinchilla", "Chipmunk", "Cobra", "Condor", - "Cougar", "Crab", "Crane", "Cricket", "Crow", "Deer", "Dingo", "Dolphin", "Dove", "Dragonfly", - "Duck", "Eagle", "Egret", "Elephant", "Elk", "Falcon", "Fawn", "Ferret", "Finch", "Firefly", - "Flamingo", "Flounder", "Fox", "Gazelle", "Gecko", "Giraffe", "Goat", "Goose", "Gopher", - "Grouse", "Hare", "Hawk", "Hedgehog", "Heron", "Hippo", "Hornet", "Horse", "Hummingbird", - "Ibex", "Iguana", "Jackal", "Jaguar", "Jay", "Kestrel", "Kingfisher", "Kiwi", "Koala", - "Ladybug", "Lark", "Leopard", "Lion", "Llama", "Lynx", "Macaw", "Magpie", "Mallard", - "Manatee", "Marmot", "Meerkat", "Mink", "Mole", "Mongoose", "Monkey", "Moose", "Mouse", - "Narwhal", "Newt", "Nightingale", "Octopus", "Opossum", "Orca", "Oriole", "Ostrich", "Otter", - "Owl", "Panda", "Parrot", "Peacock", "Pelican", "Penguin", "Pheasant", "Pigeon", "Pony", - "Porcupine", "Puffin", "Quail", "Rabbit", "Raccoon", "Ram", "Raven", "Reindeer", "Rhino", - "Roadrunner", "Robin", "Salamander", "Salmon", "Seal", "Swan", "Tiger", "Turtle", "Wolf", + "Albatross", + "Alpaca", + "Ant", + "Antelope", + "Armadillo", + "Badger", + "Bat", + "Bear", + "Beaver", + "Bee", + "Bison", + "Bluebird", + "Bobcat", + "Bullfrog", + "Bumblebee", + "Butterfly", + "Camel", + "Caribou", + "Cat", + "Caterpillar", + "Cheetah", + "Chickadee", + "Chinchilla", + "Chipmunk", + "Cobra", + "Condor", + "Cougar", + "Crab", + "Crane", + "Cricket", + "Crow", + "Deer", + "Dingo", + "Dolphin", + "Dove", + "Dragonfly", + "Duck", + "Eagle", + "Egret", + "Elephant", + "Elk", + "Falcon", + "Fawn", + "Ferret", + "Finch", + "Firefly", + "Flamingo", + "Flounder", + "Fox", + "Gazelle", + "Gecko", + "Giraffe", + "Goat", + "Goose", + "Gopher", + "Grouse", + "Hare", + "Hawk", + "Hedgehog", + "Heron", + "Hippo", + "Hornet", + "Horse", + "Hummingbird", + "Ibex", + "Iguana", + "Jackal", + "Jaguar", + "Jay", + "Kestrel", + "Kingfisher", + "Kiwi", + "Koala", + "Ladybug", + "Lark", + "Leopard", + "Lion", + "Llama", + "Lynx", + "Macaw", + "Magpie", + "Mallard", + "Manatee", + "Marmot", + "Meerkat", + "Mink", + "Mole", + "Mongoose", + "Monkey", + "Moose", + "Mouse", + "Narwhal", + "Newt", + "Nightingale", + "Octopus", + "Opossum", + "Orca", + "Oriole", + "Ostrich", + "Otter", + "Owl", + "Panda", + "Parrot", + "Peacock", + "Pelican", + "Penguin", + "Pheasant", + "Pigeon", + "Pony", + "Porcupine", + "Puffin", + "Quail", + "Rabbit", + "Raccoon", + "Ram", + "Raven", + "Reindeer", + "Rhino", + "Roadrunner", + "Robin", + "Salamander", + "Salmon", + "Seal", + "Swan", + "Tiger", + "Turtle", + "Wolf", "Yak", ]; diff --git a/crates/marmot-app/src/tests.rs b/crates/marmot-app/src/tests.rs index 0f0fdd12..64dcd32b 100644 --- a/crates/marmot-app/src/tests.rs +++ b/crates/marmot-app/src/tests.rs @@ -39,6 +39,40 @@ fn legacy_projection_update_json_defaults_new_streaming_fields() { ); } +#[test] +fn default_profile_word_lists_keep_expected_shape() { + assert_profile_word_list("adjectives", DEFAULT_PROFILE_ADJECTIVES); + assert_profile_word_list("nouns", DEFAULT_PROFILE_NOUNS); + assert_eq!( + DEFAULT_PROFILE_ADJECTIVES.len() * DEFAULT_PROFILE_NOUNS.len(), + 16_384 + ); +} + +fn assert_profile_word_list(name: &str, words: &[&str]) { + assert_eq!(words.len(), 128, "{name} should have 128 entries"); + for word in words { + assert!(!word.is_empty(), "{name} should not contain empty words"); + let mut chars = word.chars(); + assert!( + chars.next().is_some_and(|ch| ch.is_ascii_uppercase()), + "{name} word should start uppercase: {word}" + ); + assert!( + chars.all(|ch| ch.is_ascii_lowercase()), + "{name} word should be title-cased ASCII: {word}" + ); + } + for pair in words.windows(2) { + assert!( + pair[0] < pair[1], + "{name} should be sorted and unique: {} before {}", + pair[0], + pair[1] + ); + } +} + fn relay_delivery(event_id: String, pubkey: String) -> cgka_traits::TransportDelivery { let event = NostrTransportEvent { id: event_id,