Skip to content

Database Schema ​

This document describes the current PostgreSQL schema direction for Nexus.

  • Source: live database metadata via information_schema and pg_constraint
  • Generated: 2026-06-25

Schema Direction ​

Nexus is moving away from a single-schema PostgreSQL layout.

  • Current state: almost all tables live in public
  • Target state: Nexus uses multiple PostgreSQL schemas to separate platform concerns from domain modules
  • First namespace: platform

Planned PostgreSQL Schemas ​

platform ​

System objects for accounts, tenancy, sessions, preferences, token revocation, and group authorization.

  • platform.users
  • platform.user_preferences
  • platform.user_sessions
  • platform.revoked_tokens
  • platform.user_groups
  • platform.user_group_memberships
  • platform.tenants

This schema is the first extraction from public because it contains the tenancy boundary, authentication records, and authorization relationships used by every other module.

public ​

For now, the remaining module tables can continue to live in public until each domain gets its own namespace strategy.

census ​

Person and identity records used across modules.

  • census.persons
  • census.identities

education ​

Education records. These tables currently live in the census namespace while the product module is named Education.

  • census.schools
  • census.school_years
  • census.school_calendars
  • census.school_enrollments
  • census.school_employments
  • census.school_employment_assignments

assets ​

Asset catalog, inventory, assignment, circulation, and repair records.

  • assets.asset_manufacturers
  • assets.asset_types
  • assets.asset_models
  • assets.assets
  • assets.asset_assignments
  • assets.asset_circulations
  • assets.asset_repairs

locations ​

Place hierarchy and location typing records.

  • locations.location_types
  • locations.locations

Initial examples:

  • public.issues
  • public.projects
  • public.configuration_items
  • public.configuration_item_relationships

Schema Pages ​

Use these focused pages for module-level schema reference:

This page remains the schema hub and design reference. The lower snapshot section still reflects the current single-schema database state and has not yet been rewritten into namespace-qualified tables.

alembic_version ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
version_numcharacter varyingNO-YesYesNo--
  • None

asset_assignments ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
asset_idcharacterNO-NoNoYesassetsCASCADE
person_idcharacterYES-NoNoYespersonsRESTRICT
location_idcharacterYES-NoNoYeslocationsRESTRICT
start_datedateNO-NoNoNo--
end_datedateYES-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • CHECK (((((person_id IS NOT NULL))::integer + ((location_id IS NOT NULL))::integer) = 1))
  • CHECK (((end_date IS NULL) OR (end_date >= start_date)))

asset_circulations ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
asset_idcharacterNO-NoNoYesassetsCASCADE
circulation_typetextNO-NoNoNo--
person_idcharacterYES-NoNoYespersonsRESTRICT
location_idcharacterYES-NoNoYeslocationsRESTRICT
occurred_attimestamp with time zoneNOnow()NoNoNo--
notestextYES-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • CHECK ((circulation_type = ANY (ARRAY['issued_to_person'::text, 'returned_from_person'::text, 'moved_to_location'::text, 'received_at_location'::text, 'location_confirmation'::text])))

asset_manufacturers ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
tenant_idcharacterNO-NoYesYestenantsRESTRICT
namecharacter varyingNO-NoYesNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
  • None

asset_models ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
nametextNO-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tracking_typetextNO'serialized'::textNoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
manufacturer_idcharacterNO-NoNoYesasset_manufacturersRESTRICT
end_of_supportdateYES-NoNoNo--
asset_type_idcharacterNO-NoNoYesasset_typesRESTRICT
  • CHECK ((tracking_type = ANY (ARRAY['serialized'::text, 'countable'::text])))

