Release::updateRelease()   A
last analyzed

Complexity

Conditions 4
Paths 4

Size

Total Lines 29
Code Lines 22

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 22
c 0
b 0
f 0
dl 0
loc 29
rs 9.568
cc 4
nc 4
nop 14

How to fix   Many Parameters   

Many Parameters

Methods with many parameters are not only hard to understand, but their parameters also often become inconsistent when you need more, or different data.

There are several approaches to avoid long parameter lists:

1
<?php
2
3
namespace App\Models;
4
5
use Blacklight\ElasticSearchSiteSearch;
6
use Blacklight\ManticoreSearch;
7
use Illuminate\Contracts\Pagination\LengthAwarePaginator;
8
use Illuminate\Database\Eloquent\Factories\HasFactory;
9
use Illuminate\Database\Eloquent\Model;
10
use Illuminate\Database\Eloquent\Relations\BelongsTo;
11
use Illuminate\Database\Eloquent\Relations\HasMany;
12
use Illuminate\Database\Eloquent\Relations\HasOne;
13
use Illuminate\Support\Arr;
14
use Illuminate\Support\Facades\Cache;
15
use Illuminate\Support\Facades\DB;
16
17
class Release extends Model
18
{
19
    use HasFactory;
0 ignored issues
show
Bug introduced by
The trait Illuminate\Database\Eloquent\Factories\HasFactory requires the property $factoryClass which is not provided by App\Models\Release.
Loading history...
20
21
    /**
22
     * @var bool
23
     */
24
    protected $dateFormat = false;
25
26
    /**
27
     * @var bool
28
     */
29
    public $timestamps = false;
30
31
    /**
32
     * @var array
33
     */
34
    protected $guarded = [];
35
36
    public function group(): BelongsTo
37
    {
38
        return $this->belongsTo(UsenetGroup::class, 'groups_id');
39
    }
40
41
    public function download(): HasMany
42
    {
43
        return $this->hasMany(UserDownload::class, 'releases_id');
44
    }
45
46
    public function userRelease(): HasMany
47
    {
48
        return $this->hasMany(UsersRelease::class, 'releases_id');
49
    }
50
51
    public function file(): HasMany
52
    {
53
        return $this->hasMany(ReleaseFile::class, 'releases_id');
54
    }
55
56
    public function category(): BelongsTo
57
    {
58
        return $this->belongsTo(Category::class, 'categories_id');
59
    }
60
61
    public function predb(): BelongsTo
62
    {
63
        return $this->belongsTo(Predb::class, 'predb_id');
64
    }
65
66
    public function failed(): HasMany
67
    {
68
        return $this->hasMany(DnzbFailure::class, 'release_id');
69
    }
70
71
    public function nfo(): HasOne
72
    {
73
        return $this->hasOne(ReleaseNfo::class, 'releases_id');
74
    }
75
76
    public function comment(): HasMany
77
    {
78
        return $this->hasMany(ReleaseComment::class, 'releases_id');
79
    }
80
81
    public function releaseGroup(): HasMany
82
    {
83
        return $this->hasMany(ReleasesGroups::class, 'releases_id');
84
    }
85
86
    public function video(): BelongsTo
87
    {
88
        return $this->belongsTo(Video::class, 'videos_id');
89
    }
90
91
    public function videoData(): HasOne
92
    {
93
        return $this->hasOne(VideoData::class, 'releases_id');
94
    }
95
96
    public function episode(): BelongsTo
97
    {
98
        return $this->belongsTo(TvEpisode::class, 'tv_episodes_id');
99
    }
100
101
    public function movieInfo(): BelongsTo
102
    {
103
        return $this->belongsTo(MovieInfo::class, 'movieinfo_id');
104
    }
105
106
    /**
107
     * Insert a single release returning the ID on success or false on failure.
108
     *
109
     * @param  array  $parameters  Insert parameters, must be escaped if string.
110
     * @return bool|int
111
     *
112
     * @throws \Exception
113
     */
114
    public static function insertRelease(array $parameters = [])
115
    {
116
        $passwordStatus = config('nntmux_settings.check_passworded_rars') === true ? -1 : 0;
117
        $parameters['id'] = self::query()
118
            ->insertGetId(
119
                [
120
                    'name' => $parameters['name'],
121
                    'searchname' => $parameters['searchname'],
122
                    'totalpart' => $parameters['totalpart'],
123
                    'groups_id' => $parameters['groups_id'],
124
                    'adddate' => now(),
125
                    'guid' => $parameters['guid'],
126
                    'leftguid' => $parameters['guid'][0],
127
                    'postdate' => $parameters['postdate'],
128
                    'fromname' => $parameters['fromname'],
129
                    'size' => $parameters['size'],
130
                    'passwordstatus' => $passwordStatus,
131
                    'haspreview' => -1,
132
                    'categories_id' => $parameters['categories_id'],
133
                    'nfostatus' => -1,
134
                    'nzbstatus' => $parameters['nzbstatus'],
135
                    'isrenamed' => $parameters['isrenamed'],
136
                    'iscategorized' => 1,
137
                    'predb_id' => $parameters['predb_id'],
138
                    'ishashed' => $parameters['ishashed'] ?? 0,
139
                ]
140
            );
141
142
        if (config('nntmux.elasticsearch_enabled') === true) {
143
            (new ElasticSearchSiteSearch)->insertRelease($parameters);
144
        } else {
145
            (new ManticoreSearch)->insertRelease($parameters);
146
        }
147
148
        return $parameters['id'];
0 ignored issues
show
Bug Best Practice introduced by
The expression return $parameters['id'] also could return the type Illuminate\Database\Eloquent\Builder which is incompatible with the documented return type boolean|integer.
Loading history...
149
    }
150
151
    /**
152
     * @throws \Exception
153
     */
154
    public static function updateRelease($id, $name, $searchName, $fromName, $categoryId, $parts, $grabs, $size, $postedDate, $addedDate, $videoId, $episodeId, $imDbId, $aniDbId): void
155
    {
156
        $movieInfoId = null;
157
        if (! empty($imDbId)) {
158
            $movieInfoId = MovieInfo::whereImdbid($imDbId)->first(['id']);
159
        }
160
        self::whereId($id)->update(
161
            [
162
                'name' => $name,
163
                'searchname' => $searchName,
164
                'fromname' => $fromName,
165
                'categories_id' => $categoryId,
166
                'totalpart' => $parts,
167
                'grabs' => $grabs,
168
                'size' => $size,
169
                'postdate' => $postedDate,
170
                'adddate' => $addedDate,
171
                'videos_id' => $videoId,
172
                'tv_episodes_id' => $episodeId,
173
                'imdbid' => $imDbId,
174
                'anidbid' => $aniDbId,
175
                'movieinfo_id' => $movieInfoId !== null ? $movieInfoId->id : $movieInfoId,
176
            ]
177
        );
178
179
        if (config('nntmux.elasticsearch_enabled') === true) {
180
            (new ElasticSearchSiteSearch)->updateRelease($id);
181
        } else {
182
            (new ManticoreSearch)->updateRelease($id);
183
        }
184
    }
185
186
    /**
187
     * @throws \Exception
188
     */
189
    public static function updateGrab(string $guid): void
190
    {
191
        $updateGrabs = ((int) Settings::settingValue('grabstatus') !== 0);
192
        if ($updateGrabs) {
193
            self::whereGuid($guid)->increment('grabs');
194
        }
195
    }
196
197
    /**
198
     * @return Model|null|static
199
     */
200
    public static function getCatByRelId($id)
201
    {
202
        return self::whereId($id)->first(['categories_id']);
203
    }
204
205
    public static function removeVideoIdFromReleases($videoId): int
206
    {
207
        return self::whereVideosId($videoId)->update(['videos_id' => 0, 'tv_episodes_id' => 0]);
208
    }
209
210
    public static function removeAnidbIdFromReleases($anidbID): int
211
    {
212
        return self::whereAnidbid($anidbID)->update(['anidbid' => -1]);
213
    }
214
215
    /**
216
     * @return \Illuminate\Database\Eloquent\Collection|\Illuminate\Support\Collection|static[]
217
     */
218
    public static function getTopDownloads()
219
    {
220
        $expiresAt = now()->addMinutes(config('nntmux.cache_expiry_long'));
221
        $releases = Cache::get(md5('topDownloads'));
222
        if ($releases !== null) {
223
            return $releases;
224
        }
225
        $releases = self::query()
226
            ->where('grabs', '>', 0)
227
            ->select(['id', 'searchname', 'guid', 'adddate'])
228
            ->selectRaw('SUM(grabs) as grabs')
229
            ->groupBy('id', 'searchname', 'adddate')
230
            ->havingRaw('SUM(grabs) > 0')
231
            ->orderByDesc('grabs')
0 ignored issues
show
Bug introduced by
'grabs' of type string is incompatible with the type Closure|Illuminate\Datab...\Database\Query\Builder expected by parameter $column of Illuminate\Database\Query\Builder::orderByDesc(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

231
            ->orderByDesc(/** @scrutinizer ignore-type */ 'grabs')
Loading history...
232
            ->limit(10)
233
            ->get();
234
235
        Cache::put(md5('topDownloads'), $releases, $expiresAt);
236
237
        return $releases;
238
    }
239
240
    /**
241
     * @return \Illuminate\Database\Eloquent\Collection|\Illuminate\Support\Collection|static[]
242
     */
243
    public static function getTopComments()
244
    {
245
        $expiresAt = now()->addMinutes(config('nntmux.cache_expiry_long'));
246
        $releases = Cache::get(md5('topComments'));
247
        if ($releases !== null) {
248
            return $releases;
249
        }
250
        $releases = self::query()
251
            ->where('comments', '>', 0)
252
            ->select(['id', 'guid', 'searchname'])
253
            ->selectRaw('SUM(comments) AS comments')
254
            ->groupBy('id', 'searchname', 'adddate')
255
            ->havingRaw('SUM(comments) > 0')
256
            ->orderByDesc('comments')
0 ignored issues
show
Bug introduced by
'comments' of type string is incompatible with the type Closure|Illuminate\Datab...\Database\Query\Builder expected by parameter $column of Illuminate\Database\Query\Builder::orderByDesc(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

256
            ->orderByDesc(/** @scrutinizer ignore-type */ 'comments')
Loading history...
257
            ->limit(10)
258
            ->get();
259
260
        Cache::put(md5('topComments'), $releases, $expiresAt);
261
262
        return $releases;
263
    }
264
265
    /**
266
     * @return \Illuminate\Database\Eloquent\Builder[]|\Illuminate\Database\Eloquent\Collection|\Illuminate\Database\Query\Builder[]|\Illuminate\Support\Collection|mixed
267
     */
268
    public static function getReleases()
269
    {
270
        $expiresAt = now()->addMinutes(config('nntmux.cache_expiry_long'));
271
        $releases = Cache::get(md5('releases'));
272
        if ($releases !== null) {
273
            return $releases;
274
        }
275
276
        $releases = self::query()
277
            ->select(['releases.*', 'g.name as group_name', 'c.title as category_name'])
278
            ->leftJoin('categories as c', 'c.id', '=', 'releases.categories_id')
279
            ->leftJoin('usenet_groups as g', 'g.id', '=', 'releases.groups_id')
280
            ->get();
281
282
        Cache::put(md5('releases'), $releases, $expiresAt);
283
284
        return $releases;
285
    }
286
287
    /**
288
     * Used for admin page release-list.
289
     *
290
     * @param  int  $page  The page number to retrieve
291
     * @return LengthAwarePaginator|mixed
292
     */
293
    public static function getReleasesRange(int $page = 1): mixed
294
    {
295
        $expiresAt = now()->addMinutes(config('nntmux.cache_expiry_long'));
296
        $cacheKey = md5('releasesRange_'.$page);
297
        $releases = Cache::get($cacheKey);
298
        if ($releases !== null) {
299
            return $releases;
300
        }
301
302
        $releases = self::query()
303
            ->select(
304
                [
305
                    'releases.id',
306
                    'releases.name',
307
                    'releases.searchname',
308
                    'releases.size',
309
                    'releases.guid',
310
                    'releases.totalpart',
311
                    'releases.postdate',
312
                    'releases.adddate',
313
                    'releases.grabs',
314
                    'cp.title as parent_category',
315
                    'c.title as sub_category',
316
                    DB::raw('CONCAT(cp.title, \' > \', c.title) AS category_name'),
317
                ]
318
            )
319
            ->leftJoin('categories as c', 'c.id', '=', 'releases.categories_id')
320
            ->leftJoin('root_categories as cp', 'cp.id', '=', 'c.root_categories_id')
321
            ->orderByDesc('releases.postdate')
0 ignored issues
show
Bug introduced by
'releases.postdate' of type string is incompatible with the type Closure|Illuminate\Datab...\Database\Query\Builder expected by parameter $column of Illuminate\Database\Query\Builder::orderByDesc(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

321
            ->orderByDesc(/** @scrutinizer ignore-type */ 'releases.postdate')
Loading history...
322
            ->paginate(config('nntmux.items_per_page'), ['*'], 'page', $page);
323
324
        Cache::put($cacheKey, $releases, $expiresAt);
325
326
        return $releases;
327
    }
328
329
    public static function getByGuid($guid)
330
    {
331
        $query = self::with([
332
            'group:id,name',
333
            'category:id,title,root_categories_id',
334
            'category.parent:id,title',
335
            'video:id,title,tvdb,trakt,tvrage,tvmaze,source',
336
            'video.tvInfo:videos_id,summary,image',
337
            'episode:id,title,firstaired,se_complete',
338
        ]);
339
340
        if (is_array($guid)) {
341
            $query->whereIn('guid', $guid);
342
        } else {
343
            $query->where('guid', $guid);
344
        }
345
346
        $releases = $query->get();
347
348
        $releases->each(function ($release) {
349
            $release->group_name = $release->group->name ?? null;
350
            $release->showtitle = $release->video->title ?? null;
351
            $release->tvdb = $release->video->tvdb ?? null;
352
            $release->trakt = $release->video->trakt ?? null;
353
            $release->tvrage = $release->video->tvrage ?? null;
354
            $release->tvmaze = $release->video->tvmaze ?? null;
355
            $release->source = $release->video->source ?? null;
356
            $release->summary = $release->video->tvInfo->summary ?? null;
357
            $release->image = $release->video->tvInfo->image ?? null;
358
            $release->title = $release->episode->title ?? null;
359
            $release->firstaired = $release->episode->firstaired ?? null;
360
            $release->se_complete = $release->episode->se_complete ?? null;
361
            $release->parent_category = $release->category->parent->title ?? null;
362
            $release->sub_category = $release->category->title ?? null;
363
            $release->category_name = $release->parent_category.' > '.$release->sub_category;
364
            $release->category_ids = $release->category->parentid.','.$release->category->id;
365
            $release->group_names = $release->releaseGroup->map(function ($relGroup) {
366
                return $relGroup->group->name;
367
            })->implode(',');
368
        });
369
370
        return is_array($guid) ? $releases : $releases->first();
371
    }
372
373
    /**
374
     * Get a range of releases. used in admin manage list.
375
     */
376
    public static function getFailedRange(): LengthAwarePaginator
377
    {
378
        $failedList = self::query()
379
            ->select(['name', 'searchname', 'size', 'guid', 'totalpart', 'postdate', 'adddate', 'grabs', 'cp.title as parent_category', 'c.title as sub_category', DB::raw("CONCAT(cp.title, ' > ', c.title) AS category_name")])
380
            ->rightJoin('dnzb_failures', 'dnzb_failures.release_id', '=', 'releases.id')
381
            ->leftJoin('categories as c', 'c.id', '=', 'releases.categories_id')
382
            ->leftJoin('root_categories as cp', 'cp.id', '=', 'c.root_categories_id')
383
            ->orderByDesc('postdate');
0 ignored issues
show
Bug introduced by
'postdate' of type string is incompatible with the type Closure|Illuminate\Datab...\Database\Query\Builder expected by parameter $column of Illuminate\Database\Query\Builder::orderByDesc(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

383
            ->orderByDesc(/** @scrutinizer ignore-type */ 'postdate');
Loading history...
384
385
        return $failedList->paginate(config('nntmux.items_per_page'));
386
    }
387
388
    /**
389
     * @return Release|false|\Illuminate\Database\Eloquent\Builder|\Illuminate\Database\Eloquent\Model|\Illuminate\Database\Query\Builder|object|null
390
     */
391
    public static function getAlternate(string $guid, int $userid)
392
    {
393
        $rel = self::whereGuid($guid)->first(['id', 'searchname', 'categories_id']);
394
395
        if ($rel === null) {
396
            return false;
397
        }
398
        DnzbFailure::insertOrIgnore(['release_id' => $rel['id'], 'users_id' => $userid, 'failed' => 1]);
399
400
        preg_match('/(^\w+[-_. ].+?\.(\d+p)).+/i', $rel['searchname'], $similar);
401
402
        if (! empty($similar)) {
403
            if (config('nntmux.elasticsearch_enabled') === true) {
404
                $searchResult = (new ElasticSearchSiteSearch)->indexSearch($similar[1], 10);
405
            } else {
406
                $searchResult = (new ManticoreSearch)->searchIndexes('releases_rt', $similar[1]);
407
                if (! empty($searchResult)) {
408
                    $searchResult = Arr::wrap(Arr::get($searchResult, 'id'));
409
                }
410
            }
411
412
            if (empty($searchResult)) {
413
                return false;
414
            }
415
416
            return self::query()->leftJoin('dnzb_failures as df', 'df.release_id', '=', 'releases.id')->whereIn('releases.id', $searchResult)->where('df.release_id', '=', null)->where('releases.categories_id', $rel['categories_id'])->where('id', '<>', $rel['id'])->orderByDesc('releases.postdate')->first(['guid']);
0 ignored issues
show
Bug introduced by
'releases.postdate' of type string is incompatible with the type Closure|Illuminate\Datab...\Database\Query\Builder expected by parameter $column of Illuminate\Database\Query\Builder::orderByDesc(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

416
            return self::query()->leftJoin('dnzb_failures as df', 'df.release_id', '=', 'releases.id')->whereIn('releases.id', $searchResult)->where('df.release_id', '=', null)->where('releases.categories_id', $rel['categories_id'])->where('id', '<>', $rel['id'])->orderByDesc(/** @scrutinizer ignore-type */ 'releases.postdate')->first(['guid']);
Loading history...
417
        }
418
419
        return false;
420
    }
421
422
    public static function checkGuidForApi($guid): bool
423
    {
424
        $check = self::whereGuid($guid)->first();
425
426
        return $check !== null;
427
    }
428
}
429