step 5.3: done
This commit is contained in:
@@ -12,7 +12,7 @@ describe('inventoryService', () => {
|
||||
before(async () => {
|
||||
await setup();
|
||||
db = require('../../src/db').getDb();
|
||||
({ listInventory, equipItem, unequipItem } = require('../../src/services/inventoryService'));
|
||||
({ listInventory, equipItem, unequipItem, useConsumable } = require('../../src/services/inventoryService'));
|
||||
({ createCharacter } = require('../../src/services/characterService'));
|
||||
});
|
||||
|
||||
@@ -163,4 +163,111 @@ describe('inventoryService', () => {
|
||||
assert.ok(result.derived.maxHp > baseMaxHp,
|
||||
`maxHp should increase with vit bonus (was ${baseMaxHp}, now ${result.derived.maxHp})`);
|
||||
});
|
||||
|
||||
it('uses a healing potion and increases HP (capped at maxHp)', () => {
|
||||
const id = makeHero({ level: 1, str: 8, agi: 4, int: 2, vit: 8 });
|
||||
// Grant 3 Minor Healing Potions (item 14, heal:50)
|
||||
grantItem(id, 14, 3);
|
||||
|
||||
// Set HP to 60 (out of ~145 maxHp for warrior with vit=8: 50+80+5=135)
|
||||
db.prepare('UPDATE characters SET hp_current = 60 WHERE id = ?').run(id);
|
||||
|
||||
const before = listInventory(id);
|
||||
const beforeHp = db.prepare('SELECT hp_current FROM characters WHERE id = ?').get(id).hp_current;
|
||||
const maxHp = before.derived.maxHp;
|
||||
|
||||
// Use one potion: should heal to min(60+50, maxHp)
|
||||
const result = useConsumable(id, 14);
|
||||
const afterHp = db.prepare('SELECT hp_current FROM characters WHERE id = ?').get(id).hp_current;
|
||||
|
||||
assert.equal(afterHp, Math.min(beforeHp + 50, maxHp));
|
||||
// Quantity should be 3 → 2 (still in inventory)
|
||||
const potion = result.items.find((i) => i.itemId === 14);
|
||||
assert.equal(potion.quantity, 2);
|
||||
});
|
||||
|
||||
it('uses an energy tonic and restores energy (capped at 100)', () => {
|
||||
const id = makeHero({ level: 1, str: 8, agi: 4, int: 2, vit: 8 });
|
||||
// Grant 2 Energy Tonics (item 16, energy:25)
|
||||
grantItem(id, 16, 2);
|
||||
|
||||
// Set energy to 40
|
||||
db.prepare('UPDATE characters SET energy = 40 WHERE id = ?').run(id);
|
||||
|
||||
const before = listInventory(id);
|
||||
const beforeEnergy = db.prepare('SELECT energy FROM characters WHERE id = ?').get(id).energy;
|
||||
|
||||
// Use one tonic: should restore to min(40+25, 100) = 65
|
||||
const result = useConsumable(id, 16);
|
||||
const afterEnergy = db.prepare('SELECT energy FROM characters WHERE id = ?').get(id).energy;
|
||||
|
||||
assert.equal(afterEnergy, Math.min(beforeEnergy + 25, 100));
|
||||
// Quantity should be 2 → 1
|
||||
const tonic = result.items.find((i) => i.itemId === 16);
|
||||
assert.equal(tonic.quantity, 1);
|
||||
});
|
||||
|
||||
it('rejects using a non-consumable item', () => {
|
||||
const id = makeHero();
|
||||
grantItem(id, 1); // Rusty Sword (weapon)
|
||||
assert.throws(() => useConsumable(id, 1), (e) => e.code === 'VALIDATION_ERROR');
|
||||
});
|
||||
|
||||
it('rejects using an item not in inventory', () => {
|
||||
const id = makeHero();
|
||||
// Item 14 exists but not granted to this character
|
||||
assert.throws(() => useConsumable(id, 14), (e) => e.code === 'NOT_FOUND');
|
||||
});
|
||||
|
||||
it('removes inventory row when quantity reaches 0 (single-item stack)', () => {
|
||||
const id = makeHero({ level: 1, str: 8, agi: 4, int: 2, vit: 8 });
|
||||
// Grant 1 Greater Healing Potion (item 15, heal:150)
|
||||
grantItem(id, 15, 1);
|
||||
|
||||
// Set HP low
|
||||
db.prepare('UPDATE characters SET hp_current = 20 WHERE id = ?').run(id);
|
||||
|
||||
const before = listInventory(id);
|
||||
assert.equal(before.items.find((i) => i.itemId === 15).quantity, 1);
|
||||
|
||||
useConsumable(id, 15);
|
||||
|
||||
const after = listInventory(id);
|
||||
const potion = after.items.find((i) => i.itemId === 15);
|
||||
assert.equal(potion, undefined, 'consumable row should be removed when quantity hits 0');
|
||||
});
|
||||
|
||||
it('caps heal effect at maxHp', () => {
|
||||
const id = makeHero({ level: 1, str: 8, agi: 4, int: 2, vit: 8 });
|
||||
grantItem(id, 14, 5); // Minor Healing Potion (heal:50)
|
||||
|
||||
// Set HP already at max
|
||||
const before = listInventory(id);
|
||||
const maxHp = before.derived.maxHp;
|
||||
db.prepare('UPDATE characters SET hp_current = ? WHERE id = ?').run(maxHp, id);
|
||||
|
||||
useConsumable(id, 14);
|
||||
|
||||
const after = listInventory(id);
|
||||
const hp = db.prepare('SELECT hp_current FROM characters WHERE id = ?').get(id).hp_current;
|
||||
assert.equal(hp, maxHp, 'HP should not exceed maxHp');
|
||||
// Quantity should decrease
|
||||
assert.equal(after.items.find((i) => i.itemId === 14).quantity, 4);
|
||||
});
|
||||
|
||||
it('caps energy effect at ENERGY_MAX (100)', () => {
|
||||
const id = makeHero({ level: 1, str: 8, agi: 4, int: 2, vit: 8 });
|
||||
grantItem(id, 16, 5); // Energy Tonic (energy:25)
|
||||
|
||||
// Set energy to 90
|
||||
db.prepare('UPDATE characters SET energy = 90 WHERE id = ?').run(id);
|
||||
|
||||
useConsumable(id, 16);
|
||||
|
||||
const after = listInventory(id);
|
||||
const energy = db.prepare('SELECT energy FROM characters WHERE id = ?').get(id).energy;
|
||||
assert.equal(energy, 100, 'Energy should not exceed 100');
|
||||
// Quantity should decrease
|
||||
assert.equal(after.items.find((i) => i.itemId === 16).quantity, 4);
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user