<?php

declare(strict_types=1);

namespace apexl\Io\modules\menu\interfaces;

use apexl\Io\modules\user\entities\userEntity;

/**
 * Phase 5 (quiet mode) seam — a filter that narrows the already-built,
 * already permission-checked top-level menu item list before it's
 * returned to the caller.
 *
 * `menuEntity::getAllItemsAsMenu()` runs every hook-collected
 * NavFilterInterface (via `menu.collectNavFilters`, see NavFilterRegistry)
 * in registration order, each seeing the previous filter's output. This
 * lets a downstream package (e.g. `apexl/io-page-layouts`'s workspace
 * nav-allowlist) narrow the visible top-level groups WITHOUT io-menu
 * knowing anything about workspaces, and without the provider package
 * needing to fork or wrap menu-building itself.
 *
 * Implementations should be defensive: a broken/empty filter result is
 * indistinguishable from "user has access to nothing", so callers doing
 * something workspace-shaped should fail OPEN (return $menuItems
 * unchanged) rather than closed when their own data is missing/invalid.
 */
interface NavFilterInterface
{
    /**
     * @param array<int, object> $menuItems Top-level menu item objects
     *        (menuItem|stdClass) as produced by menuEntity::checkAccess() —
     *        each carries at least ->name (the dot-normalised routeName)
     *        and, for parent groups, ->links (already permission-filtered
     *        children). Return the same shape, narrowed and/or reordered.
     * @param userEntity $user The user the menu is being built for.
     * @param string $menuName The (unmodified-case) name of the menu entity
     *        being resolved — e.g. 'navigation' for the primary sidebar,
     *        'Account Menu' for the profile dropdown. Filters that only
     *        apply to one menu MUST check this themselves; io-menu applies
     *        every registered filter to every menu.
     * @return array<int, object>
     */
    public function filter(array $menuItems, userEntity $user, string $menuName): array;
}
