Я искал в заголовке файла, как это было предложено Мартином Смитом в комментариях. Я думаю, что это часть ответа, но в основном это спекуляция, основанная на наблюдении за изменениями значений флага страницы заголовка файла между выполнением сжатия и другими операциями.
Сначала я создал базу данных для тестирования, включая вторичную файловую группу:
CREATE DATABASE [Shrinkfile_Test]
ON PRIMARY
(
NAME = N'Shrinkfile_Test',
FILENAME = N'C:\Program Files\Microsoft SQL Server\MSSQL13.SQL2016\MSSQL\DATA\Shrinkfile_Test.mdf',
SIZE = 8192KB,
FILEGROWTH = 65536KB
),
FILEGROUP [SECONDARY]
(
NAME = N'ShrinkFile_Test_Secondary',
FILENAME = N'C:\Program Files\Microsoft SQL Server\MSSQL13.SQL2016\MSSQL\DATA\ShrinkFile_Test_Secondary.ndf',
SIZE = 1024KB,
FILEGROWTH = 65536KB
)
LOG ON
(
NAME = N'Shrinkfile_Test_log',
FILENAME = N'C:\Program Files\Microsoft SQL Server\MSSQL13.SQL2016\MSSQL\DATA\Shrinkfile_Test_log.ldf',
SIZE = 73728KB,
FILEGROWTH = 65536KB
)
GO
USE Shrinkfile_Test;
GO
Я посмотрел на «страницу 0» для вторичного файла, который является file_id 3:
DBCC TRACEON (3604);
GO
DBCC PAGE (N'Shrinkfile_Test', 3, 0, 3);
Есть поле с именем, m_flagBits
которое имеет значение 0x208
.
Если я опустошу этот файл:
DBCC SHRINKFILE (N'ShrinkFile_Test_Secondary' , EMPTYFILE);
Это m_flagbits
поле остается неизменным ( 0x208
). Не очень интересно, но теперь я нахожусь в ситуации, о которой вы сообщили: если я попытаюсь очистить файл снова, я получу эту ошибку:
Идентификатор файла 3 базы данных с идентификатором 19 нельзя сжать, поскольку он либо сокращен другим процессом, либо пуст.
Я попробую вырастить файл (решение, которое сработало для вас):
ALTER DATABASE ShrinkFile_Test
MODIFY FILE
(
NAME = ShrinkFile_Test_Secondary,
SIZE = 1025KB
);
GO
Сейчас m_flagbits
есть 0x8
!
На этом этапе повторная очистка файла возвращает значение, 0x208
как вы могли ожидать.
Что мне кажется интересным, так это то, что если я сделаю это после того, как вырасту файл обратно (значение флажка AKA равно 0x8
):
USE [master]
GO
ALTER DATABASE [Shrinkfile_Test] MODIFY FILEGROUP [SECONDARY] READONLY
GO
Файл помечен как is_read_only
в sys.databases
таблице и m_flagbits
установлен обратно 0x208
. Таким образом, кажется, есть некоторый подобный флаг уровня файла, установленный при сжатии файла и при установке его только для чтения.
Мое лучшее предположение состоит в том, что это значение используется вместе с некоторым другим (внутренним) флагом, чтобы указать, что файл может быть сжат. Увеличение файла, по-видимому, снимает этот флаг (по крайней мере, тот, который виден в m_flagbits
).