5

PHP 4.3.9、Apache/2.0.52を使用しています

ログインすると利用できるセッションにDB値を登録するログインシステムを機能させようとしています。リダイレクトされると、セッション変数が失われます。

次のコードを使用して、ログインフォームページとリダイレクトされたページにセッションID/値を出力しています。

echo '<font color="red">session id:</font> ' . session_id() . '<br>';
echo '<font color="red">session first name:</font> ' . $_SESSION['first_name'] . '<br>';
echo '<font color="red">session user id:</font> ' . $_SESSION['user_id'] . '<br>';
echo '<font color="red">session user level:</font> ' . $_SESSION['user_level'] . '<br><br>';

これは、ログインページからブラウザに出力されるものです(ログインページへのヘッダーリダイレクトをコメントアウトするだけです)。これは私のDBからの正しい情報でもあるので、この時点ではすべて問題ありません

session id: 1ce7ca8e7102b6fa4cf5b61722aecfbc
session first name: elvis
session user id: 2
session user level: 1

これは、リダイレクト/ログインしたページに印刷されるものです(ヘッダー/リダイレクトのコメントを解除したとき)。セッションIDは同じですが、個々のセッション変数の値が取得されません。

session id: 1ce7ca8e7102b6fa4cf5b61722aecfbc
session first name:
session user id:
session user level:

次のエラーが発生します。

未定義のインデックス:first_name
未定義のインデックス:user_id
未定義のインデックス:user_level

私のloggedIN.phpが呼び出さないグローバルheader.phpファイルがありますが、loggedOUT.phpは呼び出します-セッションをトーストします):

header.php

<?php
ob_start();
session_start();

//if NOT on loggedout.php, check for cookie. if exists, they haven't explicity logged out so take user to loggedin.php
if (!strpos($_SERVER['PHP_SELF'], 'loggedout.php')) {
    /*if (isset($_COOKIE['access'])) {
        header('Location: www.mydomain.com/loggedin.php');
    }*/
} else {
    //if on loggedout.php delete cookie
    //setcookie('access', '', time()-3600);

    //destroy session
    $_SESSION = array();
    session_destroy();
    setcookie(session_name(), '', time()-3600);
}

//defines constants and sets up custom error handler
require_once('config.php');

?><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">

some page layout stuff

Login portion is eventually called via include

footer stuff

私のloggedIN.phpはセッションを開始するだけです

<?php
session_start();
?><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">

ログインスクリプトのロジック。重要な部分は、DBの結果を$ _SESSIONに直接フェッチすることです(約半分下)。

if (isset($_POST['login'])) {
        //access db
        require_once(MYSQL);

        //initialize an errors array for non-filled out form fields
        $errors = array();

        //setup $_POST aliases, clean for db and trim any whitespace
        $email  = mysql_real_escape_string(trim($_POST['email']), $dbc);
        $pass   = mysql_real_escape_string(trim($_POST['pass']), $dbc);

        if (empty($email)) {
            $errors[] = 'Please enter your e-mail address.';
        }

        if (empty($pass)) {
            $errors[] = 'Please enter your password.';
        }

        //if all fields filled out and everything is OK
        if (empty($errors)) {
            //check db for a match
            $query = "SELECT user_id, first_name, user_level 
                    FROM the rest of my sql here, blah blah blah";

            $result = @mysql_query($query, $dbc) 
                OR trigger_error("Query: $query\n<br />MySQL Error: " . mysql_error($dbc));

            if (@mysql_num_rows($result) == 1) { //a match was made, OK to login

                //register the retrieved values into $_SESSION
                $_SESSION = mysql_fetch_array($result);
                mysql_free_result($result);
                mysql_close($dbc);
                /*              
                setcookie('access'); //if "remember me" not checked, session cookie, expires when browser closes
                                     //in FF you must close the tab before quitting/relaunching, otherwise cookie persists

                //"remember me" checked?
                if(isset($_POST['remember'])){ //expire in 1 hour (3600 = 60 seconds * 60 minutes)
                    setcookie('access', md5(uniqid(rand())), time()+60); //EXPIRES IN ONE MINUTE FOR TESTING
                }
                */

echo '<font color="red">cookie:</font> ' . print_r($_COOKIE) . '<br><br>';
echo '<font color="red">session id:</font> ' . session_id() . '<br>';
echo '<font color="red">session first name:</font> ' . $_SESSION['first_name'] . '<br>';
echo '<font color="red">session user id:</font> ' . $_SESSION['user_id'] . '<br>';
echo '<font color="red">session user level:</font> ' . $_SESSION['user_level'] . '<br><br>';

                ob_end_clean();
                session_write_close();

                $url = BASE_URL . 'loggedin_test2.php';
                header("Location: $url");
                exit();
            } else {
            //wrong username/password combo
            echo '<div id="errors"><span>Either the e-mail address or password entered is incorrect or you have not activated your account. Please try again.</span></div>';
            }

            //clear $_POST so the form isn't sticky
            $_POST = array();
        } else { 
        //report the errors
        echo '<div id="errors"><span>The following error(s) occurred:</span>';

            echo '<ul>';
            foreach($errors as $error) {
                echo "<li>$error</li>";
            }
            echo '</ul></div>';
        }

    } // end isset($_POST['login'])

ログインページでヘッダーリダイレクトをコメントアウトすると、DBからの正しい情報を使用して$_SESSION変数をエコーアウトできます。ただし、ログインページにリダイレクトされると、それらは消えて/設定されていません。

誰かアイデアはありますか?私はこれにほぼ一日を費やしてきましたが、それを理解するのにこれ以上近づいているとは言えません。

ところで、私は最近2つの簡単なテストページを作成しました。1つはセッションを開始し、いくつかの変数を設定し、フォーム送信を行って、セッション変数の読み取り/出力のみを行う2番目のページにリダイレクトしました。すべて正常に機能しているようです。メインアプリで実行している問題が発生しているだけです。

4

4 に答える 4

8

session_start()ログイン スクリプトにa がありません。$_SESSIONセッションを開始していない場合、配列に配置したデータをphpが保存するとは思いません。$_SESSIONまた、安全を期すために、全体を .xml で上書きするのではなく、明示的に変数を配列に配置し$_SESSION = mysql_fetch_array($result);ます。

于 2009-01-06T00:26:00.667 に答える
3

やってみてください

session_regenerate_id(true); 

の前に

session_write_close();

また。IMOがログインスクリプトを実行する最良の方法は次のとおりです。

ユーザーがアクセスしようとしているメインページ内でログインロジックを処理できるようにします。

  1. ユーザーが認証されていない場合、ユーザーはログインページに戻されます
  2. ユーザーが認証されると、$ _SESSION["auth"]などを取得します
  3. 次に、ユーザーがメインページまたは認証が必要な他のページを閲覧しているときに、$ _SESSION["auth"]が設定されているかどうかを確認するだけです。

そうすれば、リダイレクトの直前にセッションが保存されないという問題は発生しません。

于 2009-01-06T00:16:12.933 に答える
0

...他の回答に追加できます。スクリプトの最初の先頭に配置しないと、 session_start() が失敗するか、奇妙なことが発生することがあります。ヘッダー スクリプトで、次を試してください。

それ以外の

<?php
ob_start();
session_start();

置く

<?php
session_start();
ob_start();
于 2016-07-03T19:17:19.847 に答える
0

これを発見したとき、私は同様の問題を抱えていました:

http://www.w3schools.com/php/php_sessions.asp

session_start(); を入れなければなりません。任意の html タグの前

于 2016-11-05T19:00:52.997 に答える