1

私はこのようなcodeigniterモデルを持っています

<?php

class Model_Login extends CI_Model{
    function __construct(){
        parent::__construct();
    }

    public function login_submit($arrayData){
        extract($arrayData);
        $username=clean($txtusername);
        $password=clean($txtpassword);

        //first get salt for the respective user.
        $getsalt=$this->db->query("SELECT PASSWORD_SALT FROM USER_INFOS WHERE USER_NNAME=?",array($username))->row();
        $salt=$getsalt->PASSWORD_SALT;
        $password=sha1($salt.$password);

        $query=$this->db->query("SELECT * FROM USER_INFOS WHERE STATUS='Y' AND USER_NNAME=? AND USER_PASSWORD=?",array($username,$password));

        if($query->num_rows>0){
            $row=$query->row();
            // login successfull create session
            $this->session->set_userdata('USER_ID', $row->USER_ID);
            $this->session->set_userdata('USER_FULL_NAME', $row->USER_ENAME);

            return "success";
        }else{
            return "Invalid username and/or password.";
        }





    }
}

?>

ここで、PASSWORD_SALTは、関数を使用してハッシュされた128文字の長さのランダム(ユーザーごと)のソルトを含むデータベースフィールドですhash

USERNAMEが一意である場合、コードは完全に機能します。しかし、ユーザー名が一意であってはならないことを尋ねる可能性のあるクライアントについて考えようとしています。ユーザー名が一意でない場合は、常に最初の行が選択され、同じユーザー名を持つものを除いて、有効なユーザー名とパスワードが提供されていてもログインできません。

このシナリオでより良い回避策は何でしょうか?

編集

ユニークではないことを置くUSERNAMEのは悪い考えだと私は知っています。しかし、私たちの国には、ユーザー名が一意ではない(または、場合によってはユーザー名が予測可能でさえある)いくつかのWebサイトがあります。たとえば、銀行の特定の支店に支店コードが032、私の名前がJohn Smithであるアカウントがあり、そのebankingにアクセスするためのユーザー名はになり032JOHNSます。その支店には、最終的に同じユーザー名を持つ複数のJohnSmithが存在する可能性があります。そして、彼らのebankingシステムにログインするには、このユーザー名とパスワードを入力するだけです。

ありがとう

4

3 に答える 3

1

これの代わりに:

$getsalt=$this->db->query("SELECT PASSWORD_SALT FROM USER_INFOS WHERE USER_NNAME=?",array($username))->row();
        $salt=$getsalt->PASSWORD_SALT;
        $password=sha1($salt.$password);

        $query=$this->db->query("SELECT * FROM USER_INFOS WHERE STATUS='Y' AND USER_NNAME=? AND USER_PASSWORD=?",array($username,$password));

次のようなものを使用します。

$query=$this->db->query("SELECT * FROM USER_INFOS WHERE STATUS='Y' AND USER_NNAME=? AND USER_PASSWORD=SHA1(CONCAT(PASSWORD_SALT,?))",array($username,$password));
于 2012-11-01T06:09:51.253 に答える
1

絶対に一意でないユーザー名を使用する必要がある場合は、そのユーザー名を使用してすべてのユーザーをループし、それぞれのユーザーのパスワードを確認することができます。つまり、3 人のユーザーがユーザー名 foobar を持っていて、最初のパスワード チェックが失敗した場合、2 番目のチェックをチェックします。等々。

(注:これは絶対にお勧めしません。ユーザー名を一意にできない場合は、ログイン用の一意の識別子としてメール アドレスを使用してください)。

于 2012-11-01T06:05:44.190 に答える
1

ユーザー名が一意でない場合、ユーザーを一意に識別するものは何ですか?

ユーザーがログイン時に提供するものでなければならず、ユーザー名とパスワードの組み合わせであってはなりません。これは、2 人のユーザーが同じパスワードを選択しないという保証がないためです。

したがって、ユーザー名が一意でない場合は、他の何かが一意である必要があります (または、ユーザー名と組み合わせて一意である必要があります)。たとえば、カスタム ドメインによってある種のマルチテナントを行っている場合、それはドメインになります。

ただし、一意でないユーザー名を使用することはできず、パスワードが正しいユーザーを決定することを期待できません

(ちなみに、可能です、そうすべきではありません。たまたま、同じメール アドレスを使用して2 つの異なる Amazon アカウントにログインできてしまいましたが、パスワードが異なります。一方のパスワードをもう一方のパスワードと一致するように変更したらどうなるでしょうか。 、しかし、私は自分のアカウントを評価しすぎて試すことができません。)

于 2012-11-01T06:06:16.150 に答える