【问题标题】:jQuery DataTables Master/Details (child rows) as a laravel partial viewjQuery DataTables Master/Details(子行)作为 laravel 部分视图
【发布时间】:2015-09-28 01:43:29
【问题描述】:

我有一个 Laravel 应用程序,我在其中使用 jQuery DataTables (yajra/datatables laravel plugin) 来显示一些记录。我还使用 3 个子行来为他们显示更详细的信息。在子行中,我显示了一些额外的信息、包含每年内容数据的图表以及过去 6 个月的记录值。问题是我不能像填充第一行那样用数据填充最后 2 个子行,因为我不能将所有数据放入 1 个查询中。

这是提供数据表的控制器方法

public function getRowDetails()
{
    return view('reports.creates', compact('data'));
}

public function getRowDetailsData()
{

    $kpi = $this->getUserActiveKpi();
    $data = DB::table('reports')
              ->orderBy('month','desc')
              ->groupBy('kpi_id')
              ->take(5)
              ->get();
    return Datatables::of($kpi, $data)
              ->make(true);
}

private function getUserActiveKpi(){
    $user = Auth::user();
    $kpis = DB::table('kpis')
              ->where('kpi_status',1)
              ->where('responsible_user', $user->id);
    return $kpis;
}

这是初始化脚本:

$(document).ready(function () {
    var table;
    table = $('#monthly_table').DataTable({
        processing: true,
        serverSide: true,
        dom: "fr<'clear'>Ttip",
        ajax: '{{ url("reports/row-details-data") }}',
        tableTools: {.....},
        columns: [.....],
        order: [[1, 'asc']]
    });
});

以下是返回子行数据的函数:

var kpi;
function kpi_info(d) {
    // `d` is the original data object for the row
    return '<table cellpadding="5" cellspacing="0" border="0" style="padding-left:50px;">'+
    '<tr>' +
    '<td>KPI:</td>' +
    '<td>' + d.kpi_code + '</td>' +
    '</tr>' +
    '<tr>' +
    '<td>Workload:</td>' +
    '<td>' + d.kpi_workload + '</td>' +
    '</tr>' +
    '<tr>' +
    '<td>KPI Description:</td>' +
    '<td>'+ d.kpi_description + '</td>' +
    '</tr>' +
    '</table>'
}
function kpi_values(d) {
    // `d` is the original data object for the row
    kpi = d.id;
    // it returns the id, here I want to return the partial view 
    // that contains the data using the *kpi* as a parameter
    return kpi; 
}
function kpi_graph(d) {
    kpi = d.id;
    // it returns the id, here I want to return the partial view that
    // contains the graph using the *kpi* as a parameter
    return kpi; 
}

这是显示它们的功能:

$('#monthly_table tbody').on('click', 'td.details-control', function () {
        var tr = $(this).closest('tr');
        var row = table.row(tr);
        if (row.child.isShown()) {
            // This row is already open - close it
            row.child.hide();
            tr.removeClass('shown');
        }
        else {
            // Open this row
            row.child(kpi_data(row.data())).show();
            tr.addClass('shown');
        }
    });

现在我想要实现的是,当我单击显示子行的链接之一时,将 kpi 参数提供给以下控制器方法

public function data($id){
    $data = DB::table('reports')
              ->where('kpi_id',$id)
              ->orderBy('month','desc')
              ->take(5)
              ->get();
    return view('reports.data', compact('data'));
}

如果您还有什么需要了解的,请询问,我们将不胜感激所有帮助

编辑

I cannot put all the data inside 1 query 我的意思是我必须结合3 个查询来做到这一点。首先是:

DB::table('kpis')
    ->where('kpi_status',1)
    ->where('responsible_user', $user->id);

第二个是:

DB::table('reports')
    ->where('kpi_id',$id)
    ->orderBy('month','desc')
    ->take(5)
    ->get();

第三个是:

DB::table('reports')
    ->where('reports.is_validated',1)
    ->where('reports.year',$current_year)
    ->orderBy('month','asc')
    ->get();

我想不出一个查询可以一次获取所有这些数据。

注意

还有另一个查询,如上一个带有$prev_year 参数的查询。

编辑 2

Schema::create('kpis', function(Blueprint $table)
    {
        $table->increments('id');
        $table->string('kpi_code');
        $table->string('kpi_description');
    });

