Completed
Push — master ( 7d7b0c...47c96c )
by Leszek
39s
created

StatementDeserializer::isValidStatementType()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 3
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 3
rs 10
c 0
b 0
f 0
cc 2
eloc 2
nc 2
nop 1
1
<?php
2
3
namespace Wikibase\DataModel\Deserializers;
4
5
use Deserializers\Deserializer;
6
use Deserializers\DispatchableDeserializer;
7
use Deserializers\Exceptions\DeserializationException;
8
use Deserializers\Exceptions\InvalidAttributeException;
9
use Deserializers\Exceptions\MissingAttributeException;
10
use Deserializers\Exceptions\MissingTypeException;
11
use Deserializers\Exceptions\UnsupportedTypeException;
12
use Wikibase\DataModel\ReferenceList;
13
use Wikibase\DataModel\Snak\Snak;
14
use Wikibase\DataModel\Snak\SnakList;
15
use Wikibase\DataModel\Statement\Statement;
16
17
/**
18
 * Package private
19
 *
20
 * @license GPL-2.0+
21
 * @author Thomas Pellissier Tanon
22
 */
23
class StatementDeserializer implements DispatchableDeserializer {
24
25
	private static $rankIds = [
26
		'deprecated' => Statement::RANK_DEPRECATED,
27
		'normal' => Statement::RANK_NORMAL,
28
		'preferred' => Statement::RANK_PREFERRED
29
	];
30
31
	/**
32
	 * @var Deserializer
33
	 */
34
	private $snakDeserializer;
35
36
	/**
37
	 * @var Deserializer
38
	 */
39
	private $snaksDeserializer;
40
41
	/**
42
	 * @var Deserializer
43
	 */
44
	private $referencesDeserializer;
45
46
	public function __construct(
47
		Deserializer $snakDeserializer,
48
		Deserializer $snaksDeserializer,
49
		Deserializer $referencesDeserializer
50
	) {
51
		$this->snakDeserializer = $snakDeserializer;
52
		$this->snaksDeserializer = $snaksDeserializer;
53
		$this->referencesDeserializer = $referencesDeserializer;
54
	}
55
56
	/**
57
	 * @see DispatchableDeserializer::isDeserializerFor
58
	 *
59
	 * @param mixed $serialization
60
	 *
61
	 * @return bool
62
	 */
63
	public function isDeserializerFor( $serialization ) {
64
		return is_array( $serialization )
65
			&& array_key_exists( 'type', $serialization )
66
			&& $this->isValidStatementType( $serialization['type'] );
67
	}
68
69
	/**
70
	 * @param string $statementType
71
	 *
72
	 * @return bool
73
	 */
74
	private function isValidStatementType( $statementType ) {
75
		return $statementType === 'statement' || $statementType === 'claim';
76
	}
77
78
	/**
79
	 * @see Deserializer::deserialize
80
	 *
81
	 * @param array $serialization
82
	 *
83
	 * @throws DeserializationException
84
	 * @return Statement
85
	 */
86
	public function deserialize( $serialization ) {
87
		// Note: The following functions have been inlined on purpose, see T157013.
88
		if ( !is_array( $serialization ) || !array_key_exists( 'type', $serialization ) ) {
89
			throw new MissingTypeException();
90
		}
91
92
		if ( !$this->isValidStatementType( $serialization['type'] ) ) {
93
			throw new UnsupportedTypeException( $serialization['type'] );
94
		}
95
96
		if ( !array_key_exists( 'mainsnak', $serialization ) ) {
97
			throw new MissingAttributeException( 'mainsnak' );
98
		}
99
100
		return $this->getDeserialized( $serialization );
101
	}
102
103
	/**
104
	 * @param array $serialization
105
	 *
106
	 * @return Statement
107
	 */
108
	private function getDeserialized( array $serialization ) {
109
		/** @var Snak $mainSnak */
110
		$mainSnak = $this->snakDeserializer->deserialize( $serialization['mainsnak'] );
111
		$statement = new Statement( $mainSnak );
112
113
		// Note: The following ifs are inlined on purpose, see T157013.
114
		if ( array_key_exists( 'id', $serialization ) ) {
115
			$this->setGuidFromSerialization( $serialization, $statement );
116
		}
117
		if ( array_key_exists( 'qualifiers', $serialization ) ) {
118
			$this->setQualifiersFromSerialization( $serialization, $statement );
119
		}
120
		if ( array_key_exists( 'rank', $serialization ) ) {
121
			$this->setRankFromSerialization( $serialization, $statement );
122
		}
123
		if ( array_key_exists( 'references', $serialization ) ) {
124
			$this->setReferencesFromSerialization( $serialization, $statement );
125
		}
126
127
		return $statement;
128
	}
129
130
	private function setGuidFromSerialization( array $serialization, Statement $statement ) {
131
		if ( !is_string( $serialization['id'] ) ) {
132
			throw new DeserializationException( 'The id ' . $serialization['id'] . ' is not a valid GUID.' );
133
		}
134
135
		$statement->setGuid( $serialization['id'] );
136
	}
137
138
	private function setQualifiersFromSerialization( array $serialization, Statement $statement ) {
139
		/** @var SnakList $qualifiers */
140
		$qualifiers = $this->snaksDeserializer->deserialize( $serialization['qualifiers'] );
141
142
		if ( array_key_exists( 'qualifiers-order', $serialization ) ) {
143
			$this->assertQualifiersOrderIsArray( $serialization );
144
145
			$qualifiers->orderByProperty( $serialization['qualifiers-order'] );
146
		}
147
148
		$statement->setQualifiers( $qualifiers );
149
	}
150
151
	private function setRankFromSerialization( array $serialization, Statement $statement ) {
152
		if ( !array_key_exists( $serialization['rank'], self::$rankIds ) ) {
153
			throw new DeserializationException( 'The rank ' . $serialization['rank'] . ' is not a valid rank.' );
154
		}
155
156
		$statement->setRank( self::$rankIds[$serialization['rank']] );
157
	}
158
159
	private function setReferencesFromSerialization( array $serialization, Statement $statement ) {
160
		/** @var ReferenceList $references */
161
		$references = $this->referencesDeserializer->deserialize( $serialization['references'] );
162
		$statement->setReferences( $references );
163
	}
164
165
	private function assertQualifiersOrderIsArray( array $serialization ) {
166
		if ( !is_array( $serialization['qualifiers-order'] ) ) {
167
			throw new InvalidAttributeException(
168
				'qualifiers-order',
169
				$serialization['qualifiers-order'],
170
				'qualifiers-order attribute is not a valid array'
171
			);
172
		}
173
	}
174
175
}
176