FailedUpdates::updateAnnunci()   A
last analyzed

Complexity

Conditions 3
Paths 4

Size

Total Lines 34
Code Lines 25

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 3
eloc 25
nc 4
nop 1
dl 0
loc 34
rs 9.52
c 0
b 0
f 0
1
<?php declare( strict_types=1 );
2
3
namespace BotRiconferme\Task\Subtask;
4
5
use BotRiconferme\Message\Message;
6
use BotRiconferme\TaskHelper\TaskResult;
7
use BotRiconferme\Utils\RegexUtils;
8
use BotRiconferme\Wiki\Page\Page;
9
use BotRiconferme\Wiki\Page\PageRiconferma;
10
use BotRiconferme\Wiki\User;
11
12
/**
13
 * Update various pages around, to be done for all failed procedures
14
 */
15
class FailedUpdates extends Subtask {
16
	/**
17
	 * @inheritDoc
18
	 */
19
	public function runInternal(): int {
20
		$failed = $this->getFailures();
21
		if ( !$failed ) {
22
			return TaskResult::STATUS_NOTHING;
23
		}
24
25
		$bureaucrats = $this->getFailedBureaucrats( $failed );
26
		if ( $bureaucrats ) {
27
			$this->updateBurList( $bureaucrats );
28
		}
29
		$this->requestRemoval( $failed );
30
		$this->updateAnnunci( $failed );
31
		$this->updateUltimeNotizie( $failed );
32
		$this->updateTimeline( $failed );
33
		$this->updateCronologia( $failed );
34
		$this->blockOnPrivate( $failed );
35
36
		return TaskResult::STATUS_GOOD;
37
	}
38
39
	/**
40
	 * Get the list of failed votes
41
	 *
42
	 * @return PageRiconferma[]
43
	 */
44
	private function getFailures(): array {
45
		$ret = [];
46
		$allPages = $this->getDataProvider()->getPagesToClose();
47
		foreach ( $allPages as $page ) {
48
			if ( $page->getOutcome() & PageRiconferma::OUTCOME_FAIL ) {
49
				$ret[] = $page;
50
			}
51
		}
52
		return $ret;
53
	}
54
55
	/**
56
	 * @param User[] $users
57
	 */
58
	protected function updateBurList( array $users ): void {
59
		$this->getLogger()->info( 'Updating bur list. Removing: ' . implode( ', ', $users ) );
60
		$remList = RegexUtils::regexFromArray( '!', ...$users );
61
		$burList = $this->getPage( $this->getOpt( 'bur-list-title' ) );
62
		$content = $burList->getContent();
63
		$reg = "!^\#\{\{ *Burocrate *\| *$remList.+\n!m";
64
		$newContent = preg_replace( $reg, '', $content );
65
66
		$summary = $this->msg( 'bur-list-update-summary' )
67
			->params( [ '$remove' => Message::commaList( $users ) ] )
68
			->text();
69
70
		$burList->edit( [
71
			'text' => $newContent,
72
			'summary' => $summary
73
		] );
74
	}
75
76
	/**
77
	 * Request the removal of the flag on meta
78
	 *
79
	 * @param PageRiconferma[] $pages
80
	 */
81
	protected function requestRemoval( array $pages ): void {
82
		$this->getLogger()->info( 'Requesting flag removal for: ' . implode( ', ', $pages ) );
83
84
		$metaWiki = $this->getWikiGroup()->getCentralWiki();
85
		$flagRemPage = new Page(
86
			$this->getOpt( 'flag-removal-page-title' ),
87
			$metaWiki
88
		);
89
		$baseText = $this->msg( 'flag-removal-text' );
90
91
		$append = '';
92
		foreach ( $pages as $page ) {
93
			$append .=
94
				$baseText->params( [
95
					'$username' => $page->getUserName(),
96
					'$link' => '[[:it:' . $page->getTitle() . ']]',
97
					'$groups' => implode( ', ', $this->getUser( $page->getUserName() )->getGroups() )
98
				] )->text();
99
		}
100
101
		// NOTE: This assumes that the section for removal of access comes immediately
102
		// before the "see also" section. This is obviously not guaranteed, and this code
103
		// might break if the page structure changes.
104
		$after = '== See also ==';
105
		$newContent = str_replace( $after, "$append\n$after", $flagRemPage->getContent() );
106
		$summary = $this->msg( 'flag-removal-summary' )
107
			->params( [ '$num' => count( $pages ) ] )
108
			->text();
109
110
		$flagRemPage->edit( [
111
			'text' => $newContent,
112
			'summary' => $summary
113
		] );
114
	}
115
116
	/**
117
	 * Update [[Wikipedia:Wikipediano/Annunci]]
118
	 *
119
	 * @param PageRiconferma[] $pages
120
	 */
121
	protected function updateAnnunci( array $pages ): void {
122
		$this->getLogger()->info( 'Updating annunci' );
123
		$section = 1;
124
125
		$names = [];
126
		$text = '';
127
		foreach ( $pages as $page ) {
128
			$user = $page->getUserName();
129
			$names[] = $user;
130
			$text .= $this->msg( 'annunci-text' )->params( [ '$user' => $user ] )->text();
131
		}
132
133
		/** @var string $curMonth */
134
		$curMonth = date( 'F' );
135
		$month = ucfirst( Message::MONTHS[$curMonth] );
136
137
		$annunciPage = $this->getPage( $this->getOpt( 'annunci-page-title' ) );
138
		$content = $annunciPage->getContent( $section );
139
		$secReg = "!=== *$month *===!";
140
		if ( $annunciPage->matches( $secReg ) ) {
141
			$newContent = preg_replace( $secReg, '$0' . "\n" . $text, $content );
142
		} else {
143
			$before = '!</div>\s*}}\s*</includeonly>!';
144
			$newContent = preg_replace( $before, '$0' . "\n=== $month ===\n" . $text, $content );
145
		}
146
147
		$summary = $this->msg( 'annunci-summary' )
148
			->params( [ '$names' => Message::commaList( $names ) ] )
149
			->text();
150
151
		$annunciPage->edit( [
152
			'section' => $section,
153
			'text' => $newContent,
154
			'summary' => $summary
155
		] );
156
	}
157
158
	/**
159
	 * Update [[Wikipedia:Ultime notizie]]
160
	 *
161
	 * @param PageRiconferma[] $pages
162
	 */
163
	protected function updateUltimeNotizie( array $pages ): void {
164
		$this->getLogger()->info( 'Updating ultime notizie' );
165
		$notiziePage = $this->getPage( $this->getOpt( 'ultimenotizie-page-title' ) );
166
167
		$names = [];
168
		$text = '';
169
		$msg = $this->msg( 'ultimenotizie-text' );
170
		foreach ( $pages as $page ) {
171
			$user = $page->getUserName();
172
			$names[] = $user;
173
			$text .= $msg->params( [ '$user' => $user, '$title' => $page->getTitle() ] )->text();
174
		}
175
176
		$content = $notiziePage->getContent();
177
		$year = date( 'Y' );
178
		$secReg = "!== *$year *==!";
179
		if ( preg_match( $secReg, $content ) ) {
180
			$newContent = preg_replace( $secReg, '$0' . "\n" . $text, $content );
181
		} else {
182
			$reg = '!si veda la \[\[[^\]+relativa discussione]]\.\n!';
183
			$newContent = preg_replace( $reg, '$0' . "\n== $year ==\n" . $text, $content );
184
		}
185
186
		$summary = $this->msg( 'ultimenotizie-summary' )
187
			->params( [ '$names' => Message::commaList( $names ) ] )->text();
188
189
		$notiziePage->edit( [
190
			'text' => $newContent,
191
			'summary' => $summary
192
		] );
193
	}
194
195
	/**
196
	 * Update [[Wikipedia:Amministratori/Timeline]]
197
	 *
198
	 * @param PageRiconferma[] $pages
199
	 */
200
	protected function updateTimeline( array $pages ): void {
201
		$this->getLogger()->info( 'Updating timeline' );
202
		$timelinePage = $this->getPage( $this->getOpt( 'timeline-page-title' ) );
203
		$content = $timelinePage->getContent();
204
205
		$today = date( 'm/d/Y' );
206
		foreach ( $pages as $page ) {
207
			$name = $page->getUserName();
208
			$content = preg_replace(
209
				"/(?<=color:)current( *from:\d+/\d+/\d+ till:)end(?= text:\"\[\[(User|Utente):$name|$name]]\")/",
210
				'nonriconf$1' . $today,
211
				$content
212
			);
213
		}
214
215
		$summary = $this->msg( 'timeline-summary' )->text();
216
217
		$timelinePage->edit( [
218
			'text' => $content,
219
			'summary' => $summary
220
		] );
221
	}
222
223
	/**
224
	 * Update [[Wikipedia:Amministratori/Cronologia]]
225
	 *
226
	 * @param PageRiconferma[] $pages
227
	 */
228
	private function updateCronologia( array $pages ): void {
229
		$this->getLogger()->info( 'Updating cronologia' );
230
		$timelinePage = $this->getPage( $this->getOpt( 'cronologia-page-title' ) );
231
		$content = $timelinePage->getContent();
232
233
		foreach ( $pages as $page ) {
234
			$name = $page->getUserName();
235
			$content = preg_replace(
236
				"/(\* *)'''(\[\[(Utente|User):$name|$name]])'''( <small>dal \d+ \w+ \d+)(</small>)/",
237
				'$1$2$3' . " al {{subst:#timel:j F Y}} (non riconfermato)" . '$4',
238
				$content
239
			);
240
		}
241
242
		$summary = $this->msg( 'cronologia-summary' )->text();
243
244
		$timelinePage->edit( [
245
			'text' => $content,
246
			'summary' => $summary
247
		] );
248
	}
249
250
	/**
251
	 * Block the user on the private wiki
252
	 *
253
	 * @param PageRiconferma[] $pages
254
	 */
255
	private function blockOnPrivate( array $pages ): void {
256
		$this->getLogger()->info( 'Blocking on private wiki: ' . implode( ', ', $pages ) );
257
258
		$privWiki = $this->getWikiGroup()->getPrivateWiki();
259
		$reason = $this->msg( 'private-block-reason' )->text();
260
261
		foreach ( $pages as $page ) {
262
			$privWiki->blockUser( $page->getUserName(), $reason );
263
		}
264
	}
265
266
	/**
267
	 * Get a list of bureaucrats from the given $pages
268
	 *
269
	 * @param PageRiconferma[] $pages
270
	 * @return User[]
271
	 */
272
	private function getFailedBureaucrats( array $pages ): array {
273
		$ret = [];
274
		foreach ( $pages as $page ) {
275
			$user = $this->getUser( $page->getUserName() );
276
			if ( $user->inGroup( 'bureaucrat' ) ) {
277
				$ret[] = $user;
278
			}
279
		}
280
		return $ret;
281
	}
282
}
283