【画面作成】ログイン画面③(データベース認証) | 自転車旅行とWebサービス

自転車旅行とWebサービス

しがないSEが自転車旅行にかまけながら自前Webサービス作成を目指す

セッション管理も大事だけど、その前にまずはキチっとしときたいな~と

思いまして、ID/パスの認証をソース直書きにしているのが気持ち悪くて気持ち悪くて・・・
というわけでDBに保存しているID/パスを照合してログインの可否を判断するプログラムを作成する。


・・・そのまえに


DBのテーブルが今まで適当なやつだったが、
もう少しまともなレイアウトにしたい。
そこでこんなふう↓なテーブルを作成する。

種々の項目については後で話すとして、大まかにはそういうレイアウトをとる。
プライマリキーは単純連番とし、運用上の一意キーはユニークキーとして別途作る。

え?そんなことするなら最初からユニークキーをプライマリキーにしとけばいいじゃない?
そういうこと言う人嫌いです


ちなみにこのテーブルはまだ正規化できる。
user_idとuser_passはmstm_user_idにより更に別のテーブルに切り出し可能

こういったまだ切り分けられるもの(関数従属しているものだっけか?)を含んでいないことを第二正規形と言うとか言わないとか

まあ、めんどくさいんでやりませんけどね!





これのテーブルクリエイト文はこう↓

CREATE TABLE
    mstm_user
    (
     mstm_user_id    INT(19)           NOT NULL AUTO_INCREMENT   ,
     user_id            VARCHAR(20)  NOT NULL                  ,
     user_pass        VARCHAR(20)  NOT NULL                  ,
     enable_kbn       CHAR(1)         NOT NULL DEFAULT '0'      ,
     del_l_flg           CHAR(1)         NOT NULL DEFAULT '0'      ,
     user_email       VARCHAR(100)                           ,
     user_rank        CHAR(3)               DEFAULT '   '    ,
     user_name       VARCHAR(100)                           ,
     user_point        DEC(13,4)                              ,
     ins_ymd          DATETIME        NOT NULL DEFAULT SYSDATE  ,
     ins_user          VARCHAR(20)  NOT NULL                  ,
     ins_class         VARCHAR(30)  NOT NULL                  ,
     upd_ymd         DATETIME                               ,
     upd_user         VARCHAR(20)                            ,
     upd_class        VARCHAR(30)                            ,
    
    
    
     PRIMARY KEY(mstm_user_id)
    );

アメブロのエディタにコピペしたらなんかインデントおかしくなったぞ・・・
個々の項目を説明する

mstm_user_id  :
テーブルの物理的なキー。
ORACLEではシーケンスオブジェクトを別に作って連番をとっていたが、
MySQLではAUTO_INCREMENTと書くだけでいけるようだ。すげぇ

AUTO_INCREMENTで連番を進めるので関係はないが、
連番をとるときにMAX(mstm_user_id)+1はダメ、ゼッタイ
トランザクションが絡みあうと頭がおかしくなって死ぬ

user_id,user_pass :
まあ今回はこれさえあればいいのだが・・・
MySQLのマニュアルによると10文字だけでほとんどの場合はいけるとあるが、
何かの場合に備えて20文字とっておく。

enable_kbn :
0→予約 1→現行(有効) 2→履歴
とする。ユーザー情報を論理削除するためのしかけ

del_l_flg :
0→有効 1→削除
削除とかはチマチマやってたらパフォーマンスの悪化を招く。
ここは一旦フラグを立てて、何がしかのタイミングで一気に削除したい。

user_email 
げんだいのWebアプリではひっすである。

user_rank :
そういうのがあると夢がふくらむのだ 

user_name
 :
ユーザーの表示名。

user_point :
そういうのがあると夢がふくらむのだ 

ins_ymd,ins_user,ins_class,upd_ymd,upd_user,upd_class :
データをトレースするのに必要。
これはワークテーブルを除くすべてのテーブルにつけたい項目である。
このやり方は住○電工のフレームワークのパクリである。


とまあ、こんな具合のテーブルをクリエイト・・・できない?!

デフォルト値にSYSDATEが使えんとはどういうことだ?

デフォルトは定数じゃないとダメだと?!


・・・仕方がない
デフォルト値はなしだ・・・
トリガーを使う手も考えたが毎回書くのは悪手だと思うからやめとく・・・


テーブル作成の次はユニークキー制約を作成する。
一緒にインデックスも作成。


CREATE UNIQUE INDEX
        I_MSTM_USR_ALT1
    USING BTREE
    ON
        mstm_user
        (
            user_id           ,
            user_pass         ,
            enable_kbn        ,
            del_l_flg
        );

ネーミングセンスは許してほしい。

ちなみに、
USING BTREE
とか書いてるが、B木だけじゃなくてハッシュも選択可能
検索コストはハッシュのほうが低い=検索が速いということらしい

B木が 根~枝~葉 と辿っていくのに対し、ハッシュ関数で一発だからだ

でもまあ、ユニークキーだしパフォーマンスの悪化を招くことはない・・・はず
(そもそもDBスペに落ちる程度の実力しかないので使いこなせない)




できたテーブルにデータを放り込む



ようやく本題。
ここにアクセスしてデータを照合するPerlプログラムを書く


#!"C:\Perl64\bin\perl.exe"

use CGI::Carp qw(fatalsToBrowser);
use CGI;

use lib './CMN/DCMN';
use CMN::DCMN::DCMN;

my $dcmn = CMN::DCMN::DCMN->new();



$cgi = CGI->new();

$uname = $cgi->param('uname');
$upass = $cgi->param('upass');


$dbh = $dcmn->DCMN_connect() or die "$!";


$sql = "SELECT "
       .    "COUNT(mstm_user_id) "
       ."FROM "
       .    "sato.mstm_user "
       ."WHERE "
       .    "user_id    = ? "
       ."AND "
       .    "user_pass  = ? "
       ."AND "
       .    "enable_kbn = 1 "
       ."AND "
       .    "del_l_flg  = 0 "

       ;
      
$sth = $dbh->prepare($sql);
$sth->execute("$uname", "$upass");

@result = $sth->fetchrow_array;
if ((@result[0] eq 1) ) {
    #OK
    print $cgi->header(-location => '../LoginOK.html');
} else {
    #NG
    print $cgi->header(-location => '../Login2.html');
}

$dbh->disconnect;


ぬーん
なんだろう・・・「インジェクション対策!」とWHERE句のパラメータをバインド変数にしたが
そうすると途端にぐじゃぐじゃしだす。
なんで$dbhにexecuteが入ってへんのや!

ここも共通部品にしたくなってきたが、あんまりやりすぎると
俺専用フレームワークができ上がってしまう。

ここはぐっとこらえてさっさとセッション管理に入る。