Test Setup Failed
Pull Request — main (#426)
by MusikAnimal
17:10 queued 11:44
created

RFX::setUp()   B

Complexity

Conditions 11
Paths 28

Size

Total Lines 52
Code Lines 31

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 11
eloc 31
nc 28
nop 3
dl 0
loc 52
rs 7.3166
c 0
b 0
f 0

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
/**
3
 * An RFX object contains the parsed information for an RFX
4
 */
5
6
declare(strict_types = 1);
7
8
namespace App\Model;
9
10
/**
11
 * This class contains information about a single RfX page.
12
 * @codeCoverageIgnore
13
 */
14
class RFX extends Model
15
{
16
    /** @var array Data we parsed out of the page text */
17
    private $data;
18
19
    /** @var array Duplicate voters */
20
    private $duplicates;
21
22
    /** @var null|string Username of the user we're looking for. */
23
    private $userLookingFor;
24
25
    /** @var string Section we found the user we're looking for */
26
    private $userSectionFound;
27
28
    /**
29
     * Attempts to find a signature in $input using the default regex.
30
     * Returns matches.
31
     *
32
     * @param string $input   The line we're looking for
33
     * @param array  $matches Pointer to an array where we stash results
34
     *
35
     * @TODO: Make this cleaner
36
     *
37
     * @return int
38
     */
39
    protected function findSig(string $input, array &$matches): int
40
    {
41
        //Supports User: and User talk: wikilinks, {{fullurl}},
42
        // unsubstituted {{unsigned}}, unsubstituted {{unsigned2}},
43
        // anything that looks like a custom sig template
44
        // TODO: Cross-wiki this sucker
45
        $regexp
46
            = //1: Normal [[User:XX]] and [[User talk:XX]]
47
            "/\[\[[Uu]ser(?:[\s_][Tt]alk)?\:([^\]\|\/]*)(?:\|[^\]]*)?\]\]"
48
            //2: {{fullurl}} and {{unsigned}} templates
49
            . "|\{\{(?:[Ff]ullurl\:[Uu]ser(?:[\s_][Tt]alk)?\:|"
50
            . "[Uu]nsigned\|)([^\}\|]*)(?:|[\|\}]*)?\}\}"
51
            //3: {{User:XX/sig}} templates
52
            . "|(?:\{\{)[Uu]ser(?:[\s_][Tt]alk)?\:([^\}\/\|]*)"
53
            //4: {{unsigned2|Date|XX}} templates
54
            . "|\{\{[Uu]nsigned2\|[^\|]*\|([^\}]*)\}\}"
55
            //5: [[User:XX/sig]] links (compromise measure)
56
            . "|(?:\[\[)[Uu]ser\:([^\]\/\|]*)\/[Ss]ig[\|\]]/";
57
58
        return preg_match_all(
59
            $regexp,
60
            $input,
61
            $matches,
62
            PREG_OFFSET_CAPTURE
63
        );
64
    }
65
66
    /**
67
     * This function parses the wikitext and stores it within this function.
68
     * It's been split out to make this class testable
69
     *
70
     * @param array  $sectionArray Section names that we're looking for
71
     * @param string $rawWikiText  The text of the page we're parsing
72
     * @param string $dateRegexp   Valid Regular Expression for the end date
73
     */
74
    private function setUp(array $sectionArray, string $rawWikiText, string $dateRegexp): void
75
    {
76
        $this->data = [];
77
78
        $lines = explode("\n", $rawWikiText);
79
80
        $keys = join("|", $sectionArray);
81
82
        $lastSection = "";
83
84
        foreach ($lines as $line) {
85
            if (preg_match("/={1,6}\s?($keys)\s?={1,6}/i", $line, $matches)) {
86
                $lastSection = strtolower($matches[1]);
87
            } elseif ("" == $lastSection
88
                && preg_match(
89
                    "/$dateRegexp/i",
90
                    $line,
91
                    $matches
92
                )
93
            ) {
94
                $this->end = $matches[1];
95
            } elseif ("" != $lastSection
96
                && 0 === preg_match("/^\s*#?:.*/i", $line)
97
            ) {
98
                $this->findSig($line, $matches);
99
                if (!isset($matches[1][0])) {
100
                    continue;
101
                }
102
                $foundUser = trim($matches[1][0][0]);
103
                $this->data[$lastSection][] = $foundUser;
104
                if (strtolower($foundUser) === strtolower($this->userLookingFor)) {
0 ignored issues
show
Bug introduced by
It seems like $this->userLookingFor can also be of type null; however, parameter $string of strtolower() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

104
                if (strtolower($foundUser) === strtolower(/** @scrutinizer ignore-type */ $this->userLookingFor)) {
Loading history...
105
                    $this->userSectionFound = $lastSection;
106
                }
107
            }
108
        }
109
110
        $final = [];    // initialize the final array
111
        $finalRaw = []; // Initialize the raw data array
112
113
        foreach (array_keys($this->data) as $key) {
114
            $finalRaw = array_merge($finalRaw, $this->data[$key]);
115
        }
116
117
        foreach ($finalRaw as $foundUsername) {
118
            $final[] = $foundUsername; // group all array's elements
119
        }
120
121
        $final = array_count_values($final); // find repetition and its count
122
123
        $final = array_diff($final, [1]);    // remove single occurrences
124
125
        $this->duplicates = array_keys($final);
126
    }
127
128
    /**
129
     * RFX constructor.
130
     *
131
     * @param string      $rawWikiText    The text of the page we're parsing
132
     * @param array       $sectionArray   Section names that we're looking for
133
     * @param string      $userNamespace  Plain text of the user namespace
134
     * @param string      $dateRegexp     Valid Regular Expression for the end date
135
     * @param string|null $userLookingFor User we're trying to find.
136
     */
137
    public function __construct(
138
        string $rawWikiText,
139
        array $sectionArray = ["Support", "Oppose", "Neutral"],
140
        string $userNamespace = "User",
0 ignored issues
show
Unused Code introduced by
The parameter $userNamespace is not used and could be removed. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-unused  annotation

140
        /** @scrutinizer ignore-unused */ string $userNamespace = "User",

This check looks for parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
141
        string $dateRegexp = "final .*end(?:ing|ed)?(?: no earlier than)? (.*?)? \(UTC\)",
142
        ?string $userLookingFor = null
143
    ) {
144
        $this->userLookingFor = $userLookingFor;
145
146
        $this->setUp($sectionArray, $rawWikiText, $dateRegexp);
147
    }
148
149
    /**
150
     * Which section we found the user we're looking for.
151
     *
152
     * @return string
153
     */
154
    public function getUserSectionFound(): string
155
    {
156
        return $this->userSectionFound;
157
    }
158
159
    /**
160
     * Returns data on the given section name.
161
     *
162
     * @param string $sectionName The section we're looking at
163
     *
164
     * @return array
165
     */
166
    public function getSection(string $sectionName): array
167
    {
168
        $sectionName = strtolower($sectionName);
169
        if (!isset($this->data[$sectionName])) {
170
            return [];
171
        } else {
172
            return $this->data[$sectionName];
173
        }
174
    }
175
176
    /**
177
     * Get an array of duplicate votes.
178
     *
179
     * @return array
180
     */
181
    public function getDuplicates(): array
182
    {
183
        return $this->duplicates;
184
    }
185
}
186