Completed
Push — master ( 78a9b5...d0b390 )
by
unknown
02:29 queued 15s
created

ConstraintRepository::deleteAll()   A

Complexity

Conditions 4
Paths 3

Size

Total Lines 17

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 17
rs 9.7
c 0
b 0
f 0
cc 4
nc 3
nop 1
1
<?php
2
3
namespace WikibaseQuality\ConstraintReport;
4
5
use MediaWiki\Logger\LoggerFactory;
6
use Wikimedia\Rdbms\DBUnexpectedError;
7
use Wikimedia\Rdbms\IResultWrapper;
8
use Wikimedia\Rdbms\LikeMatch;
9
use Wikibase\DataModel\Entity\PropertyId;
10
11
/**
12
 * @author BP2014N1
13
 * @license GPL-2.0-or-later
14
 */
15
class ConstraintRepository implements ConstraintLookup {
16
17
	/**
18
	 * @param PropertyId $propertyId
19
	 *
20
	 * @return Constraint[]
21
	 */
22
	public function queryConstraintsForProperty( PropertyId $propertyId ) {
23
		$db = wfGetDB( DB_REPLICA );
24
25
		$results = $db->select(
26
			'wbqc_constraints',
27
			'*',
28
			[ 'pid' => $propertyId->getNumericId() ]
29
		);
30
31
		return $this->convertToConstraints( $results );
32
	}
33
34
	private function encodeConstraintParameters( array $constraintParameters ) {
35
		$json = json_encode( $constraintParameters, JSON_FORCE_OBJECT );
36
37
		if ( strlen( $json ) > 50000 ) {
38
			$json = json_encode( [ '@error' => [ 'toolong' => true ] ] );
39
		}
40
41
		return $json;
42
	}
43
44
	/**
45
	 * @param Constraint[] $constraints
46
	 *
47
	 * @throws DBUnexpectedError
48
	 * @return bool
49
	 */
50
	public function insertBatch( array $constraints ) {
51
		$accumulator = array_map(
52
			function ( Constraint $constraint ) {
53
				return [
54
					'constraint_guid' => $constraint->getConstraintId(),
55
					'pid' => $constraint->getPropertyId()->getNumericId(),
56
					'constraint_type_qid' => $constraint->getConstraintTypeItemId(),
57
					'constraint_parameters' => $this->encodeConstraintParameters( $constraint->getConstraintParameters() )
58
				];
59
			},
60
			$constraints
61
		);
62
63
		$db = wfGetDB( DB_MASTER );
64
		return $db->insert( 'wbqc_constraints', $accumulator );
65
	}
66
67
	/**
68
	 * @param LikeMatch $any should be IDatabase::anyChar()
69
	 *
70
	 * @return string[]
71
	 */
72
	private function uuidPattern( LikeMatch $any ) {
73
		return array_merge(
74
			array_fill( 0, 8, $any ), [ '-' ],
75
			array_fill( 0, 4, $any ), [ '-' ],
76
			array_fill( 0, 4, $any ), [ '-' ],
77
			array_fill( 0, 4, $any ), [ '-' ],
78
			array_fill( 0, 12, $any )
79
		);
80
	}
81
82
	/**
83
	 * Delete all constraints for the property ID where the constraint ID is a statement ID
84
	 * (an entity ID, a '$' separator, and a UUID).
85
	 *
86
	 * @param PropertyId $propertyId
87
	 *
88
	 * @throws DBUnexpectedError
89
	 */
90
	public function deleteForPropertyWhereConstraintIdIsStatementId( PropertyId $propertyId ) {
91
		$db = wfGetDB( DB_MASTER );
92
		$db->delete(
93
			'wbqc_constraints',
94
			[
95
				'pid' => $propertyId->getNumericId(),
96
				// AND constraint_guid LIKE %$________-____-____-____-____________
97
				'constraint_guid ' . $db->buildLike( array_merge( [ $db->anyString(), '$' ], $this->uuidPattern( $db->anyChar() ) ) )
98
			]
99
		);
100
	}
101
102
	/**
103
	 * @param IResultWrapper $results
104
	 *
105
	 * @return Constraint[]
106
	 */
107
	private function convertToConstraints( IResultWrapper $results ) {
108
		$constraints = [];
109
		foreach ( $results as $result ) {
110
			$constraintTypeItemId = $result->constraint_type_qid;
111
			$constraintParameters = json_decode( $result->constraint_parameters, true );
112
113
			if ( $constraintParameters === null ) {
114
				// T171295
115
				LoggerFactory::getInstance( 'WikibaseQualityConstraints' )
116
					->warning( 'Constraint {constraintId} has invalid constraint parameters.', [
117
						'method' => __METHOD__,
118
						'constraintId' => $result->constraint_guid,
119
						'constraintParameters' => $result->constraint_parameters,
120
					] );
121
				$constraintParameters = [ '@error' => [ /* unknown */ ] ];
122
			}
123
124
			$constraints[] = new Constraint(
125
				$result->constraint_guid,
126
				PropertyId::newFromNumber( $result->pid ),
127
				$constraintTypeItemId,
128
				$constraintParameters
129
			);
130
		}
131
		return $constraints;
132
	}
133
134
}
135