@kbediako/codex-orchestrator 0.1.4 → 0.1.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -826,11 +826,47 @@ async function runJsonRpcServer(handler, options = {}) {
826
826
  const body = buffer.slice(0, expectedLength);
827
827
  buffer = buffer.slice(expectedLength);
828
828
  expectedLength = null;
829
- await handleMessage(body.toString('utf8'));
829
+ await handleMessage(body.toString('utf8'), 'framed');
830
830
  continue;
831
831
  }
832
832
  const headerEnd = buffer.indexOf('\r\n\r\n');
833
833
  if (headerEnd === -1) {
834
+ const newlineIndex = buffer.indexOf('\n');
835
+ if (newlineIndex !== -1) {
836
+ const lineBuffer = buffer.slice(0, newlineIndex);
837
+ const line = lineBuffer.toString('utf8').trim();
838
+ buffer = buffer.slice(newlineIndex + 1);
839
+ if (!line) {
840
+ continue;
841
+ }
842
+ const normalizedLine = line.trimStart();
843
+ const looksLikeHeaderLine = /^[A-Za-z0-9-]+:/.test(normalizedLine);
844
+ const looksLikeJson = normalizedLine.startsWith('{') || normalizedLine.startsWith('[');
845
+ const isContentLength = normalizedLine.toLowerCase().startsWith('content-length:');
846
+ let restoredHeader = false;
847
+ if (!looksLikeJson && looksLikeHeaderLine) {
848
+ // Fall through to header-size checks for partial Content-Length frames (and other header lines).
849
+ buffer = Buffer.concat([Buffer.from(lineBuffer), Buffer.from('\n'), buffer]);
850
+ restoredHeader = true;
851
+ }
852
+ else if (!isContentLength) {
853
+ const lineBytes = Buffer.byteLength(line, 'utf8');
854
+ if (lineBytes > MAX_MCP_MESSAGE_BYTES) {
855
+ handleProtocolViolation(`Rejecting MCP payload (${lineBytes} bytes) larger than ${MAX_MCP_MESSAGE_BYTES}`);
856
+ return;
857
+ }
858
+ await handleMessage(line, 'jsonl');
859
+ continue;
860
+ }
861
+ if (!restoredHeader && isContentLength) {
862
+ // Fall through to header-size checks for partial Content-Length frames.
863
+ buffer = Buffer.concat([Buffer.from(lineBuffer), Buffer.from('\n'), buffer]);
864
+ }
865
+ }
866
+ else if (buffer.length > MAX_MCP_MESSAGE_BYTES) {
867
+ handleProtocolViolation(`Rejecting MCP payload (${buffer.length} bytes) larger than ${MAX_MCP_MESSAGE_BYTES}`);
868
+ return;
869
+ }
834
870
  if (buffer.length > MAX_MCP_HEADER_BYTES) {
835
871
  const overflow = buffer.slice(MAX_MCP_HEADER_BYTES);
836
872
  const allowedPrefix = MCP_HEADER_DELIMITER_BUFFER.subarray(0, overflow.length);
@@ -851,6 +887,19 @@ async function runJsonRpcServer(handler, options = {}) {
851
887
  return;
852
888
  }
853
889
  if (parsed.length === null) {
890
+ const lines = header.split(/\r?\n/).map((line) => line.trim()).filter(Boolean);
891
+ if (lines.length === 0) {
892
+ buffer = buffer.slice(headerEnd + 4);
893
+ continue;
894
+ }
895
+ const allJsonLike = lines.every((line) => line.startsWith('{') || line.startsWith('['));
896
+ if (allJsonLike) {
897
+ buffer = buffer.slice(headerEnd + 4);
898
+ for (const line of lines) {
899
+ await handleMessage(line, 'jsonl');
900
+ }
901
+ continue;
902
+ }
854
903
  handleProtocolViolation('Missing Content-Length header in MCP message');
855
904
  return;
856
905
  }
@@ -867,7 +916,7 @@ async function runJsonRpcServer(handler, options = {}) {
867
916
  buffer = buffer.slice(headerEnd + 4);
868
917
  }
869
918
  }
870
- async function handleMessage(raw) {
919
+ async function handleMessage(raw, format) {
871
920
  let request;
872
921
  try {
873
922
  request = JSON.parse(raw);
@@ -883,7 +932,7 @@ async function runJsonRpcServer(handler, options = {}) {
883
932
  try {
884
933
  const result = await handler(request);
885
934
  if (id !== null && typeof id !== 'undefined') {
886
- sendResponse({ jsonrpc: '2.0', id, result }, output);
935
+ sendResponse({ jsonrpc: '2.0', id, result }, output, format);
887
936
  }
888
937
  }
889
938
  catch (error) {
@@ -892,7 +941,7 @@ async function runJsonRpcServer(handler, options = {}) {
892
941
  jsonrpc: '2.0',
893
942
  id,
894
943
  error: { code: -32603, message: error?.message ?? String(error) }
895
- }, output);
944
+ }, output, format);
896
945
  }
897
946
  }
898
947
  }
@@ -920,10 +969,15 @@ function parseContentLengthHeader(header) {
920
969
  }
921
970
  return { length: contentLength };
922
971
  }
923
- function sendResponse(response, output = process.stdout) {
924
- const payload = Buffer.from(JSON.stringify(response), 'utf8');
925
- const header = Buffer.from(`Content-Length: ${payload.length}\r\n\r\n`, 'utf8');
926
- output.write(Buffer.concat([header, payload]));
972
+ function sendResponse(response, output = process.stdout, format = 'framed') {
973
+ const payload = JSON.stringify(response);
974
+ if (format === 'jsonl') {
975
+ output.write(`${payload}\n`);
976
+ return;
977
+ }
978
+ const buffer = Buffer.from(payload, 'utf8');
979
+ const header = Buffer.from(`Content-Length: ${buffer.length}\r\n\r\n`, 'utf8');
980
+ output.write(Buffer.concat([header, buffer]));
927
981
  }
928
982
  function safeJsonParse(text) {
929
983
  try {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kbediako/codex-orchestrator",
3
- "version": "0.1.4",
3
+ "version": "0.1.6",
4
4
  "license": "SEE LICENSE IN LICENSE",
5
5
  "type": "module",
6
6
  "bin": {