import { Role, RoleName } from "./policy.js";

/**
 * A unique identifier for a user.
 */
export type UserId = string & { __brand: "UserId" };

/**
 * The source of a user.
 */
export enum UserSource {
    /**
     * The user is an Archon administrator.
     */
    ARCHON = "archon",
    /**
     * The user is a member of your organization.
     */
    YOUR_ORG = "your_org",
    /**
     * The user is a client of your organization (i.e. a government agency, business, or individual).
     */
    CLIENT = "client",
    /**
     * The user is a service account.
     */
    SERVICE = "service"
}

export enum SessionType {
    USER = "USER",
    SERVICE = "SERVICE"
}

/**
 * A unique identifier for a session.
 */
export type SessionId = number & { __brand: "SessionId" };

/**
 * A session for a user.
 */
export interface Session {
    /**
     * The session ID
     */
    id: SessionId;
    /**
     * The user 
     */
    user: User;
    /**
     * The role the user is acting as.
     */
    role: Role;
    /**
     * The type of session. Either user or service.
     */
    type: SessionType;
}

/**
 * A unique identifier for a session change request.
 */
export type RoleChangeRequestId = number & { __brand: "RoleChangeRequestId" };

/**
 * A request to change the role of a session.
 */
export interface RoleChangeRequest {
    /**
     * The ID of the request.
     */
    id: RoleChangeRequestId;

    /**
     * A unique identifier for the request. Used when the user reauthenticates.
     */
    nonce: string;

    /**
     * The id of the user 
     */
    userId: UserId;

    /**
     * The name of the new role to switch to.
     */
    newRoleName: RoleName;

    /**
     * The URL to direct the user to in order to authenticate.
     */
    authUrl: string;

    /**
     * The URL that the user will be redirected to after the request is processed.
     */
    callbackUrl: string;

    /**
     * The reason for the role switch request.
     */
    reason?: string;
}

/**
 * Represents a user in the system.
 */
export interface User {
    /**
     * Unique identifier for the user.
     */
    id: UserId;

    /**
     * The username of the user.
     */
    username: string;

    /**
     * The source from which the user was created.
     */
    userSource: UserSource;

    /**
     * The date and time when the user was created.
     */
    createdAt: Date;
}