diff --git a/src/apps/billboard/views.py b/src/apps/billboard/views.py
index cee7604..d627e43 100644
--- a/src/apps/billboard/views.py
+++ b/src/apps/billboard/views.py
@@ -216,7 +216,7 @@ def my_notes(request):
{
"obj": n,
"title": _NOTE_META.get(n.slug, {}).get("title", n.slug),
- "recognition_title": n.display_title,
+ "recognition_title": n.card_title,
"description": _NOTE_META.get(n.slug, {}).get("description", ""),
"palette_options": _NOTE_META.get(n.slug, {}).get("palette_options", []),
"swatch_label": _NOTE_META.get(n.slug, {}).get("swatch_label"),
diff --git a/src/apps/dashboard/tests/integrated/test_views.py b/src/apps/dashboard/tests/integrated/test_views.py
index 95f6ce9..ed4fe80 100644
--- a/src/apps/dashboard/tests/integrated/test_views.py
+++ b/src/apps/dashboard/tests/integrated/test_views.py
@@ -768,7 +768,7 @@ class SetPronounsBawlmoreseUnlockTest(TestCase):
def test_brief_payload_carries_baltimorean_title(self):
response = self.client.post(self.url, data={"pronouns": "bawlmorese"})
brief = response.json()["brief"]
- self.assertEqual(brief["title"], "Ard!")
+ self.assertEqual(brief["title"], "Baltimorean")
def test_brief_payload_square_url_jumps_to_my_notes(self):
"""NOTE_UNLOCK Briefs carry a `square_url` pointing at /billboard/my-notes/
diff --git a/src/apps/drama/models.py b/src/apps/drama/models.py
index e129572..0ae9cea 100644
--- a/src/apps/drama/models.py
+++ b/src/apps/drama/models.py
@@ -212,7 +212,7 @@ _NOTE_DISPLAY = {
"nomad": {"greeting": "Welcome,", "title": "Nomad"},
"super-schizo": {"greeting": "21st Century", "title": "Schizoid Man"},
"super-nomad": {"greeting": "Howdy,", "title": "Stranger"},
- "baltimorean": {"greeting": "Ayo,", "title": "Ard!"},
+ "baltimorean": {"greeting": "Ayo,", "title": "Ard!", "card_title": "Baltimorean"},
}
# Note slugs whose grant prose uses the long admin format ("The administration
@@ -249,6 +249,15 @@ class Note(models.Model):
def display_greeting(self):
return _NOTE_DISPLAY.get(self.slug, {}).get("greeting", "Welcome,")
+ @property
+ def card_title(self):
+ """The string shown in the my-notes card's "Title:" row. Defaults to
+ `display_title` (the don-able title — most slugs render the title you
+ DON here, e.g. "Schizoid Man" for super-schizo). Baltimorean overrides
+ so the card reads "Baltimorean" instead of the navbar-only "Ard!"
+ flair."""
+ return _NOTE_DISPLAY.get(self.slug, {}).get("card_title", self.display_title)
+
@property
def display_name(self):
"""The Note's *name* (e.g., "Stargazer", "Super-Schizo") — the heading
@@ -316,9 +325,13 @@ class Note(models.Model):
"This does not entail any additional corporate benefits."
)
else:
+ # Inline attribution reads "{handle} the {Note name}", not the
+ # don-able title. For most slugs the two coincide ("the Stargazer")
+ # but Baltimorean's title is the navbar flair "Ard!" — "the Ard!"
+ # reads oddly inline; "the Baltimorean" matches the Note name.
attr_combo = (
f'{handle} '
- f'the {note.display_title}'
+ f'the {note.display_name}'
)
line_text = (
f"Look!—new Note unlocked. {note_anchor} "
@@ -339,6 +352,6 @@ class Note(models.Model):
post=post,
line=line,
kind=Brief.KIND_NOTE_UNLOCK,
- title=note.display_title,
+ title=note.display_name,
)
return note, created, brief
diff --git a/src/apps/drama/tests/integrated/test_note_brief.py b/src/apps/drama/tests/integrated/test_note_brief.py
index bd80e87..fd8b940 100644
--- a/src/apps/drama/tests/integrated/test_note_brief.py
+++ b/src/apps/drama/tests/integrated/test_note_brief.py
@@ -30,8 +30,9 @@ class GrantIfNewSpawnsBriefTest(TestCase):
self.assertEqual(brief.owner, self.user)
# The Brief's line is one of the Post's lines
self.assertIn(brief.line, list(post.lines.all()))
- # Brief title matches Note display title
- self.assertEqual(brief.title, note.display_title)
+ # Brief title matches Note display name (the Note's name — used in the
+ # banner's title slot and inline "the {name}" attribution).
+ self.assertEqual(brief.title, note.display_name)
def test_second_grant_same_slug_returns_no_brief(self):
Note.grant_if_new(self.user, "stargazer")
diff --git a/src/apps/drama/tests/unit/test_models.py b/src/apps/drama/tests/unit/test_models.py
index a947ce5..7c823db 100644
--- a/src/apps/drama/tests/unit/test_models.py
+++ b/src/apps/drama/tests/unit/test_models.py
@@ -27,6 +27,12 @@ class NoteDisplayBaltimoreanTest(SimpleTestCase):
through to `slug.title()` → 'Baltimorean'."""
self.assertEqual(_note("baltimorean").display_name, "Baltimorean")
+ def test_baltimorean_card_title_is_baltimorean(self):
+ """The my-notes card's "Title:" row uses `card_title`, which Baltimorean
+ explicitly overrides to "Baltimorean" so the navbar-only "Ard!" flair
+ doesn't leak onto the card."""
+ self.assertEqual(_note("baltimorean").card_title, "Baltimorean")
+
class NoteDisplayStargazerTest(SimpleTestCase):
"""Smoke tests for the existing stargazer entry — pins the contract that
@@ -37,3 +43,8 @@ class NoteDisplayStargazerTest(SimpleTestCase):
def test_stargazer_display_greeting_is_welcome(self):
self.assertEqual(_note("stargazer").display_greeting, "Welcome,")
+
+ def test_stargazer_card_title_falls_back_to_display_title(self):
+ """Slugs without a `card_title` override fall through to display_title —
+ for stargazer that's "Stargazer" (don-able title == Note name)."""
+ self.assertEqual(_note("stargazer").card_title, "Stargazer")
diff --git a/src/functional_tests/test_bill_baltimorean.py b/src/functional_tests/test_bill_baltimorean.py
index fcf73fa..ad1a402 100644
--- a/src/functional_tests/test_bill_baltimorean.py
+++ b/src/functional_tests/test_bill_baltimorean.py
@@ -7,7 +7,7 @@ Baltimorean Note and fires the slide-down Brief banner.
End-to-end loop captured here:
1. Game Kit → pronouns applet → click `bawlmorese` card → guard portal "OK"
- 2. Brief banner slides in with title "Ard!" + Look! prose + FYI/NVM/?-square
+ 2. Brief banner slides in with title "Baltimorean" + Look! prose + FYI/NVM/?-square
3. Navigate to /billboard/my-notes/ → Baltimorean item w. the Aaron quote
4. DON the Baltimorean Note → navbar greeting flips
"Welcome, Earthman" → "Ayo, Ard!"
@@ -106,10 +106,10 @@ class BaltimoreanNoteFromGameKitTest(FunctionalTest):
banner = self.wait_for_slow(lambda: self.browser.find_element(
By.CSS_SELECTOR, ".note-banner"
))
- # The title slot carries the recognition title — for baltimorean
- # that's "Ard!" (vs stargazer's "Stargazer").
+ # The title slot carries the Note name — "Baltimorean". The don-able
+ # title "Ard!" only surfaces in the navbar greeting after DON.
self.assertIn(
- "Ard!",
+ "Baltimorean",
banner.find_element(By.CSS_SELECTOR, ".note-banner__title").text,
)
# Look! prose lands in the description.
diff --git a/src/functional_tests/test_game_kit.py b/src/functional_tests/test_game_kit.py
index 2a24479..2c432a2 100644
--- a/src/functional_tests/test_game_kit.py
+++ b/src/functional_tests/test_game_kit.py
@@ -198,12 +198,13 @@ class PronounsAppletFlowTest(FunctionalTest):
self.assertIn("Set pronoun preference?", portal.text)
self.assertIn("yo/yo/yos", portal.text)
- # 4. Click OK — the page reloads, .active class moves to bawlmorese.
+ # 4. Click OK — first-time bawlmorese unlocks the Baltimorean Note, so
+ # the server returns 200 w. a Brief payload (no reload — the banner
+ # would be lost). Wait for the banner to confirm the commit landed
+ # before navigating away.
portal.find_element(By.CSS_SELECTOR, ".guard-yes").click()
self.wait_for(
- lambda: self.browser.find_element(
- By.CSS_SELECTOR, ".gk-pronoun-card.active[data-pronoun='bawlmorese']"
- )
+ lambda: self.browser.find_element(By.CSS_SELECTOR, ".note-banner")
)
# 5. Navigate to the Billboard — Most Recent Scroll applet must now