October 19, 2005 at 8:42 am
I am trying to find out all the tables in the user databases without any index or primary keys. Does anyone have any suggestion for scripting or does anyone have any script that provides the info?
Thanks
October 19, 2005 at 1:47 pm
I thought something like this would work:
select * from sysobjects a
where (not exists
(select * from sysindexes b where a.id = b.id))
and xtype = 'U'
order by name
But I find that my tables that don't have any indexes still have entries in sysindexes and sisindexkeys !?!? Any ideas as to why ?
Edit: I found that the table with no indexes, but records in sysindexes, does have indexes in the original prod database on another server. It's probable that my developement db was created from a restore of prod, so at the time, there were indexes. Since there are no longer indexes, I need to find a way to update sysindexes & sysindexkeys to reflect reality. I tired UPDATE STATISTICS and DBCC UPDATEUSAGE, but it had no effect
Thoughts ?
October 19, 2005 at 2:50 pm
SQL Server uses SysIndexes for statistics, so it doesn't just contain user-created indexes.
The query needs to exclude the indexes where the name is prefixed with "_WA_Sys_".
select * from sysobjects a
where (not exists
(select * from sysindexes b where a.id = b.id and name not like "_WA_Sys_%' ))
and xtype = 'U'
order by name
October 19, 2005 at 3:02 pm
I was wondering what those "_WA_Sys_%" ones were all about. I omitted them, but didn't know if that was a reliable thing to do for accurate, long term results.
I still have a non "_WA_Sys_%" record in sysindexes that's preventing me from getting expected results. In that case, indid = 0, so when I run this, my results look a lot better:
select * from sysobjects a
where (not exists
(select * from sysindexes b where a.id = b.id and name not like '_WA_Sys_%' and indid <> '0' ))
and xtype = 'U'
order by name
October 20, 2005 at 2:08 am
Warning : this query does direct access to system-objects ! They may change without warning with hotfix, sp, ...
This is what I use
print 'Server : '+@@servername + ' Database : '+db_name()
print '--------------------------------------------------'
select t.name as Tbname, t.crdate
from
(
select *
from sysobjects
where xtype = 'u'
) t
left join
(
select *
from sysobjects
where xtype = 'pk'
) k
on t.id = k.parent_obj
where k.name is null
order by tbname
-- To find tb without clustering indexes I use :
print 'Server : '+@@servername + ' Database : '+db_name()
print '-------------------------------------------------------------------------'
Print '-- tables with indexes , but without clustering key and/or primary key --'
print '-------------------------------------------------------------------------'
declare @des1 varchar(35), -- 35 matches spt_values
@des2 varchar(35),
@des4 varchar(35),
@des32 varchar(35),
@des64 varchar(35),
@des2048 varchar(35),
@des4096 varchar(35),
@des8388608 varchar(35),
@des16777216 varchar(35)
select @des1 = name from master.dbo.spt_values where type = 'I' and number = 1
select @des2 = name from master.dbo.spt_values where type = 'I' and number = 2
select @des4 = name from master.dbo.spt_values where type = 'I' and number = 4
select @des32 = name from master.dbo.spt_values where type = 'I' and number = 32
select @des64 = name from master.dbo.spt_values where type = 'I' and number = 64
select @des2048 = name from master.dbo.spt_values where type = 'I' and number = 2048
select @des4096 = name from master.dbo.spt_values where type = 'I' and number = 4096
select @des8388608 = name from master.dbo.spt_values where type = 'I' and number = 8388608
select @des16777216 = name from master.dbo.spt_values where type = 'I' and number = 16777216
Select CAST( u.name+'.'+o.name AS varchar) as TbName
, cast( case x.name when clx.name then '#' when pko.name then '*' else ' ' end as char(1)) as 'PK'
, x.indid as Ix_Id
, cast(x.name as varchar) as ixname
-- , cast(clx.name as varchar) as ClX_name
-- , cast(pko.name as varchar(50)) as PK_name
, cast(count(*) as smallint) as xCols
, convert(varchar(25), --bits 16 off, 1, 2, 16777216 on, located on group
case when (x.status & 16)<>0 then 'cl' else 'nc' end -- 'clustered' of 'nonclustered'
+ case when (x.status & 1)<>0 then ', '+@des1 else '' end
+ case when (x.status & 2)<>0 then ', '+@des2 else '' end
+ case when (x.status & 4)<>0 then ', '+@des4 else '' end
-- + case when (x.status & 64)<>0 then ', '+@des64 else case when (x.status & 32)<>0 then ', '+@des32 else '' end end
-- + case when (x.status & 2048)<>0 then ', '+@des2048 else '' end
-- + case when (x.status & 4096)<>0 then ', '+@des4096 else '' end
-- + case when (x.status & 8388608)<>0 then ', '+@des8388608 else '' end
-- + case when (x.status & 16777216)<>0 then ', '+@des16777216 else '' end
) as index_descr
--, o.id as id
--, x.indid as ix_id
--, x.rows as rijen
--, L.rowlength as rijlengte
from sysobjects o
inner join sysusers u
on o.uid = u.uid
inner join
(select id, sum(length) as rowlength
from syscolumns
group by id ) L
on o.id = L.id
left join
sysindexes x
on o.id = x.id
left join
sysindexkeys xk
on x.id = xk.id
and x.indid = xk.indid
left join
sysindexes Clx
on o.id = Clx.id
and Clx.indid = 1 -- only clustered indexes
left join sysobjects pko
on pko.xtype = 'pk'
and pko.parent_obj = o.id
where o.xtype = 'u'
-- and x.rows > 100 -- more than 100 rows
and x.indid <> 1 -- only non clustering
and Clx.indid is null -- only with no cluster ix
-- and x.keys is not null
and x.name not like '_w%'
and o.name <> 'dtproperties'
-- and ( x.name = pko.name or pko.name is null ) -- enkel de primary key indexen selecteren
and x.firstiam <> 0x000000000000 -- enkel indexen
group by u.name , o.name , L.rowlength , x.name
, pko.name , x.status
, o.id , x.indid, x.rows
, clx.name
-- having count(*) = 1
order by TbName, pk desc, ixname
Johan
Learn to play, play to learn !
Dont drive faster than your guardian angel can fly ...
but keeping both feet on the ground wont get you anywhere :w00t:
- How to post Performance Problems
- How to post data/code to get the best help[/url]
- How to prevent a sore throat after hours of presenting ppt
press F1 for solution, press shift+F1 for urgent solution 😀
Need a bit of Powershell? How about this
Who am I ? Sometimes this is me but most of the time this is me
October 20, 2005 at 11:04 pm
The following simple query might solve your problem,
Select Name
From sysObjects
Where xtype = 'U'
and ObjectProperty(id,'isIndexed') = 0
and ObjectProperty(id,'TableHasPrimaryKey') = 0
October 21, 2005 at 3:57 am
Hi
with the information_schema you can find what you need too:
select * from information_schema.tables where table_name not in
(select distinct table_name from information_schema.KEY_COLUMN_USAGE)
with this you can find those tables which don't have a unique index e.g.
Viewing 7 posts - 1 through 6 (of 6 total)
You must be logged in to reply to this topic. Login to reply