Completed
Branch 6.0 (9f50ba)
by Arjay
02:26
created

DataTable::buildPrintColumn()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 2
Bugs 0 Features 0
Metric Value
c 2
b 0
f 0
dl 0
loc 4
rs 10
cc 1
eloc 2
nc 1
nop 2
1
<?php
2
3
namespace Yajra\Datatables\Services;
4
5
use Illuminate\Contracts\View\Factory;
6
use Illuminate\Support\Collection;
7
use Maatwebsite\Excel\Classes\LaravelExcelWorksheet;
8
use Maatwebsite\Excel\Writers\LaravelExcelWriter;
9
use Yajra\Datatables\Contracts\DataTableButtonsContract;
10
use Yajra\Datatables\Contracts\DataTableContract;
11
use Yajra\Datatables\Contracts\DataTableScopeContract;
12
use Yajra\Datatables\Datatables;
13
14
abstract class DataTable implements DataTableContract, DataTableButtonsContract
15
{
16
    /**
17
     * @var \Yajra\Datatables\Datatables
18
     */
19
    protected $datatables;
20
21
    /**
22
     * @var \Illuminate\Contracts\View\Factory
23
     */
24
    protected $viewFactory;
25
26
    /**
27
     * Datatables print preview view.
28
     *
29
     * @var string
30
     */
31
    protected $printPreview;
32
33
    /**
34
     * List of columns to be exported.
35
     *
36
     * @var string|array
37
     */
38
    protected $exportColumns = '*';
39
40
    /**
41
     * List of columns to be printed.
42
     *
43
     * @var string|array
44
     */
45
    protected $printColumns = '*';
46
47
    /**
48
     * Query scopes.
49
     *
50
     * @var \Yajra\Datatables\Contracts\DataTableScopeContract[]
51
     */
52
    protected $scopes = [];
53
54
    /**
55
     * @param \Yajra\Datatables\Datatables $datatables
56
     * @param \Illuminate\Contracts\View\Factory $viewFactory
57
     */
58
    public function __construct(Datatables $datatables, Factory $viewFactory)
59
    {
60
        $this->datatables  = $datatables;
61
        $this->viewFactory = $viewFactory;
62
    }
63
64
    /**
65
     * Render view.
66
     *
67
     * @param $view
68
     * @param array $data
69
     * @param array $mergeData
70
     * @return \Illuminate\Http\JsonResponse|\Illuminate\View\View
71
     */
72
    public function render($view, $data = [], $mergeData = [])
73
    {
74
        if ($this->request()->ajax() && $this->request()->wantsJson()) {
75
            return $this->ajax();
76
        }
77
78
        switch ($this->datatables->getRequest()->get('action')) {
79
            case 'excel':
80
                return $this->excel();
81
82
            case 'csv':
83
                return $this->csv();
84
85
            case 'pdf':
86
                return $this->pdf();
87
88
            case 'print':
89
                return $this->printPreview();
90
91
            default:
92
                return $this->viewFactory->make($view, $data, $mergeData)->with('dataTable', $this->html());
93
        }
94
    }
95
96
    /**
97
     * Get Datatables Request instance.
98
     *
99
     * @return \Yajra\Datatables\Request
100
     */
101
    public function request()
102
    {
103
        return $this->datatables->getRequest();
104
    }
105
106
    /**
107
     * Export results to Excel file.
108
     *
109
     * @return mixed
110
     */
111
    public function excel()
112
    {
113
        return $this->buildExcelFile()->download('xls');
114
    }
115
116
    /**
117
     * Build excel file and prepare for export.
118
     *
119
     * @return mixed
120
     */
121
    protected function buildExcelFile()
122
    {
123
        return app('excel')->create($this->filename(), function (LaravelExcelWriter $excel) {
124
            $excel->sheet('exported-data', function (LaravelExcelWorksheet $sheet) {
125
                $sheet->fromArray($this->getDataForExport());
126
            });
127
        });
128
    }
129
130
    /**
131
     * Get filename for export.
132
     *
133
     * @return string
134
     */
135
    protected function filename()
136
    {
137
        return 'export_' . time();
138
    }
139
140
    /**
141
     * Get mapped columns versus final decorated output.
142
     *
143
     * @return array
144
     */
145 View Code Duplication
    protected function getDataForExport()
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
146
    {
147
        $decoratedData = $this->getAjaxResponseData();
148
149
        return array_map(function ($row) {
150
            if ($columns = $this->exportColumns()) {
151
                return $this->buildExportColumn($row, $columns);
152
            }
153
154
            return $row;
155
        }, $decoratedData);
156
    }
157
158
    /**
159
     * Get decorated data as defined in datatables ajax response.
160
     *
161
     * @return mixed
162
     */
163
    protected function getAjaxResponseData()
164
    {
165
        $this->datatables->getRequest()->merge(['length' => -1]);
166
167
        $response = $this->ajax();
168
        $data     = $response->getData(true);
169
170
        return $data['data'];
171
    }
172
173
    /**
174
     * Get export columns definition.
175
     *
176
     * @return array|string
177
     */
178
    private function exportColumns()
179
    {
180
        return is_array($this->exportColumns) ? $this->exportColumns : $this->getColumnsFromBuilder();
181
    }
182
183
    /**
184
     * Get columns definition from html builder.
185
     *
186
     * @return array
187
     */
188
    protected function getColumnsFromBuilder()
189
    {
190
        return $this->html()->getColumns();
191
    }
192
193
    /**
194
     * Optional method if you want to use html builder.
195
     *
196
     * @return \Yajra\Datatables\Html\Builder
197
     */
198
    public function html()
199
    {
200
        return $this->builder();
201
    }
202
203
    /**
204
     * Get Datatables Html Builder instance.
205
     *
206
     * @return \Yajra\Datatables\Html\Builder
207
     */
208
    public function builder()
209
    {
210
        return $this->datatables->getHtmlBuilder();
211
    }
212
213
    /**
214
     * @param array $row
215
     * @param array|\Illuminate\Support\Collection $columns
216
     * @return array
217
     */
218
    protected function buildExportColumn(array $row, $columns)
219
    {
220
        return $this->buildColumn($row, $columns, 'exportable');
221
    }
222
223
    /**
224
     * Build printable and exportable column.
225
     *
226
     * @param array $row
227
     * @param array|\Illuminate\Support\Collection $columns
228
     * @param string $type
229
     * @return array
230
     */
231
    protected function buildColumn(array $row, $columns, $type)
232
    {
233
        if ($columns instanceof Collection) {
234
            return $this->buildColumnByCollection($row, $columns, $type);
235
        }
236
237
        return array_only($row, $columns);
238
    }
239
240
    /**
241
     * Build column from collection.
242
     *
243
     * @param array $row
244
     * @param \Illuminate\Support\Collection $columns
245
     * @param string $type
246
     * @return array
247
     */
248
    protected function buildColumnByCollection(array  $row, Collection $columns, $type)
249
    {
250
        $results = [];
251
        foreach ($columns->all() as $column) {
252 View Code Duplication
            if ($column[$type]) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
253
                $data = array_get($row, $column['data']);
254
255
                $results[$column['title']] = $type == 'exportable' ? strip_tags($data) : $data;
256
            }
257
        }
258
259
        return $results;
260
    }
