{"version":3,"file":"sse.cjs","names":["buffer: Uint8Array[]","data: Uint8Array[]","retry: number | null"],"sources":["../../src/utils/sse.ts"],"sourcesContent":["const CR = \"\\r\".charCodeAt(0);\nconst LF = \"\\n\".charCodeAt(0);\nconst NULL = \"\\0\".charCodeAt(0);\nconst COLON = \":\".charCodeAt(0);\nconst SPACE = \" \".charCodeAt(0);\n\nconst TRAILING_NEWLINE = [CR, LF];\n\nexport function BytesLineDecoder() {\n  let buffer: Uint8Array[] = [];\n  let trailingCr = false;\n\n  return new TransformStream<Uint8Array, Uint8Array>({\n    start() {\n      buffer = [];\n      trailingCr = false;\n    },\n\n    transform(chunk, controller) {\n      // See https://docs.python.org/3/glossary.html#term-universal-newlines\n      let text = chunk;\n\n      // Handle trailing CR from previous chunk\n      if (trailingCr) {\n        text = joinArrays([[CR], text]);\n        trailingCr = false;\n      }\n\n      // Check for trailing CR in current chunk\n      if (text.length > 0 && text.at(-1) === CR) {\n        trailingCr = true;\n        text = text.subarray(0, -1);\n      }\n\n      if (!text.length) return;\n      const trailingNewline = TRAILING_NEWLINE.includes(text.at(-1)!);\n\n      const lastIdx = text.length - 1;\n      const { lines } = text.reduce<{ lines: Uint8Array[]; from: number }>(\n        (acc, cur, idx) => {\n          if (acc.from > idx) return acc;\n\n          if (cur === CR || cur === LF) {\n            acc.lines.push(text.subarray(acc.from, idx));\n            if (cur === CR && text[idx + 1] === LF) {\n              acc.from = idx + 2;\n            } else {\n              acc.from = idx + 1;\n            }\n          }\n\n          if (idx === lastIdx && acc.from <= lastIdx) {\n            acc.lines.push(text.subarray(acc.from));\n          }\n\n          return acc;\n        },\n        { lines: [], from: 0 }\n      );\n\n      if (lines.length === 1 && !trailingNewline) {\n        buffer.push(lines[0]);\n        return;\n      }\n\n      if (buffer.length) {\n        // Include existing buffer in first line\n        buffer.push(lines[0]);\n        lines[0] = joinArrays(buffer);\n        buffer = [];\n      }\n\n      if (!trailingNewline) {\n        // If the last segment is not newline terminated,\n        // buffer it for the next chunk\n        if (lines.length) buffer = [lines.pop()!];\n      }\n\n      // Enqueue complete lines\n      for (const line of lines) {\n        controller.enqueue(line);\n      }\n    },\n\n    flush(controller) {\n      if (buffer.length) {\n        controller.enqueue(joinArrays(buffer));\n      }\n    },\n  });\n}\n\ninterface StreamPart {\n  id: string | undefined;\n  event: string;\n  data: unknown;\n}\n\nexport function SSEDecoder() {\n  let event = \"\";\n  let data: Uint8Array[] = [];\n  let lastEventId = \"\";\n  let retry: number | null = null;\n\n  const decoder = new TextDecoder();\n\n  return new TransformStream<Uint8Array, StreamPart>({\n    transform(chunk, controller) {\n      // Handle empty line case\n      if (!chunk.length) {\n        if (!event && !data.length && !lastEventId && retry == null) return;\n\n        const sse = {\n          id: lastEventId || undefined,\n          event,\n          data: data.length ? decodeArraysToJson(decoder, data) : null,\n        };\n\n        // NOTE: as per the SSE spec, do not reset lastEventId\n        event = \"\";\n        data = [];\n        retry = null;\n\n        controller.enqueue(sse);\n        return;\n      }\n\n      // Ignore comments\n      if (chunk[0] === COLON) return;\n\n      const sepIdx = chunk.indexOf(COLON);\n      if (sepIdx === -1) return;\n\n      const fieldName = decoder.decode(chunk.subarray(0, sepIdx));\n      let value = chunk.subarray(sepIdx + 1);\n      if (value[0] === SPACE) value = value.subarray(1);\n\n      if (fieldName === \"event\") {\n        event = decoder.decode(value);\n      } else if (fieldName === \"data\") {\n        data.push(value);\n      } else if (fieldName === \"id\") {\n        if (value.indexOf(NULL) === -1) lastEventId = decoder.decode(value);\n      } else if (fieldName === \"retry\") {\n        const retryNum = Number.parseInt(decoder.decode(value), 10);\n        if (!Number.isNaN(retryNum)) retry = retryNum;\n      }\n    },\n\n    flush(controller) {\n      if (event) {\n        controller.enqueue({\n          id: lastEventId || undefined,\n          event,\n          data: data.length ? decodeArraysToJson(decoder, data) : null,\n        });\n      }\n    },\n  });\n}\n\nfunction joinArrays(data: ArrayLike<number>[]) {\n  const totalLength = data.reduce((acc, curr) => acc + curr.length, 0);\n  const merged = new Uint8Array(totalLength);\n  let offset = 0;\n  for (const c of data) {\n    merged.set(c, offset);\n    offset += c.length;\n  }\n  return merged;\n}\n\nfunction decodeArraysToJson(decoder: TextDecoder, data: ArrayLike<number>[]) {\n  return JSON.parse(decoder.decode(joinArrays(data)));\n}\n"],"mappings":"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"}