Test Failed
Pull Request — master (#21)
by
unknown
03:16
created

NovaSearchServicesMethod::createRequestBody()   B

Complexity

Conditions 9
Paths 18

Size

Total Lines 58
Code Lines 35

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 24
CRAP Score 11.9991

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 9
eloc 35
nc 18
nop 1
dl 0
loc 58
ccs 24
cts 36
cp 0.6667
crap 11.9991
rs 8.0555
c 1
b 0
f 0

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
namespace OrcaServices\NovaApi\Method;
4
5
use DOMDocument;
6
use DOMElement;
7
use Exception;
8
use OrcaServices\NovaApi\Parameter\NovaSearchServicesParameter;
9
use OrcaServices\NovaApi\Parser\NovaApiErrorParser;
10
use OrcaServices\NovaApi\Parser\NovaMessageParser;
11
use OrcaServices\NovaApi\Result\NovaSearchServicesResult;
12
use OrcaServices\NovaApi\Result\NovaServiceResult;
13
use OrcaServices\NovaApi\Soap\NovaApiSoapAction;
14
use OrcaServices\NovaApi\Xml\XmlDocument;
15
16
/**
17
 * SOAP method.
18
 */
19
final class NovaSearchServicesMethod implements NovaMethod
20
{
21
    /**
22
     * @var NovaApiSoapAction
23
     */
24
    private $novaSoapAction;
25
26
    /**
27
     * @var NovaApiErrorParser
28
     */
29
    private $novaErrorParser;
30
31
    /**
32
     * @var NovaMessageParser
33
     */
34
    private $novaMessageParser;
35
36
    /**
37
     * NovaSearchPartnerMethod constructor.
38
     *
39
     * @param NovaApiSoapAction $novaSoapAction The novaSoapAction
40
     * @param NovaApiErrorParser $novaErrorParser The novaErrorParser
41
     * @param NovaMessageParser $novaMessageParser The message parser
42
     */
43 12
    public function __construct(
44
        NovaApiSoapAction $novaSoapAction,
45
        NovaApiErrorParser $novaErrorParser,
46
        NovaMessageParser $novaMessageParser
47
    ) {
48 12
        $this->novaSoapAction = $novaSoapAction;
49 12
        $this->novaErrorParser = $novaErrorParser;
50 12
        $this->novaMessageParser = $novaMessageParser;
51 12
    }
52
53
    /**
54
     * Search NOVA services (customer) for a customer.
55
     *
56
     * https://confluence-ext.sbb.ch/display/NOVAUG/sucheLeistungen
57
     *
58
     * @param NovaSearchServicesParameter $parameter The parameters
59
     *
60
     * @throws Exception
61
     *
62
     * @return NovaSearchServicesResult The services matching the search parameter
63
     */
64 1
    public function searchServices(NovaSearchServicesParameter $parameter): NovaSearchServicesResult
65
    {
66
        // The SOAP endpoint url
67 1
        $url = $this->novaSoapAction->getNovaSalesServiceUrl();
68
69
        // The SOAP action (http header)
70 1
        $soapAction = $this->novaSoapAction->getSoapAction('geschaeftspartner', 'sucheLeistungen');
71
72
        // The SOAP content (http body)
73 1
        $body = $this->createRequestBody($parameter);
74
75
        try {
76 1
            $xmlContent = $this->novaSoapAction->invokeSoapRequest($url, $soapAction, $body);
77 1
            $xml = XmlDocument::createFromXmlString($xmlContent);
78
79 1
            return $this->createResult($xml);
80
        } catch (Exception $exception) {
81
            throw $this->novaErrorParser->createGeneralException($exception);
82
        }
83
    }
84
85
    /**
86
     * Create SOAP body XML content.
87
     *
88
     * @param NovaSearchServicesParameter $parameter The parameters
89
     *
90
     * @return string The xml content
91
     */
92 1
    private function createRequestBody(NovaSearchServicesParameter $parameter): string
93
    {
94 1
        $dom = new DOMDocument('1.0', 'utf-8');
95 1
        $dom->formatOutput = true;
96
97 1
        $dom->appendChild($dom->createComment(' powered by Barakuda '));
98
99 1
        $envelope = $dom->createElement('soapenv:Envelope');
100 1
        $dom->appendChild($envelope);
101 1
        $envelope->setAttribute('xmlns:soapenv', 'http://schemas.xmlsoap.org/soap/envelope/');
102
103 1
        $soapHeader = $dom->createElement('soapenv:Header');
104 1
        $envelope->appendChild($soapHeader);
105
106 1
        $body = $dom->createElement('soapenv:Body');
107 1
        $envelope->appendChild($body);
108
109 1
        $method = $dom->createElement('sucheLeistungen');
110 1
        $body->appendChild($method);
111
112 1
        $searchQuery = $dom->createElement('leistungsSuchRequest');
113 1
        $this->novaSoapAction->appendDomClientIdentifier($dom, $searchQuery, $parameter, '');
114 1
        $this->novaSoapAction->appendDomCorrelationContext($dom, $searchQuery, $parameter, '');
115
116 1
        if ($parameter->serviceId) {
117 1
            $serviceKey = $dom->createElement('leistungsSchluessel');
118 1
            $searchQuery->appendChild($serviceKey);
119 1
            $serviceKey->appendChild($dom->createElement('leistungsId', $parameter->serviceId));
120
        }
121
122 1
        if ($parameter->tkId) {
123
            $service = $dom->createElement('leistung');
124
125
            $tkid = $dom->createElement('tkid');
126
            $tkid->appendChild($dom->createTextNode($parameter->tkId));
127
            $service->appendChild($tkid);
128
129
            if ($parameter->periodOfUseStart || $parameter->periodOfUseEnd) {
130
                $periodOfUse = $dom->createElement('nutzungsZeitraum');
131
                $service->appendChild($periodOfUse);
132
            }
133
134
            if ($parameter->periodOfUseStart && isset($periodOfUse)) {
135
                $periodOfUse->setAttribute('base:von', $parameter->periodOfUseStart->format('Y-m-d'));
136
            }
137
138
            if ($parameter->periodOfUseEnd && isset($periodOfUse)) {
139
                $periodOfUse->setAttribute('base:bis', $parameter->periodOfUseEnd->format('Y-m-d'));
140
            }
141
142
            $searchQuery->appendChild($service);
143
        }
144
145 1
        $method->appendChild($searchQuery);
146
147 1
        $this->novaSoapAction->appendMethodNamespaces($method);
148
149 1
        return (string)$dom->saveXML();
150
    }
151
152
    /**
153
     * Create result object.
154
     *
155
     * @param XmlDocument $xml The xml document
156
     *
157
     * @return NovaSearchServicesResult The mapped result
158
     */
159 1
    private function createResult(XmlDocument $xml): NovaSearchServicesResult
160
    {
161 1
        $result = new NovaSearchServicesResult();
162
163 1
        $xml = $xml->withoutNamespaces();
164
165
        // Find and append all messages
166 1
        foreach ($this->novaMessageParser->findNovaMessages($xml) as $message) {
167
            $result->addMessage($message);
168
        }
169
170
        // Root node
171 1
        $responseNode = $xml->queryFirstNode('/Envelope/Body/sucheLeistungenResponse/leistungsSuchResponse');
172 1
        $serviceNodes = $xml->queryNodes('leistungsSuchErgebnis/leistung', $responseNode);
173
174
        /** @var DOMElement $serviceNode */
175 1
        foreach ($serviceNodes as $serviceNode) {
176 1
            $result->services[] = $this->createService($serviceNode, $xml);
177
        }
178
179 1
        return $result;
180
    }
181
182
    /**
183
     * Map partner node to NovaPartner object.
184
     *
185
     * @param DOMElement $serviceNode The partnerNode
186
     * @param XmlDocument $xml The xml document
187
     *
188
     * @return NovaServiceResult The new NovaService instance
189
     */
190 1
    private function createService(DOMElement $serviceNode, XmlDocument $xml): NovaServiceResult
191
    {
192 1
        $service = new NovaServiceResult();
193
194 1
        $service->tkId = $xml->getNodeValue('verkaufsParameter/wert/tkid', $serviceNode);
195 1
        $service->validFrom = $xml->createChronosFromXsDateTime(
196 1
            $xml->getAttributeValue('nutzungsInfo/nutzungsZeitraum/tarifierbarerZeitraum/@von', $serviceNode)
197
        );
198 1
        $service->validTo = $xml->createChronosFromXsDateTime(
199 1
            $xml->getAttributeValue('nutzungsInfo/nutzungsZeitraum/tarifierbarerZeitraum/@bis', $serviceNode)
200
        );
201
202 1
        $service->productNumber = $xml->getAttributeValue('@produktNummer', $serviceNode);
203
204 1
        foreach ($xml->queryNodes('geltungsBereich/zonenGeltungsBereich/zonenBuendel/zonen', $serviceNode) as $zone) {
205
            $service->zones[] = $xml->getNodeValue('code', $zone);
206
        }
207
208 1
        return $service;
209
    }
210
}
211