You may want to consider a smaller logging table and a larger archive table to do the partitioning you spoke of:
Here at the hospital where I work we had the similar issue about 15 years ago. People were trying access the audit log for reporting while the audit logging was being locked by those reports. Therefore, we separated the reporting from the logging by chunking off the log to another database for reporting purposes. To avoid gaps in service we set a timer to chunk off portions of the data to the new table--100000 possible records at a time. In your case, once you get the data to your new table, you can partition how you like.
Using this strategy your original logging table will always remain small and your archive table will grow and be the one you want to partition. For us, it was an immense benefit to separate the current logging from the historical information. I guess you'll need to weigh that benefit out for yourself. But at least, you'd still be able to write to the original table without affecting the logging that's going on--when you export the data to the archive database/table.
The users who do historical reporting, in your case, may notice because they've got a new table to go to. But logging will continue on the original table unhindered.
Here's the code, my apologies, it's a bit crusty--where newaudit is the logging database and audit is the archiving database. (Of course you'd want to test this in a dev environment before any production go-lives):
Create proc [dbo].[spExportAuditLog]
as
set nocount on
declare @errorvar int,@max int, @min int, @watermark int, @batch int, @beforecounter int, @aftercounter int, @AuditCounter int, @NewAuditCounter int, @errortext varchar(255)
select @beforecounter=0
select @aftercounter=0
select @NewAuditCounter = count(*) from newaudit.dbo.auditlog
print 'NewAudit AuditLog Count Before'
print @NewAuditCounter
print 'Audit AuditLog Count Before'
select @AuditCounter=count(*) from [TARGETSQLSERVER].audit.dbo.auditlog
print @AuditCounter
select top 1 @max=ID from newaudit.dbo.auditlog where datediff( minute, datestamp,getdate()) <= 1440 order by ID
select @min=min(ID) from newaudit.dbo.auditlog
Set XACT_ABORT on
select @batch =100000
select @watermark=@min
while (@watermark <=@max)
begin
begin transaction
insert into [TARGETSQLSERVER].audit.dbo.auditlog(ApplicationName, MessageType, Message, Comments, UserID, CustomFields, Datestamp, ServerName, MRN)
select ApplicationName, MessageType, Message, Comments, UserID, CustomFields, Datestamp, ServerName, MRN
from newaudit.dbo.auditlog where ID between @watermark and @watermark+@batch and ID <= @max order by id
if @@ERROR <> 0 select @errorvar=@errorvar+1
delete from newaudit.dbo.auditlog where ID between @watermark and @watermark+@batch and ID <= @max
if @@ERROR <> 0 select @errorvar=@errorvar+1
if @errorvar > 0
begin
select @errortext= 'ROLLBACK!! Problem with error IDs between:' + CONVERT(varchar(50), @watermark) + ' and ' +CONVERT(varchar(50), @watermark+@batch)
print @errorText
rollback
select @errorvar=0
end
else commit
select @watermark = @watermark+@batch +1
waitfor delay '000:00:10'
end
select @NewAuditCounter = count(*) from newaudit.dbo.auditlog
print 'NewAudit AuditLog Count After'
print @NewAuditCounter
print 'Audit AuditLog Count After'
select @AuditCounter=count(*) from [TARGETSQLSERVER].audit.dbo.auditlog
print @AuditCounter
inserts
andselects
are performed againts that table. @BrentOzar 110 millions of records, 32GBs in total (13 GBs of data and 19 GBs of indexes)