source: branches/version-2_12-dev/data/class/SC_Product.php @ 21433

Revision 21433, 32.6 KB checked in by Seasoft, 10 years ago (diff)

#1626 (SQLチューニングによる商品一覧処理の高速化)

  • Property svn:eol-style set to LF
  • Property svn:keywords set to Id
  • Property svn:mime-type set to text/x-httpd-php; charset=UTF-8
Line 
1<?php
2/*
3 * This file is part of EC-CUBE
4 *
5 * Copyright(c) 2000-2011 LOCKON CO.,LTD. All Rights Reserved.
6 *
7 * http://www.lockon.co.jp/
8 *
9 * This program is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU General Public License
11 * as published by the Free Software Foundation; either version 2
12 * of the License, or (at your option) any later version.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
22 */
23
24/**
25 * 商品を扱うサービスクラス.
26 *
27 * @author LOCKON CO.,LTD.
28 * @author Kentaro Ohkouchi
29 * @version $Id$
30 */
31class SC_Product {
32
33    /** 規格名一覧 */
34    var $arrClassName;
35    /** 規格分類名一覧 */
36    var $arrClassCatName;
37    var $classCategories = array();
38    var $stock_find;
39    /** 規格1クラス名 */
40    var $className1 = '';
41    /** 規格2クラス名 */
42    var $className2 = '';
43    /** 規格1が設定されている */
44    var $classCat1_find;
45    /** 規格2が設定されている */
46    var $classCat2_find;
47    var $classCats1;
48    /** 検索用並び替え条件配列 */
49    var $arrOrderData;
50
51    /**
52     * 商品検索結果の並び順を指定する。
53     *
54     * ただし指定できるテーブルはproduct_idを持っているテーブルであることが必要.
55     *
56     * @param string $col 並び替えの基準とするフィールド
57     * @param string $table 並び替えの基準とするフィールドがあるテーブル
58     * @param string $order 並び替えの順序 ASC / DESC
59     * @return void
60     */
61    function setProductsOrder($col, $table = 'dtb_products', $order = 'ASC') {
62        $this->arrOrderData = array('col' => $col, 'table' => $table, 'order' => $order);
63    }
64
65    /**
66     * SC_Queryインスタンスに設定された検索条件を元に並び替え済みの検索結果商品IDの配列を取得する。
67     *
68     * 検索条件は, SC_Query::setWhere() 関数で設定しておく必要があります.
69     *
70     * @param SC_Query $objQuery SC_Query インスタンス
71     * @param array $arrVal 検索パラメーターの配列
72     * @return array 商品IDの配列
73     */
74    function findProductIdsOrder(&$objQuery, $arrVal = array()) {
75        $table = <<< __EOS__
76            dtb_products AS alldtl
77__EOS__;
78        $objQuery->setGroupBy('alldtl.product_id');
79        if(is_array($this->arrOrderData) and $objQuery->order == ""){
80            $o_col = $this->arrOrderData['col'];
81            $o_table = $this->arrOrderData['table'];
82            $o_order = $this->arrOrderData['order'];
83            $order = <<< __EOS__
84                    (
85                        SELECT $o_col
86                        FROM
87                            $o_table as T2
88                        WHERE T2.product_id = alldtl.product_id
89                        ORDER BY T2.$o_col $o_order
90                        LIMIT 1
91                    ) $o_order, product_id
92__EOS__;
93            $objQuery->setOrder($order);
94        }
95        $results = $objQuery->select('alldtl.product_id', $table, "", $arrVal,
96                                     MDB2_FETCHMODE_ORDERED);
97        $resultValues = array();
98        foreach ($results as $val) {
99            $resultValues[] = $val[0];
100        }
101        return $resultValues;
102    }
103
104    /**
105     * SC_Queryインスタンスに設定された検索条件をもとに対象商品数を取得する.
106     *
107     * 検索条件は, SC_Query::setWhere() 関数で設定しておく必要があります.
108     *
109     * @param SC_Query $objQuery SC_Query インスタンス
110     * @param array $arrVal 検索パラメーターの配列
111     * @return array 対象商品ID数
112     */
113    function findProductCount(&$objQuery, $arrVal = array()) {
114        $table = <<< __EOS__
115            dtb_products AS alldtl
116__EOS__;
117        return $objQuery->count($table, '', $arrVal);
118    }
119
120    /**
121     * SC_Queryインスタンスに設定された検索条件をもとに商品一覧の配列を取得する.
122     *
123     * 主に SC_Product::findProductIds() で取得した商品IDを検索条件にし,
124     * SC_Query::setOrder() や SC_Query::setLimitOffset() を設定して, 商品一覧
125     * の配列を取得する.
126     *
127     * @param SC_Query $objQuery SC_Query インスタンス
128     * @return array 商品一覧の配列
129     */
130    function lists(&$objQuery) {
131        $col = <<< __EOS__
132             product_id
133            ,product_code_min
134            ,product_code_max
135            ,name
136            ,comment1
137            ,comment2
138            ,comment3
139            ,main_list_comment
140            ,main_image
141            ,main_list_image
142            ,price01_min
143            ,price01_max
144            ,price02_min
145            ,price02_max
146            ,stock_min
147            ,stock_max
148            ,stock_unlimited_min
149            ,stock_unlimited_max
150            ,deliv_date_id
151            ,status
152            ,del_flg
153            ,update_date
154__EOS__;
155        $res = $objQuery->select($col, $this->alldtlSQL());
156        return $res;
157    }
158
159
160    /**
161     * 商品IDを指定し、商品一覧を取得する
162     *
163     * SC_Query::setOrder() や SC_Query::setLimitOffset() を設定して, 商品一覧
164     * の配列を取得する.
165     * FIXME: 呼び出し元で設定した、SC_Query::setWhere() も有効に扱いたい。
166     *
167     * @param SC_Query $objQuery SC_Query インスタンス
168     * @param array|int $arrProductId 商品ID
169     * @return array 商品一覧の配列 (キー: 商品ID)
170     */
171    function getListByProductIds(&$objQuery, $arrProductId = array()) {
172        if (empty($arrProductId)) {
173            return array();
174        }
175
176        $where = 'alldtl.product_id IN (' . implode(',', array_fill(0, count($arrProductId), '?')) . ')';
177        $where .= ' AND alldtl.del_flg = 0';
178
179        $objQuery->setWhere($where, $arrProductId);
180        $arrProducts = $this->lists($objQuery);
181
182        // 配列のキーを商品IDに
183        $arrTmp = array();
184        foreach($arrProducts as $arrProduct) {
185            $arrTmp[$arrProduct['product_id']] = $arrProduct;
186        }
187        $arrProducts =& $arrTmp;
188        unset($arrTmp);
189
190        // SC_Query::setOrder() の指定がない場合、$arrProductId で指定された商品IDの順に配列要素を並び替え
191        if (strlen($objQuery->order) === 0) {
192            $arrTmp = array();
193            foreach ($arrProductId as $product_id) {
194                $arrTmp[$product_id] = $arrProducts[$product_id];
195            }
196            $arrProducts =& $arrTmp;
197            unset($arrTmp);
198        }
199
200        return $arrProducts;
201    }
202
203    /**
204     * 商品詳細を取得する.
205     *
206     * @param integer $productId 商品ID
207     * @return array 商品詳細情報の配列
208     */
209    function getDetail($productId) {
210        $objQuery =& SC_Query_Ex::getSingletonInstance();
211        $result = $objQuery->select("*", $this->alldtlSQL('product_id = ?'),
212                                    "product_id = ?",
213                                    array($productId, $productId));
214        return $result[0];
215    }
216
217    /**
218     * 商品詳細情報と商品規格を取得する.
219     *
220     * @param integer $productClassId 商品規格ID
221     * @return array 商品詳細情報と商品規格の配列
222     */
223    function getDetailAndProductsClass($productClassId) {
224        $result = $this->getProductsClass($productClassId);
225        $result = array_merge($result, $this->getDetail($result['product_id']));
226        return $result;
227    }
228
229    /**
230     * 商品IDに紐づく商品規格を自分自身に設定する.
231     *
232     * 引数の商品IDの配列に紐づく商品規格を取得し, 自分自身のフィールドに
233     * 設定する.
234     *
235     * @param array $arrProductId 商品ID の配列
236     * @param boolean $has_deleted 削除された商品規格も含む場合 true; 初期値 false
237     * @return void
238     */
239    function setProductsClassByProductIds($arrProductId, $has_deleted = false) {
240
241        $arrProductsClass = array();
242        foreach ($arrProductId as $productId) {
243            $arrProductClass = $this->getProductsClassFullByProductId($productId, $has_deleted);
244
245            $classCats1 = array();
246            $classCats1['__unselected'] = '選択してください';
247
248            // 規格1クラス名
249            $this->className1[$productId] =
250                isset($arrProductClass[0]['class_name1'])
251                ? $arrProductClass[0]['class_name1']
252                : '';
253
254            // 規格2クラス名
255            $this->className2[$productId] =
256                isset($arrProductClass[0]['class_name2'])
257                ? $arrProductClass[0]['class_name2']
258                : '';
259
260            // 規格1が設定されている
261            $this->classCat1_find[$productId] = (!SC_Utils_Ex::isBlank($arrProductClass[0]['classcategory_id1']));
262            // 規格2が設定されている
263            $this->classCat2_find[$productId] = (!SC_Utils_Ex::isBlank($arrProductClass[0]['classcategory_id2']));
264
265            $this->stock_find[$productId] = false;
266            $classCategories = array();
267            $classCategories['__unselected']['__unselected']['name'] = '選択してください';
268            $classCategories['__unselected']['__unselected']['product_class_id'] = $arrProductClass[0]['product_class_id'];
269            // 商品種別
270            $classCategories['__unselected']['__unselected']['product_type'] = $arrProductClass[0]['product_type_id'];
271            $this->product_class_id[$productId] = $arrProductClass[0]['product_class_id'];
272            // 商品種別
273            $this->product_type[$productId] = $arrProductClass[0]['product_type_id'];
274            foreach ($arrProductClass as $productsClass) {
275                $classCats2 = array();
276                $productsClass1 = $productsClass['classcategory_id1'];
277                $productsClass2 = $productsClass['classcategory_id2'];
278                // 在庫
279                $stock_find_class = ($productsClass['stock_unlimited'] || $productsClass['stock'] > 0);
280
281                $classCats2['classcategory_id2'] = $productsClass2;
282                $classCats2['name'] = $productsClass['classcategory_name2'] . ($stock_find_class ? '' : ' (品切れ中)');
283
284                $classCats2['stock_find'] = $stock_find_class;
285
286                if ($stock_find_class) {
287                    $this->stock_find[$productId] = true;
288                }
289
290                if (!in_array($classcat_id1, $classCats1)) {
291                    $classCats1[$productsClass1] = $productsClass['classcategory_name1']
292                        . ($productsClass2 == 0 && !$stock_find_class ? ' (品切れ中)' : '');
293                }
294
295                // 価格
296                $classCats2['price01']
297                    = strlen($productsClass['price01'])
298                    ? number_format(SC_Helper_DB_Ex::sfCalcIncTax($productsClass['price01']))
299                    : '';
300
301                $classCats2['price02']
302                    = strlen($productsClass['price02'])
303                    ? number_format(SC_Helper_DB_Ex::sfCalcIncTax($productsClass['price02']))
304                    : '';
305
306                // ポイント
307                $classCats2['point']
308                    = number_format(SC_Utils_Ex::sfPrePoint($productsClass['price02'], $productsClass['point_rate']));
309
310                // 商品コード
311                $classCats2['product_code'] = $productsClass['product_code'];
312                // 商品規格ID
313                $classCats2['product_class_id'] = $productsClass['product_class_id'];
314                // 商品種別
315                $classCats2['product_type'] = $productsClass['product_type_id'];
316
317                // #929(GC8 規格のプルダウン順序表示不具合)対応のため、2次キーは「#」を前置
318                if (SC_Utils_Ex::isBlank($productsClass1)) {
319                    $productsClass1 = '__unselected2';
320                }
321                $classCategories[$productsClass1]['#'] = array(
322                    'classcategory_id2' => '',
323                    'name' => '選択してください',
324                );
325                $classCategories[$productsClass1]['#' . $productsClass2] = $classCats2;
326            }
327
328            $this->classCategories[$productId] = $classCategories;
329
330            // 規格1
331            $this->classCats1[$productId] = $classCats1;
332        }
333    }
334
335    /**
336     * SC_Query インスタンスに設定された検索条件を使用して商品規格を取得する.
337     *
338     * @param SC_Query $objQuery SC_Queryインスタンス
339     * @param array $params 検索パラメーターの配列
340     * @return array 商品規格の配列
341     */
342    function getProductsClassByQuery(&$objQuery, $params) {
343        // 末端の規格を取得
344        $col = <<< __EOS__
345            T1.product_id,
346            T1.stock,
347            T1.stock_unlimited,
348            T1.sale_limit,
349            T1.price01,
350            T1.price02,
351            T1.point_rate,
352            T1.product_code,
353            T1.product_class_id,
354            T1.del_flg,
355            T1.product_type_id,
356            T1.down_filename,
357            T1.down_realfilename,
358            T2.class_combination_id,
359            T2.parent_class_combination_id,
360            T2.classcategory_id,
361            T2.level,
362            T3.name AS classcategory_name,
363            T3.rank,
364            T4.name AS class_name,
365            T4.class_id
366__EOS__;
367        $table = <<< __EOS__
368                      dtb_products_class T1
369            LEFT JOIN dtb_class_combination T2
370                   ON T1.class_combination_id = T2.class_combination_id
371            LEFT JOIN dtb_classcategory T3
372                   ON T2.classcategory_id = T3.classcategory_id
373            LEFT JOIN dtb_class T4
374                   ON T3.class_id = T4.class_id
375__EOS__;
376
377        $objQuery->setOrder('T3.rank DESC'); // XXX
378        $arrRet = $objQuery->select($col, $table, "", $params);
379        $levels = array();
380        $parents = array();
381        foreach ($arrRet as $rows) {
382            $levels[] = $rows['level'];
383            $parents[] = $rows['parent_class_combination_id'];
384        }
385        $level = max($levels);
386        $parentsClass = array();
387        // 階層分の親を取得
388        for ($i = 0; $i < $level -1; $i++) {
389            $objQuery =& SC_Query_Ex::getSingletonInstance();
390            $objQuery->setWhere('T1.class_combination_id IN (' . implode(', ', array_pad(array(), count($parents), '?')) . ')');
391
392            $col = <<< __EOS__
393                T1.class_combination_id,
394                T1.classcategory_id,
395                T1.parent_class_combination_id,
396                T1.level,
397                T2.name AS classcategory_name,
398                T2.rank,
399                T3.name AS class_name,
400                T3.class_id
401__EOS__;
402            $table = <<< __EOS__
403                          dtb_class_combination T1
404                LEFT JOIN dtb_classcategory T2
405                       ON T1.classcategory_id = T2.classcategory_id
406                LEFT JOIN dtb_class T3
407                       ON T2.class_id = T3.class_id
408__EOS__;
409
410            $objQuery->setOrder('T2.rank DESC'); // XXX
411            $arrParents = $objQuery->select($col, $table, "", $parents);
412
413            foreach ($arrParents as $rows) {
414                $parents[] = $rows['parent_class_combination_id'];
415
416                foreach ($arrRet as $child) {
417                    if ($child['parent_class_combination_id']
418                        == $rows['class_combination_id']) {
419                        $rows['product_id'] = $child['product_id'];
420                    }
421                }
422                $tmpParents[] = $rows;
423            }
424            $parentsClass = array_merge($parentsClass, $tmpParents);
425        }
426
427        // 末端から枝を作成
428        $tmpClass = array_merge($arrRet, $parentsClass);
429
430        foreach ($tmpClass as $val) {
431            $val['class_id' . $val['level']] = $val['class_id'];
432            $val['class_name' . $val['level']] = $val['class_name'];
433            $val['classcategory_name' . $val['level']] = $val['classcategory_name'];
434            $val['classcategory_id' . $val['level']] = $val['classcategory_id'];
435            $arrProductsClass[] = $val;
436        }
437        return $arrProductsClass;
438    }
439
440    /**
441     * 商品規格IDから商品規格を取得する.
442     *
443     * 削除された商品規格は取得しない.
444     *
445     * @param integer $productClassId 商品規格ID
446     * @return array 商品規格の配列
447     */
448    function getProductsClass($productClassId) {
449        $objQuery =& SC_Query_Ex::getSingletonInstance();
450        $objQuery->setWhere('product_class_id = ? AND T1.del_flg = 0');
451        $objQuery->setOrder("T2.level DESC");
452        $results = $this->getProductsClassByQuery($objQuery, $productClassId);
453        $productsClass = $this->getProductsClassFull($results);
454        return $productsClass[0];
455    }
456
457    /**
458     * 複数の商品IDに紐づいた, 商品規格を取得する.
459     *
460     * @param array $productIds 商品IDの配列
461     * @param boolean $has_deleted 削除された商品規格も含む場合 true; 初期値 false
462     * @return array 商品規格の配列
463     */
464    function getProductsClassByProductIds($productIds = array(), $has_deleted = false) {
465        if (empty($productIds)) {
466            return array();
467        }
468        $objQuery =& SC_Query_Ex::getSingletonInstance();
469        $where = 'product_id IN (' . implode(', ', array_pad(array(), count($productIds), '?')) . ')';
470        if (!$has_deleted) {
471            $where .= ' AND T1.del_flg = 0';
472        }
473        $objQuery->setWhere($where);
474        $objQuery->setOrder("T2.level DESC");
475        return $this->getProductsClassByQuery($objQuery, $productIds);
476    }
477
478    /**
479     * 商品IDに紐づいた, 商品規格を階層ごとに取得する.
480     *
481     * @param array $productId 商品ID
482     * @return array 階層ごとの商品規格の配列
483     */
484    function getProductsClassLevelByProductId($productId) {
485        $results = $this->getProductsClassByProductIds(array($productId));
486        return $this->getProductsClassLevel($results);
487    }
488
489    /**
490     * 商品IDに紐づいた, 商品規格をすべての組み合わせごとに取得する.
491     *
492     * @param array $productId 商品ID
493     * @param boolean $has_deleted 削除された商品規格も含む場合 true; 初期値 false
494     * @return array すべての組み合わせの商品規格の配列
495     */
496    function getProductsClassFullByProductId($productId, $has_deleted = false) {
497        $results = $this->getProductsClassByProductIds(array($productId), $has_deleted);
498        return $this->getProductsClassFull($results);
499    }
500
501    /**
502     * 商品規格の配列から, 商品規格を階層ごとに取得する.
503     *
504     * @access private
505     * @param array $productsClassResults 商品規格の結果の配列
506     * @return array 階層ごとの商品規格の配列
507     */
508    function getProductsClassLevel($productsClassResults) {
509        foreach ($productsClassResults as $row) {
510            $productsClassLevel['level' . $row['level']][] = $row;
511        }
512        return $productsClassLevel;
513    }
514
515    /**
516     * 商品規格の配列から, 商品規格のすべての組み合わせを取得する.
517     *
518     * @access private
519     * @param array $productsClassResults 商品規格の結果の配列
520     * @ array 階層ごとの商品規格の配列
521     */
522    function getProductsClassFull($productsClassResults) {
523        $results = $this->getProductsClassLevel($productsClassResults);
524        $productsClass = array();
525        if (SC_Utils_Ex::isBlank($results["level1"])
526            && SC_Utils_Ex::isBlank($results["level2"])) {
527            return $results['level'];
528        }
529
530        foreach ($results["level1"] as $level1) {
531            foreach ($results["level2"] as $level2) {
532                if ($level2['parent_class_combination_id'] == $level1['class_combination_id']) {
533                    $level1 = array_merge($level1, $level2);
534                }
535            }
536            $productsClass[] = $level1;
537        }
538        return $productsClass;
539    }
540
541    /**
542     * 商品IDをキーにした, 商品ステータスIDの配列を取得する.
543     *
544     * @param array 商品ID の配列
545     * @return array 商品IDをキーにした商品ステータスIDの配列
546     */
547    function getProductStatus($productIds) {
548        if (empty($productIds)) {
549            return array();
550        }
551        $objQuery =& SC_Query_Ex::getSingletonInstance();
552        $cols = 'product_id, product_status_id';
553        $from = 'dtb_product_status';
554        $where = 'del_flg = 0 AND product_id IN (' . implode(', ', array_pad(array(), count($productIds), '?')) . ')';
555        $productStatus = $objQuery->select($cols, $from, $where, $productIds);
556        $results = array();
557        foreach ($productStatus as $status) {
558            $results[$status['product_id']][] = $status['product_status_id'];
559        }
560        return $results;
561    }
562
563    /**
564     * 商品ステータスを設定する.
565     *
566     * TODO 現在は DELETE/INSERT だが, UPDATE を検討する.
567     *
568     * @param integer $productId 商品ID
569     * @param array $productStatusIds ON にする商品ステータスIDの配列
570     */
571    function setProductStatus($productId, $productStatusIds) {
572
573        $val['product_id'] = $productId;
574        $val['creator_id'] = $_SESSION['member_id'];
575        $val['create_date'] = 'CURRENT_TIMESTAMP';
576        $val['update_date'] = 'CURRENT_TIMESTAMP';
577        $val['del_flg'] = '0';
578
579        $objQuery =& SC_Query_Ex::getSingletonInstance();
580        $objQuery->delete('dtb_product_status', 'product_id = ?', array($productId));
581        foreach ($productStatusIds as $productStatusId) {
582            if($productStatusId == '') continue;
583            $val['product_status_id'] = $productStatusId;
584            $objQuery->insert('dtb_product_status', $val);
585        }
586    }
587
588    /**
589     * 商品詳細の結果から, 販売制限数を取得する.
590     *
591     * getDetailAndProductsClass() の結果から, 販売制限数を取得する.
592     *
593     * @param array $p 商品詳細の検索結果の配列
594     * @return integer 商品詳細の結果から求めた販売制限数.
595     * @see getDetailAndProductsClass()
596     */
597    function getBuyLimit($p) {
598        $limit = null;
599        if ($p['stock_unlimited'] != '1' && is_numeric($p['sale_limit'])) {
600            $limit = min($p['sale_limit'], $p['stock']);
601        } elseif (is_numeric($p['sale_limit'])) {
602            $limit = $p['sale_limit'];
603        } elseif ($p['stock_unlimited'] != '1') {
604            $limit = $p['stock'];
605        }
606        return $limit;
607    }
608
609    /**
610     * 在庫を減少させる.
611     *
612     * 指定の在庫数まで, 在庫を減少させる.
613     * 減少させた結果, 在庫数が 0 未満になった場合, 引数 $quantity が 0 の場合は,
614     * 在庫の減少を中止し, false を返す.
615     * 在庫の減少に成功した場合は true を返す.
616     *
617     * @param integer $productClassId 商品規格ID
618     * @param integer $quantity 減少させる在庫数
619     * @return boolean 在庫の減少に成功した場合 true; 失敗した場合 false
620     */
621    function reduceStock($productClassId, $quantity) {
622
623        if ($quantity == 0) {
624            return false;
625        }
626
627        $objQuery =& SC_Query_Ex::getSingletonInstance();
628        $objQuery->update('dtb_products_class', array(),
629                          "product_class_id = ?", array($productClassId),
630                          array('stock' => 'stock - ?'), array($quantity));
631        // TODO エラーハンドリング
632
633        $productsClass = $this->getDetailAndProductsClass($productClassId);
634        if ($productsClass['stock_unlimited'] != '1' && $productsClass['stock'] < 0) {
635            return false;
636        }
637
638        return true;
639    }
640
641    /**
642     * 商品情報の配列に, 税込金額を設定して返す.
643     *
644     * この関数は, 主にスマートフォンで使用します.
645     *
646     * @param array $arrProducts 商品情報の配列
647     * @return array 税込金額を設定した商品情報の配列
648     */
649    function setPriceTaxTo($arrProducts) {
650        foreach ($arrProducts as $key=>$val) {
651            $arrProducts[$key]['price01_min_format'] = number_format($arrProducts[$key]['price01_min']);
652            $arrProducts[$key]['price01_max_format'] = number_format($arrProducts[$key]['price01_max']);
653            $arrProducts[$key]['price02_min_format'] = number_format($arrProducts[$key]['price02_min']);
654            $arrProducts[$key]['price02_max_format'] = number_format($arrProducts[$key]['price02_max']);
655
656            $arrProducts[$key]['price01_min_tax'] = SC_Helper_DB::sfCalcIncTax($arrProducts[$key]['price01_min']);
657            $arrProducts[$key]['price01_max_tax'] = SC_Helper_DB::sfCalcIncTax($arrProducts[$key]['price01_max']);
658            $arrProducts[$key]['price02_min_tax'] = SC_Helper_DB::sfCalcIncTax($arrProducts[$key]['price02_min']);
659            $arrProducts[$key]['price02_max_tax'] = SC_Helper_DB::sfCalcIncTax($arrProducts[$key]['price02_max']);
660
661            $arrProducts[$key]['price01_min_tax_format'] = number_format($arrProducts[$key]['price01_min_tax']);
662            $arrProducts[$key]['price01_max_tax_format'] = number_format($arrProducts[$key]['price01_max_tax']);
663            $arrProducts[$key]['price02_min_tax_format'] = number_format($arrProducts[$key]['price02_min_tax']);
664            $arrProducts[$key]['price02_max_tax_format'] = number_format($arrProducts[$key]['price02_max_tax']);
665        }
666        return $arrProducts;
667    }
668
669    /**
670     * 商品詳細の SQL を取得する.
671     *
672     * @param string $where_products_class 商品規格情報の WHERE 句
673     * @return string 商品詳細の SQL
674     */
675    function alldtlSQL($where_products_class = '') {
676        $where_clause = '';
677        if (!SC_Utils_Ex::isBlank($where_products_class)) {
678            $where_products_class = 'AND (' . $where_products_class . ')';
679        }
680        /*
681         * point_rate, deliv_fee は商品規格(dtb_products_class)ごとに保持しているが,
682         * 商品(dtb_products)ごとの設定なので MAX のみを取得する.
683         */
684        $sql = <<< __EOS__
685            (
686                SELECT 0
687                    ,dtb_products.product_id
688                    ,dtb_products.name
689                    ,dtb_products.maker_id
690                    ,dtb_products.status
691                    ,dtb_products.comment1
692                    ,dtb_products.comment2
693                    ,dtb_products.comment3
694                    ,dtb_products.comment4
695                    ,dtb_products.comment5
696                    ,dtb_products.comment6
697                    ,dtb_products.note
698                    ,dtb_products.main_list_comment
699                    ,dtb_products.main_list_image
700                    ,dtb_products.main_comment
701                    ,dtb_products.main_image
702                    ,dtb_products.main_large_image
703                    ,dtb_products.sub_title1
704                    ,dtb_products.sub_comment1
705                    ,dtb_products.sub_image1
706                    ,dtb_products.sub_large_image1
707                    ,dtb_products.sub_title2
708                    ,dtb_products.sub_comment2
709                    ,dtb_products.sub_image2
710                    ,dtb_products.sub_large_image2
711                    ,dtb_products.sub_title3
712                    ,dtb_products.sub_comment3
713                    ,dtb_products.sub_image3
714                    ,dtb_products.sub_large_image3
715                    ,dtb_products.sub_title4
716                    ,dtb_products.sub_comment4
717                    ,dtb_products.sub_image4
718                    ,dtb_products.sub_large_image4
719                    ,dtb_products.sub_title5
720                    ,dtb_products.sub_comment5
721                    ,dtb_products.sub_image5
722                    ,dtb_products.sub_large_image5
723                    ,dtb_products.sub_title6
724                    ,dtb_products.sub_comment6
725                    ,dtb_products.sub_image6
726                    ,dtb_products.sub_large_image6
727                    ,dtb_products.del_flg
728                    ,dtb_products.creator_id
729                    ,dtb_products.create_date
730                    ,dtb_products.update_date
731                    ,dtb_products.deliv_date_id
732                    ,T4.product_code_min
733                    ,T4.product_code_max
734                    ,T4.price01_min
735                    ,T4.price01_max
736                    ,T4.price02_min
737                    ,T4.price02_max
738                    ,T4.stock_min
739                    ,T4.stock_max
740                    ,T4.stock_unlimited_min
741                    ,T4.stock_unlimited_max
742                    ,T4.point_rate
743                    ,T4.deliv_fee
744                    ,T4.class_count
745                    ,dtb_maker.name AS maker_name
746                FROM dtb_products
747                    JOIN (
748                       SELECT product_id,
749                              MIN(product_code) AS product_code_min,
750                              MAX(product_code) AS product_code_max,
751                              MIN(price01) AS price01_min,
752                              MAX(price01) AS price01_max,
753                              MIN(price02) AS price02_min,
754                              MAX(price02) AS price02_max,
755                              MIN(stock) AS stock_min,
756                              MAX(stock) AS stock_max,
757                              MIN(stock_unlimited) AS stock_unlimited_min,
758                              MAX(stock_unlimited) AS stock_unlimited_max,
759                              MAX(point_rate) AS point_rate,
760                              MAX(deliv_fee) AS deliv_fee,
761                              COUNT(*) as class_count
762                        FROM dtb_products_class
763                        WHERE del_flg = 0 $where_products_class
764                        GROUP BY product_id
765                    ) AS T4
766                        ON dtb_products.product_id = T4.product_id
767                    LEFT JOIN dtb_maker
768                        ON dtb_products.maker_id = dtb_maker.maker_id
769            ) AS alldtl
770__EOS__;
771        return $sql;
772    }
773
774    /**
775     * 商品規格詳細の SQL を取得する.
776     *
777     * MEMO: 2.4系 vw_product_classに相当(?)するイメージ
778     *
779     * @param string $where 商品詳細の WHERE 句
780     * @return string 商品規格詳細の SQL
781     */
782    function prdclsSQL($where = "") {
783        $where_clause = "";
784        if (!SC_Utils_Ex::isBlank($where)) {
785            $where_clause = " WHERE " . $where;
786        }
787        $sql = <<< __EOS__
788        (
789             SELECT dtb_products.*,
790                    dtb_products_class.product_class_id,
791                    dtb_products_class.class_combination_id,
792                    dtb_products_class.product_type_id,
793                    dtb_products_class.product_code,
794                    dtb_products_class.stock,
795                    dtb_products_class.stock_unlimited,
796                    dtb_products_class.sale_limit,
797                    dtb_products_class.price01,
798                    dtb_products_class.price02,
799                    dtb_products_class.deliv_fee,
800                    dtb_products_class.point_rate,
801                    dtb_products_class.down_filename,
802                    dtb_products_class.down_realfilename,
803                    dtb_class_combination.parent_class_combination_id,
804                    dtb_class_combination.classcategory_id,
805                    dtb_class_combination.level as classlevel,
806                    Tpcm.classcategory_id as parent_classcategory_id,
807                    Tpcm.level as parent_classlevel,
808                    Tcc1.class_id as class_id,
809                    Tcc1.name as classcategory_name,
810                    Tcc2.class_id as parent_class_id,
811                    Tcc2.name as parent_classcategory_name
812             FROM dtb_products
813                 LEFT JOIN dtb_products_class
814                     ON dtb_products.product_id = dtb_products_class.product_id
815                 LEFT JOIN dtb_class_combination
816                     ON dtb_products_class.class_combination_id = dtb_class_combination.class_combination_id
817                 LEFT JOIN dtb_class_combination as Tpcm
818                     ON dtb_class_combination.parent_class_combination_id = Tpcm.class_combination_id
819                 LEFT JOIN dtb_classcategory as Tcc1
820                     ON dtb_class_combination.classcategory_id = Tcc1.classcategory_id
821                 LEFT JOIN dtb_classcategory as Tcc2
822                     ON Tpcm.classcategory_id = Tcc2.classcategory_id
823             $where_clause
824        ) as prdcls
825__EOS__;
826        return $sql;
827    }
828}
Note: See TracBrowser for help on using the repository browser.