2013-05-30 6 views
10

Muss ich Eigentümer der Beziehung sein, um auf einschränkungsbezogene Daten im Informationsschema zugreifen zu können? Ich habe das Folgende getestet und es scheint, dass ich der Besitzer sein muss.Listeneinschränkungen für alle Tabellen mit unterschiedlichen Eigentümern in PostgreSQL

create schema rights_test; 

create table rights_test.t1 (id int primary key); 
create table rights_test.t2 (id int references rights_test.t1(id)); 

select 
     tc.constraint_name, 
     tc.constraint_schema || '.' || tc.table_name || '.' || kcu.column_name as physical_full_name, 
     tc.constraint_schema, 
     tc.table_name, 
     kcu.column_name, 
     ccu.table_name as foreign_table_name, 
     ccu.column_name as foreign_column_name, 
     tc.constraint_type 
    from 
     information_schema.table_constraints as tc 
     join information_schema.key_column_usage as kcu on (tc.constraint_name = kcu.constraint_name and tc.table_name = kcu.table_name) 
     join information_schema.constraint_column_usage as ccu on ccu.constraint_name = tc.constraint_name 
    where 
     constraint_type in ('PRIMARY KEY','FOREIGN KEY') 
     and tc.constraint_schema = 'rights_test' 

/* 
This will produce desired output: 
t1_pkey;rights_test.t1.id;rights_test;t1;id;t1;id;PRIMARY KEY 
t2_id_fkey;rights_test.t2.id;rights_test;t2;id;t1;id;FOREIGN KEY 
*/ 

create user rights_test_role with password 'password'; 

grant all on rights_test.t1 to rights_test_role; 
grant all on rights_test.t2 to rights_test_role; 

/* Now login as rights_test_role and try the same constraint select. 
    For rights_test_role it returns nothing although I've added ALL privileges 
*/ 

Gibt es einen anderen Weg, um die gleichen Informationen zu erhalten, wenn ich nicht Besitzer der Beziehung bin?

Antwort

9

Nicht alle einschränkungsbezogenen Daten sind "geschützt". Mit drei Beziehungen in Ihrer Suchanfrage:

  • table_constraints
  • key_column_usage
  • constraint_column_usage

Die ersten beiden sind nicht begrenzt, aber die Dokumentation für constraint_column_usage sagt Ihnen:

Die Ansicht constraint_column_usage identifiziert alle Spalten in den aktuellen Daten abase, die von einer Constraint verwendet werden. Es werden nur die Spalten angezeigt, die in einer Tabelle enthalten sind, die einer derzeit aktivierten Rolle gehört.

Seit information_schema.constraint_column_usage eine Ansicht ist, können Sie seine Definition siehe

\d+ information_schema.constraint_column_usage 

in der psql-Shell. Das Ergebnis sieht auf den ersten Blick erschreckend aus, aber es ist wirklich nicht so schlimm. Die interessanteste Sache - für einen ersten Test - ist der Teil in der letzten Zeile:

WHERE pg_has_role(x.tblowner, 'USAGE'::text); 

Wenn Sie die Definition in die psql Schale einzufügen, die rights_test_role von der Nicht-Besitzer geöffnet ist und löschen, die letzte Zeile, die Sie wird das gewünschte Ergebnis erhalten. Das ist gut, denn das bedeutet, dass die grundlegenden Metadaten nicht vom System geschützt werden. So können Sie die Ansichtsdefinition entfernen, um nur die Teile aufzunehmen, die Sie wirklich benötigen.

+2

'\ d +' ist dein Freund. –

16

Versuchen Sie die Verwendung .. gibt alle Constraint-Namen und Constraint-Beschreibung.

  • Fremdschlüssel
  • prüfen
  • Primärschlüssel
  • Einzigartige

Like:

select conrelid::regclass AS table_from, conname, pg_get_constraintdef(c.oid) 
from pg_constraint c 
join pg_namespace n ON n.oid = c.connamespace 
where contype in ('f', 'p','c','u') order by contype 
Verwandte Themen