const STORAGE_KEY = 'sprint-workspace-hints'

interface PerProductHint {
  lastActiveSprintId?: string | null
}

interface PerSprintHint {
  lastActiveStoryId?: string | null
  lastActiveTaskId?: string | null
}

export interface SprintWorkspaceHints {
  lastActiveProductId: string | null
  perProduct: Record<string, PerProductHint>
  perSprint: Record<string, PerSprintHint>
}

const EMPTY_HINTS: SprintWorkspaceHints = {
  lastActiveProductId: null,
  perProduct: {},
  perSprint: {},
}

function safeStorage(): Storage | null {
  if (typeof globalThis === 'undefined') return null
  try {
    const ls = (globalThis as { localStorage?: Storage }).localStorage
    return ls ?? null
  } catch {
    return null
  }
}

export function readHints(): SprintWorkspaceHints {
  const storage = safeStorage()
  if (!storage) return { ...EMPTY_HINTS, perProduct: {}, perSprint: {} }
  try {
    const raw = storage.getItem(STORAGE_KEY)
    if (!raw) return { ...EMPTY_HINTS, perProduct: {}, perSprint: {} }
    const parsed = JSON.parse(raw) as Partial<SprintWorkspaceHints> | null
    if (!parsed || typeof parsed !== 'object') {
      return { ...EMPTY_HINTS, perProduct: {}, perSprint: {} }
    }
    return {
      lastActiveProductId: parsed.lastActiveProductId ?? null,
      perProduct:
        parsed.perProduct && typeof parsed.perProduct === 'object'
          ? parsed.perProduct
          : {},
      perSprint:
        parsed.perSprint && typeof parsed.perSprint === 'object'
          ? parsed.perSprint
          : {},
    }
  } catch {
    return { ...EMPTY_HINTS, perProduct: {}, perSprint: {} }
  }
}

function writeHints(hints: SprintWorkspaceHints): void {
  const storage = safeStorage()
  if (!storage) return
  try {
    storage.setItem(STORAGE_KEY, JSON.stringify(hints))
  } catch {
    // ignore quota or serialization errors
  }
}

export function writeProductHint(productId: string | null): void {
  const hints = readHints()
  hints.lastActiveProductId = productId
  writeHints(hints)
}

function ensurePerProduct(
  hints: SprintWorkspaceHints,
  productId: string,
): PerProductHint {
  if (!hints.perProduct[productId]) {
    hints.perProduct[productId] = {}
  }
  return hints.perProduct[productId]
}

function ensurePerSprint(
  hints: SprintWorkspaceHints,
  sprintId: string,
): PerSprintHint {
  if (!hints.perSprint[sprintId]) {
    hints.perSprint[sprintId] = {}
  }
  return hints.perSprint[sprintId]
}

export function writeSprintHint(productId: string, sprintId: string | null): void {
  const hints = readHints()
  const entry = ensurePerProduct(hints, productId)
  entry.lastActiveSprintId = sprintId
  writeHints(hints)
}

export function writeStoryHint(sprintId: string, storyId: string | null): void {
  const hints = readHints()
  const entry = ensurePerSprint(hints, sprintId)
  entry.lastActiveStoryId = storyId
  if (storyId === null) {
    entry.lastActiveTaskId = null
  }
  writeHints(hints)
}

export function writeTaskHint(sprintId: string, taskId: string | null): void {
  const hints = readHints()
  const entry = ensurePerSprint(hints, sprintId)
  entry.lastActiveTaskId = taskId
  writeHints(hints)
}

export function clearHints(): void {
  const storage = safeStorage()
  if (!storage) return
  try {
    storage.removeItem(STORAGE_KEY)
  } catch {
    // ignore
  }
}
