Как исправить ошибку СУБД «Недопустимое имя объекта \"#tt2\"» в 1С:Предприятие

Системный администратор 1С v8.3 (Управляемые формы) 1С:ERP Управление предприятием IT и автоматизация бизнеса
← На главную

При работе в клиент-серверном варианте 1С:Предприятия под управлением MS SQL Server пользователи и администраторы часто сталкиваются со следующей критической ошибкой:

«Ошибка СУБД: Microsoft SQL Server Native Client 11.0: Недопустимое имя объекта "#tt2". HRESULT=80040E37, SQLSrvr: SQLSTATE=42S02»

Эта проблема чаще всего проявляется при формировании сложных отчетов, таких как Оборотно-сальдовая ведомость (ОСВ) по счету, анализе субконто или при проведении тяжелых документов в ERP-системах (например, 1С:ERP, Комплексная автоматизация или Управление торговлей). Давайте подробно разберем природу этого сбоя, выясним истинные причины его возникновения и рассмотрим все доступные методы решения — от быстрой настройки до автоматизированных скриптов обслуживания.

Почему возникает ошибка «Недопустимое имя объекта "#tt2"»?

Для начала проанализируем архитектуру взаимодействия платформы 1С и MS SQL Server. Префикс #tt во временных таблицах указывает на то, что СУБД создает локальную временную таблицу в системной базе данных tempdb. Логика работы выглядит следующим образом:

  1. Платформа 1С генерирует сложный SQL-запрос, который разбивается на несколько шагов. Чтобы оптимизировать выборку, 1С создает временную таблицу (например, #tt2) в рамках текущей сессии SQL.
  2. В эту таблицу записываются промежуточные данные (например, обороты по счетам или остатки).
  3. Следующим запросом в пакете платформа пытается обратиться к этой таблице #tt2 для вывода финального результата пользователю.

Если в процессе выполнения этого пакета соединение между рабочим процессом 1С (rphost) и SQL-сервером прерывается хотя бы на долю секунды, СУБД мгновенно закрывает сессию пользователя. Специфика локальных временных таблиц в SQL Server такова, что они существуют строго в рамках открытой сессии. Как только сессия закрывается или сбрасывается, база данных tempdb автоматически уничтожает таблицу #tt2. Платформа 1С при этом пытается восстановить соединение и продолжить выполнение запроса, но временной таблицы в СУБД уже нет, что и вызывает ошибку SQLSTATE=42S02 (объект не найден).

Рассмотрим основные технические причины, которые приводят к этому сценарию:

---

Способ 1. Быстрое временное решение — перезапуск служб

Если пользователи не могут работать, а отчеты нужно сформировать прямо сейчас, самым быстрым решением является перезапуск службы сервера 1С:Предприятия. Это очистит зависшие сессии и восстановит корректный пул соединений с SQL-сервером.

Выполните следующие действия:

  1. Откройте консоль управления службами Windows (services.msc).
  2. Найдите службу «1C:Enterprise 8.3 Server Agent» (или аналогичную для вашей версии).
  3. Нажмите кнопку «Перезапустить».

Обратите внимание! Перезапуск службы прервет работу всех активных пользователей в базе данных. Выполняйте это действие в технологическое окно или предупредив коллег.

---

Способ 2. Автоматизация перезапуска и очистки кэша сеансов (CMD-скрипт)

Поскольку ручной перезапуск служб решает проблему лишь временно, системные администраторы рекомендуют настроить регулярный ночной перезапуск серверов 1С и SQL с параллельной очисткой серверного кэша сеансов. Ниже представлен классический проверенный временем скрипт, использующий утилиты пакета PSTools для безопасной остановки служб и удаления временных файлов кэша сеансов (каталогов snccntx*):


@echo on
chcp 1251
SET SERVICE_1C_NAME="1C:Enterprise 8.3 Server Agent (x86-64)"
SET SQLSERVERAGENT="SQLSERVERAGENT"
SET MSSQLSERVER="MSSQLSERVER"
SET CNTX_PATH1C="\\1c-server\g$\srvinfo\reg_1541"
SET CNTX_1C="\\10.50.21.17"
SET CNTX_SQL="\\10.50.21.20"
SET CNTX_P="ВашПароль"
SET CNTX_U="Администратор"
SET CNTX_PST="c:\PSTools\PsService64.exe"

:: Останавливаем службу сервера 1С
%CNTX_PST% %CNTX_1C% -u %CNTX_U% -p %CNTX_P% stop %SERVICE_1C_NAME%
timeout 200

:: Останавливаем службы SQL Server
%CNTX_PST% %CNTX_SQL% -u %CNTX_U% -p %CNTX_P% stop %SQLSERVERAGENT%
timeout 10
%CNTX_PST% %CNTX_SQL% -u %CNTX_U% -p %CNTX_P% stop %MSSQLSERVER%
timeout 100

:: Очищаем кэш сеансов сервера 1С (папки snccntx)
(for /d %%i in (%CNTX_PATH1C%\snccntx*) do rd /s /q %%i)
timeout 10

:: Запускаем службы обратно
%CNTX_PST% %CNTX_SQL% -u %CNTX_U% -p %CNTX_P% start %MSSQLSERVER%
timeout 10
%CNTX_PST% %CNTX_SQL% -u %CNTX_U% -p %CNTX_P% start %SQLSERVERAGENT%
timeout 30
%CNTX_PST% %CNTX_1C% -u %CNTX_U% -p %CNTX_P% start %SERVICE_1C_NAME%

Рассмотрим подробнее логику работы этого файла: скрипт сначала останавливает службу 1С и ждет завершения всех процессов rphost (таймаут 200 секунд). Затем останавливается SQL Server, после чего происходит безопасная очистка папок snccntx, в которых хранятся кэшированные данные сессий 1С. После этого все службы запускаются в обратном порядке.

---

Способ 3. Продвинутый скрипт перезапуска служб на PowerShell

Если вы предпочитаете современную объектную нотацию и хотите иметь подробное ведение логов работы скрипта, воспользуйтесь следующим сценарием на PowerShell. Этот скрипт выполняет безопасную остановку связанных служб (включая веб-серверы Apache/IIS и репозитории конфигураций), проверяет их реальное состояние без жестких "слепых" таймаутов, а также осуществляет повторные попытки запуска в случае непредвиденных сбоев.


#requires -Version 5.1
#requires -RunAsAdministrator

[CmdletBinding()]
param()

# === КОНФИГУРАЦИЯ ===
$Config = @{
    LogDir       = "C:\log1C"
    LogBaseName  = "Restart-Services"
    StopTimeout  = 30  # Максимальное время ожидания остановки (сек)
    StartTimeout = 30  # Максимальное время ожидания запуска (сек)
    RetryCount   = 2   # Количество попыток перезапуска при ошибке
}

$Config.LogFile = Join-Path $Config.LogDir "$($Config.LogBaseName).$(Get-Date -Format 'yyyy-MM').log"

if (-not (Test-Path $Config.LogDir)) { New-Item -ItemType Directory -Path $Config.LogDir -Force | Out-Null }

function Write-Log {
    param([string]$Message, [ValidateSet("INFO","WARN","ERROR")]$Level = "INFO")
    $timestamp = Get-Date -Format 'dd.MM.yyyy HH:mm:ss'
    $entry = "[$timestamp] [$Level] $Message"
    Add-Content -Path $Config.LogFile -Value $entry -Encoding UTF8
    Write-Host $entry
}

function Wait-ServiceState {
    param(
        [System.ServiceProcess.ServiceController]$Service,
        [string]$TargetState,
        [int]$TimeoutSec
    )
    $sw = [System.Diagnostics.Stopwatch]::StartNew()
    while ($Service.Status -ne $TargetState) {
        $Service.Refresh()
        if ($sw.Elapsed.TotalSeconds -ge $TimeoutSec) { return $false }
        Start-Sleep -Milliseconds 500
    }
    return $true
}

$ServiceDisplayNames = @(
    "Ras agent 1C",
    "Apache2.4",
    "1C:Enterprise 8.3 Configuration Repository Server",
    "1C:Enterprise 8.3 Server Agent (x86-64)",
    "SQLSERVERAGENT",
    "MSSQLSERVER"
)

Write-Log "Начало процесса обслуживания серверов 1С и СУБД..."

$Services = foreach ($name in $ServiceDisplayNames) {
    $svc = Get-Service -Name $name -ErrorAction SilentlyContinue
    if (-not $svc) { $svc = Get-Service -DisplayName $name -ErrorAction SilentlyContinue }
    if ($svc) {
        Write-Log "Найдена служба: '$name' -> Системное имя: '$($svc.Name)'"
        $svc
    } else {
        Write-Log "Служба '$name' не найдена. Будет пропущена." "WARN"
    }
}

if ($Services.Count -eq 0) {
    Write-Log "Не найдено ни одной службы из списка. Завершение работы." "ERROR"
    exit 1
}

# === ФАЗА 1: ОСТАНОВКА ===
Write-Log "=== [ФАЗА 1] Остановка всех служб ==="
foreach ($svc in $Services) {
    try {
        $svc.Refresh()
        if ($svc.Status -ne 'Stopped') {
            Write-Log "Остановка '$($svc.Name)' (было: $($svc.Status))..."
            Stop-Service -InputObject $svc -ErrorAction Stop
            
            if (Wait-ServiceState -Service $svc -TargetState 'Stopped' -TimeoutSec $Config.StopTimeout) {
                Write-Log "'$($svc.Name)' успешно остановлена."
            } else {
                Write-Log "Таймаут ожидания остановки '$($svc.Name)'." "WARN"
            }
        } else {
            Write-Log "'$($svc.Name)' уже остановлена."
        }
    } catch {
        Write-Log "Ошибка остановки '$($svc.Name)': $_" "ERROR"
    }
}

Start-Sleep -Seconds 60

# === ФАЗА 2: ЗАПУСК (В ОБРАТНОМ ПОРЯДКЕ) ===
Write-Log "=== [ФАЗА 2] Запуск всех служб ==="
for ($i = $Services.Count - 1; $i -ge 0; $i--) {
    $svc = $Services[$i]
    try {
        Write-Log "Запуск '$($svc.Name)'..."
        Start-Service -InputObject $svc -ErrorAction Stop
        
        if (Wait-ServiceState -Service $svc -TargetState 'Running' -TimeoutSec $Config.StartTimeout) {
            Write-Log "'$($svc.Name)' успешно запущена."
        } else {
            Write-Log "Таймаут ожидания запуска '$($svc.Name)'." "WARN"
        }
    } catch {
        Write-Log "Ошибка запуска '$($svc.Name)': $_" "ERROR"
    }
}

# === ФАЗА 3: ПРОВЕРКА И ВОССТАНОВЛЕНИЕ ===
Write-Log "=== [ФАЗА 3] Проверка финального состояния ==="
for ($i = $Services.Count - 1; $i -ge 0; $i--) {
    $svc = $Services[$i]
    $svc.Refresh()
    if ($svc.Status -ne 'Running') {
        Write-Log "'$($svc.Name)' не запущена (статус: $($svc.Status)). Попытка восстановления..." "WARN"
        $success = $false
        for ($r = 1; $r -le $Config.RetryCount -and -not $success; $r++) {
            try {
                Start-Service -InputObject $svc -ErrorAction Stop
                Start-Sleep -Seconds 3
                $svc.Refresh()
                if ($svc.Status -eq 'Running') {
                    $success = $true
                    Write-Log "'$($svc.Name)' успешно запущена после попытки $r."
                }
            } catch {
                Write-Log "Попытка запуска '$($svc.Name)' ($r) завершилась ошибкой: $_" "WARN"
            }
        }
    } else {
        Write-Log "'$($svc.Name)' работает в штатном режиме."
    }
}
Write-Log "=== Процесс перезапуска успешно завершен ==="

---

Способ 4. Оптимизация системной базы данных TempDB

Довольно часто ошибка "Недопустимое имя объекта" возникает из-за того, что СУБД физически не успевает расширить файлы базы данных tempdb во время выполнения тяжелых запросов. Настроим СУБД по лучшим практикам (Best Practices) администрирования 1С:

  1. Равномерное распределение файлов данных: Создайте несколько файлов данных для базы tempdb. Рекомендуемое количество — по числу физических ядер процессора (если ядер больше 8, начните с 8 файлов). Все файлы данных должны иметь строго одинаковый начальный размер и одинаковый шаг авторасширения.
  2. Ограничение лога транзакций: Убедитесь, что у tempdb настроен только один файл журнала транзакций (с расширением .ldf). Наличие нескольких файлов логов транзакций в tempdb часто приводит к задержкам и блокировкам СУБД.
  3. Начальный размер и авторасширение: Установите начальный размер каждого файла данных tempdb равным хотя бы 5–10 Гб (в зависимости от объемов вашей базы), чтобы СУБД не тратила ресурсы на динамическое расширение файлов в течение рабочего дня. Шаг авторасширения установите фиксированным — например, 512 МБ или 1024 МБ (избегайте настройки авторасширения в процентах).

---

Способ 5. Проверка сетевой стабильности и отключение TCP Chimney

Если сервер приложений 1С и SQL Server разнесены на разные хосты, микроскопические разрывы TCP-пакетов гарантированно приведут к уничтожению сессионных временных таблиц #tt. Проанализируем настройки сетевых адаптеров на обоих серверах.

Для предотвращения разрывов соединений рекомендуется отключить технологии разгрузки сети на уровне операционной системы. Запустите командную строку от имени Администратора на обоих серверах и выполните команды:


netsh int tcp set global chimney=disabled
netsh int tcp set global autotuninglevel=normal
netsh int ip set global taskoffload=disabled

Дополнительно в свойствах сетевого адаптера в диспетчере устройств (Device Manager) отключите параметры IPv4 Checksum Offload, Large Send Offload (LSO) и Receive Side Scaling (RSS). Это снизит вероятность потери пакетов данных между серверами.

Если сервер 1С и MS SQL Server установлены на одном физическом компьютере, убедитесь, что в качестве протокола сетевого взаимодействия в SQL Server Configuration Manager включен протокол Shared Memory (Общая память), а в строке подключения 1С в качестве имени сервера указан localhost или . (точка) — это позволит обмениваться данными напрямую через оперативную память, минуя сетевой стек TCP/IP.

---

Способ 6. Реструктуризация таблиц через Тестирование и Исправление

Иногда после обновления конфигурации (особенно ERP или КА) структура физических таблиц на SQL-сервере может частично разойтись с внутренними метаданными платформы 1С. В таком случае оптимизатор запросов СУБД строит неверный план выполнения, что вызывает падение фоновых заданий отчетов.

Для исправления структуры таблиц выполним реструктуризацию:

  1. Запустите базу данных в режиме Конфигуратора.
  2. Обязательно сделайте резервную копию базы данных (выгрузку .dt или средствами SQL Server Management Studio).
  3. Перейдите в меню Администрирование -> Тестирование и исправление...
  4. Установите флажок напротив пункта «Реструктуризация таблиц информационной базы».
  5. В поле «При наличии нарушений целостности» выберите пункт «Создавать объекты» или «Очищать ссылки» (в зависимости от политики вашей организации).
  6. Нажмите кнопку «Выполнить» и дождитесь окончания процесса.

---

Способ 7. Временный обходной путь для пользователя

Если у конкретного бухгалтера или аналитика прямо сейчас не формируется важный регламентированный отчет, а ИТ-отдел не может перезагрузить сервер приложений в разгар рабочего дня, можно применить "клиентский" обходной путь.

В настройках запуска информационной базы в окне запуска 1С измените режим запуска на Толстый клиент:

  1. В окне запуска выберите вашу информационную базу и нажмите кнопку «Изменить...».
  2. Перейдите на вкладку «Параметры запуска».
  3. В поле «Основной режим запуска» вместо значения «Выбирать автоматически» или «Тонкий клиент» установите значение «Толстый клиент».
  4. Нажмите «Готово» и запустите программу.

В ряде случаев при использовании толстого клиента выполнение длительных запросов перенаправляется на другие внутренние потоки платформы, минуя механизмы оптимизации фоновых заданий, что позволяет сформировать отчет без ошибки СУБД.

← На главную