Completed
Push — master ( 0bdf57...ff1c2f )
by mw
6s
created

InterlanguageLinkParserFunction::parse()   B

Complexity

Conditions 4
Paths 6

Size

Total Lines 25
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 14
CRAP Score 4

Importance

Changes 9
Bugs 1 Features 2
Metric Value
c 9
b 1
f 2
dl 0
loc 25
ccs 14
cts 14
cp 1
rs 8.5806
cc 4
eloc 12
nc 6
nop 2
crap 4
1
<?php
2
3
namespace SIL;
4
5
use Onoi\Cache\CacheFactory;
6
use Title;
7
use Language;
8
9
/**
10
 * @license GNU GPL v2+
11
 * @since 1.0
12
 *
13
 * @author mwjames
14
 */
15
class InterlanguageLinkParserFunction {
16
17
	/**
18
	 * @var Title
19
	 */
20
	private $title;
21
22
	/**
23
	 * @var LanguageLinkAnnotator
24
	 */
25
	private $languageLinkAnnotator;
26
27
	/**
28
	 * @var SiteLanguageLinksParserOutputAppender
29
	 */
30
	private $siteLanguageLinksParserOutputAppender;
31
32
	/**
33
	 * @var PageContentLanguageModifier
34
	 */
35
	private $pageContentLanguageModifier;
36
37
	/**
38
	 * @var boolean
39
	 */
40
	private $interlanguageLinksHideState = false;
41
42
	/**
43
	 * @var boolean
44
	 */
45
	private $inRevisionMode = false;
46
47
	/**
48
	 * @since 1.0
49
	 *
50
	 * @param Title $title
51
	 * @param LanguageLinkAnnotator $languageLinkAnnotator
52
	 * @param SiteLanguageLinksParserOutputAppender $siteLanguageLinksParserOutputAppender
53
	 * @param PageContentLanguageModifier $pageContentLanguageModifier
54
	 */
55 16
	public function __construct( Title $title, LanguageLinkAnnotator $languageLinkAnnotator, SiteLanguageLinksParserOutputAppender $siteLanguageLinksParserOutputAppender, PageContentLanguageModifier $pageContentLanguageModifier ) {
56 16
		$this->title = $title;
57 16
		$this->languageLinkAnnotator = $languageLinkAnnotator;
58 16
		$this->siteLanguageLinksParserOutputAppender = $siteLanguageLinksParserOutputAppender;
59 16
		$this->pageContentLanguageModifier = $pageContentLanguageModifier;
60 16
	}
61
62
	/**
63
	 * @since 1.0
64
	 *
65
	 * @param boolean $interlanguageLinksHideState
66
	 */
67 10
	public function setInterlanguageLinksHideState( $interlanguageLinksHideState ) {
68 10
		$this->interlanguageLinksHideState = $interlanguageLinksHideState;
69 10
	}
70
71
	/**
72
	 * Revision mode means either in preview or edit state which is not to be
73
	 * handled to avoid storage of yet unprocessed data in cache.
74
	 *
75
	 * @since 1.2
76
	 *
77
	 * @param boolean $inRevisionMode
78
	 */
79 9
	public function setRevisionModeState( $inRevisionMode ) {
80 9
		$this->inRevisionMode = $inRevisionMode;
81 9
	}
82
83
	/**
84
	 * @since 1.0
85
	 *
86
	 * @param string $languageCode
87
	 * @param string $linkReference
88
	 *
89
	 * @return null|string
90
	 */
91 15
	public function parse( $languageCode, $linkReference ) {
92
93 15
		$languageCode = wfBCP47( $languageCode );
94
95
		// Keep reference while editing is on going to avoid a possible lag when
96
		// a DV is trying to access the page content language
97 15
		if ( ( $isSupportedLanguage = $this->isSupportedLanguage( $languageCode ) ) === true ) {
98 15
			$this->pageContentLanguageModifier->addToIntermediaryCache( $this->title, $languageCode );
99 15
		}
100
101 15
		if ( !( $title = $this->getTitleFrom( $isSupportedLanguage, $languageCode, $linkReference ) ) instanceof Title ) {
102 4
			return $title;
103
		}
104
105 11
		$interlanguageLink = new InterlanguageLink(
106 11
			$languageCode,
107 11
			$this->siteLanguageLinksParserOutputAppender->getRedirectTargetFor( $title )
108 11
		);
109
110 11
		if ( $this->languageLinkAnnotator->hasDifferentLanguageAnnotation( $interlanguageLink ) ) {
111 2
			return $this->createErrorMessageFor( 'sil-interlanguagelink-multiplecalls-different-languagecode', $languageCode );
112
		}
113
114 11
		return $this->createSiteLanguageLinks( $interlanguageLink );
115
	}
116
117 15
	private function getTitleFrom( $isSupportedLanguage, $languageCode, $linkReference ) {
118
119 15
		if ( $this->inRevisionMode || !$this->languageLinkAnnotator->canAddAnnotation() ) {
120 3
			return '';
121
		}
122
123 12
		if ( $this->interlanguageLinksHideState ) {
124 1
			return $this->createErrorMessageFor( 'sil-interlanguagelink-hideinterlanguagelinks' );
125
		}
126
127 12
		if ( !$isSupportedLanguage ) {
128 1
			return $this->createErrorMessageFor( 'sil-interlanguagelink-invalidlanguagecode', $languageCode );
129
		}
130
131 12
		$title = Title::newFromText( $linkReference );
132
133 12
		if ( $title === null ) {
134 1
			return $this->createErrorMessageFor( 'sil-interlanguageparser-linkreference-error', $linkReference );
135
		}
136
137 11
		return $title;
138
	}
139
140 11
	private function createSiteLanguageLinks( InterlanguageLink $interlanguageLink ) {
141
142 11
		$knownTargetLink = $this->siteLanguageLinksParserOutputAppender->tryAddLanguageTargetLinksToOutput(
143 11
			$interlanguageLink,
144 11
			$this->title
145 11
		);
146
147
		// If target is known we stop processing and output an error
148 11
		if ( $knownTargetLink ) {
149 2
			return $this->createErrorMessageFor(
150 2
				'sil-interlanguagelink-languagetargetcombination-exists',
151 2
				$interlanguageLink->getLanguageCode(),
152 2
				$interlanguageLink->getLinkReference()->getPrefixedText(),
153 2
				$knownTargetLink,
0 ignored issues
show
Bug introduced by
It seems like $knownTargetLink defined by $this->siteLanguageLinks...uageLink, $this->title) on line 142 can also be of type boolean; however, SIL\InterlanguageLinkPar...createErrorMessageFor() 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...
154 2
				$this->title->getPrefixedText()
155 2
			);
156
		}
157
158 10
		$this->languageLinkAnnotator->addAnnotationForInterlanguageLink(
159
			$interlanguageLink
160 10
		);
161
162 10
		return '<div class="sil-interlanguagelink"></div>';
163
	}
164
165 15
	private function isSupportedLanguage( $languageCode ) {
166
167 15
		$languageCode = trim( $languageCode );
168
169 15
		if ( strlen( $languageCode ) == 0 ) {
170 1
			return false;
171
		}
172
173 15
		return Language::isSupportedLanguage( $languageCode );
174
	}
175
176 4
	private function createErrorMessageFor( $messageKey, $arg1 = '', $arg2 = '', $arg3 = '',$arg4 = '' ) {
177 4
		return '<div class="smw-callout smw-callout-error">' . wfMessage(
178 4
			$messageKey,
179 4
			$arg1,
180 4
			$arg2,
181 4
			$arg3,
182
			$arg4
183 4
		)->inContentLanguage()->text() . '</div>';
184
	}
185
186
}
187