feat(core): programs' threads, and FILIUS' echo server and generic client after Java, measured against Java
Programs run as generators that yield what they wait for (threads.ts); the engine resumes them after every event. TCP connect, send, receive, accept and name resolution exist as such steps; the blocking calls wrap them. EchoRun records eight stories in Java FILIUS, frames, tables and each program's window lines; echoJava.test.ts plays them card by card. Not taken from Java: a connection without a route hangs for ever; a server switched off leaves its connections' last FIN unanswered. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -4,9 +4,11 @@
|
||||
//
|
||||
// Only the cables count: a host's SSID connects nothing at run time, as in
|
||||
// Java (Swift joins a wireless host to the switch of its SSID; not taken).
|
||||
// A DNS server runs only when it is switched on (Java: DNSServer.aktiv).
|
||||
// A DNS server runs only when it is switched on (Java: DNSServer.aktiv); an
|
||||
// echo server is there either way, switched on or off (it can be switched at
|
||||
// run time).
|
||||
|
||||
import { portSnapshot, topologySnapshot, type DnsServerConfiguration, type Id, type TopologySnapshot } from '@mdg-filius/core';
|
||||
import { portSnapshot, topologySnapshot, type DnsServerConfiguration, type EchoServerSnapshot, type Id, type TopologySnapshot } from '@mdg-filius/core';
|
||||
import type { ImportedProject } from './importProject.js';
|
||||
|
||||
export function projectSnapshot(project: ImportedProject): TopologySnapshot {
|
||||
@@ -14,6 +16,10 @@ export function projectSnapshot(project: ImportedProject): TopologySnapshot {
|
||||
for (const [nodeId, configuration] of project.dnsServerConfigurations) {
|
||||
if (project.activePrograms.get(nodeId)?.has('dnsServer') === true) dnsServers.set(nodeId, configuration);
|
||||
}
|
||||
const echoServers = new Map<Id, EchoServerSnapshot>();
|
||||
for (const [nodeId, configuration] of project.echoServerConfigurations) {
|
||||
echoServers.set(nodeId, { ...configuration, isActive: project.activePrograms.get(nodeId)?.has('echoServer') === true });
|
||||
}
|
||||
return topologySnapshot({
|
||||
nodes: project.graph.nodes.map((node) => ({
|
||||
id: node.id,
|
||||
@@ -32,5 +38,7 @@ export function projectSnapshot(project: ImportedProject): TopologySnapshot {
|
||||
portForwardingRowsByNodeId: project.portForwardingRowsByNodeId,
|
||||
switchConfigurationsByNodeId: project.switchConfigurations,
|
||||
ipForwardingByNodeId: project.ipForwardingByNodeId,
|
||||
echoServersByNodeId: echoServers,
|
||||
simpleClientsByNodeId: project.simpleClientConfigurations,
|
||||
});
|
||||
}
|
||||
|
||||
@@ -726,6 +726,29 @@ describe('importProject rules', () => {
|
||||
expect([...projectSnapshot(project).dnsServerConfigurationsByNodeId.keys()]).toEqual([on]);
|
||||
});
|
||||
|
||||
it('runs every echo server, switched on or off, and every generic client (projectSnapshot)', () => {
|
||||
const source = flsNode('Rechner').source;
|
||||
const echoServer = (isActive: boolean, port: number): FlsApplication => ({ key: 'echo', javaClass: 'filius.software.clientserver.ServerBaustein', source, isActive, port });
|
||||
const client: FlsApplication = { key: 'client', javaClass: 'filius.software.clientserver.ClientBaustein', source, targetAddress: '10.0.0.1', targetPort: 7 };
|
||||
const project = importProject(
|
||||
topology({
|
||||
nodes: [
|
||||
flsNode('Rechner', { interfaces: [nic('10.0.0.1')], system: { applications: [echoServer(true, 55555)] } }),
|
||||
flsNode('Rechner', { interfaces: [nic('10.0.0.2')], system: { applications: [echoServer(false, 7), client] } }),
|
||||
],
|
||||
}),
|
||||
counter(),
|
||||
);
|
||||
const [on, off] = project.graph.nodes.map((node) => node.id);
|
||||
const snapshot = projectSnapshot(project);
|
||||
|
||||
expect([...snapshot.echoServersByNodeId]).toEqual([
|
||||
[on, { port: 55555, isActive: true }],
|
||||
[off, { port: 7, isActive: false }],
|
||||
]);
|
||||
expect([...snapshot.simpleClientsByNodeId]).toEqual([[off, { targetAddress: '10.0.0.1', targetPort: 7 }]]);
|
||||
});
|
||||
|
||||
it("keeps a node's IP forwarding where it differs from its kind's: a host that forwards, a router that does not", () => {
|
||||
const system = (ipForwardingEnabled: boolean) => ({ manualRoutes: [], ipForwardingEnabled });
|
||||
const project = importProject(
|
||||
|
||||
Reference in New Issue
Block a user