Passed
Push — master ( 34d55a...7b347a )
by Guillaume
24:04
created

Clockify::runningTimer()   A

Complexity

Conditions 2
Paths 5

Size

Total Lines 16
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 9
CRAP Score 2

Importance

Changes 2
Bugs 0 Features 2
Metric Value
cc 2
eloc 9
nc 5
nop 0
dl 0
loc 16
ccs 9
cts 9
cp 1
crap 2
rs 9.9666
c 2
b 0
f 2
1
<?php
2
3
namespace Godbout\Alfred\Time\Services;
4
5
use Carbon\Carbon;
6
use Godbout\Alfred\Time\Workflow;
7
use GuzzleHttp\Client;
8
9
class Clockify extends TimerService
10
{
11
    private $client;
12
13
14 60
    public function __construct($apiToken)
15
    {
16 60
        $this->client = new Client([
17 60
            'base_uri' => 'https://api.clockify.me/api/v1/',
18
            'headers' => [
19 60
                'content-type' => 'application/json',
20 60
                'X-Api-Key' => $apiToken
21
            ]
22
        ]);
23 60
    }
24
25 12
    public function projects()
26
    {
27
        try {
28 12
            $user = json_decode(
29 12
                $this->client->get("user")->getBody()->getContents()
30
            );
31
32 8
            Workflow::getConfig()->write('clockify.active_workspace_id', $user->activeWorkspace);
33
34 8
            $response = $this->client->get("workspaces/{$user->activeWorkspace}/projects?page-size=148");
35
36 8
            $projects = json_decode($response->getBody()->getContents());
37
38 8
            return array_column($projects, 'name', 'id');
39 4
        } catch (\Exception $e) {
40 4
            return [];
41
        }
42
    }
43
44 12
    public function tags()
45
    {
46
        try {
47 12
            $workspaceId = Workflow::getConfig()->read('clockify.active_workspace_id');
48
49 12
            $response = $this->client->get("workspaces/$workspaceId/tags");
50 8
            $tags = json_decode($response->getBody()->getContents());
51
52 8
            return array_column($tags, 'name', 'id');
53 4
        } catch (\Exception $e) {
54 4
            return [];
55
        }
56
    }
57
58 36
    public function startTimer()
59
    {
60
        try {
61 36
            $workspaceId = Workflow::getConfig()->read('clockify.active_workspace_id');
62
63 36
            $response = $this->client->post(
64 36
                "workspaces/$workspaceId/time-entries",
65 36
                $this->buildPayload()
66
            );
67
68 36
            $timer = json_decode($response->getBody()->getContents());
69
70 36
            if (! isset($timer->id)) {
71 36
                return false;
72
            }
73
        } catch (\Exception $e) {
74
            return false;
75
        }
76
77 36
        return $timer->id;
78
    }
79
80 36
    protected function buildPayload()
81
    {
82
        $payload = [
83
            'json' => [
84 36
                'start' => (new \DateTime())->format('Y-m-d\TH:i:s\Z'),
85 36
                'description' => getenv('timer_description'),
86
            ]
87
        ];
88
89 36
        if (getenv('timer_project_id') !== false) {
90 36
            $payload['json']['projectId'] = getenv('timer_project_id');
91
        }
92
93 36
        if (getenv('timer_tag_id') !== false) {
94 36
            $payload['json']['tagIds'] = [getenv('timer_tag_id')];
95
        }
96
97 36
        return $payload;
98
    }
99
100 37
    public function stopCurrentTimer()
101
    {
102 37
        $user = json_decode(
103 37
            $this->client->get("user")->getBody()->getContents()
104
        );
105
106 37
        if ($this->runningTimer()) {
107 36
            $response = $this->client->patch("workspaces/{$user->activeWorkspace}/user/{$user->id}/time-entries", [
108
                'json' => [
109 36
                    'end' => (new \DateTime())->format('Y-m-d\TH:i:s\Z'),
110
                ]
111
            ]) ;
112
113 36
            $timer = json_decode($response->getBody()->getContents());
114
115 36
            if (! isset($timer->timeInterval->end)) {
116
                throw new \Exception("Can't stop current running timer.", 1);
117
            }
118
119 36
            return true;
120
        }
121
122 5
        return false;
123
    }
124
125 60
    public function runningTimer()
126
    {
127
        try {
128 60
            $user = json_decode(
129 60
                $this->client->get("user")->getBody()->getContents()
130
            );
131
132 44
            $response = $this->client->get(
133 44
                "workspaces/{$user->activeWorkspace}/user/{$user->id}/time-entries?in-progress=true"
134
            );
135
136 44
            $timer = json_decode($response->getBody()->getContents());
137
138 44
            return $timer[0]->id ?? false;
139 16
        } catch (\Exception $e) {
140 16
            return false;
141
        }
142
    }
143
144 4
    public function pastTimers()
145
    {
146
        try {
147 4
            $user = json_decode(
148 4
                $this->client->get("user")->getBody()->getContents()
149
            );
150
151 4
            $response = $this->client->get("workspaces/{$user->activeWorkspace}/user/{$user->id}/time-entries", [
152 4
                'start' => Carbon::today(),
153 4
                'end' => Carbon::today()->subDays(30),
154
            ]);
155 4
            $clockifyTimers = json_decode($response->getBody()->getContents());
156
157 4
            return $this->convertToPastTimers($clockifyTimers);
158
        } catch (\Exception $e) {
159
            return [];
160
        }
161
    }
162
163 8
    public function continueTimer($timerId = null)
164
    {
165
        /**
166
         * Timer attributes are stored in env variables
167
         * gathered in startTimer.
168
         */
169 8
        return $this->startTimer();
170
    }
171
172 4
    protected function convertToPastTimers($clockifyTimers)
173
    {
174 4
        $projects = $this->projects();
175 4
        $tags = $this->tags();
176
177
        return array_map(function ($clockifyTimer) use ($projects, $tags) {
178 4
            return $this->buildPastTimerObject($clockifyTimer, $projects, $tags);
179 4
        }, $clockifyTimers);
180
    }
181
182 4
    protected function buildPastTimerObject($clockifyTimer, $projects, $tags)
183
    {
184 4
        $pastTimer = [];
185
186 4
        $pastTimer['id'] = $clockifyTimer->id;
187 4
        $pastTimer['description'] = $clockifyTimer->description;
188
189 4
        if (isset($clockifyTimer->projectId)) {
190 4
            $pastTimer['project_id'] = $clockifyTimer->projectId;
191 4
            $pastTimer['project_name'] = $projects[$clockifyTimer->projectId];
192
        }
193
194 4
        if (isset($clockifyTimer->tagIds[0])) {
195 4
            $pastTimer['tag_id'] = $clockifyTimer->tagIds[0];
196 4
            $pastTimer['tags'] = $tags[$clockifyTimer->tagIds[0]];
197
        }
198
199 4
        $pastTimer['duration'] = $clockifyTimer->timeInterval->duration;
200
201 4
        return (object) $pastTimer;
202
    }
203
}
204