SQL Server-Abfrage zum Abrufen der Liste der Spalten in einer Tabelle zusammen mit den Einschränkungen Datentypen, NICHT NULL und PRIMARY KEY

229

Ich muss eine Abfrage auf SQL Server schreiben, um die Liste der Spalten in einer bestimmten Tabelle, die zugehörigen Datentypen (mit Länge) und wenn sie nicht null sind, abzurufen. Und ich habe es geschafft, so viel zu tun.

Aber jetzt muss ich auch in derselben Tabelle gegen eine Spalte vorgehen - TRUEwenn diese Spalte ein Primärschlüssel ist.

Wie mache ich das?

Meine erwartete Ausgabe ist:

Column name | Data type | Length | isnull | Pk
Shrayas
quelle
2
Könnten Sie den Code anzeigen, den Sie bereits haben?
DOK

Antworten:

478

Verwenden Sie user_type_id anstelle von system_type_id, um doppelte Zeilen für einige Spalten zu vermeiden.

SELECT 
    c.name 'Column Name',
    t.Name 'Data type',
    c.max_length 'Max Length',
    c.precision ,
    c.scale ,
    c.is_nullable,
    ISNULL(i.is_primary_key, 0) 'Primary Key'
FROM    
    sys.columns c
INNER JOIN 
    sys.types t ON c.user_type_id = t.user_type_id
LEFT OUTER JOIN 
    sys.index_columns ic ON ic.object_id = c.object_id AND ic.column_id = c.column_id
LEFT OUTER JOIN 
    sys.indexes i ON ic.object_id = i.object_id AND ic.index_id = i.index_id
WHERE
    c.object_id = OBJECT_ID('YourTableName')

Ersetzen YourTableNameSie einfach durch Ihren tatsächlichen Tabellennamen - funktioniert für SQL Server 2005 und höher.

Falls Sie Schemata verwenden, ersetzen YourTableName durch , YourSchemaName.YourTableNamewo YourSchemaNamedie tatsächlichen Schemanamen und YourTableNamesind die eigentlichen Tabellennamen.

marc_s
quelle
2
Dies gibt falsche Längen für den Spaltentyp nvarchar usw. an. Es gibt die Bytelänge an, die doppelt so groß ist wie die Länge im Spaltentyp.
Andrew Savinykh
14
Diese Längen sind nicht falsch - es gibt die Bytelänge an - das ist die maximal mögliche Länge in Bytes ... wenn Sie Speicherplatz usw. berechnen möchten, ist dies die Länge, die Sie erhalten möchten ...
marc_s
2
Funktioniert hervorragend für mich SQL Server 2012 :)
Doc Holiday
2
WHERE c.object_id = OBJECT_ID ('YourTableName') .... Ich brauchte WHERE c.object_id = OBJECT_ID ('MySchema.MyTableName') und dann hat alles gut funktioniert.
Ivan
7
Diese Abfrage gibt doppelte Spalten zurück, wenn Sie mehrere Indizes haben, die dieselbe Spalte betreffen. Um dies zu beheben, ersetzen Sie die letzten beiden Verknüpfungen durch die folgenden: LEFT OUTER JOIN sys.index_columns ic LEFT OUTER JOIN sys.indexes i ON ic.object_id = i.object_id AND ic.index_id = i.index_id ON ic.object_id = c.object_id AND ic.column_id = c.column_id AND i.is_primary_key=1
Razvan Socol
95

Die gespeicherte Prozedur sp_columns gibt detaillierte Tabelleninformationen zurück.

exec sp_columns MyTable
dekompiliert
quelle
2
exec sp_pkeys exec sp_fkeys
Leonardo Marques de Souza
2
kurze Abfrage, macht aber große Arbeit.
Akshay Chawla
1
schöne prägnante Antwort
t_warsop
72

Sie könnten die Abfrage verwenden:

select COLUMN_NAME, DATA_TYPE, CHARACTER_MAXIMUM_LENGTH, 
       NUMERIC_PRECISION, DATETIME_PRECISION, 
       IS_NULLABLE 
