Skip to content

Commit dfe9c1b

Browse files
committed
Implement the report service
1 parent 67be2c9 commit dfe9c1b

6 files changed

Lines changed: 401 additions & 0 deletions

File tree

src/Client.php

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
use Closure;
66
use InvalidArgumentException;
77
use Pace\Soap\DateTimeMapping;
8+
use Pace\Report\Builder as ReportBuilder;
89
use Pace\Contracts\Soap\Factory as SoapFactory;
910

1011
class Client
@@ -162,6 +163,21 @@ public function readObject($object, $key)
162163
return $this->service('ReadObject')->read($object, $key);
163164
}
164165

166+
/**
167+
* Run a report.
168+
*
169+
* @param Model|int $report
170+
* @return ReportBuilder
171+
*/
172+
public function report($report): ReportBuilder
173+
{
174+
if (!$report instanceof Model) {
175+
$report = $this->model('Report')->readOrFail($report);
176+
}
177+
178+
return new ReportBuilder($this->service('ReportService'), $report);
179+
}
180+
165181
/**
166182
* Get an instance of the specified service.
167183
*

src/Enum/ReportExportType.php

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
<?php
2+
3+
namespace Pace\Enum;
4+
5+
final class ReportExportType
6+
{
7+
const PDF = 2;
8+
const RTF = 3;
9+
const HTML = 4;
10+
const CSV = 5;
11+
const XLS = 6;
12+
const XLSX = 7;
13+
const XML = 8;
14+
const TXT = 9;
15+
}

src/Report/Builder.php

Lines changed: 170 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,170 @@
1+
<?php
2+
3+
namespace Pace\Report;
4+
5+
use Pace\Model;
6+
use InvalidArgumentException;
7+
use Pace\Enum\ReportExportType;
8+
use Pace\Services\ReportService;
9+
10+
class Builder
11+
{
12+
/**
13+
* The report service.
14+
*
15+
* @var ReportService
16+
*/
17+
protected $service;
18+
19+
/**
20+
* The report model.
21+
*
22+
* @var Model
23+
*/
24+
protected $report;
25+
26+
/**
27+
* The base object key (if applicable).
28+
*
29+
* @var null
30+
*/
31+
protected $baseObjectKey = null;
32+
33+
/**
34+
* The report parameters.
35+
*
36+
* @var array
37+
*/
38+
protected $parameters = [];
39+
40+
/**
41+
* The report export media types.
42+
*
43+
* @var array
44+
*/
45+
protected $mediaTypes = [
46+
ReportExportType::PDF => 'application/pdf',
47+
ReportExportType::RTF => 'text/rtf',
48+
ReportExportType::HTML => 'text/html',
49+
ReportExportType::CSV => 'text/csv',
50+
ReportExportType::XLS => 'application/vnd.ms-excel',
51+
ReportExportType::XLSX => 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
52+
ReportExportType::XML => 'application/xml',
53+
ReportExportType::TXT => 'text/plain',
54+
];
55+
56+
/**
57+
* Create a new report builder instance.
58+
*
59+
* @param ReportService $service
60+
* @param Model $report
61+
*/
62+
public function __construct(ReportService $service, Model $report)
63+
{
64+
$this->service = $service;
65+
$this->report = $report;
66+
}
67+
68+
/**
69+
* Set the specified parameter.
70+
*
71+
* @param int $id
72+
* @param mixed $value
73+
* @return $this
74+
*/
75+
public function parameter(int $id, $value): self
76+
{
77+
$this->parameters[$id] = $value;
78+
79+
return $this;
80+
}
81+
82+
/**
83+
* Set the specified parameter by looking up its name.
84+
*
85+
* @param string $name
86+
* @param mixed $value
87+
* @return $this
88+
*/
89+
public function namedParameter(string $name, $value): self
90+
{
91+
$id = $this->report->reportParameters()->filter('@name', $name)->get()->key();
92+
93+
if (false === $id) {
94+
throw new InvalidArgumentException("Parameter [$name] does not exist");
95+
}
96+
97+
return $this->parameter($id, $value);
98+
}
99+
100+
/**
101+
* Bulk set parameters.
102+
*
103+
* @param array $parameters
104+
* @return $this
105+
*/
106+
public function parameters(array $parameters): self
107+
{
108+
foreach ($parameters as $id => $value) {
109+
$this->parameter($id, $value);
110+
}
111+
112+
return $this;
113+
}
114+
115+
/**
116+
* Set the base object key.
117+
*
118+
* @param mixed $key
119+
* @return $this
120+
*/
121+
public function baseObjectKey($key): self
122+
{
123+
$this->baseObjectKey = $key instanceof Model ? $key->key() : $key;
124+
125+
return $this;
126+
}
127+
128+
/**
129+
* Run the report and get the file.
130+
*
131+
* @return File
132+
*/
133+
public function get(): File
134+
{
135+
$report = $this->service->executeReport($this->toWrapper());
136+
137+
return File::fromBase64($report['content'], $this->mediaTypes[$this->report->exportType] ?? null);
138+
}
139+
140+
/**
141+
* Print the report.
142+
*/
143+
public function print(): void
144+
{
145+
$this->service->printReport($this->toWrapper());
146+
}
147+
148+
/**
149+
* Convert the instance to a report wrapper.
150+
*
151+
* @return array
152+
*/
153+
public function toWrapper(): array
154+
{
155+
$parameters = [];
156+
157+
foreach ($this->parameters as $id => $value) {
158+
$parameters[] = [
159+
'reportParameterId' => $id,
160+
'value' => $value,
161+
];
162+
}
163+
164+
return [
165+
'baseObjectKey' => $this->baseObjectKey,
166+
'reportId' => $this->report->key(),
167+
'reportParameterWrappers' => $parameters,
168+
];
169+
}
170+
}

