Passed
Push — master ( b5049f...66570f )
by Mohammad
03:21
created

AbstractRepository::disableCaching()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 1
Metric Value
cc 1
eloc 2
c 1
b 0
f 1
nc 1
nop 0
dl 0
loc 4
rs 10
1
<?php
2
/**
3
 * Created by PhpStorm.
4
 * User: Hamza Alayed
5
 * Date: 11/29/18
6
 * Time: 9:38 AM.
7
 */
8
9
namespace Shamaseen\Repository\Generator\Utility;
10
11
use Exception;
12
use Illuminate\Container\Container as App;
13
use Illuminate\Contracts\Pagination\LengthAwarePaginator;
14
use Illuminate\Contracts\Pagination\Paginator;
15
use Illuminate\Database\Eloquent\Builder;
16
use Illuminate\Database\Eloquent\Collection;
17
use Illuminate\Database\Eloquent\Model;
18
use Illuminate\Database\Eloquent\ModelNotFoundException;
19
20
/**
21
 * Class Database.
22
 */
23
abstract class AbstractRepository implements ContractInterface
24
{
25
    protected $with = [];
26
27
    /**
28
     * @var App
29
     */
30
    protected $app;
31
32
    /** @var string */
33
    protected $order = null;
34
35
    protected $direction = 'desc';
36
37
    /**
38
     * @var Entity
39
     */
40
    protected $model;
41
42
    /**
43
     * @var bool
44
     */
45
    private $trash = false;
46
47
    /**
48
     * @var bool
49
     */
50
    private $withTrash = false;
51
52
    /**
53
     * @var bool
54
     */
55
    private $allowCaching = true;
56
57
    /**
58
     * @var array
59
     */
60
    private $cache = [];
61
62
    /**
63
     * @param App $app
64
     */
65
    public function __construct(App $app)
66
    {
67
        $this->app = $app;
68
        $this->makeModel();
69
    }
70
71
    protected function makeModel()
72
    {
73
        $this->model = $this->app->make($this->getModelClass());
74
    }
75
76
    /**
77
     * @return string
78
     */
79
    abstract protected function getModelClass(): string;
80
81
    /**
82
     * @param int   $limit
83
     * @param array $criteria
84
     *
85
     * @return Paginator
86
     */
87
    public function simplePaginate($limit = 10, $criteria = [])
88
    {
89
        return $this->filter($criteria)->simplePaginate($limit);
90
    }
91
92
    /**
93
     * @return \Illuminate\Database\Query\Builder|Entity
94
     */
95
    public function builder()
96
    {
97
        return $this->model->query();
98
    }
99
100
    /**
101
     * @param array $criteria
102
     *
103
     * @return Builder
104
     */
105
    public function filter($criteria = [])
106
    {
107
        $criteria = $this->order($criteria);
108
109
        /** @var Entity $latest */
110
        $latest = $this->model->with($this->with);
111
        if ('' != $this->order) {
112
            $latest->orderBy($this->order, $this->direction);
113
        }
114
115
        if (isset($criteria['search'])) {
116
            foreach ($this->model->searchable as $method => $columns) {
117
                if (method_exists($this->model, $method)) {
118
                    $latest->orWhereHas($method, function ($query) use ($criteria, $columns) {
119
                        /* @var $query Builder */
120
                        $query->where(function ($query2) use ($criteria, $columns) {
121
                            /* @var $query2 Builder */
122
                            foreach ((array) $columns as $column) {
123
                                $query2->orWhere($column, 'like', '%'.$criteria['search'].'%');
124
                            }
125
                        });
126
                    });
127
                } else {
128
                    $latest->orWhere($columns, 'like', '%'.$criteria['search'].'%');
129
                }
130
            }
131
        }
132
        unset($criteria['search']);
133
134
        if ($this->trash) {
135
            $latest->onlyTrashed();
136
        }
137
        if ($this->withTrash) {
138
            $latest->withTrashed();
139
        }
140
141
        return $latest->where($criteria);
142
    }
143
144
    /**
145
     * prepare order for query.
146
     *
147
     * @param array $criteria
148
     *
149
     * @return array
150
     */
151
    private function order($criteria = [])
152
    {
153
        if (isset($criteria['order'])) {
154
            $this->order = $criteria['order'];
155
            unset($criteria['order']);
156
        }
157
158
        if (isset($criteria['direction'])) {
159
            $this->direction = $criteria['direction'];
160
            unset($criteria['direction']);
161
        }
162
        unset($criteria['page']);
163
164
        return $criteria;
165
    }
166
167
    /**
168
     * @param int   $limit
169
     * @param array $criteria
170
     *
171
     * @return LengthAwarePaginator
172
     */
173
    public function paginate($limit = 10, $criteria = [])
174
    {
175
        return $this->filter($criteria)->paginate($limit);
176
    }
177
178
    /**
179
     * @param array $criteria
180
     *
181
     * @param array $columns
182
     * @return Builder[]|Collection
183
     */
184
    public function get($criteria = [],$columns = [])
185
    {
186
        return $this->filter($criteria)->get($columns);
187
    }
188
189
    /**
190
     * @param $entityId
191
     * @param array $attributes
192
     *
193
     * @return bool|Collection|Model|Entity
194
     */
195
    public function update($entityId = 0, $attributes = [])
196
    {
197
        $item = $this->model->findOrFail($entityId);
198
199
        if ($item->update($attributes)) {
200
            return $item;
201
        }
202
203
        return false;
204
    }
205
206
    /**
207
     * @param $entityId
208
     *
209
     * @throws Exception
210
     *
211
     * @return bool
212
     */
213
    public function delete($entityId = 0)
214
    {
215
        $item = $this->model->findOrFail($entityId);
216
217
        return $item->delete();
218
    }
219
220
    /**
221
     * @param array $attributes
222
     *
223
     * @return bool
224
     */
225
    public function insert($attributes = [])
226
    {
227
        return $this->model->insert($attributes);
228
    }
229
230
    /**
231
     * @param string $name
232
     * @param string $entityId
233
     * @param array  $criteria
234
     *
235
     * @return array
236
     */
237
    public function pluck($name = 'name', $entityId = 'id', $criteria = [])
238
    {
239
        return $this->model->where($criteria)->pluck($name, $entityId)->toArray();
240
    }
241
242
    /**
243
     * @param $entityId
244
     * @param array $columns
245
     *
246
     * @return Entity|Model
247
     */
248
    public function find($entityId = 0, $columns = ['*'])
249
    {
250
        if($this->allowCaching)
251
        {
252
            if (isset($this->cache[$entityId]))
253
                return $this->cache[$entityId];
254
        }
255
256
        $entity = $this->model->with($this->with)->find($entityId, $columns);
257
258
        if($this->allowCaching)
259
            $this->cache[$entityId] = $entity;
260
261
        return $entity;
262
    }
263
264
    /**
265
     * @param $entityId
266
     * @param array $columns
267
     *
268
     *@throws ModelNotFoundException
269
     *
270
     * @return Entity|Model
271
     */
272
    public function findOrFail($entityId = 0, $columns = ['*'])
273
    {
274
        if($this->allowCaching)
275
        {
276
            if (isset($this->cache[$entityId]))
277
                return $this->cache[$entityId];
278
        }
279
280
        $entity = $this->model->with($this->with)->findOrFail($entityId, $columns);
281
282
        if($this->allowCaching)
283
            $this->cache[$entityId] = $entity;
284
285
        return $entity;
286
    }
287
288
    /**
289
     * @param array $filter
290
     * @param array $columns
291
     *
292
     * @return Entity|Model
293
     */
294
    public function first($filter = [], $columns = ['*'])
295
    {
296
        if($this->allowCaching)
297
        {
298
            if (isset($this->cache['first']))
299
                return $this->cache['first'];
300
        }
301
302
        $entity = $this->model->with($this->with)->select($columns)->where($filter)->first();
303
304
        if($this->allowCaching)
305
            $this->cache['first'] = $entity;
306
307
        return $entity;
308
    }
309
310
    /**
311
     * @param array $filter
312
     * @param array $columns
313
     *
314
     * @return Entity|Model
315
     */
316
    public function last($filter = [], $columns = ['*'])
317
    {
318
        if($this->allowCaching)
319
        {
320
            if (isset($this->cache['last']))
321
                return $this->cache['last'];
322
        }
323
324
        $entity = $this->model->with($this->with)->select($columns)->where($filter)
325
            ->orderBy('id','desc')->first();
326
327
        if($this->allowCaching)
328
            $this->cache['last'] = $entity;
329
330
        return $entity;
331
    }
332
333
    /**
334
     * @param $haystack
335
     * @param $needle
336
     *
337
     * @return Entity[]|Model[]|Collection
338
     */
339
    public function search($haystack, $needle)
340
    {
341
        return $this->model->where($haystack, 'like', $needle)->get();
342
    }
343
344
    /**
345
     * @param $criteria
346
     * @param array $columns
347
     *
348
     * @return Entity|Model
349
     */
350
    public function findBy($criteria = [], $columns = ['*'])
351
    {
352
        return $this->model->with($this->with)->select($columns)->where($criteria)->first();
353
    }
354
355
    /**
356
     * @param array $attributes
357
     *
358
     * @return Entity|Model
359
     */
360
    public function create($attributes = [])
361
    {
362
        return $this->model->create($attributes);
363
    }
364
365
    /**
366
     * @param array $attributes
367
     *
368
     * @return Entity|Model
369
     */
370
    public function createOrUpdate($attributes = [])
371
    {
372
        return $this->model->updateOrCreate($attributes);
373
    }
374
375
    /**
376
     * @param array $data
377
     *
378
     * @return Model
379
     */
380
    public function createOrFirst($data = [])
381
    {
382
        return $this->model->firstOrCreate($data);
383
    }
384
385
    /**
386
     * Get entity name.
387
     *
388
     * @return string
389
     */
390
    public function entityName()
391
    {
392
        return $this->getModelClass();
393
    }
394
395
    /**
396
     * @param int $entityId
397
     *
398
     * @return bool
399
     */
400
    public function restore($entityId = 0)
401
    {
402
        /** @var Entity|null $entity */
403
        $entity = $this->model->withTrashed()
404
            ->whereId($entityId)
405
            ->first();
406
        if ($entity) {
0 ignored issues
show
introduced by
$entity is of type Shamaseen\Repository\Generator\Utility\Entity, thus it always evaluated to true.
Loading history...
407
            return $entity->restore() ?? false;
408
        }
409
410
        return false;
411
    }
412
413
    /**
414
     * @param int $entityId
415
     *
416
     * @return bool
417
     */
418
    public function forceDelete($entityId = 0)
419
    {
420
        /** @var Entity|null $entity */
421
        $entity = $this->model->withTrashed()
422
            ->whereId($entityId)
423
            ->first();
424
        if ($entity) {
0 ignored issues
show
introduced by
$entity is of type Shamaseen\Repository\Generator\Utility\Entity, thus it always evaluated to true.
Loading history...
425
            return $entity->forceDelete() ?? false;
426
        }
427
428
        return false;
429
    }
430
431
    public function trash()
432
    {
433
        $this->trash = true;
434
        $this->withTrash = false;
435
    }
436
437
    public function withTrash()
438
    {
439
        $this->trash = false;
440
        $this->withTrash = true;
441
    }
442
443
    public function disableCaching()
444
    {
445
        $this->allowCaching = false;
446
        return $this;
447
    }
448
449
    public function allowCaching()
450
    {
451
        $this->allowCaching = true;
452
        return $this;
453
    }
454
}
455