Schema::create('reports', function(Blueprint $table)
    {
        $table->increments('id');
        $table->integer('kpi_id')->unsigned()->nullable(); 
        //fk kpi -> values
        $table->float('value');
        $table->integer('month',false,false,'2');
        $table->integer('year',false,false,'4');
    });

Schema::table('reports', function($table){
        $table->foreign('kpi_id')->references('id')->on('kpis');
    });

【问题讨论】:

  • 您能解释一下“我不能将所有数据都放在 1 个查询中”是什么意思吗?并举一些例子。
  • @whoacowboy 编辑了问题
  • 数据是否相关?你可以利用 Laravel 的 Eloquent。
  • 是的,我正在使用 eloquent
  • 当我使用DB::table(...) 时,我通常将其保存用于极其复杂的查询。如果您以正确的方式设置模型,则可以执行类似的操作。 $kpis = Kpi::with('reports')-&gt;where('kpi_status',1)-&gt;where('responsible_user', $user-&gt;id)-&gt;get();您必须展示您的数据如何关联才能帮助您。

标签: php laravel datatables laravel-5


【解决方案1】:

此代码需要编辑,但希望您能理解。

我会查看 Eloquent: Relationships > Defining Relationships > One To Many 以及 Datables 演示网站页面 EloquentController.php - eloquent.getHasMany.title.

Kpi 模型

<?php namespace App;
use Illuminate\Database\Eloquent\Model;

class Kpi extends Model {

  /**
   * Get the reports for the kpi.
   */
  public function reports()
  {
    return $this->hasMany('App\Report')
        ->orderBy('month','desc');
  }
  /**
   * Get the Kpis for a specific user
   */
  public function scopeForUser($query, $user_id)
  {
        $query->where('kpi_status',1)
      ->where('responsible_user', $user_id);
  }
}

报告模型

<?php namespace App;
use Illuminate\Database\Eloquent\Model;

class Report extends Model {
    /**
     * A report belongs to a kpi
     *
     * @return mixed
     */
    public function kpi()
    {
        return $this->belongsTo('App\Kpi');
    }
    /**
     * Get the reports for a specific year
     */
    public function scopeForYear($query, $year)
    {
        $query->where('is_validated',1)
            ->where('year',$year)
            ->orderBy('month','asc');
    }
}

控制器

public function getRowDetails()
{
    return view('reports.creates');
}

public function getRowDetailsData()
{
    if (Auth::guest())
    {
        return ['status'=>'error', 'nessage' => 'Unauthorized user.'];
    }
    $user_id = Auth::user()->id;
    $kpis = Kpi::with(['reports' => function($q){
        $q->take(5);
    })->forUser($user_id)->get();
  return Datatables::of($kpis)
           ->make(true);
}

-&gt;take(5) 可能会将您的查询限制为总共只有 5 条记录,而不是每个 KPI 的 5 份报告。如果是这种情况,请查看this article

按 cmets 更新

您使用的插件似乎没有提供嵌套循环

你也许可以做这样的事情,但我从未使用过那个插件,所以我无法为你提供更多信息。

columns: [
  {data: 'kpi_code', name: 'kpi'},
  {data: 'kpi_workload', name: 'workload'},
  {data: 'kpi_description', name: 'description'},
  {data: 'reports[0].name', name: 'report_1'},
  {data: 'reports[1].name', name: 'report_2'},
  {data: 'reports[2].name', name: 'report_3'},
  {data: 'reports[3].name', name: 'report_4'},
  {data: 'reports[4].name', name: 'report_5'}
]    

【讨论】:

  • -&gt;take(5) 工作正常。但是我似乎无法通过 javascript 遍历报告中的所有 5 条记录
  • @xhulio 我更新了我的答案,我想你可能对那个插件不走运。我认为可能需要针对您的具体问题提出一个新问题。
  • 我正在用 javascript 循环它们,只是它不接受 data.report[i].name 的任何变量,它说 cannot read property name of undefined
  • 用 s 试试data.reports[i].name
  • 这不是问题所在。实际上我在for循环中放了一个错误的计数器,因此它显示undefined error,因为索引不存在。
猜你喜欢
  • 1970-01-01
  • 2012-02-20
  • 1970-01-01
  • 1970-01-01
  • 2019-02-01
  • 2010-11-15
  • 1970-01-01
  • 2012-07-07
  • 2020-11-01
相关资源
最近更新 更多