DeployForm   A
last analyzed

Complexity

Total Complexity 16

Size/Duplication

Total Lines 125
Duplicated Lines 16 %

Coupling/Cohesion

Components 0
Dependencies 11

Importance

Changes 0
Metric Value
wmc 16
lcom 0
cbo 11
dl 20
loc 125
rs 10
c 0
b 0
f 0

3 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 10 1
B getSelectedBuild() 0 10 5
C buildCommitSelector() 20 82 10

How to fix   Duplicated Code   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

1
<?php
2
3
/**
4
 * @deprecated  2.0.0 - moved to Dispatchers and frontend
5
 *
6
 * Validates a multi-source commit selector
7
 *
8
 * @package deploynaut
9
 * @subpackage control
10
 */
11
class DeployForm_CommitValidator extends DeployForm_ValidatorBase {
12
13
	public function php($data) {
14
		// Check release method
15
		if (empty($data['SelectRelease'])
16
			|| !in_array($data['SelectRelease'], ['Tag', 'Branch', 'Redeploy', 'SHA', 'FilteredCommits'])
17
		) {
18
			$method = empty($data['SelectRelease']) ? '(blank)' : $data['SelectRelease'];
19
			$this->validationError(
20
				'SelectRelease',
21
				"Bad release selection method: $method",
22
				"error"
23
			);
24
			return false;
25
		}
26
27
		// Check sha
28
		return $this->validateCommit(
29
			$this->form->getSelectedBuild($data),
30
			'SelectRelease'
31
		);
32
	}
33
34
}
35
36
/**
37
 * @deprecated  2.0.0 - moved to Dispatchers and frontend
38
 *
39
 * Form for generating deployments from a specified commit
40
 *
41
 * @package deploynaut
42
 * @subpackage control
43
 */
44
class DeployForm extends Form {
0 ignored issues
show
Coding Style Compatibility introduced by
PSR1 recommends that each class should be in its own file to aid autoloaders.

Having each class in a dedicated file usually plays nice with PSR autoloaders and is therefore a well established practice. If you use other autoloaders, you might not want to follow this rule.

Loading history...
45
46
	/**
47
	 * @param DNRoot $controller
48
	 * @param string $name
49
	 * @param DNEnvironment $environment
50
	 * @param DNProject $project
51
	 */
52
	public function __construct($controller, $name, DNEnvironment $environment, DNProject $project) {
53
		$field = $this->buildCommitSelector($project);
54
		$validator = new DeployForm_CommitValidator();
0 ignored issues
show
Deprecated Code introduced by
The class DeployForm_CommitValidator has been deprecated with message: 2.0.0 - moved to Dispatchers and frontend Validates a multi-source commit selector

This class, trait or interface has been deprecated. The supplier of the file has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the type will be removed from the class and what other constant to use instead.

Loading history...
55
		$actions = new FieldList(
56
			new FormAction('showDeploySummary', 'Plan deployment', 'Show deployment plan'),
0 ignored issues
show
Documentation introduced by
'Show deployment plan' is of type string, but the function expects a object<Form>|null.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
57
			new FormAction('doDeploy', 'Do deploy', 'Do deploy')
0 ignored issues
show
Documentation introduced by
'Do deploy' is of type string, but the function expects a object<Form>|null.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
58
		);
59
60
		parent::__construct($controller, $name, new FieldList($field), $actions, $validator);
61
	}
62
63
	/**
64
	 * Get the build selected from the given data
65
	 *
66
	 * @param array $data
67
	 * @return string SHA of selected build
68
	 */
69
	public function getSelectedBuild($data) {
70
		if (isset($data['SelectRelease']) && !empty($data[$data['SelectRelease']])) {
71
			// Filter out the tag/branch name if required
72
			$array = explode('-', $data[$data['SelectRelease']]);
73
			return reset($array);
74
		}
75
		if (isset($data['FilteredCommits']) && !empty($data['FilteredCommits'])) {
76
			return $data['FilteredCommits'];
77
		}
78
	}
79
80
	/**
81
	 * Construct fields to select any commit
82
	 *
83
	 * @param DNProject $project
84
	 * @return FormField
85
	 */
86
	protected function buildCommitSelector($project) {
87
		// Branches
88
		$branches = [];
89 View Code Duplication
		foreach ($project->DNBranchList() as $branch) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
90
			$sha = $branch->SHA();
91
			$name = $branch->Name();
92
			$branchValue = sprintf("%s (%s, %s old)",
93
				$name,
94
				substr($sha, 0, 8),
95
				$branch->LastUpdated()->TimeDiff()
96
			);
97
			$branches[$sha . '-' . $name] = $branchValue;
98
		}
99
100
		// Tags
101
		$tags = [];
102 View Code Duplication
		foreach ($project->DNTagList()->setLimit(null) as $tag) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
103
			$sha = $tag->SHA();
104
			$name = $tag->Name();
105
			$tagValue = sprintf("%s (%s, %s old)",
106
				$name,
107
				substr($sha, 0, 8),
108
				$branch->LastUpdated()->TimeDiff()
0 ignored issues
show
Bug introduced by
The variable $branch seems to be defined by a foreach iteration on line 89. Are you sure the iterator is never empty, otherwise this variable is not defined?

It seems like you are relying on a variable being defined by an iteration:

foreach ($a as $b) {
}

// $b is defined here only if $a has elements, for example if $a is array()
// then $b would not be defined here. To avoid that, we recommend to set a
// default value for $b.


// Better
$b = 0; // or whatever default makes sense in your context
foreach ($a as $b) {
}

// $b is now guaranteed to be defined here.
Loading history...
109
			);
110
			$tags[$sha . '-' . $name] = $tagValue;
111
		}