from INFORMATION_SCHEMA.COLUMNS
where TABLE_NAME='TableName'

um alle Metadaten zu erhalten, die Sie benötigen, mit Ausnahme der Pk-Informationen.

Ajadex
quelle
2
Ich habe das gemacht :) Aber ich brauche auch die PK: |
Shrayas
msdn.microsoft.com/pt-br/library/ms189813(v=sql.120).aspx sp_fkeys sp_pkeys
Leonardo Marques de Souza
1
Das ist großartig, weil es mit SS-Versionen funktioniert, die älter als 2005 sind. Danke!
Karl Hoaglund
19

In SQL 2012 können Sie Folgendes verwenden:

EXEC sp_describe_first_result_set N'SELECT * FROM [TableName]'

Dadurch erhalten Sie die Spaltennamen zusammen mit ihren Eigenschaften.

Amruta Kar
quelle
13

Versuche dies:

select COLUMN_NAME, DATA_TYPE, CHARACTER_MAXIMUM_LENGTH, IS_NULLABLE 
from INFORMATION_SCHEMA.COLUMNS IC
where TABLE_NAME = 'tablename' and COLUMN_NAME = 'columnname'
khaleel
quelle
2
Wie unterscheidet sich Ihre Antwort von der von Ajadex? Beide Antworten geben keine Primärschlüsselinformationen zurück.
Artemix
10

Um sicherzustellen, dass Sie die richtige Länge erhalten, müssen Sie Unicode-Typen als Sonderfall betrachten. Siehe Code unten.

Weitere Informationen finden Sie unter: https://msdn.microsoft.com/en-us/library/ms176106.aspx

SELECT 
   c.name 'Column Name',
   t.name,
   t.name +
   CASE WHEN t.name IN ('char', 'varchar','nchar','nvarchar') THEN '('+

             CASE WHEN c.max_length=-1 THEN 'MAX'

                  ELSE CONVERT(VARCHAR(4),

                               CASE WHEN t.name IN ('nchar','nvarchar')

                               THEN  c.max_length/2 ELSE c.max_length END )

                  END +')'

          WHEN t.name IN ('decimal','numeric')

                  THEN '('+ CONVERT(VARCHAR(4),c.precision)+','

                          + CONVERT(VARCHAR(4),c.Scale)+')'

                  ELSE '' END

   as "DDL name",
   c.max_length 'Max Length in Bytes',
   c.precision ,
   c.scale ,
   c.is_nullable,
   ISNULL(i.is_primary_key, 0) 'Primary Key'
FROM    
   sys.columns c
INNER JOIN 
   sys.types t ON c.user_type_id = t.user_type_id
LEFT OUTER JOIN 
   sys.index_columns ic ON ic.object_id = c.object_id AND ic.column_id = c.column_id
LEFT OUTER JOIN 
   sys.indexes i ON ic.object_id = i.object_id AND ic.index_id = i.index_id
WHERE
   c.object_id = OBJECT_ID('YourTableName')
Microsoft Developer
quelle
1
Der DDL-Name ist SO nützlich für Dynamic-SQL, das Tabellen erstellt! Vielen Dank!!
George Menoutis
6

Wenn Sie Alex 'Antwort erweitern, können Sie dies tun, um die PK-Einschränkung zu erhalten

Select C.COLUMN_NAME, C.DATA_TYPE, C.CHARACTER_MAXIMUM_LENGTH, C.NUMERIC_PRECISION, C.IS_NULLABLE, TC.CONSTRAINT_NAME
From INFORMATION_SCHEMA.COLUMNS As C
    Left Join INFORMATION_SCHEMA.TABLE_CONSTRAINTS As TC
      On TC.TABLE_SCHEMA = C.TABLE_SCHEMA
          And TC.TABLE_NAME = C.TABLE_NAME
          And TC.CONSTRAINT_TYPE = 'PRIMARY KEY'
Where C.TABLE_NAME = 'Table'

Ich muss übersehen haben, dass Sie möchten, dass ein Flag anstelle des Namens der PK-Einschränkung feststellt, ob die angegebene Spalte Teil der PK war. Dafür würden Sie verwenden:

