local EnsureApiRegistry = rawget(_G, "LIDCOUNCIL_EnsureApiRegistry")
local API, INTERNAL_API
if type(EnsureApiRegistry) == "function" then
  API, INTERNAL_API = EnsureApiRegistry()
else
  API = rawget(_G, "LIDCOUNCIL_API")
  if type(API) ~= "table" then
    API = {}
    _G.LIDCOUNCIL_API = API
  end
  if type(API.__internal) ~= "table" then
    API.__internal = {}
  end
  INTERNAL_API = API.__internal
end

INTERNAL_API.LIDCOUNCIL_CreateOutboundPressureRules_Impl = function(deps)
  deps = type(deps) == "table" and deps or {}
  local TrimText = type(deps.TrimText) == "function" and deps.TrimText or function(value)
    return tostring(value or "")
  end

  local function BuildOutboundOpcodePressure(opcodes, thresholds)
    thresholds = type(thresholds) == "table" and thresholds or {}
    local queuedThreshold = math.max(1, tonumber(thresholds.queuedNow) or 12)
    local throttleThreshold = math.max(1, tonumber(thresholds.throttled) or 3)
    local failureThreshold = math.max(1, tonumber(thresholds.failed) or 2)
    local byteThreshold = math.max(1, tonumber(thresholds.bytesSent) or 24576)
    local maxItems = math.max(1, tonumber(thresholds.maxItems) or 3)
    local severityRank = { critical = 3, warning = 2, watch = 1 }
    local pressure = {}
    for _, opcode in ipairs(type(opcodes) == "table" and opcodes or {}) do
      if type(opcode) == "table" then
        local kind = TrimText(opcode.kind)
        local queuedNow = math.max(0, tonumber(opcode.queuedNow) or 0)
        local throttled = math.max(0, tonumber(opcode.throttled) or 0)
        local failed = math.max(0, tonumber(opcode.failed) or 0)
        local payloadRejected = math.max(0, tonumber(opcode.payloadRejected) or 0)
        local bytesSent = math.max(0, tonumber(opcode.bytesSent) or 0)
        local reasons = {}
        local severity = ""
        if payloadRejected > 0 then
          severity = "critical"
          reasons[#reasons + 1] = tostring(payloadRejected) .. " payload block" .. (payloadRejected == 1 and "" or "s")
        end
        if failed >= failureThreshold then
          severity = "critical"
          reasons[#reasons + 1] = tostring(failed) .. " send failures"
        end
        if queuedNow >= queuedThreshold then
          if severity == "" then
            severity = "warning"
          end
          reasons[#reasons + 1] = tostring(queuedNow) .. " queued"
        end
        if throttled >= throttleThreshold then
          if severity == "" then
            severity = "warning"
          end
          reasons[#reasons + 1] = tostring(throttled) .. " throttles"
        end
        if bytesSent >= byteThreshold then
          if severity == "" then
            severity = "watch"
          end
          reasons[#reasons + 1] = tostring(bytesSent) .. " B sent"
        end
        if kind ~= "" and severity ~= "" then
          pressure[#pressure + 1] = {
            kind = kind,
            severity = severity,
            queuedNow = queuedNow,
            throttled = throttled,
            failed = failed,
            payloadRejected = payloadRejected,
            bytesSent = bytesSent,
            reasons = reasons,
          }
        end
      end
    end
    table.sort(pressure, function(left, right)
      local leftRank = severityRank[left.severity] or 0
      local rightRank = severityRank[right.severity] or 0
      if leftRank ~= rightRank then
        return leftRank > rightRank
      end
      if left.queuedNow ~= right.queuedNow then
        return left.queuedNow > right.queuedNow
      end
      if left.bytesSent ~= right.bytesSent then
        return left.bytesSent > right.bytesSent
      end
      return string.lower(left.kind) < string.lower(right.kind)
    end)
    while #pressure > maxItems do
      table.remove(pressure)
    end
    return pressure
  end

  local function BuildOutboundLanePressure(laneTelemetry, thresholds)
    laneTelemetry = type(laneTelemetry) == "table" and laneTelemetry or {}
    thresholds = type(thresholds) == "table" and thresholds or {}
    local maxItems = math.max(1, tonumber(thresholds.maxItems) or 3)
    local severityRank = { critical = 3, warning = 2, watch = 1 }
    local pressure = {}
    for _, lane in ipairs({ "live", "bootstrap", "archive", "stats", "control" }) do
      local entry = type(laneTelemetry[lane]) == "table" and laneTelemetry[lane] or {}
      local laneThresholds = type(thresholds[lane]) == "table" and thresholds[lane] or {}
      local queuedThreshold = math.max(1, tonumber(laneThresholds.queuedNow) or 12)
      local throttleThreshold = math.max(1, tonumber(laneThresholds.throttled) or 3)
      local failureThreshold = math.max(1, tonumber(laneThresholds.failed) or 2)
      local byteThreshold = math.max(1, tonumber(laneThresholds.bytesSent) or 32768)
      local queuedNow = math.max(0, tonumber(entry.queuedNow) or 0)
      local throttled = math.max(0, tonumber(entry.throttled) or 0)
      local failed = math.max(0, tonumber(entry.failed) or 0)
      local bytesSent = math.max(0, tonumber(entry.bytesSent) or 0)
      local reasons = {}
      local severity = ""
      if failed >= failureThreshold then
        severity = "critical"
        reasons[#reasons + 1] = tostring(failed) .. " send failures"
      end
      if queuedNow >= queuedThreshold then
        if severity == "" then
          severity = "warning"
        end
        reasons[#reasons + 1] = tostring(queuedNow) .. " queued"
      end
      if throttled >= throttleThreshold then
        if severity == "" then
          severity = "warning"
        end
        reasons[#reasons + 1] = tostring(throttled) .. " throttles"
      end
      if bytesSent >= byteThreshold then
        if severity == "" then
          severity = "watch"
        end
        reasons[#reasons + 1] = tostring(bytesSent) .. " B sent"
      end
      if severity ~= "" then
        pressure[#pressure + 1] = {
          lane = lane,
          severity = severity,
          queuedNow = queuedNow,
          throttled = throttled,
          failed = failed,
          bytesSent = bytesSent,
          reasons = reasons,
        }
      end
    end
    table.sort(pressure, function(left, right)
      local leftRank = severityRank[left.severity] or 0
      local rightRank = severityRank[right.severity] or 0
      if leftRank ~= rightRank then
        return leftRank > rightRank
      end
      if left.queuedNow ~= right.queuedNow then
        return left.queuedNow > right.queuedNow
      end
      if left.bytesSent ~= right.bytesSent then
        return left.bytesSent > right.bytesSent
      end
      return left.lane < right.lane
    end)
    while #pressure > maxItems do
      table.remove(pressure)
    end
    return pressure
  end

  local function ShouldYieldArchiveForLanePressure(lanePressure)
    for _, pressure in ipairs(type(lanePressure) == "table" and lanePressure or {}) do
      if type(pressure) == "table" then
        local lane = TrimText(pressure.lane)
        local severity = TrimText(pressure.severity)
        if (lane == "live" or lane == "control") and (severity == "critical" or severity == "warning") then
          return true, lane, severity
        end
      end
    end
    return false, "", ""
  end

  return {
    BuildOutboundOpcodePressure = BuildOutboundOpcodePressure,
    BuildOutboundLanePressure = BuildOutboundLanePressure,
    ShouldYieldArchiveForLanePressure = ShouldYieldArchiveForLanePressure,
  }
end
