Completed
Push — master ( eb7ec6...39bb91 )
by mw
93:13 queued 58:24
created

JsonFileReader::__construct()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 2
nc 1
nop 1
dl 0
loc 3
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace SMW\Tests\Utils\File;
4
5
use RuntimeException;
6
7
/**
8
 * @license GNU GPL v2+
9
 * @since 2.1
10
 *
11
 * @author mwjames
12
 */
13
class JsonFileReader {
14
15
	/**
16
	 * @var string|null
17
	 */
18
	private $file = null;
19
20
	/**
21
	 * @var array|null
22
	 */
23
	private $contents = null;
24
25
	/**
26
	 * @since 2.1
27
	 *
28
	 * @param string|null $file
29
	 */
30
	public function __construct( $file = null ) {
31
		$this->setFile( $file );
32
	}
33
34
	/**
35
	 * @since 2.1
36
	 *
37
	 * @param string $file
38
	 */
39
	public function setFile( $file ) {
40
		$this->file = str_replace( array( '\\', '/' ), DIRECTORY_SEPARATOR, $file );
41
		$this->contents = null;
42
	}
43
44
	/**
45
	 * @since 2.1
46
	 *
47
	 * @return array
48
	 * @throws RuntimeException
49
	 */
50
	public function read() {
51
52
		if ( $this->contents === null && $this->isReadable() ) {
53
			$this->contents = $this->decodeJsonFileContentsToArray( $this->file );
54
		}
55
56
		if ( $this->contents !== null ) {
57
			return $this->contents;
58
		}
59
60
		throw new RuntimeException( "Expected a readable {$this->file} file" );
61
	}
62
63
	/**
64
	 * @since 2.1
65
	 *
66
	 * @return boolean
67
	 */
68
	public function isReadable() {
69
		return is_file( $this->file ) && is_readable( $this->file );
70
	}
71
72
	/**
73
	 * @since 2.1
74
	 *
75
	 * @return integer
76
	 * @throws RuntimeException
77
	 */
78
	public function getModificationTime() {
79
80
		if ( $this->isReadable() ) {
81
			return filemtime( $this->file );
82
		}
83
84
		throw new RuntimeException( "Expected a readable {$this->file} file" );
85
	}
86
87
	private function decodeJsonFileContentsToArray( $file ) {
88
89
		$contents = json_decode( file_get_contents( $file ), true );
90
91
		if ( $contents !== null && json_last_error() === JSON_ERROR_NONE ) {
92
			return $contents;
93
		}
94
95
		throw new RuntimeException( $this->printDescriptiveJsonError( json_last_error() ) );
96
	}
97
98
	private function printDescriptiveJsonError( $errorCode ) {
99
100
		$errorMessages = array(
101
			JSON_ERROR_STATE_MISMATCH => 'Underflow or the modes mismatch, malformed JSON',
102
			JSON_ERROR_CTRL_CHAR => 'Unexpected control character found, possibly incorrectly encoded',
103
			JSON_ERROR_SYNTAX => 'Syntax error, malformed JSON',
104
			JSON_ERROR_UTF8   => 'Malformed UTF-8 characters, possibly incorrectly encoded',
105
			JSON_ERROR_DEPTH  => 'The maximum stack depth has been exceeded'
106
		);
107
108
		return sprintf(
109
			"Expected a JSON compatible format but failed with '%s'",
110
			$errorMessages[$errorCode]
111
		);
112
	}
113
114
}
115