Select C.COLUMN_NAME, C.DATA_TYPE, C.CHARACTER_MAXIMUM_LENGTH
    , C.NUMERIC_PRECISION, C.NUMERIC_SCALE
    , C.IS_NULLABLE
    , Case When Z.CONSTRAINT_NAME Is Null Then 0 Else 1 End As IsPartOfPrimaryKey
From INFORMATION_SCHEMA.COLUMNS As C
    Outer Apply (
                Select CCU.CONSTRAINT_NAME
                From INFORMATION_SCHEMA.TABLE_CONSTRAINTS As TC
                    Join INFORMATION_SCHEMA.CONSTRAINT_COLUMN_USAGE As CCU
                        On CCU.CONSTRAINT_NAME = TC.CONSTRAINT_NAME
                Where TC.TABLE_SCHEMA = C.TABLE_SCHEMA
                    And TC.TABLE_NAME = C.TABLE_NAME
                    And TC.CONSTRAINT_TYPE = 'PRIMARY KEY'
                    And CCU.COLUMN_NAME = C.COLUMN_NAME
                ) As Z
Where C.TABLE_NAME = 'Table'
Thomas
quelle
Gut. Es gibt mir nicht das erforderliche Ergebnis :(
Shrayas
5

Wählen Sie mit dem Tabellennamen im Abfrageeditor den Namen aus und drücken Sie Alt + F1. Daraufhin werden alle Informationen der Tabelle angezeigt.

Abu Zafor
quelle
Er bittet um eine Anfrage, aber Sie haben Recht, so können Sie alle Informationen sehen.
Rafa Barragan
aber dennoch; super ordentlich :-)
netfed
4
SELECT COLUMN_NAME, IS_NULLABLE, DATA_TYPE, CHARACTER_MAXIMUM_LENGTH FROM information_schema.columns WHERE table_name = '<name_of_table_or_view>'

Führen Sie SELECT *die obige Anweisung aus, um zu sehen, was information_schema.columns zurückgibt.

Diese Frage wurde bereits beantwortet - https://stackoverflow.com/a/11268456/6169225

Marquistador
quelle
Wenn diese Frage bereits beantwortet wurde, kennzeichnen Sie den Beitrag als Duplikat .
Martijn Pieters
4

Ich bin ein bisschen überrascht, dass niemand etwas erwähnt hat

sp_help 'mytable'
Mario Levesque
quelle
3
IF EXISTS (SELECT 1 FROM INFORMATION_SCHEMA.TABLES 
     WHERE TABLE_TYPE = 'BASE TABLE' AND TABLE_NAME = 'Table')
      BEGIN
        SELECT COLS.COLUMN_NAME, COLS.DATA_TYPE, COLS.CHARACTER_MAXIMUM_LENGTH, 
              (SELECT 'Yes' FROM INFORMATION_SCHEMA.TABLE_CONSTRAINTS TC JOIN INFORMATION_SCHEMA.KEY_COLUMN_USAGE KCU
                              ON COLS.TABLE_NAME = TC.TABLE_NAME 
                             AND TC.CONSTRAINT_TYPE = 'PRIMARY KEY'
                             AND KCU.TABLE_NAME = TC.TABLE_NAME
                             AND KCU.CONSTRAINT_NAME = TC.CONSTRAINT_NAME
                             AND KCU.COLUMN_NAME = COLS.COLUMN_NAME) AS KeyX
        FROM INFORMATION_SCHEMA.COLUMNS COLS WHERE TABLE_NAME = 'Table' ORDER BY KeyX DESC, COLUMN_NAME
      END
Pete vM
quelle
3

Wenn Sie eine weitere Antwort in den Ring werfen, erhalten Sie folgende Spalten und mehr:

SELECT col.TABLE_CATALOG AS [Database]
     , col.TABLE_SCHEMA AS Owner
     , col.TABLE_NAME AS TableName
     , col.COLUMN_NAME AS ColumnName
     , col.ORDINAL_POSITION AS OrdinalPosition
     , col.COLUMN_DEFAULT AS DefaultSetting
     , col.DATA_TYPE AS DataType
     , col.CHARACTER_MAXIMUM_LENGTH AS MaxLength
     , col.DATETIME_PRECISION AS DatePrecision
     , CAST(CASE col.IS_NULLABLE
                WHEN 'NO' THEN 0
                ELSE 1
            END AS bit)AS IsNullable
     , COLUMNPROPERTY(OBJECT_ID('[' + col.TABLE_SCHEMA + '].[' + col.TABLE_NAME + ']'), col.COLUMN_NAME, 'IsIdentity')AS IsIdentity
     , COLUMNPROPERTY(OBJECT_ID('[' + col.TABLE_SCHEMA + '].[' + col.TABLE_NAME + ']'), col.COLUMN_NAME, 'IsComputed')AS IsComputed
     , CAST(ISNULL(pk.is_primary_key, 0)AS bit)AS IsPrimaryKey
  FROM INFORMATION_SCHEMA.COLUMNS AS col
       LEFT JOIN(SELECT SCHEMA_NAME(o.schema_id)AS TABLE_SCHEMA
                      , o.name AS TABLE_NAME
                      , c.name AS COLUMN_NAME
                      , i.is_primary_key
                   FROM sys.indexes AS i JOIN sys.index_columns AS ic ON i.object_id = ic.object_id
                                                                     AND i.index_id = ic.index_id
                                         JOIN sys.objects AS o ON i.object_id = o.object_id
                                         LEFT JOIN sys.columns AS c ON ic.object_id = c.object_id
                                                                   AND c.column_id = ic.column_id
                  WHERE i.is_primary_key = 1)AS pk ON col.TABLE_NAME = pk.TABLE_NAME
                                                  AND col.TABLE_SCHEMA = pk.TABLE_SCHEMA
                                                  AND col.COLUMN_NAME = pk.COLUMN_NAME
 WHERE col.TABLE_NAME = 'YourTableName'
   AND col.TABLE_SCHEMA = 'dbo'
 ORDER BY col.TABLE_NAME, col.ORDINAL_POSITION;
JustinStolle
quelle
2
select
      c.name as [column name], 
      t.name as [type name],
      tbl.name as [table name]
from sys.columns c
         inner join sys.types t 
      on c.system_type_id = t.system_type_id 
         inner join sys.tables tbl
      on c.object_id = tbl.object_id
where
      c.object_id = OBJECT_ID('YourTableName1') 
          and 
      t.name like '%YourSearchDataType%'
union
(select
      c.name as [column name], 
      t.name as [type name],
      tbl.name as [table name]
from sys.columns c
         inner join sys.types t 
      on c.system_type_id = t.system_type_id 
         inner join sys.tables tbl
      on c.object_id = tbl.object_id
where
      c.object_id = OBJECT_ID('YourTableName2') 
          and 
      t.name like '%YourSearchDataType%')
union
(select
      c.name as [column name], 
      t.name as [type name],
      tbl.name as [table name]
from sys.columns c
         inner join sys.types t 
      on c.system_type_id = t.system_type_id 
         inner join sys.tables tbl
      on c.object_id = tbl.object_id
where
      c.object_id = OBJECT_ID('YourTableName3') 
          and 
      t.name like '%YourSearchDataType%')
order by tbl.name

Suchen Sie anhand Ihres Suchdatentyps nach drei verschiedenen Tabellen in einer Datenbank, welche Spalte sich in welcher Tabelle befindet. Diese Abfrage kann auf 'n' Tabellen erweitert werden.

mtinyavuz
quelle
2

Das Kombinationsergebnis für Datentyp und Länge finden und kann in Form von "NULL" und "Nicht null" auf Null gesetzt werden. Verwenden Sie die folgende Abfrage.

SELECT c.name AS 'Column Name',
       t.name + '(' + cast(c.max_length as varchar(50)) + ')' As 'DataType',
       case 
         WHEN  c.is_nullable = 0 then 'null' else 'not null'
         END AS 'Constraint'
  FROM sys.columns c
  JOIN sys.types t
    ON c.user_type_id = t.user_type_id
 WHERE c.object_id    = Object_id('TableName')

