Failed Conditions
Push — master ( 4f9353...7eeb29 )
by Michel
02:37
created

SyncService::parseTimeEntry()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 20
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 20
rs 9.4285
c 0
b 0
f 0
cc 3
eloc 12
nc 3
nop 1
1
<?php
2
declare(strict_types=1);
3
4
namespace TogglJira\Service;
5
6
use GuzzleHttp\Command\Guzzle\GuzzleClient;
7
use Psr\Log\LoggerAwareInterface;
8
use Psr\Log\LoggerAwareTrait;
9
use TogglJira\Entity\WorkLogEntry;
10
use TogglJira\Hydrator\WorkLogHydrator;
11
use TogglJira\Jira\Api;
12
13
class SyncService implements LoggerAwareInterface
14
{
15
    use LoggerAwareTrait;
16
17
    /**
18
     * @var Api
19
     */
20
    private $api;
21
    /**
22
     * @var GuzzleClient
23
     */
24
    private $togglClient;
25
    /**
26
     * @var WorkLogHydrator
27
     */
28
    private $workLogHydrator;
29
    /**
30
     * @var string
31
     */
32
    private $userID;
33
34
    /**
35
     * @param Api $api
36
     * @param GuzzleClient $togglClient
37
     * @param WorkLogHydrator $workLogHydrator
38
     * @param string $userID
39
     */
40
    public function __construct(Api $api, GuzzleClient $togglClient, WorkLogHydrator $workLogHydrator, string $userID)
41
    {
42
        $this->api = $api;
43
        $this->togglClient = $togglClient;
44
        $this->workLogHydrator = $workLogHydrator;
45
        $this->userID = $userID;
46
    }
47
48
    /**
49
     * @throws \Exception
50
     * @return void
51
     */
52
    public function sync(string $startDate): void
53
    {
54
        $workLogEntries = [];
55
56
        try {
57
            /** @var array $timeEntries */
58
            $timeEntries = $this->togglClient->getTimeEntries(['start_date' => $startDate]);
59
        } catch (\Exception $e) {
60
            $this->logger->error(
61
                "Failed to get time entries from Toggl: {$e->getMessage()}",
62
                ['exception' => $e]
63
            );
64
            return;
65
        }
66
67
        foreach ($timeEntries as $timeEntry) {
68
            $workLogEntry = $this->parseTimeEntry($timeEntry);
69
70
            if (!$workLogEntry) {
71
                continue;
72
            }
73
74
            $workLogEntries[] = $workLogEntry;
75
76
            $this->logger->info("Found time entry for user story {$workLogEntry->getIssueID()}");
77
        }
78
79
        /** @var WorkLogEntry $workLogEntry */
80
        foreach ($workLogEntries as $workLogEntry) {
81
            try {
82
                $this->api->addWorkLogEntry(
83
                    $workLogEntry->getIssueID(),
84
                    $workLogEntry->getTimeSpent(),
85
                    $this->userID,
86
                    $workLogEntry->getComment(),
87
                    $workLogEntry->getSpentOn()->format(DATE_ATOM)
88
                );
89
90
                $this->logger->info("Added worklog entry for issue {$workLogEntry->getIssueID()}");
91
            } catch (\Exception $e) {
92
                $this->logger->error("Could not add worklog entry: {$e->getMessage()}", ['exception' => $e]);
93
            }
94
        }
95
96
        $this->logger->info('All done for today, time to go home!');
97
    }
98
99
    /**
100
     * @param array $timeEntry
101
     * @return WorkLogEntry|null
102
     * @throws \Exception
103
     */
104
    private function parseTimeEntry(array $timeEntry): ?WorkLogEntry
105
    {
106
        $data = [
107
            'issueID' => explode(' ', $timeEntry['description'])[0],
108
            'timeSpent' => $timeEntry['duration'],
109
            'comment' => $timeEntry['description'],
110
            'spentOn' => $timeEntry['at']
111
        ];
112
113
        if (strpos($data['issueID'], '-') === false) {
114
            $this->logger->warning('Could not parse issue string, cannot link to Jira');
115
            return null;
116
        }
117
118
        if ($data['timeSpent'] < 0) {
119
            $this->logger->info("0 seconds, or timer still running for {$data['issueID']}, skipping");
120
            return null;
121
        }
122
123
        return $this->workLogHydrator->hydrate($data, new WorkLogEntry());
124
    }
125
}
126