update
This commit is contained in:
@@ -0,0 +1,16 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\System\Model\EntityLanguageModel;
|
||||
use Hura8\Interfaces\EntityType;
|
||||
|
||||
|
||||
class ProductAttributeLanguageModel extends EntityLanguageModel
|
||||
{
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct(EntityType::PRODUCT_ATTRIBUTE);
|
||||
}
|
||||
|
||||
}
|
||||
175
inc/Hura8/Components/Product/Model/ProductAttributeModel.php
Normal file
175
inc/Hura8/Components/Product/Model/ProductAttributeModel.php
Normal file
@@ -0,0 +1,175 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\AppResponse;
|
||||
use Hura8\System\Language;
|
||||
use Hura8\System\Model\aEntityBaseModel;
|
||||
use Hura8\Interfaces\iEntityModel;
|
||||
use Hura8\Interfaces\EntityType;
|
||||
use Hura8\System\Security\DataClean;
|
||||
use Hura8\System\Security\DataType;
|
||||
|
||||
class ProductAttributeModel extends aEntityBaseModel {
|
||||
|
||||
protected $tb_product_category = "tb_product_category";
|
||||
protected $tb_attribute_value = "tb_attribute_value";
|
||||
|
||||
protected $tb_product_spec_group = "tb_product_spec_group";
|
||||
protected $tb_attribute_per_spec_group = "tb_attribute_per_spec_group";
|
||||
protected $tb_attribute_per_category = "tb_attribute_per_category";
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct(EntityType::PRODUCT_ATTRIBUTE);
|
||||
}
|
||||
|
||||
|
||||
protected function extendedFilterOptions() : array
|
||||
{
|
||||
return [
|
||||
// empty for now
|
||||
];
|
||||
}
|
||||
|
||||
// SPEC-GROUP
|
||||
|
||||
public function getSpecGroupAttributeWithValues($group_id) {
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT
|
||||
a.title,
|
||||
a.summary,
|
||||
a.is_filter,
|
||||
a.value_match_all,
|
||||
a.filter_code,
|
||||
a.is_display,
|
||||
a.is_header,
|
||||
a.is_multi, a.in_summary,
|
||||
a.value_count,
|
||||
g.attr_id,
|
||||
g.ordering,
|
||||
g.status
|
||||
FROM ".$this->tb_attribute_per_spec_group." g, ".$this->tb_entity." a
|
||||
WHERE g.`group_id`= ? AND g.`attr_id`= a.`id`
|
||||
ORDER BY g.`ordering` DESC, a.`ordering` DESC ",
|
||||
['d'],
|
||||
[$group_id]
|
||||
) ;
|
||||
|
||||
$attribute_ids = [];
|
||||
$value_per_attribute_ids = [];
|
||||
$result = [];
|
||||
foreach ($this->db->fetchAll($query) as $item) {
|
||||
$attribute_ids[] = $item['attr_id'];
|
||||
$value_per_attribute_ids[$item['attr_id']] = [];
|
||||
|
||||
$result[$item['attr_id']] = [
|
||||
"attribute_info" => $item,
|
||||
"attribute_values" => &$value_per_attribute_ids[$item['attr_id']],
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
if(!sizeof($attribute_ids)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
// now get all values for each attribute
|
||||
list($parameterized_ids, $bind_types) = create_bind_sql_parameter_from_value_list($attribute_ids, "int");
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT * FROM ".$this->tb_attribute_value."
|
||||
WHERE `attribute_id` IN (".$parameterized_ids.")
|
||||
ORDER BY `ordering` DESC, `title` ASC ",
|
||||
$bind_types,
|
||||
$attribute_ids
|
||||
) ;
|
||||
|
||||
foreach ($this->db->fetchAll($query) as $item) {
|
||||
$value_per_attribute_ids[$item['attribute_id']][] = $item;
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
public function getSpecGroupAttribute($group_id) {
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT
|
||||
a.title,
|
||||
a.summary,
|
||||
a.is_filter,
|
||||
a.value_match_all,
|
||||
a.filter_code,
|
||||
a.is_display,
|
||||
a.is_header, a.is_multi, a.value_count,
|
||||
g.attr_id,
|
||||
g.ordering,
|
||||
g.status
|
||||
FROM ".$this->tb_attribute_per_spec_group." g, ".$this->tb_entity." a
|
||||
WHERE g.`group_id`= ? AND g.`attr_id`= a.`id`
|
||||
ORDER BY g.`ordering` DESC, a.`ordering` DESC ",
|
||||
['d'],
|
||||
[$group_id]
|
||||
) ;
|
||||
|
||||
return $this->db->fetchAll($query);
|
||||
}
|
||||
|
||||
|
||||
public function getProductMatchAllAttributeValueIds(array $_att_value_list) {
|
||||
/*$query = $this->db->runQuery("
|
||||
SELECT `pro_id` , COUNT(*) AS num_pro
|
||||
FROM ".TB_PRODUCT_ATTRIBUTE."
|
||||
WHERE " . join(" OR ", array_map(function ($_item){ return " `attr_value_id` = '".intval($_item['id'])."' "; }, $_att_value_list )) ."
|
||||
GROUP BY pro_id
|
||||
HAVING num_pro = ".sizeof($_att_value_list)."
|
||||
LIMIT 10000
|
||||
");
|
||||
|
||||
return array_map(function ($item){
|
||||
return $item["pro_id"];
|
||||
}, $this->db->fetchAll($query));*/
|
||||
|
||||
return [];
|
||||
}
|
||||
|
||||
public function getProductMatchAttributeValue(array $value_ids) {
|
||||
$product_filter_id_match = array();
|
||||
// todo:
|
||||
/*if(sizeof($query_attr_id)) {
|
||||
$query = $this->db->runQuery("
|
||||
SELECT DISTINCT pro_id , COUNT(*) as num_pro
|
||||
FROM ".TB_PRODUCT_ATTRIBUTE."
|
||||
WHERE attr_value_id IN (".join(',', $query_attr_id).")
|
||||
GROUP BY pro_id
|
||||
HAVING num_pro = ".$count_filter."
|
||||
LIMIT 10000
|
||||
");
|
||||
foreach ( $this->db->fetchAll($query) as $rs ) {
|
||||
$product_filter_id_match[] = $rs["pro_id"];
|
||||
}
|
||||
}*/
|
||||
|
||||
return $product_filter_id_match;
|
||||
}
|
||||
|
||||
protected function _buildQueryConditionExtend(array $filter_condition) : ?array
|
||||
{
|
||||
/*$condition = array(
|
||||
"q" => "",
|
||||
"letter" => "",
|
||||
"status" => 0,
|
||||
);*/
|
||||
|
||||
$catCondition = [];
|
||||
$bind_types = [];
|
||||
$bind_values = [];
|
||||
|
||||
return array( join(" ", $catCondition), $bind_types, $bind_values);
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,83 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\AppResponse;
|
||||
use Hura8\System\Model\aEntityBaseModel;
|
||||
use Hura8\Interfaces\EntityType;
|
||||
use Hura8\System\Security\DataClean;
|
||||
use Hura8\System\Security\DataType;
|
||||
|
||||
|
||||
class ProductAttributeValueModel extends aEntityBaseModel
|
||||
{
|
||||
|
||||
const MAX_VALUE_PER_ATTRIBUTE = 100; // one attribute should not have more that this number of values
|
||||
|
||||
protected $attribute_id = 0;
|
||||
|
||||
protected $tb_attribute = 'tb_attribute';
|
||||
protected $tb_product_attribute = 'tb_product_attribute';
|
||||
|
||||
public function __construct($attribute_id) {
|
||||
parent::__construct(EntityType::PRODUCT_ATTRIBUTE_VALUE);
|
||||
$this->attribute_id = $attribute_id;
|
||||
}
|
||||
|
||||
|
||||
protected function extendedFilterOptions() : array
|
||||
{
|
||||
return [
|
||||
// empty for now
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
public function getProductAttributes($product_id) {
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT `attr_id`, `attr_value_id` FROM `".$this->tb_product_attribute."` WHERE `pro_id` = ? ",
|
||||
['d'], [ $product_id]
|
||||
);
|
||||
|
||||
return $this->db->fetchAll($query);
|
||||
}
|
||||
|
||||
|
||||
protected function getAttributeValueCount() {
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT `value_count` FROM `".$this->tb_attribute."` WHERE `id` = ? LIMIT 1 ",
|
||||
['d'], [$this->attribute_id]
|
||||
);
|
||||
|
||||
if($info = $this->db->fetchAssoc($query)) {
|
||||
return $info['value_count'];
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
protected function _buildQueryConditionExtend(array $filter_condition) : ?array
|
||||
{
|
||||
|
||||
$catCondition = [" AND `attribute_id` = ? "];
|
||||
$bind_types = ["d"];
|
||||
$bind_values = [$this->attribute_id];
|
||||
|
||||
|
||||
return array( join(" ", $catCondition), $bind_types, $bind_values);
|
||||
}
|
||||
|
||||
|
||||
public function getInfoByCode($filter_code)
|
||||
{
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT * FROM `".$this->tb_entity."` WHERE `attribute_id` = ? AND `filter_code` = ? LIMIT 1",
|
||||
['d', 's'], [$this->attribute_id, $filter_code ]
|
||||
);
|
||||
|
||||
return $this->db->fetchAssoc($query);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Database\iConnectDB;
|
||||
|
||||
class ProductCategoryInfoModel
|
||||
{
|
||||
/* @var $db iConnectDB */
|
||||
protected $db;
|
||||
|
||||
protected $tb_category_info = "tb_product_category_info";
|
||||
|
||||
public function __construct() {
|
||||
$this->db = get_db();
|
||||
}
|
||||
|
||||
public function getInfo($id) {
|
||||
return $this->db->select(
|
||||
$this->tb_category_info,
|
||||
[],
|
||||
[
|
||||
'id' => ['=', $id],
|
||||
]
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
|
||||
use Hura8\System\Model\EntityLanguageModel;
|
||||
use Hura8\Interfaces\EntityType;
|
||||
|
||||
|
||||
class ProductCategoryLanguageModel extends EntityLanguageModel
|
||||
{
|
||||
|
||||
protected $richtext_fields = [
|
||||
'description',
|
||||
];
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct(EntityType::PRODUCT_CATEGORY, '', $this->richtext_fields);
|
||||
}
|
||||
|
||||
}
|
||||
83
inc/Hura8/Components/Product/Model/ProductCategoryModel.php
Normal file
83
inc/Hura8/Components/Product/Model/ProductCategoryModel.php
Normal file
@@ -0,0 +1,83 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
|
||||
use Hura8\Interfaces\iEntityCategoryModel;
|
||||
use Hura8\System\Model\aCategoryBaseModel;
|
||||
use Hura8\Interfaces\EntityType;
|
||||
|
||||
|
||||
class ProductCategoryModel extends aCategoryBaseModel implements iEntityCategoryModel
|
||||
{
|
||||
static $url_module = "product";
|
||||
static $url_view = "category";
|
||||
static $url_type = "product:category";
|
||||
|
||||
protected $tb_category_info = "tb_product_category_info";
|
||||
protected $tb_product_per_category = "tb_product_per_category";
|
||||
protected $tb_attribute_per_category = "tb_attribute_per_category";
|
||||
protected $tb_attribute_value = "tb_attribute_value";
|
||||
protected $tb_attribute = "tb_attribute";
|
||||
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct(EntityType::PRODUCT_CATEGORY);
|
||||
}
|
||||
|
||||
|
||||
public function getAttributeList($catId) {
|
||||
$query = $this->db->runQuery("SELECT
|
||||
a.id ,
|
||||
a.filter_code ,
|
||||
a.title ,
|
||||
a.value_count ,
|
||||
a.is_filter ,
|
||||
c.ordering ,
|
||||
c.status ,
|
||||
a.is_header
|
||||
FROM ".$this->tb_attribute." a
|
||||
LEFT JOIN ".$this->tb_attribute_per_category." c ON a.id = c.attr_id
|
||||
WHERE c.category_id = ?
|
||||
ORDER BY c.ordering desc
|
||||
", ['d'], [ $catId ]) ; // AND isSearch = 1
|
||||
|
||||
return $this->db->fetchAll($query);
|
||||
}
|
||||
|
||||
|
||||
public function getFullInfo($id) : ?array {
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT * FROM `".$this->tb_entity."` basic, `".$this->tb_category_info."` info
|
||||
WHERE basic.`id` = info.`id` AND basic.id = ?
|
||||
LIMIT 1 ",
|
||||
['d'], [$id]
|
||||
);
|
||||
|
||||
if( $item_info = $this->db->fetchAssoc($query)){
|
||||
$item_info['settings'] = ($item_info['settings']) ? \json_decode($item_info['settings'], true) : [];
|
||||
return $item_info;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
public function getEmptyInfo($addition_field_value = []) : array
|
||||
{
|
||||
// basic table
|
||||
$basic_empty = parent::getEmptyInfo($addition_field_value);
|
||||
|
||||
// info table
|
||||
foreach ($this->db->getTableInfo($this->tb_category_info) as $field => $field_info) {
|
||||
$basic_empty[$field] = ( in_array($field_info['DATA_TYPE'], ['int', 'float']) ) ? 0 : '' ;
|
||||
}
|
||||
|
||||
if(sizeof($addition_field_value)) {
|
||||
return array_merge($basic_empty, $addition_field_value);
|
||||
}
|
||||
|
||||
return $basic_empty;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\EntityType;
|
||||
use Hura8\System\Model\EntityLanguageModel;
|
||||
|
||||
|
||||
class ProductCollectionLanguageModel extends EntityLanguageModel
|
||||
{
|
||||
|
||||
protected $richtext_fields = [
|
||||
'description',
|
||||
];
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct(EntityType::PRODUCT_COLLECTION, '', $this->richtext_fields);
|
||||
|
||||
//$this->createTableLang();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,85 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\EntityType;
|
||||
use Hura8\System\Model\aCategoryBaseModel;
|
||||
|
||||
|
||||
class ProductCollectionModel extends aCategoryBaseModel
|
||||
{
|
||||
|
||||
protected $tb_collection_product = "tb_collection_product";
|
||||
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct(EntityType::PRODUCT_COLLECTION);
|
||||
}
|
||||
|
||||
public function getInfoByUrl($url): ?array
|
||||
{
|
||||
$query = $this->db->runQuery(
|
||||
" SELECT * FROM `".$this->tb_entity."` WHERE `url_index` = ? LIMIT 1",
|
||||
['s'], [$url]
|
||||
);
|
||||
|
||||
return $this->db->fetchAssoc($query);
|
||||
}
|
||||
|
||||
public function getTotalProduct($collection_id, array $condition = [])
|
||||
{
|
||||
$query = $this->db->runQuery(
|
||||
" SELECT COUNT(*) as total FROM `".$this->tb_collection_product."` WHERE `collection_id` = ? ",
|
||||
['d'], [$collection_id]
|
||||
);
|
||||
|
||||
$total = 0;
|
||||
if ($rs = $this->db->fetchAssoc($query)) {
|
||||
$total = $rs['total'];
|
||||
}
|
||||
|
||||
return $total;
|
||||
}
|
||||
|
||||
|
||||
public function getListProduct($collection_id, array $condition = [])
|
||||
{
|
||||
$numPerPage = (isset($condition['numPerPage']) && $condition['numPerPage'] > 0 ) ? intval($condition['numPerPage']) : 20 ;
|
||||
$page = (isset($condition['page']) && $condition['page'] > 0 ) ? intval($condition['page']) : 1 ;
|
||||
$order_by = " `ordering` DESC, `id` DESC";
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT `product_id`, `ordering` FROM ".$this->tb_collection_product." WHERE `collection_id` = ?
|
||||
ORDER BY ".$order_by."
|
||||
LIMIT ".(($page-1) * $numPerPage).", ".$numPerPage ,
|
||||
['d'], [$collection_id]
|
||||
) ;
|
||||
|
||||
$item_list = array();
|
||||
$counter = ($page-1) * $numPerPage;
|
||||
foreach ( $this->db->fetchAll($query) as $item ) {
|
||||
$counter += 1;
|
||||
|
||||
$item_list[$item['product_id']] = [
|
||||
'counter' => $counter,
|
||||
'ordering' => $item['ordering'],
|
||||
];
|
||||
}
|
||||
|
||||
$objProductModel = new ProductModel();
|
||||
$product_list_info = $objProductModel->getListByIds(array_keys($item_list));
|
||||
|
||||
// final list
|
||||
$final_list = [];
|
||||
foreach ($item_list as $_pro_id => $_pro_info_in_collection) {
|
||||
$pro_basic = $product_list_info[$_pro_id] ?? null;
|
||||
if($pro_basic) {
|
||||
$final_list[] = array_merge($pro_basic, $_pro_info_in_collection);
|
||||
}
|
||||
}
|
||||
|
||||
return $final_list;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
452
inc/Hura8/Components/Product/Model/ProductFilterModel.php
Normal file
452
inc/Hura8/Components/Product/Model/ProductFilterModel.php
Normal file
@@ -0,0 +1,452 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Components\Brand\Model\BrandModel;
|
||||
use Hura8\Database\iConnectDB;
|
||||
use Hura8\Interfaces\TableName;
|
||||
use Hura8\Traits\ClassCacheTrait;
|
||||
|
||||
|
||||
class ProductFilterModel
|
||||
{
|
||||
|
||||
use ClassCacheTrait;
|
||||
|
||||
/* @var $db iConnectDB */
|
||||
protected $db;
|
||||
|
||||
|
||||
public function __construct() {
|
||||
$this->db = get_db('', ENABLE_DB_DEBUG);
|
||||
}
|
||||
|
||||
|
||||
public function findProductListIdMatchFilters(array $SQLConditionFromFilters) {
|
||||
list(
|
||||
$where_query,
|
||||
$current_page_id,
|
||||
$number_per_page,
|
||||
$ordering_clause
|
||||
) = $SQLConditionFromFilters;
|
||||
|
||||
$db_condition = join(" ", $where_query);
|
||||
|
||||
$total_number = 0;
|
||||
$query = $this->db->runQuery("SELECT COUNT(`id`) AS total FROM ".TableName::PRODUCT." WHERE 1 ".$db_condition." ");
|
||||
if($rs = $this->db->fetchAssoc($query)) {
|
||||
$total_number = $rs['total'];
|
||||
}
|
||||
|
||||
$query = $this->db->runQuery("
|
||||
SELECT * FROM ".TableName::PRODUCT."
|
||||
WHERE 1 ".$db_condition."
|
||||
".$ordering_clause."
|
||||
LIMIT ". ($current_page_id - 1) * $number_per_page .", ".$number_per_page."
|
||||
");
|
||||
|
||||
$item_list = $this->db->fetchAll($query);
|
||||
|
||||
return [$total_number, $item_list];
|
||||
}
|
||||
|
||||
|
||||
public function ratingList(array $list_product_ids) {
|
||||
|
||||
if(!sizeof($list_product_ids)) return [];
|
||||
|
||||
list($parameterized_ids, $bind_types) = create_bind_sql_parameter_from_value_list($list_product_ids, 'int');
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
"
|
||||
SELECT `review_rate`, COUNT(`id`) as num
|
||||
FROM ".TableName::PRODUCT."
|
||||
WHERE `id` IN (".$parameterized_ids.")
|
||||
GROUP BY `review_rate`
|
||||
ORDER BY review_rate ASC
|
||||
",
|
||||
$bind_types,
|
||||
$list_product_ids
|
||||
);
|
||||
|
||||
return $this->db->fetchAll($query);
|
||||
}
|
||||
|
||||
|
||||
public function categoryList(array $current_category_ids, array $list_product_ids) {
|
||||
if(!sizeof($list_product_ids)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
list($parameterized_ids, $bind_types) = create_bind_sql_parameter_from_value_list($list_product_ids, 'int');
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
"
|
||||
SELECT `category_id`, COUNT(`item_id`) AS numPro
|
||||
FROM ".TableName::PRODUCT_PER_CATEGORY."
|
||||
WHERE `item_id` IN (".$parameterized_ids.")
|
||||
GROUP BY `category_id` ",
|
||||
$bind_types,
|
||||
$list_product_ids
|
||||
);
|
||||
|
||||
//lay ket qua dem
|
||||
$result_count = [];
|
||||
foreach ($this->db->fetchAll($query) as $rs ){
|
||||
$result_count[$rs['category_id']] = $rs['numPro'];
|
||||
}
|
||||
|
||||
if(sizeof($result_count)) {
|
||||
|
||||
$objProductCategoryModel = new ProductCategoryModel();
|
||||
|
||||
$final_result = [];
|
||||
foreach ($objProductCategoryModel->getListByIds(array_keys($result_count)) as $rs ){
|
||||
|
||||
$rs['count'] = $result_count[$rs['id']];
|
||||
$rs['is_selected'] = in_array($rs['id'], $current_category_ids);
|
||||
|
||||
$final_result[] = $rs;
|
||||
}
|
||||
|
||||
return $final_result;
|
||||
}
|
||||
|
||||
return [];
|
||||
}
|
||||
|
||||
|
||||
public function brandList(array $current_brand_ids, array $list_product_ids) {
|
||||
|
||||
if(!sizeof($list_product_ids)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
list($parameterized_ids, $bind_types) = create_bind_sql_parameter_from_value_list($list_product_ids, 'int');
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
" SELECT `brand_id`, COUNT(`id`) AS total
|
||||
FROM ".TableName::PRODUCT."
|
||||
WHERE `id` IN (".$parameterized_ids.")
|
||||
GROUP BY `brand_id`
|
||||
ORDER BY total DESC
|
||||
LIMIT 100",
|
||||
$bind_types,
|
||||
$list_product_ids
|
||||
);
|
||||
|
||||
|
||||
$neededList = array();
|
||||
foreach ( $this->db->fetchAll($query) as $result ) {
|
||||
$neededList[$result['brand_id']] = array(
|
||||
"id" => $result['brand_id'] ,
|
||||
"count" => $result['total'] ,
|
||||
);
|
||||
}
|
||||
|
||||
$brand_list_ids[] = array_keys($neededList);
|
||||
$result_list = array();
|
||||
|
||||
if(sizeof($brand_list_ids)) {
|
||||
|
||||
$objBrandModel = new BrandModel();
|
||||
|
||||
foreach ( $objBrandModel->getListByIds($brand_list_ids) as $_brand ) {
|
||||
|
||||
$item_count = (isset($neededList[$_brand['id']])) ? $neededList[$_brand['id']]['count'] : 0;
|
||||
|
||||
$_brand['count'] = $item_count;
|
||||
$_brand["is_selected"] = in_array($_brand['id'], $current_brand_ids);
|
||||
|
||||
|
||||
$result_list[$_brand['id']] = $_brand;
|
||||
}
|
||||
}
|
||||
|
||||
return array_values($result_list);
|
||||
}
|
||||
|
||||
|
||||
public function attributeList(array $current_filter_attribute_value_ids, array $current_category_ids, array $list_product_ids) {
|
||||
if(!sizeof($list_product_ids)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
$category_attribute_filter_array = $this->countNumProPerAttributeForCategory($current_category_ids, $list_product_ids);
|
||||
|
||||
if(!sizeof($category_attribute_filter_array)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
$filter_box = array();
|
||||
|
||||
foreach($category_attribute_filter_array as $attributeIdGroup){
|
||||
|
||||
$attribute_value_array = $attributeIdGroup['value_list'];
|
||||
$attribute_name = $attributeIdGroup['name'];
|
||||
$attribute_selected = 0;
|
||||
$filterList = array();
|
||||
|
||||
$count_num = 0;
|
||||
|
||||
foreach($attribute_value_array as $att_value_id => $rs_value){
|
||||
$att_value_name = $rs_value["info"]["name"];
|
||||
$att_value_description = $rs_value["info"]["description"];
|
||||
$count_pro = $rs_value["pro_count"];
|
||||
$is_selected = in_array($att_value_id, $current_filter_attribute_value_ids);
|
||||
if($is_selected) {
|
||||
$attribute_selected = 1;
|
||||
}
|
||||
|
||||
unset($this_filter_query, $this_filter_col_value);
|
||||
|
||||
//gioi han danh sach
|
||||
if($count_num > 50) {
|
||||
break;
|
||||
}
|
||||
|
||||
$count_num++;
|
||||
|
||||
$filterList[] = array(
|
||||
"id" => $att_value_id ,
|
||||
"name" => $att_value_name ,
|
||||
'api_key' => $rs_value["info"]["api_key"],
|
||||
"description" => $att_value_description,
|
||||
"count" => $count_pro ,
|
||||
"is_selected" => $is_selected,
|
||||
);
|
||||
}
|
||||
|
||||
if($count_num > 0){
|
||||
$filter_box[] = [
|
||||
"name" => $attribute_name,
|
||||
'filter_code' => $attributeIdGroup['filter_code'],
|
||||
"is_selected" => $attribute_selected,
|
||||
"value_list" => $filterList ,
|
||||
];
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return $filter_box;
|
||||
}
|
||||
|
||||
|
||||
protected function countNumProPerAttributeForCategory(array $current_category_ids, array $list_product_ids){
|
||||
|
||||
if(!sizeof($list_product_ids)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
$category_attributes = $this->getAttributesForCategory($current_category_ids);
|
||||
$att_value_id_list = [];
|
||||
foreach ($category_attributes as $attribute) {
|
||||
$att_value_id_list = array_merge($att_value_id_list, array_keys($attribute['value_list']));
|
||||
}
|
||||
|
||||
// count product per attribute-value-id
|
||||
$result_count = array();
|
||||
if(sizeof($att_value_id_list)) {
|
||||
$query = $this->db->runQuery("
|
||||
SELECT
|
||||
pro_att.`attr_value_id`,
|
||||
COUNT(DISTINCT ".TB_PRODUCT_CATEGORY.".pro_id) AS numPro
|
||||
FROM ".TB_PRODUCT_ATTRIBUTE." pro_att
|
||||
LEFT JOIN ".TB_PRODUCT_CATEGORY." ON pro_att.pro_id = ".TB_PRODUCT_CATEGORY.".pro_id
|
||||
WHERE pro_att.pro_id IN (".join(',', $list_product_ids ).")
|
||||
AND pro_att.`attr_value_id` IN (".join(",", $att_value_id_list).")
|
||||
GROUP BY pro_att.`attr_value_id` ");
|
||||
|
||||
//lay ket qua dem
|
||||
foreach ($this->db->fetchAll($query) as $rs ){
|
||||
$result_count[$rs['attr_value_id']] = $rs['numPro'];
|
||||
}
|
||||
}
|
||||
|
||||
$final_result = [];
|
||||
foreach ($category_attributes as $attribute) {
|
||||
$new_value_list = [];
|
||||
foreach ($attribute['value_list'] as $_value_id => $_value_info) {
|
||||
$pro_count = isset($result_count[$_value_id]) ? $result_count[$_value_id] : 0;
|
||||
if($pro_count) {
|
||||
$_value_info['pro_count'] = $pro_count;
|
||||
$new_value_list[$_value_id] = $_value_info;
|
||||
}
|
||||
}
|
||||
$attribute['value_list'] = $new_value_list;
|
||||
$final_result[] = $attribute;
|
||||
}
|
||||
|
||||
return $final_result;
|
||||
}
|
||||
|
||||
|
||||
// 15-07-2020 get all attributes and values for a list of category
|
||||
protected function getAttributesForCategory(array $category_ids){
|
||||
|
||||
if(!sizeof($category_ids)) {
|
||||
return array();
|
||||
}
|
||||
|
||||
|
||||
$final_result = array();//array to return
|
||||
|
||||
$category_att_id_list = array();
|
||||
$attribute_array = array(); //keep & re-order attribute
|
||||
|
||||
list($parameterized_ids, $bind_types) = create_bind_sql_parameter_from_value_list($category_ids, 'int');
|
||||
|
||||
$query = $this->db->runQuery("
|
||||
SELECT `attr_id`, `ordering` FROM `idv_attribute_category`
|
||||
WHERE `category_id` IN (". $parameterized_ids .") AND `status` = 1 ", $bind_types, $category_ids);
|
||||
|
||||
foreach ($this->db->fetchAll($query) as $rs ){
|
||||
$category_att_id_list[] = $rs['attr_id'];
|
||||
$attribute_array[$rs['attr_id']] = $rs['ordering'];
|
||||
}
|
||||
|
||||
if(!sizeof($category_att_id_list)) {
|
||||
return array();
|
||||
}
|
||||
|
||||
|
||||
$att_value_id_list = array();
|
||||
$attribute_info = array();
|
||||
$attribute_att_value_item = array();
|
||||
$attribute_value_info = array();
|
||||
$query = $this->db->runQuery("
|
||||
SELECT
|
||||
attval.id ,
|
||||
attval.attributeId ,
|
||||
attval.value ,
|
||||
attval.description ,
|
||||
attval.api_key ,
|
||||
attval.value_en ,
|
||||
att.attribute_code ,
|
||||
att.filter_code,
|
||||
att.name ,
|
||||
att.ordering
|
||||
FROM ".TB_ATTRIBUTE_VALUE." attval
|
||||
LEFT JOIN ".TB_ATTRIBUTE." att ON attval.attributeId = att.id
|
||||
WHERE att.id IN (".join(',', $category_att_id_list).") AND att.isSearch = 1
|
||||
ORDER BY attval.ordering DESC ");
|
||||
|
||||
foreach ($this->db->fetchAll($query) as $rs ){
|
||||
$att_value_id = $rs['id'];
|
||||
$att_id = $rs['attributeId'];
|
||||
|
||||
$att_value_id_list[] = $att_value_id;
|
||||
|
||||
$attribute_att_value_item[$att_id][] = $att_value_id; //in ordering
|
||||
|
||||
$attribute_info[$att_id] = array(
|
||||
"id" => $att_id,
|
||||
"name" => $rs['name'],
|
||||
"code" => $rs['attribute_code'],
|
||||
"filter_code" => $rs['filter_code'],
|
||||
);
|
||||
$attribute_value_info[$att_value_id] = array(
|
||||
"id" => $att_value_id,
|
||||
"name" => $rs['value'],
|
||||
"description" => $rs['description'],
|
||||
"api_key" => $rs['api_key'],
|
||||
);
|
||||
}
|
||||
|
||||
//cho ra ket qua
|
||||
arsort($attribute_array); //sap xep thu tu cua attribute theo ordering
|
||||
|
||||
foreach($attribute_array as $att_id => $att_order){
|
||||
$this_attribute_atr_value_item = array();
|
||||
if(isset($attribute_att_value_item[$att_id])) {
|
||||
foreach($attribute_att_value_item[$att_id] as $att_value_id){
|
||||
$this_attribute_atr_value_item[$att_value_id] = array(
|
||||
"id" => $att_value_id,
|
||||
"info" => $attribute_value_info[$att_value_id],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
if(isset($attribute_info[$att_id])) {
|
||||
$info = $attribute_info[$att_id];
|
||||
$info['value_list'] = $this_attribute_atr_value_item;
|
||||
|
||||
$final_result[] = $info;
|
||||
}
|
||||
}
|
||||
|
||||
return $final_result;
|
||||
}
|
||||
|
||||
|
||||
public function priceList($current_max_price, $current_min_price, array $list_product_ids, array $category_price_range) {
|
||||
|
||||
if(!sizeof($list_product_ids)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
$total_prices = sizeof($category_price_range);
|
||||
if( ! $total_prices ){
|
||||
return [];
|
||||
}
|
||||
|
||||
//pad head and tail with 0
|
||||
array_unshift($category_price_range, 0);
|
||||
$category_price_range[] = 0;
|
||||
|
||||
$result = array();
|
||||
$queries = [];
|
||||
|
||||
for($i = 0; $i <= $total_prices ; $i++){
|
||||
|
||||
$range_key = md5($category_price_range[$i] .'-'. $category_price_range[$i+1] );
|
||||
$queries[] = $this->buildRangeQuery($list_product_ids, $range_key, $category_price_range[$i], $category_price_range[$i+1]);
|
||||
|
||||
$min_price = intval($category_price_range[$i]);
|
||||
$max_price = intval($category_price_range[$i+1]);
|
||||
$is_selected = ($max_price == $current_max_price && $min_price == $current_min_price );
|
||||
|
||||
$result[$range_key] = array(
|
||||
"min" => $min_price ,
|
||||
"max" => $max_price,
|
||||
"count" => 0 ,
|
||||
"is_selected" => ($is_selected) ? 1 : 0 ,
|
||||
);
|
||||
|
||||
}
|
||||
|
||||
$query = $this->db->runQuery(" SELECT `range_key`, `total` FROM ( ".join(' UNION ALL ', $queries)." ) AS tmp");
|
||||
foreach ($this->db->fetchAll($query) as $rs) {
|
||||
$result[$rs['range_key']]['count'] = $rs['total'];
|
||||
}
|
||||
|
||||
// get only range with product-count > 0
|
||||
return array_values(array_filter( $result , function ($item){
|
||||
return $item['count'] > 0;
|
||||
}));
|
||||
}
|
||||
|
||||
|
||||
private function buildRangeQuery(array $list_product_ids, $range_key, $minPrice, $maxPrice){
|
||||
|
||||
$minPrice = (int) $minPrice;
|
||||
$maxPrice = (int) $maxPrice;
|
||||
if($minPrice < 10) $minPrice = 10;
|
||||
|
||||
$new_price_range = " AND `id` IN (".join(',', $list_product_ids ).") ";
|
||||
|
||||
if($maxPrice > 0 && $minPrice > 0){
|
||||
$new_price_range .= " AND ( `price` BETWEEN '".$minPrice."' AND '".$maxPrice."' ) ";
|
||||
}elseif($maxPrice > 0){
|
||||
$new_price_range .= " AND `price` < '".$maxPrice."' ";
|
||||
}elseif($minPrice > 0 && $maxPrice == 0){
|
||||
$new_price_range .= " AND `price` >='".$minPrice."' ";
|
||||
}
|
||||
|
||||
return " SELECT '".$range_key."' AS `range_key`, COUNT(`id`) AS total
|
||||
FROM ".TableName::PRODUCT."
|
||||
WHERE 1 ".$new_price_range;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
95
inc/Hura8/Components/Product/Model/ProductHotModel.php
Normal file
95
inc/Hura8/Components/Product/Model/ProductHotModel.php
Normal file
@@ -0,0 +1,95 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Components\Product\AdminController\AProductHotController;
|
||||
use Hura8\Database\iConnectDB;
|
||||
use Hura8\System\Config;
|
||||
|
||||
|
||||
class ProductHotModel
|
||||
{
|
||||
|
||||
/* @var $db iConnectDB */
|
||||
protected $db;
|
||||
|
||||
protected $tb_product = "tb_product";
|
||||
protected $tb_product_hot = "tb_product_hot";
|
||||
|
||||
public function __construct() {
|
||||
$this->db = get_db();
|
||||
}
|
||||
|
||||
public function updateProductHot($pro_id, array $new_types) {
|
||||
|
||||
$this->db->runQuery("DELETE FROM " . $this->tb_product_hot . " WHERE `pro_id` = ? ", ['d'], [ $pro_id ]);
|
||||
$this->db->update(
|
||||
$this->tb_product,
|
||||
[
|
||||
"hot_type" => '',
|
||||
],
|
||||
[
|
||||
'id' => $pro_id,
|
||||
]
|
||||
);
|
||||
|
||||
|
||||
$config_hottype = Config::getProductHotTypeList();
|
||||
|
||||
//insert what good
|
||||
$batch_insert = array();
|
||||
$accepted_types = array();
|
||||
foreach ($new_types as $hot_type) {
|
||||
if (!isset($config_hottype[$hot_type])) continue;
|
||||
|
||||
$batch_insert[] = [
|
||||
"pro_id" => $pro_id,
|
||||
"hot_type" => $hot_type,
|
||||
];
|
||||
|
||||
$accepted_types[] = $hot_type;
|
||||
}
|
||||
|
||||
if (sizeof($batch_insert)) {
|
||||
|
||||
$this->db->bulk_insert($this->tb_product_hot, $batch_insert );
|
||||
|
||||
$this->db->update(
|
||||
$this->tb_product,
|
||||
[
|
||||
"hot_type" => join(",", $accepted_types),
|
||||
],
|
||||
[
|
||||
"id" => $pro_id,
|
||||
]
|
||||
);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
public function getProductHot(array $product_ids) {
|
||||
|
||||
if(!sizeof($product_ids)){
|
||||
return [];
|
||||
}
|
||||
|
||||
list($parameterized_ids, $bind_types) = create_bind_sql_parameter_from_value_list($product_ids, 'int');
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT `pro_id`, `hot_type` FROM ".$this->tb_product_hot." WHERE `pro_id` IN (".$parameterized_ids.") ",
|
||||
$bind_types,
|
||||
$product_ids
|
||||
);
|
||||
|
||||
$result = [];
|
||||
foreach ( $this->db->fetchAll($query) as $rs ) {
|
||||
$result[$rs['pro_id']][] = $rs['hot_type'];
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
78
inc/Hura8/Components/Product/Model/ProductImageModel.php
Normal file
78
inc/Hura8/Components/Product/Model/ProductImageModel.php
Normal file
@@ -0,0 +1,78 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Database\MysqlValue;
|
||||
use Hura8\Interfaces\AppResponse;
|
||||
use Hura8\System\Model\aEntityBaseModel;
|
||||
|
||||
class ProductImageModel extends aEntityBaseModel
|
||||
{
|
||||
|
||||
protected $product_id = 0;
|
||||
|
||||
/* @var ProductModel $objProductModel */
|
||||
protected $objProductModel;
|
||||
|
||||
public function __construct($product_id = 0) {
|
||||
parent::__construct('product_image');
|
||||
|
||||
$this->product_id = $product_id;
|
||||
$this->objProductModel = new ProductModel();
|
||||
}
|
||||
|
||||
|
||||
protected function extendedFilterOptions() : array
|
||||
{
|
||||
return [
|
||||
// empty for now
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
public function setProduct($product_id) {
|
||||
$this->product_id = $product_id;
|
||||
}
|
||||
|
||||
public function countProductImage($product_id) {
|
||||
$query = $this->db->runQuery("SELECT COUNT(*) AS total FROM `".$this->tb_entity."` WHERE `pro_id` = ? ", ['d'], [ $product_id]);
|
||||
if($info = $this->db->fetchAssoc($query)) {
|
||||
return $info['total'];
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
protected function _buildQueryOrderBy($sort_by = "new")
|
||||
{
|
||||
return " `ordering` DESC, `id` DESC ";
|
||||
}
|
||||
|
||||
|
||||
protected function _buildQueryConditionExtend(array $filter_condition) : ?array
|
||||
{
|
||||
/*$condition = array(
|
||||
"q" => "",
|
||||
"letter" => "",
|
||||
"status" => 0,
|
||||
);*/
|
||||
|
||||
$catCondition = [" AND `pro_id` = ? "];
|
||||
$bind_types = ['d'];
|
||||
$bind_values = [$this->product_id];
|
||||
|
||||
return array( join(" ", $catCondition), $bind_types, $bind_values);
|
||||
}
|
||||
|
||||
|
||||
protected function getProductMainImage() {
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT `id` FROM `".$this->tb_entity."` WHERE `pro_id` = ? AND `is_main` = 1 LIMIT 1",
|
||||
['d'], [ $this->product_id]
|
||||
);
|
||||
|
||||
return $this->db->fetchAssoc($query);
|
||||
}
|
||||
|
||||
}
|
||||
35
inc/Hura8/Components/Product/Model/ProductInfoModel.php
Normal file
35
inc/Hura8/Components/Product/Model/ProductInfoModel.php
Normal file
@@ -0,0 +1,35 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\AppResponse;
|
||||
use Hura8\System\Model\aEntityBaseModel;
|
||||
|
||||
class ProductInfoModel extends aEntityBaseModel
|
||||
{
|
||||
|
||||
protected $richtext_fields = [
|
||||
'description',
|
||||
'spec',
|
||||
'instruction',
|
||||
];
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct('product_info', '', null, $this->richtext_fields);
|
||||
}
|
||||
|
||||
|
||||
protected function extendedFilterOptions() : array
|
||||
{
|
||||
return [
|
||||
// empty for now
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
protected function _buildQueryConditionExtend(array $filter_condition) : ?array
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
21
inc/Hura8/Components/Product/Model/ProductLanguageModel.php
Normal file
21
inc/Hura8/Components/Product/Model/ProductLanguageModel.php
Normal file
@@ -0,0 +1,21 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\System\Model\EntityLanguageModel;
|
||||
use Hura8\Interfaces\EntityType;
|
||||
|
||||
class ProductLanguageModel extends EntityLanguageModel
|
||||
{
|
||||
|
||||
protected $richtext_fields = [
|
||||
'description',
|
||||
'spec',
|
||||
'instruction',
|
||||
];
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct(EntityType::PRODUCT, '', $this->richtext_fields);
|
||||
}
|
||||
|
||||
}
|
||||
410
inc/Hura8/Components/Product/Model/ProductModel.php
Normal file
410
inc/Hura8/Components/Product/Model/ProductModel.php
Normal file
@@ -0,0 +1,410 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\iEntityModel;
|
||||
use Hura8\System\Config;
|
||||
use Hura8\System\Model\aEntityBaseModel;
|
||||
use Hura8\Interfaces\EntityType;
|
||||
use Hura8\System\Security\DataClean;
|
||||
use Hura8\System\Security\DataType;
|
||||
|
||||
|
||||
class ProductModel extends aEntityBaseModel implements iEntityModel
|
||||
{
|
||||
|
||||
static $url_module = "product";
|
||||
static $url_view = "detail";
|
||||
static $url_type = "product:detail";
|
||||
|
||||
protected $tb_product_per_category = 'tb_product_per_category';
|
||||
protected $tb_collection_product = "tb_collection_product";
|
||||
protected $tb_product_info = 'tb_product_info';
|
||||
protected $tb_product_hot = "tb_product_hot";
|
||||
|
||||
protected $richtext_fields = [
|
||||
//'special_offer',
|
||||
];
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct(
|
||||
EntityType::PRODUCT,
|
||||
"",
|
||||
new ProductSearchModel(),
|
||||
$this->richtext_fields
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
protected function extendedFilterOptions() : array
|
||||
{
|
||||
return [
|
||||
"price" => array('max' => 0, 'min'=> 0),
|
||||
"brand" => array(), // array(1,2,3,)
|
||||
"collection" => array(), // array(1,2,3,)
|
||||
"supplier" => array(), // array(1,2,3,)
|
||||
"rating" => array(), // array(1,2,3,)
|
||||
"category" => array(), // array(1,2,3,)
|
||||
"status" => array(), // array(1,2,3,)
|
||||
"hotType" => array(),// array(saleoff | not | new)
|
||||
"attribute" => array(), // array(1,2,3,)
|
||||
"promotion" => "",
|
||||
"other_filter" => array(), // array(in-stock, has-promotion etc...)
|
||||
"spec_group_id" => array(), // array(1,2,3,)
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
public function getProductInfoBySKU(string $sku) {
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT * FROM `".$this->tb_entity."` basic, `".$this->tb_product_info."` info
|
||||
WHERE basic.`id` = info.`id` AND basic.sku = ?
|
||||
LIMIT 1 ",
|
||||
['d'], [$sku]
|
||||
);
|
||||
|
||||
if( $item_info = $this->db->fetchAssoc($query)){
|
||||
return $item_info;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
public function getFullInfo($id) {
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT * FROM `".$this->tb_entity."` basic, `".$this->tb_product_info."` info
|
||||
WHERE basic.`id` = info.`id` AND basic.id = ?
|
||||
LIMIT 1 ",
|
||||
['d'], [$id]
|
||||
);
|
||||
|
||||
if( $item_info = $this->db->fetchAssoc($query)){
|
||||
return $item_info;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
public function getProductCategoryList($pro_id) {
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT `category_id` FROM ".$this->tb_product_per_category." WHERE `item_id` = ? ",
|
||||
['d'], [ $pro_id ]
|
||||
) ;
|
||||
|
||||
$pro_cat = [];
|
||||
foreach ( $this->db->fetchAll($query) as $rs ) {
|
||||
$pro_cat[] = $rs['category_id'];
|
||||
}
|
||||
|
||||
return $pro_cat;
|
||||
}
|
||||
|
||||
|
||||
protected function _buildQueryConditionExtend(array $filter_condition) : ?array
|
||||
{
|
||||
$where_query = [];
|
||||
$bind_types = [];
|
||||
$bind_values = [];
|
||||
|
||||
//-------------------
|
||||
|
||||
//other filters
|
||||
if( array_key_exists("other_filter", $filter_condition) && sizeof($filter_condition["other_filter"])) {
|
||||
foreach ($filter_condition["other_filter"] as $_filter) {
|
||||
switch ($_filter) {
|
||||
case "in-stock";
|
||||
$where_query[] = " AND quantity > 0 ";
|
||||
break;
|
||||
case "has-vat";
|
||||
$where_query[] = " AND `has_vat` = 1 ";
|
||||
break;
|
||||
case "out-stock";
|
||||
$where_query[] = " AND `quantity` = 0 ";
|
||||
break;
|
||||
case "has-market-price";
|
||||
$where_query[] = " AND `market_price` > 0 ";
|
||||
break;
|
||||
case "no-price";
|
||||
$where_query[] = " AND `price` = 0 ";
|
||||
break;
|
||||
case "no-warranty";
|
||||
$where_query[] = " AND LENGTH(`warranty`) < 2 ";
|
||||
break;
|
||||
case "no-sku";
|
||||
$where_query[] = " AND LENGTH(`sku`) < 2 ";
|
||||
break;
|
||||
case "has-config";
|
||||
$where_query[] = " AND `config_count` > 0 ";
|
||||
break;
|
||||
case "no-image";
|
||||
$where_query[] = " AND `image_count` = 0 ";
|
||||
break;
|
||||
case "no-category";
|
||||
$where_query[] = " AND `category` = '0' ";
|
||||
break;
|
||||
case "display-off";
|
||||
$where_query[] = " AND `status`=0 ";
|
||||
break;
|
||||
case "display-on";
|
||||
$where_query[] = " AND `status`=1 ";
|
||||
break;
|
||||
case "has-promotion":
|
||||
$where_query[] = " AND LENGTH(`special_offer`) < 5 ";
|
||||
break;
|
||||
//...add more
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//- brand id or ids or brand_indexes
|
||||
if( array_key_exists("brand", $filter_condition) && sizeof($filter_condition["brand"])) {
|
||||
|
||||
$condition = array();
|
||||
foreach ($filter_condition["brand"] as $brand_id) {
|
||||
if(!intval($brand_id)) continue;
|
||||
$condition[] = " brand_id = ? ";
|
||||
$bind_types[] = 'd';
|
||||
$bind_values[] = $brand_id;
|
||||
}
|
||||
|
||||
if(sizeof($condition)) {
|
||||
$where_query[] = " AND ( ".join(" OR ", $condition)." )";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//- collection id or ids
|
||||
if( array_key_exists("collection", $filter_condition) && sizeof($filter_condition["collection"])) {
|
||||
$condition = array();
|
||||
|
||||
foreach ($filter_condition["collection"] as $_id) {
|
||||
if(!intval($_id)) continue;
|
||||
|
||||
$condition[] = " `id` IN ( SELECT `product_id` FROM ".$this->tb_collection_product." WHERE `collection_id` = ? ) ";
|
||||
$bind_types[] = 'd';
|
||||
$bind_values[] = $_id;
|
||||
}
|
||||
|
||||
$where_query[] = " AND ( ".join(" OR ", $condition)." )";
|
||||
}
|
||||
|
||||
|
||||
//- rating: 1-> 5
|
||||
if( array_key_exists("rating", $filter_condition) && sizeof($filter_condition["rating"])) {
|
||||
$condition = array();
|
||||
foreach ($filter_condition["rating"] as $_id) {
|
||||
$condition[] = " `rating` = ? ";
|
||||
$bind_types[] = 'd';
|
||||
$bind_values[] = $_id;
|
||||
}
|
||||
|
||||
$where_query[] = " AND ( ".join(" OR ", $condition)." )";
|
||||
}
|
||||
|
||||
|
||||
//- category id or ids
|
||||
if( array_key_exists("category", $filter_condition) && sizeof($filter_condition["category"])) {
|
||||
|
||||
$objProductCategoryModel = new ProductCategoryModel();
|
||||
|
||||
$condition = array();
|
||||
foreach ($filter_condition["category"] as $cat_id) {
|
||||
|
||||
$cat_info = $objProductCategoryModel->getInfo($cat_id);
|
||||
if(!$cat_info) continue;
|
||||
|
||||
if($cat_info["is_parent"]) {
|
||||
$childListId = ($cat_info["child_ids"]) ?: '0';
|
||||
$condition[] = " `category_id` IN (".$childListId .") ";
|
||||
}else{
|
||||
$condition[] = " `category_id` = ? ";
|
||||
$bind_types[] = 'd';
|
||||
$bind_values[] = $cat_id;
|
||||
}
|
||||
}
|
||||
|
||||
if(sizeof($condition)) {
|
||||
$where_query[] = " AND `id` IN ( SELECT DISTINCT `item_id` FROM ".$this->tb_product_per_category." WHERE " . join(" OR ", $condition) . " )";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// spec_group_id
|
||||
if( array_key_exists("spec_group_id", $filter_condition) && sizeof($filter_condition["spec_group_id"])) {
|
||||
|
||||
$condition = array();
|
||||
foreach ($filter_condition["spec_group_id"] as $_id) {
|
||||
if(!$_id) continue;
|
||||
|
||||
$condition[] = " `spec_group_id` = ? ";
|
||||
$bind_types[] = 'd';
|
||||
$bind_values[] = $_id;
|
||||
}
|
||||
|
||||
$where_query[] = " AND ( ".join(" OR ", $condition )." ) ";
|
||||
}
|
||||
|
||||
|
||||
//- hotType: saleoff | not | new | or combination of types
|
||||
if( array_key_exists("hotType", $filter_condition) && sizeof($filter_condition["hotType"])) {
|
||||
$config_hottype = Config::getProductHotTypeList();
|
||||
$condition = array();
|
||||
foreach ($filter_condition["hotType"] as $_id) {
|
||||
if(!array_key_exists($_id, $config_hottype)) continue;
|
||||
|
||||
$condition[] = " `hot_type` = ? ";
|
||||
$bind_types[] = 's';
|
||||
$bind_values[] = $_id;
|
||||
}
|
||||
|
||||
if(sizeof($condition)) {
|
||||
$where_query[] = " AND `id` IN (SELECT `pro_id` FROM ".$this->tb_product_hot." WHERE 1 AND ( ".join(" OR ", $condition)." ) ) ";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
//- attribute values
|
||||
/*
|
||||
if( array_key_exists("attribute", $filter_condition) && sizeof($filter_condition["attribute"])) {
|
||||
$filter_attr_value_list = $filter_condition["attribute"];
|
||||
//filter = attr_value_1-attr_value_2-attr_value_3,
|
||||
$query_attr_id = [];
|
||||
$count_filter = 0;
|
||||
|
||||
foreach($filter_attr_value_list as $attr_id){
|
||||
$attr_id = (int) $attr_id;
|
||||
if($attr_id) {
|
||||
$query_attr_id[] = $attr_id;
|
||||
$count_filter ++;
|
||||
}
|
||||
}
|
||||
|
||||
$product_filter_id_match = array();
|
||||
if(sizeof($query_attr_id)) {
|
||||
$query = $this->db->runQuery("
|
||||
SELECT DISTINCT pro_id , COUNT(*) as num_pro
|
||||
FROM ".TB_PRODUCT_ATTRIBUTE."
|
||||
WHERE attr_value_id IN (".join(',', $query_attr_id).")
|
||||
GROUP BY pro_id
|
||||
HAVING num_pro = ".$count_filter."
|
||||
LIMIT 10000
|
||||
");
|
||||
foreach ( $this->db->fetchAll($query) as $rs ) {
|
||||
$product_filter_id_match[] = $rs["pro_id"];
|
||||
}
|
||||
}
|
||||
|
||||
$where_query[] = (sizeof($product_filter_id_match)) ? " AND `id` IN (".join(', ', $product_filter_id_match).") " : " AND `id` = 0 " ;
|
||||
|
||||
//xay lai url de back
|
||||
if(!$this->objCategoryProduct) $this->objCategoryProduct = new CategoryProduct();
|
||||
|
||||
foreach($filter_attr_value_list as $value_id ){
|
||||
$att_name = $this->objCategoryProduct->atrValueName($value_id);
|
||||
|
||||
$filterPath["attribute"][] = array(
|
||||
"id" => $value_id,
|
||||
"name" => $att_name,
|
||||
);
|
||||
$filter_messages[] = [
|
||||
'title' => $att_name,
|
||||
'reset' => Url::buildUrl($this->_request_url, ['filter' => join(FILTER_VALUE_SEPARATOR, remove_item_from_array($filter_condition["attribute"], $value_id))] ),
|
||||
];
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
*/
|
||||
|
||||
//- attribute values
|
||||
if( array_key_exists("attribute", $filter_condition) && sizeof($filter_condition["attribute"])) {
|
||||
|
||||
$filter_attr_value_list = $filter_condition["attribute"];
|
||||
|
||||
$attr_values_per_attribute = $this->groupAttributeValuesByAttributeId($filter_attr_value_list);
|
||||
|
||||
$having_match_count = sizeof(array_keys($attr_values_per_attribute));
|
||||
|
||||
$attribute_info_list = $this->groupAttributeListInfo(array_keys($attr_values_per_attribute));
|
||||
|
||||
$attr_where_query = [];
|
||||
foreach ($attr_values_per_attribute as $_att_id => $_att_value_list) {
|
||||
// if same attribute : find products that match either ONE of these values (not match ALL values)
|
||||
$_att_info = $attribute_info_list[$_att_id];
|
||||
if (!$_att_info) continue;
|
||||
|
||||
// this attribute requires all products must have ALL selected values
|
||||
if ($_att_info['value_match_all'] && sizeof($_att_value_list) > 1) {
|
||||
|
||||
$_product_id_match_all = $this->getProductMatchAllAttributeValueIds($_att_value_list);
|
||||
|
||||
if (sizeof($_product_id_match_all) > 0) {
|
||||
$attr_where_query[] = " ( `id` IN (" . join(",", $_product_id_match_all) . ") ) ";
|
||||
} else {
|
||||
$attr_where_query[] = " ( `id` = -1 ) ";
|
||||
}
|
||||
|
||||
} else {
|
||||
$attr_where_query[] = " ( SELECT DISTINCT `pro_id` FROM " . TB_PRODUCT_ATTRIBUTE . " WHERE (" .
|
||||
join(" OR ", array_map(function ($_item) { return " `attr_value_id` = '" . intval($_item['id']) . "' "; }, $_att_value_list))
|
||||
. " ) ) ";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
$product_filter_id_match = array();
|
||||
|
||||
if (sizeof($attr_where_query)) {
|
||||
$query = $this->db->runQuery("
|
||||
SELECT `pro_id` , COUNT(*) AS num_pro
|
||||
FROM ( " . join(" UNION ALL ", $attr_where_query) . " ) AS tpm_tb
|
||||
GROUP BY pro_id
|
||||
HAVING num_pro = " . $having_match_count . "
|
||||
LIMIT 10000
|
||||
");
|
||||
foreach ($this->db->fetchAll($query) as $rs) {
|
||||
$product_filter_id_match[] = $rs["pro_id"];
|
||||
}
|
||||
}
|
||||
|
||||
$where_query[] = (sizeof($product_filter_id_match)) ? " AND " . TB_PRODUCT_LIGHT . ".`id` IN (" . join(', ', $product_filter_id_match) . ") " : " AND " . TB_PRODUCT_LIGHT . ".`id` = 0 ";
|
||||
|
||||
}
|
||||
|
||||
|
||||
//- price range
|
||||
if(
|
||||
isset($filter_condition["price"])
|
||||
&& sizeof($filter_condition["price"])
|
||||
&& ($filter_condition["price"]['min'] > 0 || $filter_condition["price"]['max'] > 0)
|
||||
) {
|
||||
|
||||
//limit by price range
|
||||
$maxPrice = DataClean::makeInputSafe($filter_condition["price"]['max'], DataType::INTEGER);
|
||||
$minPrice = DataClean::makeInputSafe($filter_condition["price"]['min'], DataType::INTEGER);
|
||||
|
||||
$price_range_query = '';
|
||||
if($maxPrice > 0 && $minPrice > 0){
|
||||
$price_range_query = " ( `price` BETWEEN '".$minPrice."' AND '".$maxPrice."' ) ";
|
||||
|
||||
}else if($maxPrice > 0){
|
||||
$price_range_query = " `price` < '".$maxPrice."' ";
|
||||
|
||||
}else if($minPrice > 0){
|
||||
$price_range_query = " `price` >='".$minPrice."' ";
|
||||
}
|
||||
|
||||
$where_query[] = " AND ". $price_range_query;
|
||||
}
|
||||
|
||||
// ------------
|
||||
|
||||
return array( join(" ", $where_query), $bind_types, $bind_values);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
33
inc/Hura8/Components/Product/Model/ProductSearchModel.php
Normal file
33
inc/Hura8/Components/Product/Model/ProductSearchModel.php
Normal file
@@ -0,0 +1,33 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\iSearch;
|
||||
use Hura8\System\Model\aSearchBaseModel;
|
||||
|
||||
class ProductSearchModel extends aSearchBaseModel implements iSearch
|
||||
{
|
||||
|
||||
private $filter_fields = [
|
||||
"price" => "tb_product.price",
|
||||
"ranking" => "tb_product.ranking",
|
||||
"status" => "tb_product.status",
|
||||
"brand" => "tb_product.brand_id",
|
||||
];
|
||||
|
||||
private $fulltext_fields = [
|
||||
"category_keywords" => ["tb_product_category.title", ],
|
||||
"product_keywords" => ["tb_product.sku", "tb_product.title", "tb_product.model", "tb_product.related_keywords"],
|
||||
];
|
||||
|
||||
|
||||
public function __construct()
|
||||
{
|
||||
parent::__construct(
|
||||
"tb_product",
|
||||
$this->fulltext_fields,
|
||||
$this->filter_fields
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,65 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\AppResponse;
|
||||
use Hura8\System\Model\aEntityBaseModel;
|
||||
|
||||
class ProductSpecGroupAttributeModel extends aEntityBaseModel
|
||||
{
|
||||
|
||||
protected $tb_product = 'tb_product';
|
||||
protected $tb_product_spec = 'tb_product_spec';
|
||||
protected $tb_product_spec_group = 'tb_product_spec_group';
|
||||
protected $tb_product_spec_group_record = 'tb_product_spec_group_record';
|
||||
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct('product_spec_group_record');
|
||||
}
|
||||
|
||||
|
||||
protected function extendedFilterOptions() : array
|
||||
{
|
||||
return [
|
||||
// empty for now
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
public function getSpecGroupAttribute($group_id)
|
||||
{
|
||||
$query = $this->db->runQuery(
|
||||
"SELECT * FROM `".$this->tb_product_spec_group_record."` WHERE `group_id` = ? ORDER BY `ordering` ASC ",
|
||||
['d'], [$group_id]
|
||||
);
|
||||
|
||||
return $this->db->fetchAll($query);
|
||||
}
|
||||
|
||||
|
||||
|
||||
protected function updateGroupAttributeCount($group_id) {
|
||||
$this->db->runQuery("UPDATE `".$this->tb_product_spec_group."` SET
|
||||
`attribute_count` = (SELECT COUNT(*) FROM `".$this->tb_product_spec_group_record."` WHERE `group_id` = ? )
|
||||
WHERE `id` = ? LIMIT 1 ", ['d', 'd' ], [ $group_id, $group_id ]);
|
||||
}
|
||||
|
||||
protected function buildQueryCondition(array $condition)
|
||||
{
|
||||
// TODO: Implement buildQueryCondition() method.
|
||||
}
|
||||
|
||||
protected function buildOrderByCondition($order_by)
|
||||
{
|
||||
// TODO: Implement buildOrderByCondition() method.
|
||||
}
|
||||
|
||||
|
||||
protected function _buildQueryConditionExtend(array $extend_filter_conditions) : ?array
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
151
inc/Hura8/Components/Product/Model/ProductSpecGroupModel.php
Normal file
151
inc/Hura8/Components/Product/Model/ProductSpecGroupModel.php
Normal file
@@ -0,0 +1,151 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Interfaces\AppResponse;
|
||||
use Hura8\System\Model\aEntityBaseModel;
|
||||
|
||||
class ProductSpecGroupModel extends aEntityBaseModel
|
||||
{
|
||||
|
||||
|
||||
protected $tb_product = 'tb_product';
|
||||
protected $tb_product_spec_group = 'tb_product_spec_group';
|
||||
protected $tb_product_attribute = 'tb_product_attribute';
|
||||
|
||||
public function __construct() {
|
||||
parent::__construct('product_spec_group');
|
||||
}
|
||||
|
||||
|
||||
protected function extendedFilterOptions() : array
|
||||
{
|
||||
return [
|
||||
// empty for now
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
public function getSpecGroupAttribute($group_id) {
|
||||
$objProductSpecGroupAttributeModel = new ProductSpecGroupAttributeModel();
|
||||
return $objProductSpecGroupAttributeModel->getSpecGroupAttribute($group_id);
|
||||
}
|
||||
|
||||
|
||||
protected function clearProductAttributes($product_id) {
|
||||
$this->db->runQuery(
|
||||
"DELETE FROM `".$this->tb_product_attribute."` WHERE `pro_id` = ? ",
|
||||
[ 'd' ], [ $product_id ]
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
public function clearProductSpecGroup($product_id) {
|
||||
|
||||
$this->clearProductAttributes($product_id);
|
||||
|
||||
$product_spec_group_id = $this->getProductSpecGroupId($product_id);
|
||||
|
||||
// update
|
||||
$this->db->runQuery(
|
||||
"UPDATE `".$this->tb_product."` SET
|
||||
`spec_group_id` = 0
|
||||
WHERE `id` = ? LIMIT 1 ",
|
||||
[ 'd' ], [ $product_id ]
|
||||
);
|
||||
|
||||
$this->updateSpecGroupProductCount($product_spec_group_id);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
public function setProductSpecGroup($product_id, $new_group_id)
|
||||
{
|
||||
$current_group_id = $this->getProductSpecGroupId($product_id);
|
||||
|
||||
if($current_group_id != $new_group_id) {
|
||||
// update
|
||||
$this->db->runQuery(
|
||||
"UPDATE `".$this->tb_product."` SET
|
||||
`spec_group_id` = ?
|
||||
WHERE `id` = ? LIMIT 1 ",
|
||||
[ 'd', 'd' ], [ $new_group_id, $product_id ]
|
||||
);
|
||||
|
||||
$this->updateSpecGroupProductCount($new_group_id);
|
||||
|
||||
$this->clearProductAttributes($product_id);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
protected function updateSpecGroupProductCount($group_id) {
|
||||
$this->db->runQuery(
|
||||
"UPDATE `".$this->tb_product_spec_group."` SET
|
||||
`product_count` = (SELECT COUNT(*) FROM ".$this->tb_product." WHERE `spec_group_id` = ? )
|
||||
WHERE `id` = ? LIMIT 1 ",
|
||||
[ 'd', 'd' ], [ $group_id, $group_id ]
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
public function getProductSpecGroupInfo($product_id)
|
||||
{
|
||||
$product_spec_group_id = $this->getProductSpecGroupId($product_id);
|
||||
|
||||
return ($product_spec_group_id) ? $this->getSpecGroupInfo($product_spec_group_id) : false ;
|
||||
}
|
||||
|
||||
|
||||
public function getProductSpecGroupId($product_id)
|
||||
{
|
||||
$query = $this->db->runQuery("SELECT `spec_group_id` FROM `".$this->tb_product."` WHERE `id` = ? LIMIT 1 ", ['d'], [$product_id]);
|
||||
|
||||
if ($info = $this->db->fetchAssoc($query) ) {
|
||||
return $info['spec_group_id'] ;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
public function getSpecGroupInfo($group_id)
|
||||
{
|
||||
$query = $this->db->runQuery("SELECT * FROM `".$this->tb_product_spec_group."` WHERE `id` = ? ", ['d'], [$group_id]);
|
||||
|
||||
return $this->db->fetchAssoc($query);
|
||||
}
|
||||
|
||||
|
||||
protected function buildQueryCondition(array $condition)
|
||||
{
|
||||
$catCondition = [];
|
||||
|
||||
//Tim kiem theo tu khoa
|
||||
if(isset($condition["q"]) && $condition["q"]){
|
||||
$catCondition[] = " AND `title` LIKE '%".$this->db->escape($condition["q"])."%' ";
|
||||
}
|
||||
|
||||
return join(" ", $catCondition);
|
||||
}
|
||||
|
||||
protected function _buildQueryConditionExtend(array $filter_condition) : ?array
|
||||
{
|
||||
$where_condition = "";
|
||||
$bind_types = [];
|
||||
$bind_values = [];
|
||||
|
||||
return [
|
||||
$where_condition,
|
||||
$bind_types,
|
||||
$bind_values
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
181
inc/Hura8/Components/Product/Model/ProductVariantModel.php
Normal file
181
inc/Hura8/Components/Product/Model/ProductVariantModel.php
Normal file
@@ -0,0 +1,181 @@
|
||||
<?php
|
||||
|
||||
namespace Hura8\Components\Product\Model;
|
||||
|
||||
use Hura8\Components\Product\Controller\ProductController;
|
||||
use Hura8\Interfaces\AppResponse;
|
||||
use Hura8\System\Model\aEntityBaseModel;
|
||||
use Hura8\System\Security\DataClean;
|
||||
use Hura8\System\Security\DataType;
|
||||
|
||||
|
||||
class ProductVariantModel extends aEntityBaseModel
|
||||
{
|
||||
|
||||
protected $product_id = 0;
|
||||
|
||||
protected $tb_product = "tb_product";
|
||||
protected $tb_variant_option_sample = "tb_product_variant_option_sample";
|
||||
|
||||
public function __construct($product_id) {
|
||||
parent::__construct('product_variant');
|
||||
$this->product_id = $product_id;
|
||||
}
|
||||
|
||||
|
||||
protected function extendedFilterOptions() : array
|
||||
{
|
||||
return [
|
||||
// empty for now
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
public function getProductVariantOption($product_id){
|
||||
$query = $this->db->runQuery("SELECT `variant_option` FROM `".$this->tb_product."` WHERE `id` = ? LIMIT 1", ['d'], [ $product_id ]) ;
|
||||
|
||||
if($rs = $this->db->fetchAssoc($query)) {
|
||||
return ($rs['variant_option']) ? \json_decode($rs['variant_option'], true) : null;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
//use a product's variant-option to create a sample, so next product can select without recreate from beginning
|
||||
public function createVariantOptionSample($use_from_pro_id, $sample_title) {
|
||||
|
||||
if( !$use_from_pro_id || strlen($sample_title) < 3 ) return false;
|
||||
|
||||
$pro_variant_option = $this->getProductVariantOption($use_from_pro_id);
|
||||
if(!$pro_variant_option) {
|
||||
return false;
|
||||
}
|
||||
|
||||
$pro_variant_option_index = md5(\json_encode($pro_variant_option));
|
||||
|
||||
$check_duplicate = $this->db->runQuery(
|
||||
"SELECT `id` FROM ".$this->tb_variant_option_sample." WHERE `variant_option_index` = ? LIMIT 1 ",
|
||||
['s'], [ $pro_variant_option_index ]
|
||||
);
|
||||
|
||||
if($this->db->fetchAssoc($check_duplicate)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// ok to save
|
||||
$this->db->insert(
|
||||
$this->tb_variant_option_sample,
|
||||
[
|
||||
"title" => $sample_title,
|
||||
"variant_option" => \json_encode($pro_variant_option),
|
||||
"variant_option_index" => $pro_variant_option_index,
|
||||
"create_time" => CURRENT_TIME,
|
||||
]
|
||||
);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public function getVariantOptionSample() {
|
||||
$query = $this->db->runQuery("SELECT * FROM ".$this->tb_variant_option_sample." ORDER BY `id` DESC LIMIT 500 ");
|
||||
|
||||
return $this->db->fetchAll($query);
|
||||
}
|
||||
|
||||
public function getProductVariantPriceRange(){
|
||||
$result = [
|
||||
"sale_price" => [
|
||||
"min" => 0,
|
||||
"max" => 0,
|
||||
],
|
||||
"market_price" => [
|
||||
"min" => 0,
|
||||
"max" => 0,
|
||||
],
|
||||
];
|
||||
|
||||
$query = $this->db->runQuery(
|
||||
" SELECT `sale_price`, `market_price`, `extend` FROM `".$this->tb_entity."` WHERE `product_id` = ? ",
|
||||
['d'], [$this->product_id]
|
||||
);
|
||||
|
||||
foreach ( $this->db->fetchAll($query) as $info) {
|
||||
|
||||
// find min
|
||||
if($info["sale_price"] > 0 && ( $info["sale_price"] < $result["sale_price"]["min"] || $result["sale_price"]["min"] == 0 ) ) {
|
||||
$result["sale_price"]["min"] = $info["sale_price"];
|
||||
}
|
||||
|
||||
// find max
|
||||
if($info["sale_price"] > 0 && $info["sale_price"] > $result["sale_price"]["max"] ) {
|
||||
$result["sale_price"]["max"] = $info["sale_price"];
|
||||
}
|
||||
|
||||
// market_price
|
||||
$market_price = $info["market_price"];
|
||||
if($info['extend']) {
|
||||
$extend = unserialize($info['extend']);
|
||||
if(isset($extend['market_price'])) $market_price = clean_price($extend['market_price'], "vnd");
|
||||
}
|
||||
|
||||
if($market_price > 0 && ( $market_price < $result["market_price"]["min"] || $result["market_price"]["min"] == 0 ) ) {
|
||||
$result["market_price"]["min"] = $market_price;
|
||||
}
|
||||
|
||||
if($market_price > 0 && $market_price > $result["market_price"]["max"] ) {
|
||||
$result["market_price"]["max"] = $market_price;
|
||||
}
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
protected function _buildQueryConditionExtend(array $filter_condition) : ?array
|
||||
{
|
||||
$where_condition = " AND `product_id` = ? ";
|
||||
$bind_types = ["d"];
|
||||
$bind_values = [$this->product_id];
|
||||
|
||||
return [
|
||||
$where_condition,
|
||||
$bind_types,
|
||||
$bind_values
|
||||
];
|
||||
}
|
||||
|
||||
protected function _buildQueryOrderBy($sort_by = "new")
|
||||
{
|
||||
return " `ordering` DESC, `id` DESC ";
|
||||
}
|
||||
|
||||
protected function formatItemInList(array $item_info): array
|
||||
{
|
||||
$info = $item_info;
|
||||
|
||||
if($item_info['attribute']) $info['attribute'] = \json_decode($item_info['attribute'], true);
|
||||
|
||||
return $info;
|
||||
}
|
||||
|
||||
protected function updateProductVariantCount() {
|
||||
$this->db->runQuery(
|
||||
"UPDATE ".$this->tb_product." SET
|
||||
`config_count` = ( SELECT COUNT(*) AS total FROM `".$this->tb_entity."` WHERE `product_id` = ? AND `status` = 1 )
|
||||
WHERE `id` = ? ",
|
||||
['d', 'd'], [ $this->product_id, $this->product_id]
|
||||
) ;
|
||||
}
|
||||
|
||||
protected function formatItemInfo(array $item_info) : ?array
|
||||
{
|
||||
$info = $item_info;
|
||||
|
||||
if($info['attribute']) $info['attribute'] = \json_decode($info['attribute'], true);
|
||||
|
||||
return $info;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user