src/Report/File.php

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
<?php
2+
3+
namespace Pace\Report;
4+
5+
use finfo;
6+
7+
class File
8+
{
9+
/**
10+
* The file's content.
11+
*
12+
* @var string
13+
*/
14+
protected $content;
15+
16+
/**
17+
* The file's media type.
18+
*
19+
* @var string|null
20+
*/
21+
protected $mediaType;
22+
23+
/**
24+
* Create a new file instance.
25+
*
26+
* @param string $content
27+
* @param string|null $mediaType
28+
*/
29+
public function __construct(string $content, string $mediaType = null)
30+
{
31+
$this->content = $content;
32+
$this->mediaType = $mediaType;
33+
}
34+
35+
/**
36+
* Create a new file instance from a Base64-encoded file.
37+
*
38+
* @param string $content
39+
* @param string|null $mediaType
40+
* @return static
41+
*/
42+
public static function fromBase64(string $content, string $mediaType = null): self
43+
{
44+
return new static(base64_decode($content), $mediaType);
45+
}
46+
47+
/**
48+
* Get the file's media type.
49+
*
50+
* @return string
51+
*/
52+
public function getMediaType(): string
53+
{
54+
if (!is_null($this->mediaType)) {
55+
return $this->mediaType;
56+
}
57+
58+
$finfo = new finfo(FILEINFO_MIME_TYPE);
59+
60+
return $finfo->buffer(substr($this->content, 0, 65536)) ?: 'application/octet-stream';
61+
}
62+
63+
/**
64+
* Get the file's content.
65+
*
66+
* @return string
67+
*/
68+
public function getContent(): string
69+
{
70+
return $this->content;
71+
}
72+
}

src/Services/ReportService.php

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
<?php
2+
3+
namespace Pace\Services;
4+
5+
use Pace\Service;
6+
7+
class ReportService extends Service
8+
{
9+
/**
10+
* Execute the specified report.
11+
*
12+
* @param array $wrapper
13+
* @return array
14+
*/
15+
public function executeReport(array $wrapper): array
16+
{
17+
$response = $this->soap->executeReport(['in0' => $wrapper]);
18+
19+
return (array)$response->out;
20+
}
21+
22+
/**
23+
* Print the specified report.
24+
*
25+
* @param array $wrapper
26+
*/
27+
public function printReport(array $wrapper): void
28+
{
29+
$this->soap->printReport(['in0' => $wrapper]);
30+
}
31+
}

0 commit comments

Comments
 (0)