10月cms查询

时间:2018-01-14 19:55:11

标签: mysql activerecord octobercms octobercms-plugins

我试图优化这个嵌套查询,这需要很长时间才能加载。

基本思想是获得属于某个部门的所有系列,中间是属于许多部门和许多系列的产品。 表结构

部门* LT; - &GT *产品* LT; - > *系列

在模型中,关系定义如下:部门模型

public $belongsToMany  = [
      'products' => [
        '\depcore\parts\Models\Product',
        'table' => 'depcore_parts_products_departments',
      ],
      // 'series' => [
      //   '\depcore\parts\Models\Series',
      //   'table' => 'depcore_parts_products_series',
      // ]
    ];

系列型号

public $hasMany = [
      'products' => [
        '\depcore\parts\Models\Product',
        'table' => 'depcore_parts_products_departments',
      ]
    ];

产品型号

public $belongsToMany = [
      'series' => [
        'depcore\parts\Models\Series',
        'table' => 'depcore_parts_products_series',
        'order' => 'name',
        ],
      'departments' => [
        'depcore\parts\Models\Department',
        'table' => 'depcore_parts_products_departments',
        // 'order' => 'name'
        ]
    ];

在部门模型中,我创建了一种方法来检索属于部门的所有系列,这些系列在分析后导致一些严重的性能问题

public function series (){

      $seriesArray = array( );
      $products = $this->products()->remember(100)->get();
      foreach ($products as $product) {
        $productSeries = $product->series()->remember(100)->get();
        foreach ($productSeries as $series) {
            if (!isset($seriesArray[$series->id]) and $series->published )
                $seriesArray[$series->id] = $series;
        }
      }

     return \Illuminate\Database\Eloquent\Collection::make($seriesArray);

    }

我猜这可以通过原始SQL或更好的实现在活动记录中完成,但我仍然坚持两者。

我稍后添加了remember()方法,但没有结果。 现在网页的加载时间大约是20秒。当立即删除此代码时。

感谢任何建议。

从表结构中我想这将是运行适当的SQL命令(命令)以获得所需的结果

SELECT DISTINCT series_id FROM depcore_parts_products_series WHERE product_id IN (SELECT DISTINCT product_id FROM depcore_parts_products_departments WHERE department_id = 3);

此查询仅在中间表上运行,并获得series_id的正确结果(在phpmyadmin中)(以department_id = 3为例)

使用Hardik Satasiya代码我必须更改几行或视图不会显示任何系列只是空行。

public function series (){

        $sql = 'SELECT DISTINCT series_id FROM depcore_parts_products_series WHERE product_id IN (SELECT DISTINCT product_id FROM depcore_parts_products_departments WHERE department_id = :dep_id)';

        $data = ['dep_id' => $this->id];
        $query = \DB::select($sql, $data);
        $data = $query;

        $ids = array();
        // I had to rewrite this pare and make it more inelegant still 
        // but the refresh method appeared to made it step out the execution cycle 
        foreach ($data as $key => $value) {
            $ids[] = $value->series_id;
        }

        // in $data we are passing only id information
        // so this records have only id, not db all attributes
        // what ever you pass in $data will become model attributes if its in list
        $collection = \depcore\parts\Models\Series::hydrate($ids);
        return Series::published()->whereIn('id',$ids)->get();

    }

块部分

<div class="element-grid">
    <h4 {% if hideChildren|length and departmentModel.id not in filters.departments %} class='inactive' {% endif %}  ><a href="{{ url('/')}}/parts?Filter[departments][]={{ departmentModel.id }}">{{ departmentModel.name }}</a></h4>
    {% if not hideChildren|length %}
    <div class="list">
      <div class="block left-block">
          {% if departmentModel.getChildren|length %}
              <ul class='departments'>
                {% for child in departmentModel.getChildren %}
                     {% if child.published %}
                        <li><strong><a href="{{ url('/')}}/parts?Filter[departments][]={{ departmentModel.id }}&Filter[departments][]={{ child.id }}">{{ child.name }}</a></li></strong>
                     {% endif %}

                {% endfor %}
              </ul>
          {% endif %}
         <ul class="series">
           {% for series in departmentModel.departmentSeries.series|slice(0,10) %}
             <li><a href="{{ url('/')}}/parts?Filter[departments][]={{ departmentModel.id }}&{{ departmentModel.departmentSeries.childrenString }}&Filter[series][]={{ series.id }}">{{ series.name }}</a></li>
           {% endfor %}
         </ul>
        </div>
        <div class="block right-block">
             <ul class="series series-right">
                {% for series in departmentModel.departmentSeries.series|slice(10,length) %}
                    <li><a href="{{ url('/')}}/parts?Filter[departments][]={{ departmentModel.id }}&{{ departmentModel.departmentSeries.childrenString }}&Filter[series][]={{ series.id }}">{{ series.name }}</a></li>
                {% endfor %}
             </ul>
        </div>
    </div>
    <img src="{{ departmentModel.image.file_name | media }}" alt="">
    {% endif %}
