Completed
Push — master ( 7e068f...d722f0 )
by Dan Michael O.
10:27
created

Response::handleDiagnostic()   B

Complexity

Conditions 6
Paths 8

Size

Total Lines 24
Code Lines 15

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 24
rs 8.5125
cc 6
eloc 15
nc 8
nop 1
1
<?php namespace Scriptotek\Sru;
2
3
use Danmichaelo\QuiteSimpleXMLElement\QuiteSimpleXMLElement;
4
5
/**
6
 * Generic SRU response
7
 */
8
class Response implements ResponseInterface
9
{
10
    public static $errorMessages = array(
11
        'info:srw/diagnostic/1/1' => 'General system error',
12
        'info:srw/diagnostic/1/2' => 'System temporarily unavailable',
13
        'info:srw/diagnostic/1/3' => 'Authentication error',
14
        'info:srw/diagnostic/1/4' => 'Unsupported operation',
15
        'info:srw/diagnostic/1/5' => 'Unsupported version',
16
        'info:srw/diagnostic/1/6' => 'Unsupported parameter value',
17
        'info:srw/diagnostic/1/7' => 'Mandatory parameter not supplied',
18
        'info:srw/diagnostic/1/8' => 'Unsupported parameter',
19
        'info:srw/diagnostic/1/10' => 'Query syntax error',
20
        'info:srw/diagnostic/1/12' => 'Too many characters in query',
21
        'info:srw/diagnostic/1/13' => 'Invalid or unsupported use of parentheses',
22
        'info:srw/diagnostic/1/14' => 'Invalid or unsupported use of quotes',
23
        'info:srw/diagnostic/1/15' => 'Unsupported context set',
24
        'info:srw/diagnostic/1/16' => 'Unsupported index',
25
        'info:srw/diagnostic/1/18' => 'Unsupported combination of indexes',
26
        'info:srw/diagnostic/1/19' => 'Unsupported relation',
27
        'info:srw/diagnostic/1/20' => 'Unsupported relation modifier',
28
        'info:srw/diagnostic/1/21' => 'Unsupported combination of relation modifers',
29
        'info:srw/diagnostic/1/22' => 'Unsupported combination of relation and index',
30
        'info:srw/diagnostic/1/23' => 'Too many characters in term',
31
        'info:srw/diagnostic/1/24' => 'Unsupported combination of relation and term',
32
        'info:srw/diagnostic/1/26' => 'Non special character escaped in term',
33
        'info:srw/diagnostic/1/27' => 'Empty term unsupported',
34
        'info:srw/diagnostic/1/28' => 'Masking character not supported',
35
        'info:srw/diagnostic/1/29' => 'Masked words too short',
36
        'info:srw/diagnostic/1/30' => 'Too many masking characters in term',
37
        'info:srw/diagnostic/1/31' => 'Anchoring character not supported',
38
        'info:srw/diagnostic/1/32' => 'Anchoring character in unsupported position',
39
        'info:srw/diagnostic/1/33' => 'Combination of proximity/adjacency and masking characters not supported',
40
        'info:srw/diagnostic/1/34' => 'Combination of proximity/adjacency and anchoring characters not supported',
41
        'info:srw/diagnostic/1/35' => 'Term contains only stopwords',
42
        'info:srw/diagnostic/1/36' => 'Term in invalid format for index or relatio',
43
        'info:srw/diagnostic/1/37' => 'Unsupported boolean operator',
44
        'info:srw/diagnostic/1/38' => 'Too many boolean operators in query',
45
        'info:srw/diagnostic/1/39' => 'Proximity not supported',
46
        'info:srw/diagnostic/1/40' => 'Unsupported proximity relation',
47
        'info:srw/diagnostic/1/41' => 'Unsupported proximity distance',
48
        'info:srw/diagnostic/1/42' => 'Unsupported proximity unit',
49
        'info:srw/diagnostic/1/43' => 'Unsupported proximity ordering',
50
        'info:srw/diagnostic/1/44' => 'Unsupported combination of proximity modifiers',
51
        'info:srw/diagnostic/1/46' => 'Unsupported boolean modifier',
52
        'info:srw/diagnostic/1/47' => 'Cannot process query; reason unknown',
53
        'info:srw/diagnostic/1/48' => 'Query feature unsupported',
54
        'info:srw/diagnostic/1/49' => 'Masking character in unsupported position',
55
        'info:srw/diagnostic/1/50' => 'Result sets not supported',
56
        'info:srw/diagnostic/1/51' => 'Result set does not exist',
57
        'info:srw/diagnostic/1/52' => 'Result set temporarily unavailable',
58
        'info:srw/diagnostic/1/53' => 'Result sets only supported for retrieval',
59
        'info:srw/diagnostic/1/55' => 'Combination of result sets with search terms not supported',
60
        'info:srw/diagnostic/1/58' => 'Result set created with unpredictable partial results available',
61
        'info:srw/diagnostic/1/59' => 'Result set created with valid partial results available',
62
        'info:srw/diagnostic/1/60' => 'Result set not created: too many matching records',
63
        'info:srw/diagnostic/1/61' => 'First record position out of range',
64
        'info:srw/diagnostic/1/64' => 'Record temporarily unavailable',
65
        'info:srw/diagnostic/1/65' => 'Record does not exist',
66
        'info:srw/diagnostic/1/66' => 'Unknown schema for retrieval',
67
        'info:srw/diagnostic/1/67' => 'Record not available in this schema',
68
        'info:srw/diagnostic/1/68' => 'Not authorised to send record',
69
        'info:srw/diagnostic/1/69' => 'Not authorised to send record in this schema',
70
        'info:srw/diagnostic/1/70' => 'Record too large to send',
71
        'info:srw/diagnostic/1/71' => 'Unsupported record packing',
72
        'info:srw/diagnostic/1/72' => 'XPath retrieval unsupported',
73
        'info:srw/diagnostic/1/73' => 'XPath expression contains unsupported feature',
74
        'info:srw/diagnostic/1/74' => 'Unable to evaluate XPath expression',
75
        'info:srw/diagnostic/1/80' => 'Sort not supported',
76
        'info:srw/diagnostic/1/82' => 'Unsupported sort sequence',
77
        'info:srw/diagnostic/1/83' => 'Too many records to sort',
78
        'info:srw/diagnostic/1/84' => 'Too many sort keys to sort',
79
        'info:srw/diagnostic/1/86' => 'Cannot sort: incompatible record formats',
80
        'info:srw/diagnostic/1/87' => 'Unsupported schema for sort',
81
        'info:srw/diagnostic/1/88' => 'Unsupported path for sort',
82
        'info:srw/diagnostic/1/89' => 'Path unsupported for schema',
83
        'info:srw/diagnostic/1/90' => 'Unsupported direction',
84
        'info:srw/diagnostic/1/91' => 'Unsupported case',
85
        'info:srw/diagnostic/1/92' => 'Unsupported missing value action',
86
        'info:srw/diagnostic/1/93' => 'Sort ended due to missing value',
87
        'info:srw/diagnostic/1/94' => 'Sort spec included both in query and protocol: query prevails',
88
        'info:srw/diagnostic/1/95' => 'Sort spec included both in query and protocol: protocol prevails',
89
        'info:srw/diagnostic/1/96' => 'Sort spec included both in query and protocol: error',
90
        'info:srw/diagnostic/1/110' => 'Stylesheets not supported',
91
        'info:srw/diagnostic/1/120' => 'Response position out of range',
92
        'info:srw/diagnostic/1/130' => 'Too many terms matched by masked query term',
93
    );
94
95
    /** @var string Raw XML response */
96
    protected $rawResponse = '';
97
98
    /** @var QuiteSimpleXMLElement XML response */
99
    protected $response;
100
101
    /** @var Client Reference to SRU client object */
102
    protected $client;
103
104
    /** @var string SRU protocol version */
105
    public $version;
106
107
    /**
108
     * Create a new response
109
     *
110
     * @param string $text Raw XML response
111
     * @param Client $client SRU client reference (optional)
112
     */
113
    public function __construct($text = null, &$client = null)
114
    {
115
        $this->client = $client;
116
117
        if (!is_null($text)) {
118
            $this->initializeFromText($text);
119
        }
120
    }
121
122
    protected function initializeFromText($text)
123
    {
124
        // Fix missing namespace in Alma records:
125
        $text = str_replace('<record xmlns="">', '<record xmlns="http://www.loc.gov/MARC21/slim">', $text);
126
127
        $this->rawResponse = $text;
128
129
        // Throws Danmichaelo\QuiteSimpleXMLElement\InvalidXMLException on invalid xml
130
        $this->response = QuiteSimpleXMLElement::make($text, [
131
            'srw' => 'http://www.loc.gov/zing/srw/',
132
            'exp' => 'http://explain.z3950.org/dtd/2.0/',
133
            'd' => 'http://www.loc.gov/zing/srw/diagnostic/',
134
        ]);
135
136
        $this->version = $this->response->text('/srw:*/srw:version');
137
138
        $this->handleDiagnostic($this->response->first('/srw:*/srw:diagnostics/d:diagnostic'));
139
    }
140
141
    protected function handleDiagnostic(QuiteSimpleXMLElement $node = null)
142
    {
143
        if (is_null($node)) {
144
            return;
145
        }
146
147
        // Only the 'uri' field is required, 'message' and 'details' are optional
148
        $uri = $node->text('d:uri');
149
        if (strlen($uri)) {
150
            $msg = $node->text('d:message');
151
            $details = $node->text('d:details');
152
            if (empty($msg)) {
153
                if (isset(self::$errorMessages[$uri])) {
154
                    $msg = self::$errorMessages[$uri];
155
                } else {
156
                    $msg = 'Unknown error';
157
                }
158
            }
159
            if (!empty($details)) {
160
                $msg .= ' (' . $details . ')';
161
            }
162
            throw new Exceptions\SruErrorException($msg, $uri);
163
        }
164
    }
165
166
    /**
167
     * Get the raw xml response
168
     *
169
     * @return string
170
     */
171
    public function asXml()
172
    {
173
        return $this->rawResponse;
174
    }
175
}
176