Ошибка Cannot modify header information - headers already sent

Если вы не новичок в PHP то скорее всего знаете что значит ошибка "Cannot modify header information - headers already sent by...". Это значит что вы пытаетесь отправить http заголовки, которые уже были отправлены в каком-то месте скрипта. Чаще всего это случается если нечаянно вставили пробел или пустую строку перед выводом PHP скрипта:

  1. ..
  2. <?php

Реже - файл может быть сохранен как "UTF-8 with BOM". То есть в начале файла добавляют байты 0xEF, 0xBB, 0xBF, сохраняемого в кодировке UTF-8. Это метка порядка байтов Юникода (англ. Byte Order Mark, BOM), по которым некоторые программы могут автоматически определить, является ли файл закодированным в UTF-8, однако файлы с такой сигнатурой могут некорректно обрабатываться РНР интерпретатором.

Для начала с помощью функции headers_sent() определим в каком скрипте и на какой строчке отправляются заголовки:

  1. if (headers_sent($filename, $linenum)) {
  2. echo "Заголовки уже отправлены в $filename на строке $linenum";
  3. }

В моем случае оказалось что один из модулей движка Bitrix выводил переменную $content которая являлась пустой строкой, содержащей байты BOM.
Перелопачивать около 50000 файлов битрикса и смотреть какой из них сохранен не так у меня не было никакого желания, проще было просто удалить BOM:

  1. if(substr($content, 0, 3) == pack('CCC', 0xef, 0xbb, 0xbf)) {
  2. $content = substr($content, 3);
  3. }