2

DBにサブスクリプションを実装しています。メールは一意である必要があるため、データベースにUNIQUEインデックスがあります。私は私のページの初期化にこのコードを持っています:

$f = $p->add('MVCForm');
$f->setModel('Account',array('name','surname','email'));
$f->elements['Save']->setLabel('Subscribe');

if($f->isSubmitted())
{
    try
    {
         $f->update();

         //More useful code to execute when all is ok :)

    }
    catch(Exception_ValidityCheck $v)
    {
        //Handles validity constraint from the model
        $f->getElement($v->getField())->displayFieldError($v->getMessage());
    }
    catch(SQLException $se)
    {
        //If I'm here there is a problem with the db/query or a duplicate email
    }
}

の唯一の情報SQLExceptionはフォーマットされたHTMLメッセージですが、これはエラーが重複したエントリからのものであるかどうかを検出する唯一の方法ですか?

4

3 に答える 3

1

これを行う1つの方法は次のとおりです。

https://github.com/atk4/atk4-web/blob/master/lib/Model/ATK/User.php#L95

複製に対してカスタムアクションを実行する場合でも、getByをモデルの外のページのロジックに移動する必要があります。

于 2011-10-07T00:41:01.087 に答える
0

@Colが提案したように、「挿入無視」を使用します。

$ form-> update()はModel-> update()に依存し、Model-> update()はクエリの構築にDSQLクラスに依存します。DSQLはオプションをサポートしていますが、モデルは新しいSQLを生成します。

Model-> dsql()は、モデルのクエリを作成します。複数の「インスタンス」で機能でき、各インスタンスには個別のクエリがあります。私はこのアプローチが特に好きではなく、新しいモデルクラスを追加する可能性がありますが、今のところは機能します。

こちらをご覧ください: https ://github.com/atk4/atk4-addons/blob/master/mvc/Model/MVCTable.php#L933

insertRecord()関数はdsql('modify'、false)を数回呼び出して、クエリを作成します。おそらく、あなたができる最も簡単なことは次のとおりです。

function insertRecord($data=array()){
    $this->dsql('modify',false)->option('IGNORE');
    return parent::insertRecord($data);
}

レコードが挿入された後、AgileToolkitは新しく追加されたレコードを自動的にロードしようとします。ただし、関連する条件を使用します。レコードが無視された場合よりも、とにかく例外が発生すると思います。可能であれば、ワークフローの例外を回避してください。例外はバックトレースをキャプチャするため、CPUに負荷がかかります。

唯一の方法は、insertRecordを完全に再定義することかもしれません。理想的ではありませんが、必要に応じて1つのクエリを実行できます。

モデルの条件を考慮して結合するため、loadBy(またはgetBy)を使用して手動で条件を確認することをお勧めします。たとえば、テーブルにソフト削除があり、MySQLキーでは入力できませんが、Modelは入力でき、model-wayはビジネスロジックにとっても理にかなっています。

于 2011-10-07T01:00:14.850 に答える
-1

単純な選択を実行して、電子メールがすでに受信されているかどうかを確認してみませんか?

または、INSERT IGNOREにして、affected_rowsを確認します。

于 2011-10-06T11:11:12.053 に答える