Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > PHP: Общие вопросы > использование header('location: ')


Автор: s0lman 21.1.2008, 14:45
Здравствуйте.
Имею элементарное подобие админпанели
файл switch.php
Код

Error_Reporting(E_ALL & ~E_NOTICE);
define('CONFIG',$_SERVER['DOCUMENT_ROOT'].'/config.php');
include(CONFIG);
define('SETCONFIG', 'http://' . $_SERVER['SERVER_NAME'].'/'.$setconfig);
if(fopen(CONFIG,"rb")){    
switch($sendto){
        case "one": {echo "<a href='".SETCONFIG."?both'>Включить переадресацию</a>";break;}
        case "both": {echo "<a href='".SETCONFIG."?one'>Отключить переадресацию</a>";break;}
    }}


config.php
Код

$sendto = "one";

$switch = "switch.php";

$setconfig = "setconfig.php";


setconfig.php
Код

Error_Reporting(E_ALL & ~E_NOTICE);
define('CONFIG',$_SERVER['DOCUMENT_ROOT'].'/config.php');
include(CONFIG);
if(isset($_GET['both'])){$confmas['sendto']="both";header('location: '.$switch);}
if(isset($_GET['one'])){$confmas['sendto']="one";header('location: '.$switch);}
$confmas['switch']=$switch;
$confmas['setconfig']=$setconfig;

...
 запись в файл
...

теперь собственно вопрос.
почему после щелчка по ссылке "Включить переадресацию" получаю сообщение
Warning: Cannot modify header information - headers already sent by (output started at /sata1/home/users/creditonl/www/www.credit-online.in.ua/config.php:15) in /sata1/home/users/creditonl/www/www.credit-online.in.ua/setconfig.php on line 12
хотя нужное значение в config.php записывается.
отключение же проходит "гладко".

Автор: GeneralElectric 21.1.2008, 15:39
во-первых, после заголовка Location нельзя писать никакой код. поскольку нет гарантии, что он будет выполнен.
во-вторых, тебе же все пишет: в 15 строке файла  config.php идет вывод в браузер. следовательно, заголовки уже отправить нельзя.
подробнее можно почитать здесь: http://phpfaq.ru/headers

Добавлено через 1 минуту и 14 секунд
ой! а зачем ты открываешь config.php на чтение?

Автор: s0lman 21.1.2008, 15:58
Цитата(GeneralElectric @ 21.1.2008,  15:39)
а зачем ты открываешь config.php на чтение?

действительно.... зачем?  smile 
но на конечный результат ессесно не влияет.

Автор: MoLeX 21.1.2008, 16:07
Цитата(s0lman @  21.1.2008,  15:58 Найти цитируемый пост)
действительно.... зачем? 

это у тебя надо спрашивать уважаемый)

Автор: s0lman 21.1.2008, 16:34
единственное не пойму - какой вывод в config.php?
там только присваивание значений переменным.

Автор: smartov 21.1.2008, 16:42
s0lman, 
Цитата(s0lman @  21.1.2008,  13:45 Найти цитируемый пост)
почему после щелчка по ссылке "Включить переадресацию" получаю сообщение

После header('Location...') должен сразу идти exit;
Код

if(isset($_GET['both'])){$confmas['sendto']="both";header('location: '.$switch);exit;}
if(isset($_GET['one'])){$confmas['sendto']="one";header('location: '.$switch);exit;}


В 12 строке файла setconfig.php скорее всего возникает notice или warning, который не может корректно появиться потому, что хедеры уже отправлены ранее.

---

Вышенаписанное неверно

Автор: vasac 21.1.2008, 19:44
Цитата(GeneralElectric @  21.1.2008,  15:39 Найти цитируемый пост)
во-первых, после заголовка Location нельзя писать никакой код. поскольку нет гарантии, что он будет выполнен.

Что за чепухень? Какая разница интерпретатору, что там было послано в функции header()?
Более того, после Location по-правильному желательно вывести страницу, с описанием ситуации, и, не плохо бы, META-переадресацией.

