Completed
Pull Request — master (#93)
by no
07:24 queued 03:27
created

YearMonthDayTimeParserTest::validInputProvider()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 71
Code Lines 43

Duplication

Lines 0
Ratio 0 %

Importance

Changes 4
Bugs 0 Features 1
Metric Value
c 4
b 0
f 1
dl 0
loc 71
rs 9.137
cc 3
eloc 43
nc 3
nop 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 ValueParsers\Test;
4
5
use DataValues\TimeValue;
6
use ValueParsers\EraParser;
7
use ValueParsers\YearMonthDayTimeParser;
8
9
/**
10
 * @covers ValueParsers\YearMonthDayTimeParser
11
 *
12
 * @group DataValue
13
 * @group DataValueExtensions
14
 * @group TimeParsers
15
 * @group ValueParsers
16
 *
17
 * @licence GNU GPL v2+
18
 * @author Thiemo Mättig
19
 */
20
class YearMonthDayTimeParserTest extends StringValueParserTest {
21
22
	/**
23
	 * @deprecated since 0.3, just use getInstance.
24
	 */
25
	protected function getParserClass() {
26
		throw new \LogicException( 'Should not be called, use getInstance' );
27
	}
28
29
	/**
30
	 * @see ValueParserTestBase::getInstance
31
	 *
32
	 * @return YearMonthDayTimeParser
33
	 */
34
	protected function getInstance() {
35
		return $this->getYearMonthDayTimeParser();
36
	}
37
38
	/**
39
	 * @param int[] $months
40
	 *
41
	 * @return YearMonthDayTimeParser
42
	 */
43
	private function getYearMonthDayTimeParser( array $months = array() ) {
44
		return new YearMonthDayTimeParser( null, $months );
45
	}
46
47
	/**
48
	 * @see ValueParserTestBase::validInputProvider
49
	 */
50
	public function validInputProvider() {
51
		$gregorian = 'http://www.wikidata.org/entity/Q1985727';
52
		$julian = 'http://www.wikidata.org/entity/Q1985786';
53
54
		$valid = array(
55
			// YMD, typically used in ISO 8601
56
			'2015-12-31' => array( '+2015-12-31T00:00:00Z' ),
57
			'2015 12 31' => array( '+2015-12-31T00:00:00Z' ),
58
			'2015 1 13' => array( '+2015-01-13T00:00:00Z' ),
59
60
			// DMY
61
			'31.12.2015' => array( '+2015-12-31T00:00:00Z' ),
62
			'31. 12. 2015' => array( '+2015-12-31T00:00:00Z' ),
63
			'31/12/2015' => array( '+2015-12-31T00:00:00Z' ),
64
			'31 12 2015' => array( '+2015-12-31T00:00:00Z' ),
65
			'31th 12th 2015' => array( '+2015-12-31T00:00:00Z' ),
66
			'day 31, month 12, year 2015' => array( '+2015-12-31T00:00:00Z' ),
67
68
			// MDY, almost exclusively used in the United States
69
			'12/31/2015' => array( '+2015-12-31T00:00:00Z' ),
70
			'12-31-2015' => array( '+2015-12-31T00:00:00Z' ),
71
			'12 31 2015' => array( '+2015-12-31T00:00:00Z' ),
72
73
			// YDM, exclusively used in Kazakhstan
74
			// https://en.wikipedia.org/wiki/Calendar_date#Gregorian.2C_year-day-month_.28YDM.29
75
			'2015.31.12' => array( '+2015-12-31T00:00:00Z' ),
76
			'2015 13 1' => array( '+2015-01-13T00:00:00Z' ),
77
78
			// Month and day are the same, does not matter if DMY or MDY
79
			'01 1 2015' => array( '+2015-01-01T00:00:00Z' ),
80
			'12 12 2015' => array( '+2015-12-12T00:00:00Z' ),
81
82
			// Month and day are the same, does not matter if YMD or YDM
83
			'2015 01 1' => array( '+2015-01-01T00:00:00Z' ),
84
			'2015 12 12' => array( '+2015-12-12T00:00:00Z' ),
85
86
			// Julian
87
			'32-12-31' => array( '+0032-12-31T00:00:00Z', $julian ),
88
			'31.12.32' => array( '+0032-12-31T00:00:00Z', $julian ),
89
			'12/31/60' => array( '+0060-12-31T00:00:00Z', $julian ),
90
91
			// Negative years
92
			'-2015-12-31' => array( '-2015-12-31T00:00:00Z', $julian ),
93
			'year -2015-12-31' => array( '-2015-12-31T00:00:00Z', $julian ),
94
			'31 12 -2015' => array( '-2015-12-31T00:00:00Z', $julian ),
95
			'12/31/-2015' => array( '-2015-12-31T00:00:00Z', $julian ),
96
			'2015-12-31 BC' => array( '-2015-12-31T00:00:00Z', $julian ),
97
			'31 12 2015 BC' => array( '-2015-12-31T00:00:00Z', $julian ),
98
			'12/31/2015 BC' => array( '-2015-12-31T00:00:00Z', $julian ),
99
100
			// A negative number must be the year.
101
			'year -3-2-13' => array( '-0003-02-13T00:00:00Z', $julian ),
102
			'13. 2. -3' => array( '-0003-02-13T00:00:00Z', $julian ),
103
			'23:12:-59' => array( '-0059-12-23T00:00:00Z', $julian ),
104
		);
105
106
		$cases = array();
107
108
		foreach ( $valid as $value => $args ) {
109
			$timestamp = $args[0];
110
			$calendarModel = isset( $args[1] ) ? $args[1] : $gregorian;
111
112
			$cases[] = array(
113
				// Because PHP magically turns numeric keys into ints/floats
114
				(string)$value,
115
				new TimeValue( $timestamp, 0, 0, 0, TimeValue::PRECISION_DAY, $calendarModel )
116
			);
117
		}
118
119
		return $cases;
120
	}
121
122
	/**
123
	 * @see StringValueParserTest::invalidInputProvider
124
	 */
125
	public function invalidInputProvider() {
126
		$invalid = array(
127
			// This parser can only parse strings that contain exactly three numbers.
128
			'2015',
129
			'12.2015',
130
			'May 1 2015',
131
			'1. May 2015',
132
			'1 2015-12-31',
133
			'31.12.2015 23',
134
			'31.12.2015 23:59',
135
			'+2015-12-31T00:00:00Z',
136
137
			// Can be confused with a time (HMS)
138
			'12:31:59',
139
			'12:59:59',
140
			'23:12:59',
141
			'23:12:31',
142
			'-23:12:31',
143
			'-24:00:00',
144
145
			// No year can be identified if all numbers are smaller than 32.
146
			'12 12 12',
147
			'31 12 12',
148
			'12 31 12',
149
			'31 31 12',
150
			'12 12 31',
151
			'31 12 31',
152
			'12 31 31',
153
			'31 31 31',
154
155
			// Two or more candidates for the year.
156
			'32 32 12',
157
			'32 12 32',
158
			'12 32 32',
159
			'32 32 32',
160
161
			// Year can be identified, but month and day can not be distinguished.
162
			'32 2 1',
163
			'2015-12-11',
164
			'1 2 32',
165
			'11.12.2015',
166
167
			// Formats DYM and MYD do not exist and should not be parsed.
168
			'12 -1 12',
169
			'12 32 12',
170
			'12 2015 31',
171
			'31 2015 12',
172
173
			// Duplicate era.
174
			'year -2015-12-31 BC',
175
			'31.12.-2015 BC',
176
177
			// Zeros.
178
			'-2015-00-00',
179
			'0000-00-00',
180
			'2015-00-00',
181
			'2015-12-00',
182
			'0. 0. -2015',
183
			'0. 0. 0',
184
			'0. 0. 2015',
185
			'0. 12. 2015',
186
187
			// To long.
188
			'2015-12-031',
189
			'2015-012-31',
190
		);
191
192
		$cases = parent::invalidInputProvider();
193
194
		foreach ( $invalid as $value ) {
195
			$cases[] = array( $value );
196
		}
197
198
		return $cases;
199
	}
200
201
	/**
202
	 * @dataProvider monthNamesProvider
203
	 */
204
	public function testMonthNameParsing( $value, array $months, TimeValue $expected ) {
205
		$parser = $this->getYearMonthDayTimeParser( $months );
206
		$this->assertTrue( $expected->equals( $parser->parse( $value ) ) );
207
	}
208
209
	public function monthNamesProvider() {
210
		$gregorian = 'http://www.wikidata.org/entity/Q1985727';
211
		$julian = 'http://www.wikidata.org/entity/Q1985786';
0 ignored issues
show
Unused Code introduced by
$julian is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
212
213
		$valid = array(
214
			'13.12.1999' => array(
215
				array(),
216
				'+1999-12-13T00:00:00Z',
217
			),
218
			'13. February 1999' => array(
219
				array( 'February' => 2 ),
220
				'+1999-02-13T00:00:00Z',
221
			),
222
		);
223
224
		$cases = array();
225
226
		foreach ( $valid as $value => $args ) {
227
			$months = $args[0];
228
			$timestamp = $args[1];
229
			$calendarModel = isset( $args[2] ) ? $args[2] : $gregorian;
230
231
			$cases[] = array(
232
				(string)$value,
233
				$months,
234
				new TimeValue( $timestamp, 0, 0, 0, TimeValue::PRECISION_DAY, $calendarModel )
0 ignored issues
show
Bug introduced by
It seems like $calendarModel defined by isset($args[2]) ? $args[2] : $gregorian on line 229 can also be of type array; however, DataValues\TimeValue::__construct() does only seem to accept string, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
235
			);
236
		}
237
238
		return $cases;
239
	}
240
241
	/**
242
	 * @dataProvider invalidMonthNamesProvider
243
	 */
244
	public function testInvalidMonthNameParsing( $value, array $months ) {
245
		$parser = $this->getYearMonthDayTimeParser( $months );
246
		$this->setExpectedException( 'ValueParsers\ParseException' );
247
		$parser->parse( $value );
248
	}
249
250
	public function invalidMonthNamesProvider() {
251
		return array(
252
			array( '13. February 1999', array() ),
253
			array( 'February. February 1999', array( 'February' => 2 ) ),
254
			array( '13. Feb 1999', array( 'February' => 2 ) ),
255
		);
256
	}
257
258
}
259