112
		$tags = array_reverse($tags);
113
114
		// Past deployments
115
		$redeploy = [];
116
		foreach ($project->DNEnvironmentList() as $dnEnvironment) {
117
			$envName = $dnEnvironment->Name;
118
			foreach ($dnEnvironment->DeployHistory()->filter('State', \DNDeployment::STATE_COMPLETED) as $deploy) {
119
				$sha = $deploy->SHA;
120
				if (!isset($redeploy[$envName])) {
121
					$redeploy[$envName] = [];
122
				}
123
				if (!isset($redeploy[$envName][$sha])) {
124
					$pastValue = sprintf("%s (deployed %s)",
125
						substr($sha, 0, 8),
126
						$deploy->obj('LastEdited')->Ago()
127
					);
128
					$redeploy[$envName][$sha] = $pastValue;
129
				}
130
			}
131
		}
132
133
		// Merge fields
134
		$releaseMethods = [];
135
		if (!empty($branches)) {
136
			$releaseMethods[] = new SelectionGroup_Item(
137
				'Branch',
138
				new DropdownField('Branch', 'Select a branch', $branches),
139
				'Deploy the latest version of a branch'
140
			);
141
		}
142
		if ($tags) {
143
			$releaseMethods[] = new SelectionGroup_Item(
144
				'Tag',
145
				new DropdownField('Tag', 'Select a tag', $tags),
146
				'Deploy a tagged release'
147
			);
148
		}
149
		if ($redeploy) {
150
			$releaseMethods[] = new SelectionGroup_Item(
151
				'Redeploy',
152
				new GroupedDropdownField('Redeploy', 'Redeploy', $redeploy),
153
				'Redeploy a release that was previously deployed (to any environment)'
154
			);
155
		}
156
157
		$releaseMethods[] = new SelectionGroup_Item(
158
			'SHA',
159
			new Textfield('SHA', 'Please specify the full SHA'),
160
			'Deploy a specific SHA'
161
		);
162
163
		$field = new TabbedSelectionGroup('SelectRelease', $releaseMethods);
164
		$field->setValue(reset($releaseMethods)->getValue());
165
		$field->addExtraClass('clearfix');
166
		return $field;
167
	}
168
}
169