0

私は CakePHP 2 に次のコードを持っています:

$this->Order->id = 5;
$this->Order->saveAll(array(
    'Order' => array(
        'person_id' => $this->Session->read('Person.id'),
        'amount' => $total,
        'currency_id' => $code                   
    ),
    'Lineitem' => $lineitems  /* a correctly-formatted array */
));

Orderこれにより、テーブルの主キーが 5 の行が更新されLineitem、order_id が 5 の行が挿入されると予想されます。

ただし、新しい行を作成し、新しいレコードOrderの新しい ID を使用して行を作成するだけです。OrderListitem

注:上記のように ID を設定しているのは、デバッグの目的と、この質問を簡単に説明するためだけです。最終的なコードでは、現在の保留中の注文が既に存在するかどうかを確認し、存在するかどうかを確認しperson_idます。$this->Order->id = $var;$this->Order->create();

つまり、INSERT したい場合もあれば (この場合は を発行$this->Order->create();します)、UPDATE したい場合もあります (この場合は を発行し$this->Order->id = $var;ます)。上記のテスト ケースは UPDATE を生成するはずですが、代わりに INSERT を生成しています。

私がここで間違っていることは何か分かりますか?

4

2 に答える 2

3

渡す配列にModel->saveAll()は注文の ID が含まれていないため、Cake は新しい ID を作成します。既存のレコードを更新したい場合は、渡された配列に注文 ID を設定するか、検索で取得します。ドキュメントは明示的に述べています

新しい値を作成するのではなく、値を更新する場合は、主キー フィールドをデータ配列に渡していることを確認してください。

$order = $this->Order->findById(5);
// ... modify $order if needed
$this->Order->saveAll(array('Order' => $order, 'LineItem' => $items));

あなたの場合、できるだけ簡潔にするために、次のようなものを使用することができます。Model::saveAssociated()に応じて作成または更新するのに十分スマートidですが、適切な入力を提供する必要があります。Model::read($fields, $id)internal$dataを初期化します。既存のレコードの場合、すべてのフィールドがデータベースから読み取られますが、存在しない ID の場合、成功するには正しいデータを提供する必要があります。注文が顧客であると仮定すると、注文belongsToが存在しない場合は顧客IDを提供します

// set the internal Model::$data['Order']
$this->Order->read(null, 5);
// You may want to supply needed information to create
// a new order if it doesn't exist, like the customer
if (! $this->Order->exists()) {
    $this->Order->set(array("Customer" => array("id" => $customer_id)));
}
$this->Order->set(array('LineItem' => $items));
$this->Order->saveAssociated();

最後に、ショッピング カートを実装しているようです。その場合は、フラグ付きのShoppingCart代わりにセパレートを使用する方が明確になるでしょう。Orderfinalized

于 2012-10-01T08:52:27.267 に答える
2

次のことを試しましたか?

$this->Order->saveAll(array(
    'Order' => array(
        'id' => 5,
        'person_id' => $this->Session->read('Person.id'),
        'amount' => $total,
        'currency_id' => $code                   
    ),
'Lineitem' => $lineitems  /* a correctly-formatted array */
));

それはあなたがしたこととほとんど同じです:

$this->Order->id = 5;

多分それはあなたの問題を解決するでしょう。Cakeは、idフィールドを設定しているかどうかをチェックしており、設定されている場合はレコードを更新し、見つからない場合は代わりに新しいレコードを作成します。

更新:次に、saveAllを実行する前にidフィールドがあるかどうかを確認し、確認結果をブール値に保存して、このブール値によって決定される保存する配列を作成します。次に例を示します。

if($id_exist) $order['Order']['id'] = 5;
$order['Order']['id'] = 5;
$order['Order']['person_id'] = $this->Session->read('Person.id'),
$order['Order']['amount'] = $total;
$order['Order']['currency_id'] = $code;

    $this->Order->saveAll(array(
    'Order' => $order,
'Lineitem' => $lineitems  /* a correctly-formatted array */
));
于 2012-10-01T08:59:43.967 に答える