backups: show that a check happened, not just that a change did
Some checks failed
CI / backend (push) Failing after 7s
CI / naming (push) Successful in 2s
CI / frontend (push) Successful in 9s
CI / migrations-mysql (push) Failing after 7s

lastseenat already recorded it and the API already returned it; nothing
displayed it, so from the UI a healthy machine still looked abandoned - one
revision from last spring and no sign anything had looked at it since.

The history page gains a Last verified column beside Captured, and the asset
panel a Verified field. Only the CURRENT revision carries one: an older
revision was superseded, so saying it was verified today would be false - what
was verified is the configuration the PC holds now.

A current revision with no check yet says "not yet checked" rather than showing
a blank or borrowing the captured date. That state is real and temporary: the
column is new, so every chain reports it until its PC next posts.
This commit is contained in:
cproudlock
2026-08-11 15:00:25 -04:00
parent e0e4cce8bd
commit 294ddbb38e
4 changed files with 51 additions and 0 deletions

View File

@@ -960,3 +960,24 @@ def test_the_threshold_is_a_setting_and_zero_disables_the_card(bk_app, bk_plugin
{'value': '0'})
_db.session.commit()
assert stalechains() == []
def test_the_history_reports_when_a_config_was_last_verified(bk_app, bk_plugin):
"""A machine checked daily for a year still shows one revision, because an
unchanged config writes none. The API has to say the check happened or that
machine reads as abandoned."""
from plugins.backups.models import BackupRevision
with bk_app.app_context():
result = bk_plugin.apply_collector_payload(_payload())
revision = _db.session.get(BackupRevision, result['backuprevisionid'])
data = revision.to_dict()
assert data['lastseenat'] is not None
assert data['lastseenat'].endswith('Z')
def test_the_panel_shows_verified_beside_captured(bk_app, bk_plugin):
with bk_app.app_context():
panels = bk_plugin.get_asset_panels()
listpanel = next(p for p in panels if p.get('render') == 'list')
labels = [m['label'] for m in listpanel['map']['meta']]
assert 'Captured' in labels and 'Verified' in labels