mirror of
https://github.com/prosolis/gogobee.git
synced 2026-07-15 08:32:41 +00:00
Combat narration: format magnitude for stat_drain/debuff/ally_buff
These three stateful enemy-effect cases emitted their flavor pool via bare
pickRand, leaking the literal %d placeholder to players ("-%d damage on
every strike from here"). The magnitude is carried in CombatEvent.Damage,
exactly like the already-correct max_hp_drain / spell_fizzle cases; wrap
them in fmt.Sprintf. Add a regression test asserting no placeholder leaks.
This commit is contained in:
@@ -326,9 +326,9 @@ func renderEvent(e CombatEvent, playerName, enemyName string, result CombatResul
|
|||||||
case "survive_at_1":
|
case "survive_at_1":
|
||||||
return pickRand(narrativeSurvive)
|
return pickRand(narrativeSurvive)
|
||||||
case "stat_drain":
|
case "stat_drain":
|
||||||
return pickRand(narrativeStatDrain)
|
return fmt.Sprintf(pickRand(narrativeStatDrain), e.Damage)
|
||||||
case "debuff":
|
case "debuff":
|
||||||
return pickRand(narrativeDebuff)
|
return fmt.Sprintf(pickRand(narrativeDebuff), e.Damage)
|
||||||
case "max_hp_drain":
|
case "max_hp_drain":
|
||||||
return fmt.Sprintf(pickRand(narrativeMaxHPDrain), e.Damage)
|
return fmt.Sprintf(pickRand(narrativeMaxHPDrain), e.Damage)
|
||||||
|
|
||||||
@@ -346,7 +346,7 @@ func renderEvent(e CombatEvent, playerName, enemyName string, result CombatResul
|
|||||||
case "fear_resist":
|
case "fear_resist":
|
||||||
return pickRand(narrativeFearResist)
|
return pickRand(narrativeFearResist)
|
||||||
case "ally_buff":
|
case "ally_buff":
|
||||||
return pickRand(narrativeAllyBuff)
|
return fmt.Sprintf(pickRand(narrativeAllyBuff), e.Damage)
|
||||||
|
|
||||||
case "timeout":
|
case "timeout":
|
||||||
return pickRand(narrativeTimeout)
|
return pickRand(narrativeTimeout)
|
||||||
|
|||||||
24
internal/plugin/combat_narrative_drain_test.go
Normal file
24
internal/plugin/combat_narrative_drain_test.go
Normal file
@@ -0,0 +1,24 @@
|
|||||||
|
package plugin
|
||||||
|
|
||||||
|
import (
|
||||||
|
"strings"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
// TestRenderEvent_StatefulDrainsFormatMagnitude is a regression test for the
|
||||||
|
// leaked "%d" in stateful enemy-effect narration. stat_drain, debuff and
|
||||||
|
// ally_buff carry their magnitude in CombatEvent.Damage and their flavor
|
||||||
|
// pools contain a %d placeholder; renderEvent must fmt.Sprintf them rather
|
||||||
|
// than emit the template raw (which surfaced "-%d damage" to players).
|
||||||
|
func TestRenderEvent_StatefulDrainsFormatMagnitude(t *testing.T) {
|
||||||
|
for _, action := range []string{"stat_drain", "debuff", "ally_buff"} {
|
||||||
|
e := CombatEvent{Actor: "enemy", Action: action, Damage: 4}
|
||||||
|
out := renderEvent(e, "Rurina", "Shadow", CombatResult{}, newActionPicker())
|
||||||
|
if strings.Contains(out, "%") {
|
||||||
|
t.Errorf("%s: leaked format placeholder in output: %q", action, out)
|
||||||
|
}
|
||||||
|
if !strings.Contains(out, "4") {
|
||||||
|
t.Errorf("%s: expected magnitude 4 in output: %q", action, out)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user