Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
0.00% covered (danger)
0.00%
0 / 41
0.00% covered (danger)
0.00%
0 / 5
CRAP
0.00% covered (danger)
0.00%
0 / 1
CheckTranslationActionApi
0.00% covered (danger)
0.00%
0 / 41
0.00% covered (danger)
0.00%
0 / 5
156
0.00% covered (danger)
0.00%
0 / 1
 execute
0.00% covered (danger)
0.00%
0 / 14
0.00% covered (danger)
0.00%
0 / 1
12
 validateTranslation
0.00% covered (danger)
0.00%
0 / 12
0.00% covered (danger)
0.00%
0 / 1
30
 getDefinition
0.00% covered (danger)
0.00%
0 / 4
0.00% covered (danger)
0.00%
0 / 1
6
 getAllowedParams
0.00% covered (danger)
0.00%
0 / 10
0.00% covered (danger)
0.00%
0 / 1
2
 isInternal
0.00% covered (danger)
0.00%
0 / 1
0.00% covered (danger)
0.00%
0 / 1
2
1<?php
2declare( strict_types = 1 );
3
4namespace MediaWiki\Extension\Translate\Validation;
5
6use ApiBase;
7use MediaWiki\Extension\Translate\MessageLoading\FatMessage;
8use MediaWiki\Extension\Translate\MessageLoading\MessageHandle;
9use MediaWiki\Title\Title;
10use Wikimedia\ParamValidator\ParamValidator;
11
12/** @license GPL-2.0-or-later */
13class CheckTranslationActionApi extends ApiBase {
14    public function execute(): void {
15        $params = $this->extractRequestParams();
16
17        $title = Title::newFromText( $params[ 'title' ] );
18        if ( !$title ) {
19            $this->dieWithError( [ 'apierror-invalidtitle', wfEscapeWikiText( $params['title'] ) ] );
20        }
21        $handle = new MessageHandle( $title );
22        $translation = $params[ 'translation' ];
23
24        $validationResult = $this->validateTranslation( $handle, $translation );
25
26        $validationOutput = [ 'errors' => [], 'warnings' => [] ];
27        if ( $validationResult ) {
28            $validationOutput['errors'] =
29                $validationResult->getDescriptiveErrors( $this->getContext() );
30            $validationOutput['warnings'] =
31                $validationResult->getDescriptiveWarnings( $this->getContext() );
32        }
33
34        $this->getResult()->addValue( null, 'validation', $validationOutput );
35    }
36
37    private function validateTranslation( MessageHandle $handle, string $translation ): ?ValidationResult {
38        if ( $handle->isDoc() || !$handle->isValid() ) {
39            return null;
40        }
41
42        $messageValidator = $handle->getGroup()->getValidator();
43        if ( !$messageValidator ) {
44            return null;
45        }
46
47        $definition = $this->getDefinition( $handle );
48        if ( $definition === null ) {
49            // Very unlikely to happen since the handle is already found to be valid
50            return null;
51        }
52
53        $message = new FatMessage( $handle->getKey(), $definition );
54        $message->setTranslation( $translation );
55
56        $validationResult = $messageValidator->validateMessage( $message, $handle->getCode() );
57
58        return $validationResult;
59    }
60
61    private function getDefinition( MessageHandle $handle ): ?string {
62        $group = $handle->getGroup();
63        if ( method_exists( $group, 'getMessageContent' ) ) {
64            // @phan-suppress-next-line PhanUndeclaredMethod
65            return $group->getMessageContent( $handle );
66        } else {
67            return $group->getMessage( $handle->getKey(), $group->getSourceLanguage() );
68        }
69    }
70
71    protected function getAllowedParams(): array {
72        return [
73            'title' => [
74                ParamValidator::PARAM_TYPE => 'string',
75                ParamValidator::PARAM_REQUIRED => true,
76            ],
77            'translation' => [
78                ParamValidator::PARAM_TYPE => 'string',
79                ParamValidator::PARAM_REQUIRED => true,
80            ],
81        ];
82    }
83
84    public function isInternal(): bool {
85        return true;
86    }
87}