SQL Server 2008 - SELECT query - sql

I have a database with over a 150 tables. I need to be able to find every table that has a column called EmployeeID. Is there a way for me to find all tables that have this column? It's kind of a long process if I go through each table and try to find if it has that column.

Use INFORMATION_SCHEMA.COLUMNS:
select c.*
from INFORMATION_SCHEMA.COLUMNS c
where column_name = 'EmployeeID';

Related

SQL query to return the table structure

Knowing only the name of a table, is there a way in SQL to query the structure of the table so I can inspect the columns?
This works in MS SQL server.This will show you column datatype and size.
select * from INFORMATION_SCHEMA.COLUMNS where TABLE_NAME='<Table Name>'

Postgresql how do i find a table based on column name?

I know that I have a table with the column "fortyid" but I cant remember which table it is and I have like 350 tables in my database.
Is there a way to find all tables that has "fortyid" as column? (doesn't matter the type)
You can use the metadata defined by the SQL standard, specifically INFORMATION_SCHEMA.COLUMNS.
select c.*
from information_schema.columns c
where c.column_name = 'fortyid';

Select the first 20 columns

Is it possible to select the first 20 columns from my table, without naming out each column in the select?
The columns are always ordered in the same way when I do a select, so there must be some underlying order.
The below query forms the SQL for you. It uses the dictionary table all_tab_columns to fetch the column names for the table.
SELECT ' SELECT '
|| REPLACE(LISTAGG(column_name,',') WITHIN GROUP( ORDER BY column_id),',',','
||CHR(10))
|| ' FROM YOUR_TABLE'
FROM all_tab_columns
WHERE owner ='YOUR_SCHEMA_NAME'
AND table_name='YOUR_TABLE_NAME'
AND column_id <= 20;
you can use column index instead of column name like select 0,1,2,.....
There is a table in a SQL Server database called sysColumns that records all the columns in every table. I think it is a SQL standard and should be in Oracle too.
EDIT: thanks to comment from #davegreen100, this table is in Oracle but is named DBA_TAB_COLUMNS.
try running Select * from DBA_TAB_COLUMNS and see what the results are, and work from there.
If it's there (in Oracle), you will eventually end up with something like
Select name from DBA_TAB_COLUMNS
Where id = #tableId -- <--- the id of the table
and colOrder <= 20
Your final SQL will be probably have to be generated dynamically using the output from the above

Need to select all tables from a database in SQL Server where the most recent date-timestamp is from a year or more ago

I'm going through all tables in a database trying to determine which tables are old (have not been altered in a long time). I've been going through and flagging all tables with old DTS's as "old"
Is there a more efficient way to do this? Can I run a statement that scans all tables in a database for date-timestamp fields and then looks at the most recent ones?
Thank you in advance for any help you can provide!
You can use the INFORMATION_SCHEMA.COLUMNS view to retrieve all the tables having the timestamp column (assuming the column name is known and not used for other columns).
Use these to generate Dynamic SQL of the form
SELECT COUNT(*) ,#TableName FROM #TableName WHERE #TimeStampColumn < #TimestampToCheck
The tables where count(*) is 0 are the ones you need to look at
I would do something like this:
Show a COUNT(*) of rows written in the last year... if you get 0, you know the table isn't in use.
Use the information_schema to get the columns/tables.
SELECT 'SELECT COUNT(*) AS ['+TABLE_NAME+'] FROM ['+TABLE_CATALOG+'].['+TABLE_SCHEMA+'].['+TABLE_NAME+'] WHERE '+COLUMN_NAME+' > DATEADD(YY,-1,CONVERT(DATETIME,FLOOR(CONVERT(FLOAT,GETDATE()))))'
-- SELECT *
FROM INFORMATION_SCHEMA.COLUMNS
WHERE DATA_TYPE='DATETIME'
--AND (COLUMN_DEFAULT='(getdate())' OR COLUMN_DEFAULT='CURRENT_TIMESTAMP')
You can add the last line in, if you only want columns with a default value.
Then take the output, copy to a new window, and run it!

SQL: use computed string as table name, join all rows of select for counting

I have access to a MS SQL Server with MS Access via ODBC and I want to display the table names, their column names and the number of rows per table. The table names are stored in a table named "sys_tables", the column names in "sys_columns". Unfornunately the number of rows per table has to be counted. As I'm not experienced in SQL, my first try is not working:
SELECT t.name, c.name, t.object_id, x.cnt
FROM sys_tables AS t INNER JOIN sys_columns AS c ON t.object_id = c.object_id
LEFT OUTER JOIN (SELECT COUNT(*) AS cnt FROM #t.name AS tbl ON tbl.cnt > 0) AS x
What is the right way to use a computed string in a SELECT as table name? Can I do a sub select that selects all rows without real relation?
You can't use a variable table name in a SQL statement on the server side. You will need to get the table names from SQL Server and then use those to send new queries (one for each table) back to SQL Server. You could also write a stored procedure on the SQL Server to handle this using dynamic SQL (just be sure that you are familiar with injection attacks whenever you are using dynamic SQL).
SQL Server stores some row count information in sysindexes (not to be confused with sys.indexes) in the rowcnt column. This information is not always 100% accurate though.
Finally, you can use the undocumented stored procedure sp_MSForEachTable like so:
EXEC sp_msForEachTable
'SELECT PARSENAME(''?'', 1),
COUNT(*) FROM ?'
Be aware that this last method will return multiple result sets (one for each table), so you need to handle it that way in Access or combine them together in a temporary table and then return them as one result set. You can do all of that in a stored procedure.
You cannot use a variable for a table name. The only workaround is dynamic SQL.
However, I suspect that there's a table somewhere in sys which gives the row count for each table, though it may not be kept perfectly up-to-date.
Can't you do this:
SELECT COUNT(t.name)
FROM sys_tables AS t INNER JOIN sys_columns AS c ON t.object_id = c.object_id