2008年2月15日

[PHP-users 33287] Re:MySql で二重書き込みを防ぐには?

ミカヤ様

お世話になります。

テーブル構造を以下に変更しました。
実際にエクスポートしたものです。

--

-- テーブルの構造 `counter2`
--

CREATE TABLE `counter2` (
`bid` int(10) NOT NULL,
`ac` int(11) NOT NULL DEFAULT '0',
`pc` int(11) NOT NULL DEFAULT '0',
`mb` int(11) NOT NULL DEFAULT '0',
`date` int(11) NOT NULL,
UNIQUE KEY `datebid` (`date`,`bid`)
) ENGINE=MyISAM DEFAULT CHARSET=ujis;

しかくうまく動作しませんでした。

phpで実行された実際のSQLは以下になります。
----------------------------------
INSERT INTO counter2
(datebid,date,bid,mb)
VALUES
(200802154,20080215,4,1)
ON DUPLICATE KEY UPDATE
mb=mb+1;
----------------------------------

DBで直接SQLを実行すると
#1054 - Unknown column 'datebid' in 'field list'

になってしまいます。

datebidというフィードが必要なのでしょうか?

お手数お掛けいたします。


萩原

----- Original Message -----
From: "池谷 美歌也" <mikaya_ikeya@xxxxx>
To: "'PHP-users ML'" <php-users@xxxxx>
Sent: Friday, February 15, 2008 5:31 PM
Subject: [PHP-users 33286] Re:MySql で二重書き込みを防ぐには?


