1
0
Fork 0
mirror of https://github.com/retspen/webvirtcloud synced 2026-11-10 12:16:49 +00:00

fix(virtsecrets): a secret's value never reaches the page

The edit dialog of a secret was filled with its current value, so every
readable secret's value was in the secrets page's HTML. A private
secret, or one with no value yet, cannot be read: its field held the
text "None", which is valid base64, and saving the dialog unchanged set
the secret to the three bytes it decodes to. The dialog now only writes
a new value: the field starts empty, is a password field and is
required. The page no longer reads secret values, and get_secret_value,
used only for that, is gone.
This commit is contained in:
catborise 2026-10-20 21:50:41 +03:00
parent ce7c772aae
commit 4ece22230e
5 changed files with 35 additions and 16 deletions

View file

@ -35,12 +35,9 @@ class SecretValueTests(SimpleTestCase):
secret = get.return_value.secretLookupByUUIDString.return_value
return conn, secret
def test_the_shown_value_written_back_keeps_the_secret(self):
def test_a_base64_value_is_stored_as_its_bytes(self):
conn, secret = self.secrets()
secret.value.return_value = b"pw\x00\xff"
shown = conn.get_secret_value("uuid")
self.assertEqual(shown, "cHcA/w==") # base64 text, what the edit dialog shows
conn.set_secret_value("uuid", shown)
conn.set_secret_value("uuid", "cHcA/w==")
secret.setValue.assert_called_once_with(b"pw\x00\xff")
def test_a_value_that_is_not_base64_is_refused(self):

View file

@ -0,0 +1,31 @@
"""The secrets page never holds a secret's value: the edit dialog only
writes a new one."""
from unittest.mock import patch
from computes.models import Compute
from django.contrib.auth import get_user_model
from django.test import TestCase
from django.urls import reverse
from libvirt import VIR_SECRET_USAGE_TYPE_CEPH
from lxml import html
class SecretsPageTests(TestCase):
def test_the_page_holds_no_secret_value(self):
compute = Compute.objects.create(name="secrets-page", hostname="localhost", login="", password="", type=4)
self.client.force_login(get_user_model().objects.create_superuser("page", "page@example.com", "pw"))
with patch("virtsecrets.views.wvmSecrets") as conn:
conn.return_value.get_secrets.return_value = ["0e5b1f0a-8f3e-4c1a-9d2b-5c6d7e8f9a0b"]
secret = conn.return_value.get_secret.return_value
secret.usageID.return_value = "client.libvirt"
secret.UUIDString.return_value = "0e5b1f0a-8f3e-4c1a-9d2b-5c6d7e8f9a0b"
secret.usageType.return_value = VIR_SECRET_USAGE_TYPE_CEPH
secret.value.return_value = b"cephx key"
conn.return_value.get_secret_value.return_value = "Y2VwaHgga2V5"
response = self.client.get(reverse("virtsecrets", args=[compute.id]))
self.assertEqual(response.status_code, 200)
self.assertFalse(b"Y2VwaHgga2V5" in response.content, "the secret's value is on the page")
field = html.fromstring(response.content).get_element_by_id("secret_value_0e5b1f0a-8f3e-4c1a-9d2b-5c6d7e8f9a0b")
self.assertIsNone(field.get("value"))
self.assertEqual(field.get("type"), "password")