import { readFileSync } from "fs";
import { join } from "path";
/**
* Tests to validate fixes for critical code policy violations identified by code-reviewer:
* 1. CRITICAL - Unrequested Fallback Code in WebServerManager
* 2. HIGH - Legacy Method in SSHConnectionManager
* 3. MEDIUM - Command Source Validation should be at beginning
* 4. MEDIUM - Input Validation for CommandId
* 5. MEDIUM - Error Response Format
*/
describe("Code Policy Violation Detection", () => {
describe("CRITICAL - Fallback Code Must Be Removed", () => {
it("should fail because fallback code still exists in web-server-manager.ts lines 230-235", () => {
// Read the web-server-manager.ts source file
const webServerPath = join(__dirname, "../src/web-server-manager.ts");
const webServerContent = readFileSync(webServerPath, "utf-8");
// Check for the specific fallback pattern that violates policy
const fallbackPattern = /Fallback if handler not ready yet/i;
const hasFallback = fallbackPattern.test(webServerContent);
// This test SHOULD FAIL initially because fallback code exists
expect(hasFallback).toBe(false); // Will fail until fallback is removed
});
it("should fail because term.write fallback call still exists", () => {
const webServerPath = join(__dirname, "../src/web-server-manager.ts");
const webServerContent = readFileSync(webServerPath, "utf-8");
// Check for the specific term.write fallback call
const termWriteInFallback = webServerContent.includes("term.write(data.data)");
const fallbackContext = webServerContent.includes("// Fallback if handler not ready yet");
// This test SHOULD FAIL initially because fallback term.write exists
expect(termWriteInFallback && fallbackContext).toBe(false); // Will fail until fallback is removed
});
});
describe("HIGH - Legacy Method Must Be Removed", () => {
it("should fail because legacy broadcastTerminalOutput method still exists", () => {
const sshManagerPath = join(__dirname, "../src/ssh-connection-manager.ts");
const sshManagerContent = readFileSync(sshManagerPath, "utf-8");
// Check for the specific legacy method comment and implementation
const legacyMethodPattern = /Legacy method - now just calls the live broadcast/i;
const hasLegacyMethod = legacyMethodPattern.test(sshManagerContent);
// This test SHOULD FAIL initially because legacy method exists at line 198
expect(hasLegacyMethod).toBe(false); // Will fail until legacy method is removed
});
it("should fail because broadcastTerminalOutput wrapper method exists", () => {
const sshManagerPath = join(__dirname, "../src/ssh-connection-manager.ts");
const sshManagerContent = readFileSync(sshManagerPath, "utf-8");
// Check for the method signature that's just a wrapper
const wrapperMethodExists = sshManagerContent.includes("private broadcastTerminalOutput(");
const callsLiveBroadcast = sshManagerContent.includes("this.broadcastToLiveListeners(sessionName, data, stream);");
// This test SHOULD FAIL initially because wrapper method exists
expect(wrapperMethodExists && callsLiveBroadcast).toBe(false); // Will fail until wrapper is removed
});
});
describe("MEDIUM - Command Source Validation Order", () => {
it("should fail because command source validation is not at the beginning of executeCommand", () => {
const sshManagerPath = join(__dirname, "../src/ssh-connection-manager.ts");
const sshManagerContent = readFileSync(sshManagerPath, "utf-8");
// Find the executeCommand method
const executeCommandMatch = sshManagerContent.match(/async executeCommand\([^{]+\{([^}]+(?:\{[^}]*\}[^}]*)*)\}/s);
expect(executeCommandMatch).toBeDefined();
if (executeCommandMatch) {
const methodBody = executeCommandMatch[1];
const lines = methodBody.split('\n').map(line => line.trim()).filter(line => line.length > 0);
// Find where source validation happens
const validationLineIndex = lines.findIndex(line => line.includes("validateCommandSource"));
const sessionValidationIndex = lines.findIndex(line => line.includes("getValidatedSession"));
// Validation should happen BEFORE session validation (should be first substantive action)
// This test SHOULD FAIL initially because validation happens later
expect(validationLineIndex).toBeLessThan(sessionValidationIndex); // Will fail until moved to beginning
expect(validationLineIndex).toBe(0); // Should be the very first action
}
});
});
describe("MEDIUM - CommandId Validation Missing", () => {
it("should fail because comprehensive CommandId validation does not exist", () => {
const sshManagerPath = join(__dirname, "../src/ssh-connection-manager.ts");
const sshManagerContent = readFileSync(sshManagerPath, "utf-8");
// Check for CommandId validation method
const hasCommandIdValidation = sshManagerContent.includes("validateCommandId") ||
sshManagerContent.includes("CommandId") && sshManagerContent.includes("validation");
// This test SHOULD FAIL initially because CommandId validation doesn't exist
expect(hasCommandIdValidation).toBe(true); // Will fail until validation is implemented
});
});
describe("MEDIUM - Standardized Error Response Missing", () => {
it("should fail because ErrorResponse interface does not exist in types.ts", () => {
const typesPath = join(__dirname, "../src/types.ts");
const typesContent = readFileSync(typesPath, "utf-8");
// Check for ErrorResponse interface
const hasErrorResponseInterface = typesContent.includes("interface ErrorResponse") ||
typesContent.includes("type ErrorResponse");
// This test SHOULD FAIL initially because ErrorResponse interface doesn't exist
expect(hasErrorResponseInterface).toBe(true); // Will fail until interface is added
});
it("should fail because standardized error handling is not implemented", () => {
const sshManagerPath = join(__dirname, "../src/ssh-connection-manager.ts");
const sshManagerContent = readFileSync(sshManagerPath, "utf-8");
// Check for consistent error response creation
const hasStandardizedErrors = sshManagerContent.includes("createErrorResponse") ||
sshManagerContent.includes("ErrorResponse");
// This test SHOULD FAIL initially because standardized error handling doesn't exist
expect(hasStandardizedErrors).toBe(true); // Will fail until standardized errors are implemented
});
});
});