Scrutinizer GitHub App not installed

We could not synchronize checks via GitHub's checks API since Scrutinizer's GitHub App is not installed for this repository.

Install GitHub App

Failed Conditions
Push — main ( 5797ad...3faf69 )
by Dan
29s queued 24s
created

SectorsFile   A

Complexity

Total Complexity 41

Size/Duplication

Total Lines 183
Duplicated Lines 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 121
dl 0
loc 183
rs 9.1199
c 1
b 0
f 0
wmc 41

1 Method

Rating   Name   Duplication   Size   Complexity  
F create() 0 181 41

How to fix   Complexity   

Complex Class

Complex classes like SectorsFile often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes.

Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.

While breaking up the class, it is a good idea to analyze how other classes use SectorsFile, and based on these observations, apply Extract Interface, too.

1
<?php declare(strict_types=1);
2
3
namespace Smr;
4
5
use AbstractSmrPlayer;
6
use Globals;
7
use SmrForce;
8
use SmrGame;
9
use SmrLocation;
10
use SmrPlanet;
11
use SmrPort;
12
use SmrSector;
13
use SmrShipType;
14
use SmrWeaponType;
15
16
class SectorsFile {
17
18
	public static function create(int $gameID, ?AbstractSmrPlayer $player, bool $adminCreate = false): never {
19
		// NOTE: If the format of this file is changed in an incompatible way,
20
		// make sure to update the SMR_FILE_VERSION!
21
22
		$file = ';SMR1.6 Sectors File v' . SMR_FILE_VERSION . '
23
		; Created on ' . date(DEFAULT_DATE_TIME_FORMAT) . '
24
		[Races]
25
		; Name = ID' . EOL;
26
		foreach (Race::getAllNames() as $raceID => $raceName) {
27
			$file .= inify($raceName) . '=' . $raceID . EOL;
28
		}
29
30
		$file .= '[Goods]
31
		; ID = Name, BasePrice' . EOL;
32
		foreach (Globals::getGoods() as $good) {
33
			$file .= $good['ID'] . '=' . inify($good['Name']) . ',' . $good['BasePrice'] . EOL;
34
		}
35
36
		$file .= '[Weapons]
37
		; Weapon = Race,Cost,Shield,Armour,Accuracy,Power level,Restriction
38
		; Restriction: 0=none, 1=good, 2=evil, 3=newbie, 4=port, 5=planet' . EOL;
39
		foreach (SmrWeaponType::getAllWeaponTypes() as $weapon) {
40
			$file .= inify($weapon->getName()) . '=' . inify($weapon->getRaceName()) . ',' . $weapon->getCost() . ',' . $weapon->getShieldDamage() . ',' . $weapon->getArmourDamage() . ',' . $weapon->getAccuracy() . ',' . $weapon->getPowerLevel() . ',' . $weapon->getBuyerRestriction()->value . EOL;
41
		}
42
43
		$file .= '[ShipEquipment]
44
		; Name = Cost' . EOL;
45
		$hardwares = Globals::getHardwareTypes();
46
		foreach ($hardwares as $hardware) {
47
			$file .= inify($hardware['Name']) . '=' . $hardware['Cost'] . EOL;
48
		}
49
50
		$file .= '[Ships]
51
		; Name = Race,Cost,TPH,Hardpoints,Power,Class,+Equipment (Optional),+Restrictions(Optional)
52
		; Restrictions:Align(Integer)' . EOL;
53
		foreach (SmrShipType::getAll() as $ship) {
54
			$file .= inify($ship->getName()) . '=' . inify($ship->getRaceName()) . ',' . $ship->getCost() . ',' . $ship->getSpeed() . ',' . $ship->getHardpoints() . ',' . $ship->getMaxPower() . ',' . $ship->getClass()->name;
55
			$shipEquip = [];
56
			foreach ($ship->getAllMaxHardware() as $hardwareID => $maxHardware) {
57
				$shipEquip[] = $hardwares[$hardwareID]['Name'] . '=' . $maxHardware;
58
			}
59
			if (!empty($shipEquip)) {
60
				$file .= ',ShipEquipment=' . implode(';', $shipEquip);
61
			}
62
			$file .= ',Restrictions=' . $ship->getRestriction()->value;
63
			$file .= EOL;
64
		}
65
66
		$file .= '[Locations]
67
		; Name = +Sells' . EOL;
68
		foreach (SmrLocation::getAllLocations($gameID) as $location) {
69
			$file .= inify($location->getName()) . '=';
70
			$locSells = '';
71
			if ($location->isWeaponSold()) {
72
				$locSells .= 'Weapons=';
73
				foreach ($location->getWeaponsSold() as $locWeapon) {
74
					$locSells .= $locWeapon->getName() . ';';
75
				}
76
				$locSells = substr($locSells, 0, -1) . ',';
77
			}
78
			if ($location->isHardwareSold()) {
79
				$locSells .= 'ShipEquipment=';
80
				foreach ($location->getHardwareSold() as $locHardware) {
81
					$locSells .= $locHardware['Name'] . ';';
82
				}
83
				$locSells = substr($locSells, 0, -1) . ',';
84
			}
85
			if ($location->isShipSold()) {
86
				$locSells .= 'Ships=';
87
				foreach ($location->getShipsSold() as $locShip) {
88
					$locSells .= $locShip->getName() . ';';
89
				}
90
				$locSells = substr($locSells, 0, -1) . ',';
91
			}
92
			if ($location->isBank()) {
93
				$locSells .= 'Bank=,';
94
			}
95
			if ($location->isBar()) {
96
				$locSells .= 'Bar=,';
97
			}
98
			if ($location->isHQ()) {
99
				$locSells .= 'HQ=,';
100
			}
101
			if ($location->isUG()) {
102
				$locSells .= 'UG=,';
103
			}
104
			if ($location->isFed()) {
105
				$locSells .= 'Fed=,';
106
			}
107
			if ($locSells != '') {
108
				$file .= substr($locSells, 0, -1);
109
			}
110
			$file .= EOL;
111
		}
112
113
		// Everything below here must be valid INI syntax (safe to parse)
114
		$game = SmrGame::getGame($gameID);
115
		$file .= '[Metadata]
116
		FileVersion=' . SMR_FILE_VERSION . '
117
		[Game]
118
		Name=' . inify($game->getName()) . '
119
		[Galaxies]
120
		';
121
		$galaxies = $game->getGalaxies();
122
		foreach ($galaxies as $galaxy) {
123
			$file .= $galaxy->getGalaxyID() . '=' . $galaxy->getWidth() . ',' . $galaxy->getHeight() . ',' . $galaxy->getGalaxyType() . ',' . inify($galaxy->getName()) . ',' . $galaxy->getMaxForceTime() . EOL;
124
		}
125
126
		foreach ($galaxies as $galaxy) {
127
			// Efficiently construct the caches before proceeding
128
			$galaxy->getLocations();
129
			$galaxy->getPlanets();
130
			$galaxy->getForces();
131
132
			foreach ($galaxy->getSectors() as $sector) {
133
				$file .= '[Sector=' . $sector->getSectorID() . ']' . EOL;
134
135
				if (!$sector->isVisited($player) && $adminCreate === false) {
136
					continue;
137
				}
138
139
				foreach ($sector->getLinks() as $linkName => $link) {
140
					$file .= $linkName . '=' . $link . EOL;
141
				}
142
				if ($sector->hasWarp()) {
143
					$file .= 'Warp=' . $sector->getWarp() . EOL;
144
				}
145
				if (($adminCreate !== false && $sector->hasPort()) || is_object($player) && $sector->hasCachedPort($player)) {
146
					if ($adminCreate !== false) {
147
						$port = $sector->getPort();
148
					} else {
149
						$port = $sector->getCachedPort($player);
150
					}
151
					$file .= 'Port Level=' . $port->getLevel() . EOL;
152
					$file .= 'Port Race=' . $port->getRaceID() . EOL;
153
					if (!empty($port->getSellGoodIDs())) {
154
						$file .= 'Buys=' . implode(',', $port->getSellGoodIDs()) . EOL;
155
					}
156
					if (!empty($port->getBuyGoodIDs())) {
157
						$file .= 'Sells=' . implode(',', $port->getBuyGoodIDs()) . EOL;
158
					}
159
				}
160
				if ($sector->hasPlanet()) {
161
					$planetType = $sector->getPlanet()->getTypeID();
162
					$file .= 'Planet=' . $planetType . EOL;
163
				}
164
				if ($sector->hasLocation()) {
165
					$locationsString = 'Locations=';
166
					foreach ($sector->getLocations() as $location) {
167
						$locationsString .= inify($location->getName()) . ',';
168
					}
169
					$file .= substr($locationsString, 0, -1) . EOL;
170
				}
171
				if ($adminCreate === false && $sector->hasFriendlyForces($player)) {
172
					$forcesString = 'FriendlyForces=';
173
					foreach ($sector->getFriendlyForces($player) as $forces) {
174
						$forcesString .= inify($forces->getOwner()->getPlayerName()) . '=' . inify(Globals::getHardwareName(HARDWARE_MINE)) . '=' . $forces->getMines() . ';' . inify(Globals::getHardwareName(HARDWARE_COMBAT)) . '=' . $forces->getCDs() . ';' . inify(Globals::getHardwareName(HARDWARE_SCOUT)) . '=' . $forces->getSDs() . ',';
175
					}
176
					$file .= substr($forcesString, 0, -1) . EOL;
177
				}
178
			}
179
			SmrPort::clearCache();
180
			SmrForce::clearCache();
181
			SmrPlanet::clearCache();
182
			SmrSector::clearCache();
183
		}
184
185
		$size = strlen($file);
186
187
		header('Pragma: public');
188
		header('Expires: 0');
189
		header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
190
		header('Cache-Control: private', false);
191
		header('Content-Type: application/force-download');
192
		header('Content-Disposition: attachment; filename="' . $game->getName() . '.smr"');
193
		header('Content-Transfer-Encoding: binary');
194
		header('Content-Length: ' . $size);
195
196
		echo $file;
197
198
		exit;
0 ignored issues
show
Best Practice introduced by
Using exit here is not recommended.

In general, usage of exit should be done with care and only when running in a scripting context like a CLI script.

Loading history...
199
	}
200
201
}
202