asset_repairs ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
asset_idcharacterNO-NoNoYesassetsCASCADE
titletextNO-NoNoNo--
descriptiontextYES-NoNoNo--
location_idcharacterYES-NoNoYeslocationsRESTRICT
statustextNO'open'::textNoNoNo--
prioritytextNO'normal'::textNoNoNo--
reported_attimestamp with time zoneNOnow()NoNoNo--
resolved_attimestamp with time zoneYES-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • CHECK (((resolved_at IS NULL) OR (resolved_at >= reported_at)))
  • CHECK ((priority = ANY (ARRAY['low'::text, 'normal'::text, 'high'::text, 'critical'::text])))
  • CHECK ((status = ANY (ARRAY['open'::text, 'in_progress'::text, 'resolved'::text, 'cancelled'::text])))
  • CHECK ((char_length(title) > 0))

asset_types ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
tenant_idcharacterNO-NoYesYestenantsRESTRICT
namecharacter varyingNO-NoYesNo--
end_of_support_labelcharacter varyingYES-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
  • None

assets ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
nametextNO-NoNoNo--
serial_numbertextYES-NoYesNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
model_idcharacterNO-NoNoYesasset_modelsRESTRICT
quantityintegerNO1NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • CHECK ((quantity > 0))

identities ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
person_idcharacterNO-NoNoYespersonsCASCADE
last_nametextNO-NoNoNo--
first_nametextNO-NoNoNo--
middle_nametextYES-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

location_types ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
namecharacter varyingNO-NoYesNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

locations ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
parent_idcharacterYES-NoNoYeslocationsSET NULL
namecharacter varyingNO-NoNoNo--
type_idcharacterNO-NoNoYeslocation_typesRESTRICT
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

persons ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
current_identity_idcharacterYES-NoNoYesidentitiesSET NULL
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

revoked_tokens ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
jticharacterNO-YesYesNo--
user_idcharacterNO-NoNoYesusersCASCADE
expires_attimestamp with time zoneNO-NoNoNo--
revoked_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

school_calendars ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
school_idcharacterNO-NoNoYesschoolsCASCADE
calendar_idcharacterNO-NoNoYesschool_yearsRESTRICT
namecharacter varyingNO-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

school_employment_assignments ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
person_idcharacterNO-NoNoYespersonsCASCADE
school_idcharacterNO-NoNoYesschoolsCASCADE
start_datedateNO-NoNoNo--
end_datedateYES-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
  • CHECK (((end_date IS NULL) OR (end_date >= start_date)))

school_employments ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
person_idcharacterNO-NoNoYespersonsCASCADE
start_datedateNO-NoNoNo--
end_datedateYES-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
  • CHECK (((end_date IS NULL) OR (end_date >= start_date)))

school_enrollments ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
person_idcharacterNO-NoNoYespersonsCASCADE
calendar_idcharacterNO-NoNoYesschool_calendarsCASCADE
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

school_years ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
namecharacter varyingNO-NoYesNo--
start_datedateNO-NoNoNo--
end_datedateNO-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • CHECK ((end_date >= start_date))

schools ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
namecharacter varyingNO-NoYesNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

tenants ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesYesuser_groupsRESTRICT
namecharacter varyingNO-NoYesNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
tenant_admin_group_idcharacterNO-NoNoYesuser_groupsRESTRICT
tenant_users_group_idcharacterNO-NoNoYesuser_groupsRESTRICT
  • None

user_group_memberships ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
tenant_idcharacterNO-NoYesYestenantsRESTRICT
user_idcharacterNO-NoYesYesusersCASCADE
user_group_idcharacterNO-NoYesYesuser_groupsCASCADE
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
  • None

user_groups ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
tenant_idcharacterNO-NoYesYestenantsRESTRICT
namecharacter varyingNO-NoYesNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
  • None

users ​

ColumnTypeNullableDefaultPKUniqueFKFK TargetOn Delete
idcharacterNO-YesYesNo--
usernametextNO-NoYesNo--
emailtextNO-NoYesNo--
password_hashtextNO-NoNoNo--
created_attimestamp with time zoneNOnow()NoNoNo--
updated_attimestamp with time zoneNOnow()NoNoNo--
person_idcharacterYES-NoNoYespersonsSET NULL
tenant_idcharacterNO-NoNoYestenantsRESTRICT
  • None

Nexus by McGuire Technology