</div>

departmentSeries范围。

public function scopeDepartmentSeries( $query ){
        $children = $query->getModel()->getChildren();
        // dd($children);
        if ( count( $children ) > 0 ) {
            $seriesArray = array (  );

            foreach ($children as $child) {
                $childrenIds[] = 'Filter[departments][]='.$child->id;

                foreach ($child->series (  ) as $series) {

                    if (!in_array($series->id,$seriesArray)) $seriesArray[] = $series->id;

                    if (!array_key_exists($series->id,$seriesArray)) $seriesArray[$series->id] = $series->name;

                }
            } // endforeach children as child
            $childrenString = implode( '&', $childrenIds );
            return ["series" => Series::whereIn ( 'id',$seriesArray )->get (  ),
                    "childrenString" => $childrenString];
        }
        return ["series" => $query->getModel()->series(  )];
    }

1 个答案:

答案 0 :(得分:1)

您可以使用Raw查询并将<iframe id="F1" src="URL 1"></iframe> <iframe id="F2" src="URL 2"></iframe> <iframe id="F3" src="URL 3"></iframe> <iframe id="F4" src="URL 4"></iframe> 转换为模型,您可以编写此代码。

fetched id

如果您发现任何困难,请发表评论。

更新

  

我的部门模型

$sql = 'SELECT DISTINCT series_id FROM depcore_parts_products_series WHERE product_id IN (SELECT DISTINCT product_id FROM depcore_parts_products_departments WHERE department_id = :dep_id');

$data = ['dep_id' => 2];
$query = \DB::select($sql, $data);
$data = $query;

foreach ($data as $model) {
    $ids[] = $model->series_id;
}

$returnData = Series::whereIn('id',$ids)->get();
// dd($returnData);

return $returnData;
  

use \October\Rain\Database\Traits\SimpleTree; public $belongsTo = [ 'parent' => ['HardikSatasiya\StackDemo\Models\Departments', 'key' => 'parent_id'], ]; public $hasMany = [ 'children' => ['HardikSatasiya\StackDemo\Models\Departments', 'key' => 'parent_id'], ]; public function series() { $sql = 'SELECT DISTINCT series_id FROM hardiksatasiya_stackdemo_product_series WHERE product_id IN (SELECT DISTINCT product_id FROM hardiksatasiya_stackdemo_department_product WHERE department_id = :dep_id)'; $data = ['dep_id' => $this->id]; $query = \DB::select($sql, $data); $data = $query; foreach ($data as $model) { $ids[] = $model->series_id; } $returnData = Series::whereIn('id',$ids)->get(); // dd($returnData); return $returnData; } public function scopeDepartmentSeries( $query ) { $children = $query->getModel()->getChildren(); //dd($children); if ( count( $children ) > 0 ) { $seriesArray = array ( ); foreach ($children as $child) { $childrenIds[] = 'Filter[departments][]='.$child->id; foreach ($child->series ( ) as $series) { if (!in_array($series->id,$seriesArray)) $seriesArray[] = $series->id; // if (!array_key_exists($series->id,$seriesArray)) $seriesArray[$series->id] = $series->name; } } // endforeach children as child $childrenString = implode( '&', $childrenIds ); return ["series" => Series::whereIn ( 'id',$seriesArray )->get ( ), "childrenString" => $childrenString]; } return ["series" => $query->getModel()->series( )]; }

page code section
  

我正在使用您提供的function onInit() { $departmentModel = \HardikSatasiya\StackDemo\Models\Departments::find(1); //dd($departmentModel->getChildren()); $this['departmentModel'] = $departmentModel; } ,它似乎在此处工作