Sie finden das Ergebnis wie unten gezeigt.

Geben Sie hier die Bildbeschreibung ein

Danke dir.

Ankit Mori
quelle
1
Ihr Zustand der Einschränkung sollte umgekehrt sein.
Allen
0
SELECT  
   T.NAME AS [TABLE NAME]
   ,C.NAME AS [COLUMN NAME]
   ,P.NAME AS [DATA TYPE]
   ,P.MAX_LENGTH AS [Max_SIZE]
   ,C.[max_length] AS [ActualSizeUsed]
   ,CAST(P.PRECISION AS VARCHAR) +'/'+ CAST(P.SCALE AS VARCHAR) AS [PRECISION/SCALE]
FROM SYS.OBJECTS AS T
JOIN SYS.COLUMNS AS C
    ON T.OBJECT_ID = C.OBJECT_ID
JOIN SYS.TYPES AS P
    ON C.SYSTEM_TYPE_ID = P.SYSTEM_TYPE_ID
    AND C.[user_type_id] = P.[user_type_id]
WHERE T.TYPE_DESC='USER_TABLE'
  AND T.name = 'InventoryStatus'
ORDER BY 2
Rajiv Singh
quelle
1
Bitte verwenden Sie Einrückung anstelle von Inline-Markup und fügen Sie Ihrer Antwort eine Erklärung hinzu.
Toxantron
Warum mit 2 bestellen?
Reggaeguitar
0

Geben Sie hier die Bildbeschreibung ein

Abfrage: EXEC SP_DESCRIBE_FIRST_RESULT_SET N'SELECT ANNUAL_INCOME FROM [BSLID2C]. [DBO]. [EMPLOYEE] '

HINWEIS: IN EINIGER IDE, BEVOR SELECT N FUNKTIONIERT ODER IN EINIGER IDE OHNE N FUNKTIONIERT

Abdullah Pariyani
quelle
0

Hier gibt es keinen Primärschlüssel, aber dies kann anderen Benutzern helfen, die nur einen Tabellennamen mit Feldnamen und grundlegenden Feldeigenschaften haben möchten

USE [**YourDB**]
GO
SELECT tbl.name, fld.[Column Name],fld.[Constraint],fld.DataType 
FROM sys.all_objects as tbl left join 
(SELECT c.OBJECT_ID,  c.name AS 'Column Name',
       t.name + '(' + cast(c.max_length as varchar(50)) + ')' As 'DataType',
       case 
         WHEN  c.is_nullable = 0 then 'null' else 'not null'
         END AS 'Constraint'
  FROM sys.columns c
  JOIN sys.types t
    ON c.user_type_id = t.user_type_id
) as fld on tbl.OBJECT_ID = fld.OBJECT_ID
WHERE ( tbl.[type]='U' and tbl.[is_ms_shipped] = 0)
ORDER BY tbl.[name],fld.[Column Name]
GO
Suhail Abdul Rehman Chougule
quelle
-1

Ich habe gerade marc_s "Präsentation fertig" gemacht:

SELECT 
    c.name 'Column Name',
    t.name 'Data type',
    IIF(t.name = 'nvarchar', c.max_length / 2, c.max_length) 'Max Length',
    c.precision 'Precision',
    c.scale 'Scale',
    IIF(c.is_nullable = 0, 'No', 'Yes') 'Nullable',
    IIF(ISNULL(i.is_primary_key, 0) = 0, 'No', 'Yes') 'Primary Key'
FROM    
    sys.columns c
INNER JOIN 
    sys.types t ON c.user_type_id = t.user_type_id
LEFT OUTER JOIN 
    sys.index_columns ic ON ic.object_id = c.object_id AND ic.column_id = c.column_id
LEFT OUTER JOIN 
    sys.indexes i ON ic.object_id = i.object_id AND ic.index_id = i.index_id
WHERE
    c.object_id = OBJECT_ID('YourTableName')
krs
quelle