Code Coverage |
||||||||||
Lines |
Functions and Methods |
Classes and Traits |
||||||||
Total | |
0.00% |
0 / 41 |
|
0.00% |
0 / 6 |
CRAP | |
0.00% |
0 / 1 |
GerritExtDistProvider | |
0.00% |
0 / 41 |
|
0.00% |
0 / 6 |
272 | |
0.00% |
0 / 1 |
__construct | |
0.00% |
0 / 3 |
|
0.00% |
0 / 1 |
6 | |||
makeGerritApiRequest | |
0.00% |
0 / 14 |
|
0.00% |
0 / 1 |
12 | |||
fetchBranches | |
0.00% |
0 / 8 |
|
0.00% |
0 / 1 |
12 | |||
fetchRepositoryList | |
0.00% |
0 / 13 |
|
0.00% |
0 / 1 |
42 | |||
getTarballLocation | |
0.00% |
0 / 2 |
|
0.00% |
0 / 1 |
2 | |||
getCacheDuration | |
0.00% |
0 / 1 |
|
0.00% |
0 / 1 |
2 |
1 | <?php |
2 | |
3 | namespace MediaWiki\Extension\ExtensionDistributor\Providers; |
4 | |
5 | use MediaWiki\Json\FormatJson; |
6 | use MediaWiki\MediaWikiServices; |
7 | use MediaWiki\Status\Status; |
8 | |
9 | /** |
10 | * ExtensionDistributor provider for the Gerrit Code Review system |
11 | * Requires an external service to provide tarballs |
12 | * |
13 | * @author Legoktm |
14 | * |
15 | * Example configuration for Wikimedia sites: |
16 | * |
17 | * use MediaWiki\Extension\ExtensionDistributor\Providers\GerritExtDistProvider; |
18 | * |
19 | * $wgExtDistAPIConfig = [ |
20 | * 'class' => GerritExtDistProvider::class, |
21 | * 'apiUrl' => 'https://gerrit.wikimedia.org/r/projects/mediawiki%2F$TYPE%2F$EXT/branches', |
22 | * 'tarballUrl' => 'http://extdist.wmflabs.org/dist/$TYPE/$EXT-$REF-$SHA.tar.gz', |
23 | * 'tarballName' => '$EXT-$REF-$SHA.tar.gz', |
24 | * 'repoListUrl' => 'https://gerrit.wikimedia.org/r/projects/?b=master&p=mediawiki/$TYPE/', |
25 | * 'sourceUrl' => 'https://gerrit.wikimedia.org/r/mediawiki/$TYPE/$EXT.git', |
26 | * ]; |
27 | * |
28 | */ |
29 | class GerritExtDistProvider extends ExtDistProvider { |
30 | |
31 | /** @var string|false */ |
32 | private $repoListUrl = false; |
33 | |
34 | public function __construct( array $options ) { |
35 | parent::__construct( $options ); |
36 | if ( isset( $options['repoListUrl'] ) ) { |
37 | $this->repoListUrl = $options['repoListUrl']; |
38 | } |
39 | } |
40 | |
41 | /** |
42 | * @param string $url full URL to request |
43 | * @return array[] |
44 | */ |
45 | private function makeGerritApiRequest( $url ) { |
46 | $options = []; |
47 | if ( $this->proxy ) { |
48 | $options['proxy'] = $this->proxy; |
49 | } |
50 | |
51 | $req = MediaWikiServices::getInstance()->getHttpRequestFactory() |
52 | ->create( $url, $options, __METHOD__ ); |
53 | $status = $req->execute(); |
54 | if ( !$status->isOK() ) { |
55 | $errorText = Status::wrap( $status )->getWikiText( false, false, 'en' ); |
56 | $this->logger->error( __METHOD__ . ": Could not fetch \"{$url}\", " . |
57 | "received: " . $errorText |
58 | ); |
59 | return []; |
60 | } |
61 | // Gerrit API responses start with )]}' so trim it, then parse the JSON |
62 | $clean = substr( $req->getContent(), 4 ); |
63 | return wfObjectToArray( FormatJson::decode( $clean ), true ); |
64 | } |
65 | |
66 | /** @inheritDoc */ |
67 | protected function fetchBranches( $name ) { |
68 | $url = $this->substituteUrlVariables( $this->apiUrl, $name ); |
69 | $info = $this->makeGerritApiRequest( $url ); |
70 | $branches = []; |
71 | foreach ( $info as $branch ) { |
72 | if ( strpos( $branch['ref'], 'refs/heads/' ) === 0 ) { |
73 | $name = substr( $branch['ref'], strlen( 'refs/heads/' ) ); |
74 | $branches[$name] = $branch['revision']; |
75 | } |
76 | } |
77 | |
78 | return $branches; |
79 | } |
80 | |
81 | protected function fetchRepositoryList() { |
82 | if ( !$this->repoListUrl ) { |
83 | // Not configured, fallback to default |
84 | return parent::fetchRepositoryList(); |
85 | } |
86 | |
87 | $repos = []; |
88 | $out = $this->makeGerritApiRequest( |
89 | $this->substituteUrlVariables( $this->repoListUrl ) |
90 | ); |
91 | foreach ( $out as $name => $info ) { |
92 | // Skip read-only repositories |
93 | if ( isset( $info['state'] ) && $info['state'] === 'READ_ONLY' ) { |
94 | continue; |
95 | } |
96 | $parts = explode( '/', $name ); |
97 | if ( count( $parts ) === 3 ) { |
98 | $repos[] = array_pop( $parts ); |
99 | } |
100 | } |
101 | |
102 | return $repos; |
103 | } |
104 | |
105 | /** @inheritDoc */ |
106 | public function getTarballLocation( $ext, $version ) { |
107 | $shortHash = $this->getBranchSha( $ext, $version ); |
108 | return $this->substituteUrlVariables( $this->tarballUrl, $ext, $version, $shortHash ); |
109 | } |
110 | |
111 | /** |
112 | * Cache list of branches for 30 minutes |
113 | * |
114 | * @return int |
115 | */ |
116 | protected function getCacheDuration() { |
117 | return 60 * 30; |
118 | } |
119 | } |