Автор: GeneralElectric 21.1.2008, 20:46
интерпретатору такая разница, что ему браузер закроет соединение. и скрипт завершится.

по поводу канонической отработки Location - это да. соглашусь, что желательно писать текстовое сообщение и ссылку.
но на практике, поскольку никто никогда не сталкивался с клиентами, не поддерживающими 3хх, этим все пренебрегают.

Автор: Staind 21.1.2008, 20:49
Цитата

Что за чепухень? Какая разница интерпретатору, что там было послано в функции header()?

Человек же привел статью, если читать влом, не пишите глупостей: http://phpfaq.ru/headers

Автор: GeneralElectric 21.1.2008, 21:09
Staind, в статье речь о том, что пишется до header
а здесь разговор зашёл о том, что после =)

Автор: Staind 21.1.2008, 22:47
Понял, значит вот статейка: http://www.php.su/functions/?header

Автор: GeneralElectric 21.1.2008, 23:19
Гм. Ну, там я тоже не увидел по теме разговора.
Она, напомню, состоит в том, что я порекомендовал не полагаться на то, что код, следующий за location, будет весь исполнен.
то есть, ситуация, противоположная установке exit - здесь exit не ставится специально.
Хотя теперь я в этом не уверен. Надо автора спросить

Автор: smartov 21.1.2008, 23:29
Код после header('location...') может быть при чем какой угодно. Что тут такого. Просто нужно помнить, что хедеры отосланы, и при попытке вывести echo что-нибудь php сам попытается заново отослать хедеры, что у него, естественно, не получится.

Автор: flashaa 21.1.2008, 23:53
Цитата(smartov @  21.1.2008,  16:42 Найти цитируемый пост)
скорее всего возникает notice или warning,

Ещё могут быть лишние фрагменты текста вне тегов <?php ?> - тоже частые и трудновылавливаемые грабли.
К примеру:
Код

<?php
...
?> \n

Любой текст вне тегов <?php ?> будет вывыден в браузер,  в примере - лишний перенос строки в конце. При чем проверять надо все включаемые до header() файлы.

Автор: s0lman 21.1.2008, 23:59
Да господа если кого-то интересует
после location прописал .$_SERVER['HTTP_REFERER'] и все отлично работает  smile 
хотя чем это принципиально отличается от того что было я так и не понял.

Автор: GeneralElectric 22.1.2008, 00:09
smartov, 
Цитата(smartov @  21.1.2008,  23:29 Найти цитируемый пост)
Код после header('location...') может быть при чем какой угодно

Смотря что имеется в виду под "при чем".

Цитата(smartov @  21.1.2008,  23:29 Найти цитируемый пост)
Просто нужно помнить, что хедеры отосланы, и при попытке вывести echo что-нибудь php сам попытается заново отослать хедеры, что у него, естественно, не получится. 

Да ну, все у него получится.
Если контент тайп уже ушел, то он и не будет пытаться. а если нет - то отправит, и это прекрасно у него получится.

Добавлено @ 00:10
s0lman, HTTP_REFERER нельзя писать в Location

Автор: smartov 22.1.2008, 13:10
GeneralElectric, 
Цитата(GeneralElectric @  21.1.2008,  23:09 Найти цитируемый пост)
Да ну, все у него получится.
Если контент тайп уже ушел, то он и не будет пытаться

То есть по-твоему Content-Type нормально уйдет после Location и все будет ок?  smile 

Автор: GeneralElectric 22.1.2008, 13:23
Да, я думаю - да.
Вообще, интересно. Надо попробовать. 
Но на чем-то же основана рекомендация после локейшена писать кучерявый текст, который браузер покажет, если не поддерживает локейшен. Какой-то ведь тип у этого текста должен быть.

Автор: smartov 22.1.2008, 14:33
GeneralElectric, о, натюрлихъ. Извиняюсь ошибся. Вывод не должен уйти до location, после - можно. 

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)