Passed
Pull Request — main (#54)
by Thierry
13:54
created

ReportService::__construct()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 7
Code Lines 0

Duplication

Lines 0
Ratio 0 %

Importance

Changes 3
Bugs 0 Features 0
Metric Value
cc 1
eloc 0
nc 1
nop 10
dl 0
loc 7
rs 10
c 3
b 0
f 0

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 Siak\Tontine\Service\Report;
4
5
use Illuminate\Support\Arr;
6
use Illuminate\Support\Collection;
7
use Illuminate\Support\Str;
8
use Siak\Tontine\Model\Round;
9
use Siak\Tontine\Model\Session;
10
use Siak\Tontine\Service\LocaleService;
11
use Siak\Tontine\Service\TenantService;
12
use Siak\Tontine\Service\Meeting\Saving\SavingService;
13
use Siak\Tontine\Service\Meeting\Saving\ProfitService;
14
use Siak\Tontine\Service\Meeting\SummaryService;
15
use Siak\Tontine\Service\Planning\SubscriptionService;
16
use Siak\Tontine\Service\Report\RoundService;
17
use Siak\Tontine\Service\Tontine\FundService;
18
19
use function compact;
20
use function strtolower;
21
use function trans;
22
23
class ReportService
24
{
25
    /**
26
     * @var int
27
     */
28
    private $depositsAmount;
29
30
    /**
31
     * @var int
32
     */
33
    private $remitmentsAmount;
34
35
    /**
36
     * @param LocaleService $localeService
37
     * @param TenantService $tenantService
38
     * @param SessionService $sessionService
39
     * @param MemberService $memberService
40
     * @param RoundService $roundService
41
     * @param FundService $fundService
42
     * @param SavingService $savingService
43
     * @param SummaryService $summaryService
44
     * @param ReportService $reportService
45
     * @param SubscriptionService $subscriptionService
46
     */
47
    public function __construct(protected LocaleService $localeService,
48
        protected TenantService $tenantService, protected SessionService $sessionService,
49
        protected MemberService $memberService, protected RoundService $roundService,
50
        protected FundService $fundService, protected SavingService $savingService,
51
        protected SummaryService $summaryService, protected ProfitService $profitService,
52
        protected SubscriptionService $subscriptionService)
53
    {}
54
55
    /**
56
     * Get pools with receivables and payables.
57
     *
58
     * @param Session $session
59
     *
60
     * @return Collection
61
     */
62
    public function getPools(Session $session): Collection
63
    {
64
        $this->depositsAmount = 0;
65
        $this->remitmentsAmount = 0;
66
        $pools = $this->tenantService->round()->pools;
67
68
        return $pools->each(function($pool) use($session) {
69
            $subscriptionCount = $pool->subscriptions()->count();
70
            $subscriptionIds = $pool->subscriptions()->pluck('id');
71
            // Receivables
72
            $query = $session->receivables()->whereIn('subscription_id', $subscriptionIds);
73
            // Expected
74
            $pool->receivables_count = $query->count();
75
            // Paid
76
            $pool->deposits_count = $query->whereHas('deposit')->count();
77
            // Amount
78
            $pool->deposits_amount = $pool->deposits_count * $pool->amount;
79
            $this->depositsAmount += $pool->deposits_amount;
80
81
            // Payables
82
            $query = $session->payables()->whereIn('subscription_id', $subscriptionIds);
83
            // Expected
84
            $pool->payables_count = $this->summaryService->getSessionRemitmentCount($pool, $session);
85
            // Paid
86
            $pool->remitments_count = $query->whereHas('remitment')->count();
87
            // Amount
88
            $pool->remitments_amount = $pool->remitments_count * $pool->amount * $subscriptionCount;
89
            $this->remitmentsAmount += $pool->remitments_amount;
90
        });
91
    }
92
93
    /**
94
     * @param Session $session
95
     * @param Collection $funds
96
     *
97
     * @return array
98
     */
99
    private function getFundClosings(Session $session, Collection $funds): array
100
    {
101
        $closings = $this->savingService->getSessionClosings($session);
102
        return Arr::only($closings, $funds->keys()->all());
103
    }
104
105
    /**
106
     * @param Session $session
107
     *
108
     * @return array
109
     */
110
    public function getClosings(Session $session): array
111
    {
112
        $closings = $this->savingService->getSessionClosings($session);
113
        $funds = $this->fundService->getFundList();
114
        return Arr::only($closings, $funds->keys()->all());
115
    }
116
117
    /**
118
     * @param Session $session
119
     *
120
     * @return array
121
     */
122
    public function getSessionReport(Session $session): array
123
    {
124
        $tontine = $this->tenantService->tontine();
125
        [$country] = $this->localeService->getNameFromTontine($tontine);
0 ignored issues
show
Bug introduced by
It seems like $tontine can also be of type null; however, parameter $tontine of Siak\Tontine\Service\Loc...e::getNameFromTontine() does only seem to accept Siak\Tontine\Model\Tontine, maybe add an additional type check? ( Ignorable by Annotation )

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

125
        [$country] = $this->localeService->getNameFromTontine(/** @scrutinizer ignore-type */ $tontine);
Loading history...
126
127
        return [
128
            'tontine' => $tontine,
129
            'session' => $session,
130
            'country' => $country,
131
            'deposits' => [
132
                'session' => $session,
133
                'receivables' => $this->memberService->getReceivables($session),
134
                'pools' => $this->sessionService->getReceivables($session),
135
            ],
136
            'remitments' => [
137
                'session' => $session,
138
                'payables' => $this->memberService->getPayables($session),
139
                'pools' => $this->sessionService->getPayables($session),
140
                'auctions' => $this->memberService->getAuctions($session),
141
            ],
142
            'bills' => [
143
                'bills' => $this->memberService->getBills($session),
144
                'charges' => [
145
                    'session' => $this->sessionService->getSessionCharges($session),
146
                    'total' => $this->sessionService->getTotalCharges($session),
147
                ],
148
            ],
149
            'loans' => [
150
                'loans' => $this->memberService->getLoans($session),
151
                'total' => $this->sessionService->getLoan($session),
152
            ],
153
            'refunds' => [
154
                'refunds' => $this->memberService->getRefunds($session),
155
                'total' => $this->sessionService->getRefund($session),
156
            ],
157
            'savings' => [
158
                'savings' => $this->memberService->getSavings($session),
159
                'funds' => $this->fundService->getFundList(),
160
                'total' => $this->sessionService->getSaving($session),
161
            ],
162
            'disbursements' => [
163
                'disbursements' => $this->memberService->getDisbursements($session),
164
                'total' => $this->sessionService->getDisbursement($session),
165
            ],
166
        ];
167
    }
168
169
    /**
170
     * @param Session $session
171
     *
172
     * @return array
173
     */
174
    public function getProfitsReport(Session $session): array
175
    {
176
        $tontine = $this->tenantService->tontine();
177
        [$country] = $this->localeService->getNameFromTontine($tontine);
0 ignored issues
show
Bug introduced by
It seems like $tontine can also be of type null; however, parameter $tontine of Siak\Tontine\Service\Loc...e::getNameFromTontine() does only seem to accept Siak\Tontine\Model\Tontine, maybe add an additional type check? ( Ignorable by Annotation )

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

177
        [$country] = $this->localeService->getNameFromTontine(/** @scrutinizer ignore-type */ $tontine);
Loading history...
178
        $funds = $this->fundService->getFundList();
179
        $closings = $this->getFundClosings($session, $funds);
180
        $profits = Arr::map($closings, fn($amount, $fundId) => [
181
            'fund' => $funds[$fundId],
182
            'profitAmount' => $amount,
183
            'savings' => $this->profitService->getDistributions($session, $fundId, $amount),
184
        ]);
185
186
        return compact('tontine', 'session', 'country', 'profits');
187
    }
188
189
    /**
190
     * @param Round $round
191
     *
192
     * @return array
193
     */
194
    public function getRoundReport(Round $round): array
195
    {
196
        $tontine = $this->tenantService->tontine();
197
        [$country, $currency] = $this->localeService->getNameFromTontine($tontine);
0 ignored issues
show
Bug introduced by
It seems like $tontine can also be of type null; however, parameter $tontine of Siak\Tontine\Service\Loc...e::getNameFromTontine() does only seem to accept Siak\Tontine\Model\Tontine, maybe add an additional type check? ( Ignorable by Annotation )

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

197
        [$country, $currency] = $this->localeService->getNameFromTontine(/** @scrutinizer ignore-type */ $tontine);
Loading history...
198
199
        $pools = $this->subscriptionService->getPools(false)
200
            ->each(function($pool) {
201
                $pool->figures = $this->summaryService->getFigures($pool);
202
            });
203
204
        $sessions = $round->sessions()->orderBy('start_at', 'asc')->get();
205
        // Sessions with data
206
        $sessionIds = $sessions->filter(function($session) {
207
            return $session->status === Session::STATUS_CLOSED ||
208
                $session->status === Session::STATUS_OPENED;
209
        })->pluck('id');
210
        $amounts = [
211
            'sessions' => $sessions,
212
            'auctions' => $this->roundService->getAuctionAmounts($sessionIds),
213
            'settlements' => $this->roundService->getSettlementAmounts($sessionIds),
214
            'loans' => $this->roundService->getLoanAmounts($sessionIds),
215
            'refunds' => $this->roundService->getRefundAmounts($sessionIds),
216
            'savings' => $this->roundService->getSavingAmounts($sessionIds),
217
            'disbursements' => $this->roundService->getDisbursementAmounts($sessionIds),
218
        ];
219
220
        return compact('tontine', 'round', 'country', 'currency', 'pools', 'amounts');
221
    }
222
223
    /**
224
     * @param Session $session
225
     *
226
     * @return string
227
     */
228
    public function getSessionReportFilename(Session $session): string
229
    {
230
        return strtolower(trans('meeting.titles.report')) . '-' . Str::slug($session->title) . '.pdf';
231
    }
232
233
    /**
234
     * @param Session $session
235
     *
236
     * @return string
237
     */
238
    public function getProfitsReportFilename(Session $session): string
239
    {
240
        return Str::slug(trans('meeting.titles.profits')) . '-' . Str::slug($session->title) . '.pdf';
241
    }
242
243
    /**
244
     * @param Round $round
245
     *
246
     * @return string
247
     */
248
    public function getRoundReportFilename(Round $round): string
249
    {
250
        return strtolower(trans('meeting.titles.report')) . '-' . Str::slug($round->title) . '.pdf';
251
    }
252
}
253