Passed
Pull Request — main (#69)
by Tan
03:05
created

VisitorLogsService::trackPostView()   A

Complexity

Conditions 4
Paths 4

Size

Total Lines 27
Code Lines 14

Duplication

Lines 0
Ratio 0 %

Importance

Changes 9
Bugs 2 Features 0
Metric Value
cc 4
eloc 14
nc 4
nop 3
dl 0
loc 27
rs 9.7998
c 9
b 2
f 0
1
<?php
2
3
namespace CSlant\Blog\Api\Services;
4
5
use Carbon\Carbon;
6
use CSlant\Blog\Api\Models\VisitorLog;
7
use CSlant\Blog\Core\Models\Post;
8
use Illuminate\Database\Eloquent\Model;
9
10
class VisitorLogsService
11
{
12
    /**
13
     * @param  int  $postId
14
     * @param  string|null  $ipAddress
15
     * @param  string|null  $userAgent
16
     *
17
     * @return VisitorLog|Model
18
     */
19
    public function trackPostView(
20
        int $postId,
21
        ?string $ipAddress,
22
        ?string $userAgent = null
23
    ): Model|VisitorLog {
24
        $now = Carbon::now();
25
        $post = Post::query()->lockForUpdate()->findOrFail($postId);
26
27
        $visitorLog = VisitorLog::query()->firstOrNew([
28
            'viewable_id' => $post->getKey(),
29
            'viewable_type' => Post::class,
30
            'ip_address' => $ipAddress ?: '',
31
        ]);
32
33
        $shouldCountView = !$visitorLog->exists || $now->isAfter($visitorLog->expired_at);
34
35
        if ($shouldCountView) {
36
            $visitorLog->fill([
37
                'user_agent' => $userAgent,
38
                'expired_at' => $now->copy()->addMinutes((int) config('blog-core.view_throttle_minutes')),
39
            ]);
40
            $visitorLog->save();
41
42
            Post::where('id', $postId)->increment('views');
43
        }
44
45
        return $visitorLog;
46
    }
47
}
48