middleware('active.account'); } public function index(Request $request): View { if (! $request->user()?->isVIP()) { abort(404); } [$selectedMonth, $selectedYear] = $this->selectedPeriod($request); $startTime = microtime(true); $statistics = $this->dashboardService->overview($request->user(), $selectedMonth, $selectedYear); $performance = [ 'duration_ms' => round((microtime(true) - $startTime) * 1000, 2), 'source_label' => $statistics['_meta']['source_label'] ?? 'Live', 'calculated_at' => $statistics['_meta']['calculated_at'] ?? null, ]; return view('user.backoffice.statistics.index', [ 'selectedMonth' => $selectedMonth, 'selectedYear' => $selectedYear, 'filterMonths' => HTMLHelper::getTransMonths(), 'filterYears' => HTMLHelper::getYearRange(2022), 'statistics' => $statistics, 'performance' => $performance, ]); } public function details(Request $request): View { if (! $request->user()?->isVIP()) { abort(404); } [$selectedMonth, $selectedYear] = $this->selectedPeriod($request); $line = (int) $request->get('line', 1); $metric = (string) $request->get('metric', 'consultants'); return view('user.backoffice.statistics.details', [ 'selectedMonth' => $selectedMonth, 'selectedYear' => $selectedYear, 'details' => $this->drilldownService->details($request->user(), $line, $metric, $selectedMonth, $selectedYear), ]); } public function export(Request $request): StreamedResponse { if (! $request->user()?->isVIP()) { abort(404); } [$selectedMonth, $selectedYear] = $this->selectedPeriod($request); $line = (int) $request->get('line', 1); $metric = (string) $request->get('metric', 'consultants'); $details = $this->drilldownService->details($request->user(), $line, $metric, $selectedMonth, $selectedYear); $filename = sprintf( 'backoffice-statistik-%s-linie-%s-%02d-%d.csv', $metric, $line === 0 ? 'alle' : $line, $selectedMonth, $selectedYear ); return response()->streamDownload(function () use ($details): void { $output = fopen('php://output', 'w'); fwrite($output, "\xEF\xBB\xBF"); fputcsv($output, $this->csvHeaders($details['metric']), ';'); foreach ($details['rows'] as $row) { fputcsv($output, $this->csvRow($details['metric'], $row), ';'); } fputcsv($output, []); fputcsv($output, $this->csvSummaryRow($details), ';'); fclose($output); }, $filename, [ 'Content-Type' => 'text/csv; charset=UTF-8', ]); } public function overviewExport(Request $request): StreamedResponse { if (! $request->user()?->isVIP()) { abort(404); } [$selectedMonth, $selectedYear] = $this->selectedPeriod($request); $statistics = $this->dashboardService->overview($request->user(), $selectedMonth, $selectedYear); $filename = sprintf('backoffice-statistik-uebersicht-%02d-%d.csv', $selectedMonth, $selectedYear); return response()->streamDownload(function () use ($statistics): void { $output = fopen('php://output', 'w'); fwrite($output, "\xEF\xBB\xBF"); fputcsv($output, $this->overviewCsvHeaders(), ';'); foreach ($statistics['lines'] as $line) { fputcsv($output, $this->overviewCsvRow($line), ';'); } fputcsv($output, []); fputcsv($output, $this->overviewCsvRow($statistics['totals']), ';'); fclose($output); }, $filename, [ 'Content-Type' => 'text/csv; charset=UTF-8', ]); } /** * @return array{0: int, 1: int} */ private function selectedPeriod(Request $request): array { $selectedMonth = max(1, min(12, (int) $request->get('month', session(self::SESSION_MONTH_KEY, now()->month)))); $selectedYear = (int) $request->get('year', session(self::SESSION_YEAR_KEY, now()->year)); session([ self::SESSION_MONTH_KEY => $selectedMonth, self::SESSION_YEAR_KEY => $selectedYear, ]); return [$selectedMonth, $selectedYear]; } /** * @return string[] */ private function overviewCsvHeaders(): array { return [ 'Linie', 'Berater', 'Neupartner', 'Teamabos', 'Neue Teamabos', 'Teamkundenabos', 'Neue Teamkundenabos', 'Eigenpunkte', 'Externe Punkte', 'Kundenabo-Punkte', 'Einzelbestellungs-Punkte', 'Sonstige Kundenpunkte', 'Gesamtpunkte', '1000 Punkte Shop', 'Umsatz Netto', ]; } /** * @param array $row * @return array */ private function overviewCsvRow(array $row): array { return [ $row['label'] ?? '', $row['consultants'] ?? 0, $row['new_partners'] ?? 0, $row['team_partner_abos'] ?? 0, $row['team_partner_abos_new'] ?? 0, $row['team_customer_abos'] ?? 0, $row['team_customer_abos_new'] ?? 0, $row['own_points'] ?? 0, $row['external_points'] ?? 0, $row['customer_abo_points'] ?? 0, $row['customer_single_order_points'] ?? 0, $row['customer_other_points'] ?? 0, $row['total_points'] ?? 0, $row['shop_1000'] ?? 0, $row['turnover_net'] ?? 0, ]; } /** * @return string[] */ private function csvHeaders(string $metric): array { if (in_array($metric, ['team_partner_abos', 'team_customer_abos'], true)) { return ['Name', 'E-Mail', 'Karriere-Level', 'Berater', 'Abo-Punkte', 'Status', 'Status-Grund', 'Besteht seit', 'Naechste Ausfuehrung', 'Lieferungen']; } if (in_array($metric, ['own_points', 'external_points', 'customer_abo_points', 'customer_single_order_points', 'customer_other_points', 'total_points', 'shop_1000'], true)) { return ['Name', 'E-Mail', 'Karriere-Level', 'Eigenpunkte', 'Externe Punkte', 'Kundenabo-Punkte', 'Einzelbestellungs-Punkte', 'Sonstige Kundenpunkte', 'Gesamtpunkte']; } return ['Name', 'E-Mail', 'Karriere-Level', 'Aktiv seit', 'Account gueltig bis', 'Account Status']; } /** * @param array $row * @return array */ private function csvRow(string $metric, array $row): array { if (in_array($metric, ['team_partner_abos', 'team_customer_abos'], true)) { return [ $row['name'] ?? '', $row['email'] ?? '', $row['career_level'] ?? '', $row['consultant_name'] ?? $row['name'] ?? '', $row['points'] ?? 0, $row['status_label'] ?? '', $row['status_reason'] ?? '', $row['start_date'] ?? '', $row['next_date'] ?? '', $row['deliveries'] ?? 0, ]; } if (in_array($metric, ['own_points', 'external_points', 'customer_abo_points', 'customer_single_order_points', 'customer_other_points', 'total_points', 'shop_1000'], true)) { return [ $row['name'] ?? '', $row['email'] ?? '', $row['career_level'] ?? '', $row['own_points'] ?? 0, $row['external_points'] ?? 0, $row['customer_abo_points'] ?? 0, $row['customer_single_order_points'] ?? 0, $row['customer_other_points'] ?? 0, $row['total_points'] ?? 0, ]; } return [ $row['name'] ?? '', $row['email'] ?? '', $row['career_level'] ?? '', $row['active_date'] ?? '', $row['payment_account'] ?? '', $row['account_status'] ?? '', ]; } /** * @param array $details * @return array */ private function csvSummaryRow(array $details): array { $metric = $details['metric']; $summary = $details['summary']; if (in_array($metric, ['team_partner_abos', 'team_customer_abos'], true)) { return ['Summe', $summary['count'].' Eintraege', '', '', $summary['points'], '', '', '', '', $summary['deliveries']]; } if (in_array($metric, ['own_points', 'external_points', 'customer_abo_points', 'customer_single_order_points', 'customer_other_points', 'total_points', 'shop_1000'], true)) { return ['Summe', $summary['count'].' Eintraege', '', $summary['own_points'], $summary['external_points'], $summary['customer_abo_points'], $summary['customer_single_order_points'], $summary['customer_other_points'], $summary['total_points']]; } return ['Summe', $summary['count'].' Eintraege', '', '', '', '']; } }