261
262
    /**
263
     * Export results to CSV file.
264
     *
265
     * @return mixed
266
     */
267
    public function csv()
268
    {
269
        return $this->buildExcelFile()->download('csv');
270
    }
271
272
    /**
273
     * Export results to PDF file.
274
     *
275
     * @return mixed
276
     */
277
    public function pdf()
278
    {
279
        return $this->buildExcelFile()->download('pdf');
280
    }
281
282
    /**
283
     * Display printable view of datatables.
284
     *
285
     * @return \Illuminate\Contracts\View\View
286
     */
287
    public function printPreview()
288
    {
289
        $data = $this->getDataForPrint();
290
        $view = $this->printPreview ?: 'datatables::print';
291
292
        return $this->viewFactory->make($view, compact('data'));
293
    }
294
295
    /**
296
     * Get mapped columns versus final decorated output.
297
     *
298
     * @return array
299
     */
300 View Code Duplication
    protected function getDataForPrint()
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
301
    {
302
        $decoratedData = $this->getAjaxResponseData();
303
304
        return array_map(function ($row) {
305
            if ($columns = $this->printColumns()) {
306
                return $this->buildPrintColumn($row, $columns);
307
            }
308
309
            return $row;
310
        }, $decoratedData);
311
    }
312
313
    /**
314
     * Get printable columns.
315
     *
316
     * @return array|string
317
     */
318
    protected function printColumns()
319
    {
320
        return is_array($this->printColumns) ? $this->printColumns : $this->getColumnsFromBuilder();
321
    }
322
323
    /**
324
     * Build printable column.
325
     *
326
     * @param array $row
327
     * @param array|\Illuminate\Support\Collection $columns
328
     * @return array
329
     */
330
    protected function buildPrintColumn(array $row, $columns)
331
    {
332
        return $this->buildColumn($row, $columns, 'printable');
333
    }
334
335
    /**
336
     * Add basic array query scopes.
337
     *
338
     * @param \Yajra\Datatables\Contracts\DataTableScopeContract $scope
339
     * @return $this
340
     */
341
    public function addScope(DataTableScopeContract $scope)
342
    {
343
        $this->scopes[] = $scope;
344
345
        return $this;
346
    }
347
348
    /**
349
     * @param array $row
350
     * @param $type
351
     * @param $column
352
     * @param $results
353
     * @return mixed
354
     */
355
    protected function getRowColumnData(array $row, $type, $column, $results)
356
    {
357
        if ($column[$type]) {
358
            $data = array_get($row, $column['data']);
359 View Code Duplication
            if ($type == 'exportable') {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
360
                $results[$column['title']] = strip_tags($data);
361
362
                return $results;
363
            } else {
364
                $results[$column['title']] = $data;
365
366
                return $results;
367
            }
368
        }
369
370
        return $results;
371
    }
372
373
    /**
374
     * Apply query scopes.
375
     *
376
     * @param \Illuminate\Database\Query\Builder|\Illuminate\Database\Eloquent\Builder $query
377
     * @return mixed
378
     */
379
    protected function applyScopes($query)
380
    {
381
        foreach ($this->scopes as $scope) {
382
            $scope->apply($query);
383
        }
384
385
        return $query;
386
    }
387
388
    /**
389
     * Get default builder parameters.
390
     *
391
     * @return array
392
     */
393
    protected function getBuilderParameters()
394
    {
395
        return [
396
            'order'   => [[0, 'desc']],
397
            'buttons' => [
398
                'create',
399
                [
400
                    'extend'  => 'collection',
401
                    'text'    => '<i class="fa fa-download"></i> Export',
402
                    'buttons' => [
403
                        'csv',
404
                        'excel',
405
                        'pdf',
406
                    ],
407
                ],
408
                'print',
409
                'reset',
410
                'reload',
411
            ],
412
        ];
413
    }
414
}
415