> ミカヤです。
>
>> --
>> -- テーブルの構造 `counter2`
>> --
>>
>> CREATE TABLE `counter2` (
>> `bid` int(10) NOT NULL,
>> `ac` int(11) NOT NULL DEFAULT '0',
>> `pc` int(11) NOT NULL DEFAULT '0',
>> `mb` int(11) NOT NULL DEFAULT '0',
>> `date` int(11) NOT NULL,
>> UNIQUE KEY `bid` (`bid`),
>> UNIQUE KEY `date` (`date`)
>> ) ENGINE=MyISAM DEFAULT CHARSET=ujis;
>
> このユニークキーの設定では「複数」にユニークキーになってしまいます。
> この設定だとbidとdateのどちらもユニークでなければならないので望みのデータ保存は出来ません。
>
> 「複合」のユニークキーは下のように設定します。
> -- -------------------------------------
> CREATE TABLE IF NOT EXISTS `counter2` (
> `bid` int(10) NOT NULL,
> `ac` int(11) NOT NULL default '0',
> `pc` int(11) NOT NULL default '0',
> `mb` int(11) NOT NULL default '0',
> `date` int(11) NOT NULL,
> UNIQUE KEY `datebid` (`date`,`bid`)
> ) ENGINE=MyISAM DEFAULT CHARSET=ujis;
> -- -------------------------------------
> こうするとdateとbidのセットでユニーク、という設定になります。
>
>
>
>> $type = $_GET[type];
>> $bid = $_GET[bid];
>>
>> $sql = <<< EOSQL
>> INSERT INTO counter2
>> (datebid,date,bid,$type)
>> VALUES
>> ($m$bid,$m,$bid,1)
>> ON DUPLICATE KEY UPDATE
>> {$type}={$type}+1;
>> EOSQL;
>> mysql_query($sql);
> 説明が足りなかったのかも知れませんが、このコードはテーブルに「datebid」というユニークキーの列を追加したという前提で書いたものです。
> これをそのまま使用しても、テーブルにdatebidという列がないので普通にUnknown
> columnのエラーが出ませんか?
>
> 環境に合わせるなら次のようなコードになるんじゃないでしょうか。
> // -------------------------------------
> $type = $_GET[type];
> $bid = $_GET[bid];
>
> $sql = <<< EOSQL
> INSERT INTO counter2
> (date,bid,ac,$type)
> VALUES
> ($m,$bid,1,1)
> ON DUPLICATE KEY UPDATE
> ac=ac+1, {$type}={$type}+1;
> EOSQL;
> mysql_query($sql);
> // -------------------------------------
>
>
> あとおせっかいかもしれませんが、自動で吐き出すタグのURLとはいえGETのクエリ文字列をそのままSQLに埋め込むのは危険だと思いますよ。
> // -------------------------------------
> $type = mysql_real_escape_string($_GET[type]);
> $bid = mysql_real_escape_string($_GET[bid]);
> // -------------------------------------
> せめてこれくらいの対策はしたほうがいいです。
>
>
>> -----Original Message-----
>> From: php-users-bounces@xxxxx
>> [mailto:php-users-bounces@xxxxx] On Behalf Of 萩原
>> Sent: Friday, February 15, 2008 4:50 PM
>> To: PHP-users ML
>> Subject: [PHP-users 33284] Re:MySql で二重書き込みを防ぐには?
>>
>> ミヤカ様
>>
>> ありがとうございます。
>>
>> ご指示いただいたスクリプトを試してみました。
>> しかし、INSERTとUPDATEともにうまく処理されませんでした。
>>
>> 自分でもON DUPLICATE KEY について調べてみましたが、
>> 原因が特定できません。
>>
>> 何か基本的な事が間違っているのでしょうか?
>>
>> 今までのスクリプトをストップできないので、
>> counter2というテスト用テーブルを作成して試しています。
>>
>>
>>
>> //カウント
>> if(!$res[0]){ //なかったらインサート
>>
>> $sql = "insert into counter set bid = '$_GET[bid]',date =
>> '$m',$_GET[type] = '1',ac = '1'"; mysql_query($sql); echo $sql;
>>
>> }else if($res[0]){ //あったらカウント追加
>>
>> $sql = "update counter set $_GET[type] = $_GET[type]+1,ac =
>> ac+1 where date = '$m' && bid = '$_GET[bid]'";
>>
>> mysql_query($sql);
>> echo $sql;
>>
>> }
>>
>> ここまでは正常に処理されています
>>
>> //カウント(ここからご指示いただいたスクリプトテストです)
>> $type = $_GET[type];
>> $bid = $_GET[bid];
>>
>> $sql = <<< EOSQL
>> INSERT INTO counter2
>> (datebid,date,bid,$type)
>> VALUES
>> ($m$bid,$m,$bid,1)
>> ON DUPLICATE KEY UPDATE
>> {$type}={$type}+1;
>> EOSQL;
>> mysql_query($sql);
>>
>>
>> --
>> -- テーブルの構造 `counter2`
>> --
>>
>> CREATE TABLE `counter2` (
>> `bid` int(10) NOT NULL,
>> `ac` int(11) NOT NULL DEFAULT '0',
>> `pc` int(11) NOT NULL DEFAULT '0',
>> `mb` int(11) NOT NULL DEFAULT '0',
>> `date` int(11) NOT NULL,
>> UNIQUE KEY `bid` (`bid`),
>> UNIQUE KEY `date` (`date`)
>> ) ENGINE=MyISAM DEFAULT CHARSET=ujis;
>>
>>
>> ※以下のタグでカウンターを読み込んでいます
>>
>> <img src='http://******.***/count.php?bid=1&type=pc'
>> width="1" height="1">
>>
>> お忙しいところお手数お掛けいたします。
>>
>>
>> 萩原
>>
>
> _______________________________________________
> PHP-users mailing list PHP-users@xxxxx
> http://ml.php.gr.jp/mailman/listinfo/php-users
> PHP初心者のためのページ - 質問する前にはこちらをお読みください
> http://oldwww.php.gr.jp/php/novice.php3
>

_______________________________________________
PHP-users mailing list PHP-users@xxxxx
http://ml.php.gr.jp/mailman/listinfo/php-users
PHP初心者のためのページ - 質問する前にはこちらをお読みください
http://oldwww.php.gr.jp/php/novice.php3

投稿者 xml-rpc : 2008年2月15日 19:22
役に立ちました?:
過去のフィードバック 平均:(0) 総合:(0) 投票回数:(0)
本記事へのTrackback: http://hoop.euqset.org/blog/mt-tb2006.cgi/69760
トラックバック
コメント
コメントする




画像の中に見える文字を入力してください。