export type OpaqueId<Name extends string> = string & { readonly __awpId: Name };

export type ProjectId = OpaqueId<"ProjectId">;
export type ProjectVisionVersionId = OpaqueId<"ProjectVisionVersionId">;
export type GoalId = OpaqueId<"GoalId">;
export type PlanId = OpaqueId<"PlanId">;
export type PlanRevisionId = OpaqueId<"PlanRevisionId">;
export type PlanningSessionId = OpaqueId<"PlanningSessionId">;
export type PlanningTurnId = OpaqueId<"PlanningTurnId">;
export type TaskId = OpaqueId<"TaskId">;
export type FactoryRunId = OpaqueId<"FactoryRunId">;
export type AgentRunId = OpaqueId<"AgentRunId">;
export type AttemptId = OpaqueId<"AttemptId">;
export type WorkspaceId = OpaqueId<"WorkspaceId">;
export type ChangeSetId = OpaqueId<"ChangeSetId">;
export type ReviewId = OpaqueId<"ReviewId">;
export type VerificationEvidenceId = OpaqueId<"VerificationEvidenceId">;
export type ReviewFindingId = OpaqueId<"ReviewFindingId">;
export type DecisionId = OpaqueId<"DecisionId">;
export type ApprovalId = OpaqueId<"ApprovalId">;
export type ConnectionId = OpaqueId<"ConnectionId">;
export type CredentialReferenceId = OpaqueId<"CredentialReferenceId">;
export type RepositoryId = OpaqueId<"RepositoryId">;
export type PrincipalId = OpaqueId<"PrincipalId">;
export type SessionId = OpaqueId<"SessionId">;
export type ProviderId = OpaqueId<"ProviderId">;
export type AccountId = OpaqueId<"AccountId">;
export type EventId = OpaqueId<"EventId">;
export type AuditRecordId = OpaqueId<"AuditRecordId">;
export type OutboxMessageId = OpaqueId<"OutboxMessageId">;
export type CorrelationId = OpaqueId<"CorrelationId">;
export type CausationId = OpaqueId<"CausationId">;
export type OperationId = OpaqueId<"OperationId">;
export type ClusterId = OpaqueId<"ClusterId">;
export type MachineId = OpaqueId<"MachineId">;
export type MachineCapabilityId = OpaqueId<"MachineCapabilityId">;
export type MachineEnrollmentId = OpaqueId<"MachineEnrollmentId">;

export type AwpId =
  | ProjectId
  | ProjectVisionVersionId
  | GoalId
  | PlanId
  | PlanRevisionId
  | PlanningSessionId
  | PlanningTurnId
  | TaskId
  | FactoryRunId
  | AgentRunId
  | AttemptId
  | WorkspaceId
  | ChangeSetId
  | ReviewId
  | VerificationEvidenceId
  | ReviewFindingId
  | DecisionId
  | ApprovalId
  | ConnectionId
  | CredentialReferenceId
  | RepositoryId
  | PrincipalId
  | SessionId
  | ProviderId
  | AccountId
  | EventId
  | AuditRecordId
  | OutboxMessageId
  | CorrelationId
  | CausationId
  | OperationId
  | ClusterId
  | MachineId
  | MachineCapabilityId
  | MachineEnrollmentId;

export function unsafeOpaqueId<T extends AwpId>(value: string): T {
  if (value.length === 0) throw new Error("AWP IDs must not be empty");
  return value as T;
}
