Introspecting DEFAULT-Werte und berechnete Spalten
-
24-09-2019 - |
Frage
Für eine Perl-Bibliothek, die Dumps Sybase-Schemas für DBIx :: Class (:: Schema :: Loader), muss ich introspect Defaults und berechnete Spalten können.
Angenommen, wir haben:
create table bar (
id INTEGER IDENTITY PRIMARY KEY,
foo VARCHAR(10) DEFAULT 'foo',
adt AS getdate(),
ts timestamp
)
Hier ist so weit ich habe:
select substring(c.name,1,5) name, c.cdefault, c.computedcol from syscolumns c
join sysobjects o on c.id = o.id where o.name = 'bar' and o.type = 'U'
name cdefault computedcol
---------- ----------- -----------
id 0 NULL
foo 602182610 NULL
adt 0 618182667
ts 0 NULL
Das sagt mir, dass Spalte ‚foo‘ hat eine gespeicherte Prozedur mit der ID 602182610, die den Wert zurückgibt. Wie erhalte ich den ursprünglichen Standard ‚foo‘ aus dieser ID?
Die Timestamp-Spalte hat nicht berechnete Spalte Objekt noch eine Standard sproc, aber ich musste irgendwie wissen, dass es in der Tat eine Timestamp-Spalte ist. Mit Blick auf dem Datentyp zurück von DBI es sagt mir, dass es ‚varbinary‘, die interne Darstellung eines Zeitstempels. Wie kann ich wissen, ob es ist oder nicht ein?
Es sagt mir auch, dass Spalte ‚adt‘ ist eine berechnete Spalte, das Objekt für diese Spalte mit der ID 618182667.
Suchen Sie in sysobjects für die id sagt mir wenig, dass scheint nützlich, außer:
select substring(name,1,15) name, type from sysobjects where id = 618182667
name type
------------------------------ ----
bar_adt_6181826 C
Jede Hilfe sehr geschätzt.
Lösung
In Bezug auf Ihre erste Frage, über Standardwerte
select text from syscomments
where id = 602182610
Wie für Zeitstempel-Spalten, die type
Spalte in syscolumns Referenzen systypes.type
. In dieser Tabelle name
Spalte enthält den Datentyp Namen.
Andere Tipps
Dies ist die Abfrage, die ich mit, falls jemand am Ende interessiert:
SELECT c.name name, t.name type, cm.text deflt
FROM syscolumns c
JOIN sysobjects o ON c.id = o.id
LEFT JOIN systypes t ON c.type = t.type AND c.usertype = t.usertype
LEFT JOIN syscomments cm
ON cm.id = CASE WHEN c.cdefault = 0 THEN c.computedcol ELSE c.cdefault END
WHERE o.name = 'table_name' AND o.type = 'U'
Es scheint gut zu funktionieren, obwohl ich noch einige weitere Datentypprüfungen schreiben müssen:)