-- IHF Phase 8 — Federated Hub Maturity -- Workplan: IHUB-WP-0008 CREATE TABLE widget_ownerships ( id UUID DEFAULT uuid_generate_v4() PRIMARY KEY NOT NULL, widget_id UUID NOT NULL REFERENCES widgets(id), owner_hub_id UUID NOT NULL REFERENCES hubs(id), steward_hub_id UUID REFERENCES hubs(id), ownership_type TEXT NOT NULL DEFAULT 'local', effective_from TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT now(), effective_until TIMESTAMP WITH TIME ZONE, notes TEXT, created_at TIMESTAMP WITH TIME ZONE DEFAULT now() NOT NULL ); CREATE INDEX widget_ownerships_widget_id_idx ON widget_ownerships (widget_id); CREATE INDEX widget_ownerships_owner_hub_idx ON widget_ownerships (owner_hub_id); CREATE INDEX widget_ownerships_steward_hub_idx ON widget_ownerships (steward_hub_id); CREATE TABLE hub_routing_rules ( id UUID DEFAULT uuid_generate_v4() PRIMARY KEY NOT NULL, source_hub_id UUID NOT NULL REFERENCES hubs(id), target_hub_id UUID NOT NULL REFERENCES hubs(id), match_category TEXT, match_widget_type TEXT, priority INTEGER NOT NULL DEFAULT 0, status TEXT NOT NULL DEFAULT 'inactive', notes TEXT, created_at TIMESTAMP WITH TIME ZONE DEFAULT now() NOT NULL, updated_at TIMESTAMP WITH TIME ZONE DEFAULT now() NOT NULL ); CREATE INDEX hub_routing_rules_source_idx ON hub_routing_rules (source_hub_id); CREATE INDEX hub_routing_rules_status_idx ON hub_routing_rules (status); ALTER TABLE requirement_candidates ADD COLUMN routed_to_hub_id UUID REFERENCES hubs(id); CREATE INDEX requirement_candidates_routed_hub_idx ON requirement_candidates (routed_to_hub_id) WHERE routed_to_hub_id IS NOT NULL; CREATE TABLE federated_policy_overlays ( id UUID DEFAULT uuid_generate_v4() PRIMARY KEY NOT NULL, title TEXT NOT NULL, policy_text TEXT NOT NULL, applies_to_hubs JSONB NOT NULL DEFAULT '[]', enforced_from TIMESTAMP WITH TIME ZONE, status TEXT NOT NULL DEFAULT 'draft', notes TEXT, created_at TIMESTAMP WITH TIME ZONE DEFAULT now() NOT NULL, updated_at TIMESTAMP WITH TIME ZONE DEFAULT now() NOT NULL ); CREATE INDEX federated_policy_overlays_status_idx ON federated_policy_overlays (status); CREATE TABLE stewardship_roles ( id UUID DEFAULT uuid_generate_v4() PRIMARY KEY NOT NULL, hub_id UUID NOT NULL REFERENCES hubs(id), role_name TEXT NOT NULL, assigned_to TEXT NOT NULL, granted_at TIMESTAMP WITH TIME ZONE DEFAULT now() NOT NULL, revoked_at TIMESTAMP WITH TIME ZONE, notes TEXT ); CREATE INDEX stewardship_roles_hub_id_idx ON stewardship_roles (hub_id); CREATE INDEX stewardship_roles_active_idx ON stewardship_roles (revoked_at) WHERE revoked_at IS NULL; CREATE TABLE archive_records ( id UUID DEFAULT uuid_generate_v4() PRIMARY KEY NOT NULL, subject_type TEXT NOT NULL, subject_id UUID NOT NULL, archived_at TIMESTAMP WITH TIME ZONE DEFAULT now() NOT NULL, reason TEXT NOT NULL, archived_by TEXT NOT NULL, lineage_ref TEXT ); CREATE INDEX archive_records_subject_type_idx ON archive_records (subject_type); CREATE INDEX archive_records_subject_id_idx ON archive_records (subject_id); ALTER TABLE widgets ADD COLUMN is_archived BOOLEAN NOT NULL DEFAULT FALSE; CREATE INDEX widgets_is_archived_idx ON widgets (is_archived) WHERE is_archived = TRUE;