Completed
Push — master ( ab60f2...c901a1 )
by Ricardo
07:00
created

ProjectController   F

Complexity

Total Complexity 95

Size/Duplication

Total Lines 652
Duplicated Lines 10.28 %

Coupling/Cohesion

Components 1
Dependencies 6

Importance

Changes 0
Metric Value
wmc 95
lcom 1
cbo 6
dl 67
loc 652
rs 1.948
c 0
b 0
f 0

15 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 5 1
A recent() 0 34 5
F myproject() 4 80 12
A getOptions() 0 16 2
A createIndex() 20 46 4
B createMultiIndex() 15 49 5
B updMultiStatus() 0 24 6
A search() 6 16 3
B index() 10 40 9
C store() 0 68 13
A initialize() 0 8 2
B show() 0 60 8
C update() 12 65 14
B destroy() 0 41 9
A checkKey() 0 5 2

How to fix   Duplicated Code    Complexity   

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:

Complex Class

 Tip:   Before tackling complexity, make sure that you eliminate any duplication first. This often can reduce the size of classes significantly.

Complex classes like ProjectController 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. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.

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 ProjectController, and based on these observations, apply Extract Interface, too.

1
<?php
2
3
namespace Fabrica\Http\Api;
4
5
use Illuminate\Http\Request;
6
use Illuminate\Support\Facades\Schema;
7
use Illuminate\Support\Facades\Event;
8
use Fabrica\Events\IssueEvent;
9
10
use Fabrica\Http\Requests;
11
use Fabrica\Http\Api\Controller;
12
use Fabrica\Project\Eloquent\Project;
13
use Fabrica\Project\Eloquent\UserGroupProject;
14
use Fabrica\Project\Eloquent\AccessProjectLog;
15
use Fabrica\Customization\Eloquent\Type;
16
use Fabrica\Acl\Acl;
17
use Fabrica\Project\Provider;
18
19
use Fabrica\Events\AddUserToRoleEvent;
20
use Fabrica\Events\DelUserFromRoleEvent;
21
use Fabrica\System\Eloquent\SysSetting;
22
use Sentinel;
23
use DB;
24
25
use MongoDB\BSON\ObjectID;
26
use MongoDB\Model\CollectionInfo;
27
28
class ProjectController extends Controller
29
{
30
    public function __construct()
31
    {
32
        $this->middleware('privilege:sys_admin', [ 'only' => [ 'index', 'getOptions', 'updMultiStatus', 'createMultiIndex', 'destroy' ] ]);
33
        parent::__construct();
34
    }
35
36
    /**
37
     * Display a listing of the resource.
38
     *
39
     * @return \Illuminate\Http\Response
40
     */
41
    public function recent(Request $request)
42
    {
43
        // get bound groups
44
        $group_ids = array_column(Acl::getBoundGroups($this->user->id), 'id');
45
        $user_projects = UserGroupProject::whereIn('ug_id', array_merge($group_ids, [ $this->user->id ]))
46
            ->where('link_count', '>', 0)
47
            ->get(['project_key'])
48
            ->toArray();
49
        $pkeys = array_column($user_projects, 'project_key');
50
51
        // get latest access projects
52
        $accessed_projects = AccessProjectLog::where('user_id', $this->user->id)
53
            ->orderBy('latest_access_time', 'desc')
54
            ->get(['project_key'])
55
            ->toArray();
56
        $accessed_pkeys = array_column($accessed_projects, 'project_key');
57
58
        $new_accessed_pkeys = array_unique(array_intersect($accessed_pkeys, $pkeys));
59
60
        $projects = [];
61
        foreach ($new_accessed_pkeys as $pkey)
62
        {
63
            $project = Project::where('key', $pkey)->first();
64
            if (!$project || $project->status === 'closed') 
65
            {
66
                continue;
67
            }
68
69
            $projects[] = [ 'key' => $project->key, 'name' => $project->name ];
70
            if (count($projects) >= 5) { break; }
71
        }
72
73
        return  Response()->json([ 'ecode' => 0, 'data' => $projects ]); 
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
74
    }
75
76
    /**
77
     * Display a listing of the resource.
78
     *
79
     * @return \Illuminate\Http\Response
80
     */
81
    public function myproject(Request $request)
82
    {
83
        // get bound groups
84
        $group_ids = array_column(Acl::getBoundGroups($this->user->id), 'id');
85
        // fix me
86
        $user_projects = UserGroupProject::whereIn('ug_id', array_merge($group_ids, [ $this->user->id ]))
87
            ->where('link_count', '>', 0)
88
            ->orderBy('created_at', 'asc')
89
            ->get(['project_key'])
90
            ->toArray();
91
92
        $pkeys = array_values(array_unique(array_column($user_projects, 'project_key')));
93
94
        $offset_key = $request->input('offset_key');
95
        if (isset($offset_key))
96
        {
97
            $ind = array_search($offset_key, $pkeys);
98
            if ($ind === false)
99
            {
100
                $pkeys = [];
101
            }
102
            else
103
            {
104
                $pkeys = array_slice($pkeys, $ind + 1); 
105
            }
106
        }
107
108
        $limit = $request->input('limit');
109
        if (!isset($limit))
110
        {
111
            $limit = 36;
112
        }
113
        $limit = intval($limit);
114
115
        $status = $request->input('status');
116
        if (!isset($status))
117
        {
118
            $status = 'all';
119
        }
120
121
        $name = $request->input('name');
122
123
        $projects = [];
124
        foreach ($pkeys as $pkey)
125
        {
126
            $query = Project::where('key', $pkey);
127
            if ($name)
128
            {
129
                $query->where(function ($query) use ($name) {
130
                    $query->where('key', 'like', '%' . $name . '%')->orWhere('name', 'like', '%' . $name . '%');
131
                });
132
            }
133
            if ($status != 'all')
134
            {
135
                $query = $query->where('status', $status);
136
            }
137
138
            $project = $query->first();
139
            if (!$project) 
140
            {
141
                continue;
142
            }
143
144
            $projects[] = $project->toArray();
145
            if (count($projects) >= $limit)
146
            {
147
                break;
148
            }
149
        }
150
        
151 View Code Duplication
        foreach ($projects as $key => $project)
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...
152
        {
153
            $projects[$key]['principal']['nameAndEmail'] = $project['principal']['name'] . '(' . $project['principal']['email'] . ')';
154
        }
155
156
        $syssetting = SysSetting::first();
157
        $allow_create_project = isset($syssetting->properties['allow_create_project']) ? $syssetting->properties['allow_create_project'] : 0;
158
159
        return Response()->json([ 'ecode' => 0, 'data' => $projects, 'options' => [ 'limit' => $limit, 'allow_create_project' => $allow_create_project ] ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
160
    }
161
162
    /**
163
     * get the options of project.
164
     *
165
     * @return \Illuminate\Http\Response
166
     */
167
    public function getOptions(Request $request)
168
    {
169
        $principals = Project::distinct('principal')->get([ 'principal' ])->toArray();
170
171
        $newPrincipals = [];
172
        foreach ($principals as $principal)
173
        {
174
            $tmp = [];
175
            $tmp['id'] = $principal['id'];
176
            $tmp['name'] = $principal['name'];
177
            $tmp['email'] = $principal['email'];
178
            $newPrincipals[] = $tmp;
179
        }
180
181
        return Response()->json([ 'ecode' => 0, 'data' => [ 'principals' => $newPrincipals ] ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
182
    }
183
184
    /**
185
     * create index of the project.
186
     *
187
     * @return \Illuminate\Http\Response
188
     */
189
    public function createIndex(Request $request, $id)
190
    {
191
        $project = Project::find($id);
192
        if (!$project)
193
        {
194
            throw new \UnexpectedValueException('the project does not exist.', -14006);
195
        }
196 View Code Duplication
        if ($project->principal['id'] !== $this->user->id && !$this->user->hasAccess('sys_admin'))
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...
197
        {
198
            return Response()->json(['ecode' => -10002, 'emsg' => 'permission denied.']);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
199
        }
200
201 View Code Duplication
        Schema::collection('issue_' . $project->key, function($col) {
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...
202
            $col->index('type');
203
            $col->index('state');
204
            $col->index('resolution');
205
            $col->index('priority');
206
            $col->index('created_at');
207
            $col->index('updated_at');
208
            $col->index('epic');
209
            $col->index('module');
210
            $col->index('resolve_version');
211
            $col->index('labels');
212
            $col->index('no');
213
            $col->index('parent_id');
214
            $col->index('assignee.id');
215
            $col->index('reporter.id');
216
        });
217
        Schema::collection('activity_' . $project->key, function($col) {
218
            $col->index('event_key');
219
        });
220
        Schema::collection('comments_' . $project->key, function($col) {
221
            $col->index('issue_id');
222
        });
223
        Schema::collection('issue_his_' . $project->key, function($col) {
224
            $col->index('issue_id');
225
        });
226
        Schema::collection('document_' . $project->key, function($col) {
227
            $col->index('parent');
228
        });
229
        Schema::collection('wiki_' . $project->key, function($col) {
230
            $col->index('parent');
231
        });
232
233
        return Response()->json([ 'ecode' => 0, 'data' => $project ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
234
    }
235
236
    /**
237
     * create index of all selected projects.
238
     *
239
     * @return \Illuminate\Http\Response
240
     */
241
    public function createMultiIndex(Request $request)
242
    {
243
        $ids = $request->input('ids');
244
        if (!isset($ids) || !$ids)
245
        {
246
            throw new \InvalidArgumentException('the selected projects cannot been empty.', -14007);
247
        }
248
249
        foreach ($ids as $id)
250
        {
251
            $project = Project::find($id);
252
            if (!$project)
253
            {
254
                continue;
255
            }
256
257 View Code Duplication
            Schema::collection('issue_' . $project->key, function($col) {
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...
258
                $col->index('type');
259
                $col->index('state');
260
                $col->index('resolution');
261
                $col->index('priority');
262
                $col->index('created_at');
263
                $col->index('updated_at');
264
                $col->index('module');
265
                $col->index('epic');
266
                $col->index('resolve_version');
267
                $col->index('labels');
268
                $col->index('no');
269
                $col->index('assignee.id');
270
                $col->index('reporter.id');
271
            });
272
            Schema::collection('activity_' . $project->key, function($col) {
273
                $col->index('event_key');
274
            });
275
            Schema::collection('comments_' . $project->key, function($col) {
276
                $col->index('issue_id');
277
            });
278
            Schema::collection('issue_his_' . $project->key, function($col) {
279
                $col->index('issue_id');
280
            });
281
            Schema::collection('document_' . $project->key, function($col) {
282
                $col->index('parent');
283
            });
284
            Schema::collection('wiki_' . $project->key, function($col) {
285
                $col->index('parent');
286
            });
287
        }
288
        return Response()->json([ 'ecode' => 0, 'data' => [ 'ids' => $ids ] ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
289
    }
290
291
    /**
292
     * update status of all selected projects.
293
     *
294
     * @return \Illuminate\Http\Response
295
     */
296
    public function updMultiStatus(Request $request)
297
    {
298
        $ids = $request->input('ids');
299
        if (!isset($ids) || !$ids)
300
        {
301
            throw new \InvalidArgumentException('the selected projects cannot been empty.', -14007);
302
        }
303
304
        $status = $request->input('status');
305
        if (!isset($status) || !$status)
306
        {
307
            throw new \InvalidArgumentException('the status cannot be empty.', -14008);
308
        }
309
310
        $newIds = [];
311
        foreach ($ids as $id)
312
        {
313
            $newIds[] = new ObjectID($id);
314
        }
315
316
        Project::whereRaw([ '_id' => [ '$in' => $newIds ] ])->update([ 'status' => $status ]);
317
318
        return Response()->json([ 'ecode' => 0, 'data' => [ 'ids' => $ids ] ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
319
    }
320
321
    /**
322
     * search project by the name or code.
323
     *
324
     * @return \Illuminate\Http\Response
325
     */
326
    public function search(Request $request)
327
    {
328
        $query = DB::collection('project');
329
330
        $s = $request->input('s');
331 View Code Duplication
        if (isset($s) && $s)
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...
332
        {
333
            $query->where(function ($query) use ($s) {
334
                $query->where('key', 'like', '%' . $s . '%')->orWhere('name', 'like', '%' . $s . '%');
335
            });
336
        }
337
338
        $projects = $query->take(10)->get([ 'name', 'key' ]);
339
340
        return Response()->json([ 'ecode' => 0, 'data' => parent::arrange($projects) ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
Comprehensibility Bug introduced by
It seems like you call parent on a different method (arrange() instead of search()). Are you sure this is correct? If so, you might want to change this to $this->arrange().

This check looks for a call to a parent method whose name is different than the method from which it is called.

Consider the following code:

class Daddy
{
    protected function getFirstName()
    {
        return "Eidur";
    }

    protected function getSurName()
    {
        return "Gudjohnsen";
    }
}

class Son
{
    public function getFirstName()
    {
        return parent::getSurname();
    }
}

The getFirstName() method in the Son calls the wrong method in the parent class.

Loading history...
341
    }
342
343
    /**
344
     * Display a listing of the resource.
345
     *
346
     * @return \Illuminate\Http\Response
347
     */
348
    public function index(Request $request)
349
    {
350
        $query = DB::collection('project');
351
352
        $principal_id = $request->input('principal_id');
353
        if (isset($principal_id) && $principal_id)
354
        {
355
            $query = $query->where('principal.id', $principal_id);
356
        }
357
358
        $status = $request->input('status');
359
        if (isset($status) && $status !== 'all')
360
        {
361
            $query = $query->where('status', $status);
362
        }
363
364
        $name = $request->input('name');
365 View Code Duplication
        if (isset($name) && $name)
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...
366
        {
367
            $query->where(function ($query) use ($name) {
368
                $query->where('key', 'like', '%' . $name . '%')->orWhere('name', 'like', '%' . $name . '%');
369
            });
370
        }
371
372
        // get total
373
        $total = $query->count();
374
375
        $query->orderBy('created_at', 'desc');
376
377
        $page_size = 30;
378
        $page = $request->input('page') ?: 1;
379
        $query = $query->skip($page_size * ($page - 1))->take($page_size);
380
        $projects = $query->get([ 'name', 'key', 'description', 'status', 'principal' ]);
381 View Code Duplication
        foreach ($projects as $key => $project)
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...
382
        {
383
            $projects[$key]['principal']['nameAndEmail'] = $project['principal']['name'] . '(' . $project['principal']['email'] . ')';
384
        }
385
386
        return Response()->json([ 'ecode' => 0, 'data' => parent::arrange($projects), 'options' => [ 'total' => $total, 'sizePerPage' => $page_size ] ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
Comprehensibility Bug introduced by
It seems like you call parent on a different method (arrange() instead of index()). Are you sure this is correct? If so, you might want to change this to $this->arrange().

This check looks for a call to a parent method whose name is different than the method from which it is called.

Consider the following code:

class Daddy
{
    protected function getFirstName()
    {
        return "Eidur";
    }

    protected function getSurName()
    {
        return "Gudjohnsen";
    }
}

class Son
{
    public function getFirstName()
    {
        return parent::getSurname();
    }
}

The getFirstName() method in the Son calls the wrong method in the parent class.

Loading history...
387
    }
388
389
    /**
390
     * Store a newly created resource in storage.
391
     *
392
     * @param  \Illuminate\Http\Request  $request
393
     * @return \Illuminate\Http\Response
394
     */
395
    public function store(Request $request)
396
    {
397
        $syssetting = SysSetting::first();
398
        $allow_create_project = isset($syssetting->properties['allow_create_project']) ? $syssetting->properties['allow_create_project'] : 0;        
399
        if ($allow_create_project !== 1 && !$this->user->hasAccess('sys_admin'))
400
        {
401
            return Response()->json(['ecode' => -10002, 'emsg' => 'permission denied.']);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
402
        }
403
404
        $insValues = [];
405
406
        $name = $request->input('name');
407
        if (!$name)
408
        {
409
            throw new \UnexpectedValueException('the name can not be empty.', -14000);
410
        }
411
        $insValues['name'] = $name;
412
413
        $key = $request->input('key');
414
        if (!$key)
415
        {
416
            throw new \InvalidArgumentException('project key cannot be empty.', -14001);
417
        }
418
        if (Project::Where('key', $key)->exists())
419
        {
420
            throw new \InvalidArgumentException('project key has been taken.', -14002);
421
        }
422
        $insValues['key'] = $key;
423
424
        $principal = $request->input('principal');
425
        if (!isset($principal) || !$principal)
426
        {
427
            $insValues['principal'] = [ 'id' => $this->user->id, 'name' => $this->user->first_name, 'email' => $this->user->email ];
428
        }
429
        else
430
        {
431
            $principal_info = Sentinel::findById($principal);
432
            if (!$principal_info)
433
            {
434
                throw new \InvalidArgumentException('the user is not exists.', -14003);
435
            }
436
            $insValues['principal'] = [ 'id' => $principal_info->id, 'name' => $principal_info->first_name, 'email' => $principal_info->email ];
437
        }
438
439
        $description = $request->input('description');
440
        if (isset($description) && $description)
441
        {
442
            $insValues['description'] = $description;
443
        }
444
445
        $insValues['category'] = 1;
446
        $insValues['status'] = 'active';
447
        $insValues['creator'] = [ 'id' => $this->user->id, 'name' => $this->user->first_name, 'email' => $this->user->email ];
448
449
        // save the project
450
        $project = Project::create($insValues); //fix me
451
        // add issue-type template to project
452
        $this->initialize($project->key);
453
        // trigger add user to usrproject
454
        Event::fire(new AddUserToRoleEvent([ $insValues['principal']['id'] ], $key));
455
456
        if (isset($project->principal))
457
        {
458
            $project->principal = array_merge($insValues['principal'], [ 'nameAndEmail' => $insValues['principal']['name'] . '(' . $insValues['principal']['email'] . ')' ]);
459
        }
460
461
        return Response()->json([ 'ecode' => 0, 'data' => $project ]);
462
    }
463
464
    /**
465
     * initialize project data.
466
     *
467
     * @param  string  $key
468
     * @param  int     $id
0 ignored issues
show
Bug introduced by
There is no parameter named $id. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
469
     * @return 
470
     */
471
    public function initialize($key)
472
    {
473
        $types = Type::where('project_key', '$_sys_$')->get()->toArray();
474
        foreach ($types as $type)
475
        {
476
            Type::create(array_only($type, [ 'name', 'abb', 'screen_id', 'workflow_id', 'sn', 'type', 'disabled', 'default' ]) + [ 'project_key' => $key ]);
477
        }
478
    }
479
480
    /**
481
     * Display the specified resource.
482
     *
483
     * @param  int  $id
0 ignored issues
show
Bug introduced by
There is no parameter named $id. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
484
     * @return \Illuminate\Http\Response
485
     */
486
    public function show($key)
487
    {
488
        $project = Project::where('key', $key)->first();
489
        if (!$project)
490
        {
491
            return Response()->json(['ecode' => -14004, 'emsg' => 'the project does not exist.']);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
492
        }
493
494
        if ($project->status !== 'active')
495
        {
496
            return Response()->json(['ecode' => -14009, 'emsg' => 'the project has been closed.']);
497
        }
498
499
        // get action allow of the project.
500
        $permissions = Acl::getPermissions($this->user->id, $project->key);
501
        if ($this->user->id === $project->principal['id'] || $this->user->email === '[email protected]')
502
        {
503
            !in_array('view_project', $permissions) && $permissions[] = 'view_project';
504
            !in_array('manage_project', $permissions) && $permissions[] = 'manage_project';
505
        }
506
507
        //if (!$permissions)
508
        //{
509
        //    $isMember = UserProject::where('user_id', $this->user->id)
510
        //        ->where('project_key', $key)
511
        //        ->where('link_count', '>', 0)
512
        //        ->exists();
513
        //    if ($isMember)
514
        //    {
515
        //        $permissions[] = 'view_project';
516
        //    }
517
        //}
518
        // get searchers
519
        //$searchers = DB::collection('searcher_' . $key)->where('user', $this->user->id)->orderBy('created_at', 'asc')->get();
520
        // get project users
521
        //$users = Provider::getUserList($project->key);
522
        // get state list
523
        //$states = Provider::getStateList($project->key, ['name']);
524
        // get resolution list
525
        //$resolutions = Provider::getResolutionList($project->key, ['name']);
526
        // get priority list
527
        //$priorities = Provider::getPriorityList($project->key, ['color', 'name']);
528
        // get version list
529
        //$versions = Provider::getVersionList($project->key, ['name']);
530
        // get module list
531
        //$modules = Provider::getModuleList($project->key, ['name']);
532
        // get project types
533
        //$types = Provider::getTypeListExt($project->key, [ 'assignee' => $users, 'state' => $states, 'resolution' => $resolutions, 'priority' => $priorities, 'version' => $versions, 'module' => $modules ]);
534
535
        // record the project access date
536
        if (in_array('view_project', $permissions))
537
        {
538
            AccessProjectLog::where('project_key', $key)
539
                ->where('user_id', $this->user->id)
540
                ->delete();
541
            AccessProjectLog::create([ 'project_key' => $key, 'user_id' => $this->user->id, 'latest_access_time' => time() ]);
542
        }
543
544
        return Response()->json([ 'ecode' => 0, 'data' => $project, 'options' => parent::arrange([ 'permissions' => $permissions ]) ]);
0 ignored issues
show
Comprehensibility Bug introduced by
It seems like you call parent on a different method (arrange() instead of show()). Are you sure this is correct? If so, you might want to change this to $this->arrange().

This check looks for a call to a parent method whose name is different than the method from which it is called.

Consider the following code:

class Daddy
{
    protected function getFirstName()
    {
        return "Eidur";
    }

    protected function getSurName()
    {
        return "Gudjohnsen";
    }
}

class Son
{
    public function getFirstName()
    {
        return parent::getSurname();
    }
}

The getFirstName() method in the Son calls the wrong method in the parent class.

Loading history...
545
    }
546
547
    /**
548
     * Update the specified resource in storage.
549
     *
550
     * @param  \Illuminate\Http\Request  $request
551
     * @param  int  $id
552
     * @return \Illuminate\Http\Response
553
     */
554
    public function update(Request $request, $id)
555
    {
556
        $updValues = [];
557
        $name = $request->input('name');
558 View Code Duplication
        if (isset($name))
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...
559
        {
560
            if (!$name)
561
            {
562
                throw new \UnexpectedValueException('the name can not be empty.', -14000);
563
            }
564
            $updValues['name'] = $name;
565
        }
566
        // check is user is available
567
        $principal = $request->input('principal');
568
        if (isset($principal))
569
        {
570
            if (!$principal)
571
            {
572
                throw new \InvalidArgumentException('the principal must be appointed.', -14005);
573
            }
574
575
            $principal_info = Sentinel::findById($principal);
576
            if (!$principal_info)
577
            {
578
                throw new \InvalidArgumentException('the user is not exists.', -14003);
579
            }
580
            $updValues['principal'] = [ 'id' => $principal_info->id, 'name' => $principal_info->first_name, 'email' =>  $principal_info->email ]; 
581
        }
582
583
        $description = $request->input('description');
584
        if (isset($description))
585
        {
586
            $updValues['description'] = $description;
587
        }
588
589
        $status = $request->input('status');
590
        if (isset($status) && in_array($status, [ 'active', 'closed' ]))
591
        {
592
            $updValues['status'] = $status;
593
        }
594
595
        $project = Project::find($id);
596
        if (!$project)
597
        {
598
            throw new \UnexpectedValueException('the project does not exist.', -14004);
599
        }
600 View Code Duplication
        if ($project->principal['id'] !== $this->user->id && !$this->user->hasAccess('sys_admin'))
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...
601
        {
602
            return Response()->json(['ecode' => -10002, 'emsg' => 'permission denied.']);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
603
        }
604
605
        $old_principal = $project->principal;
606
        $project->fill($updValues)->save();
607
608
        if (isset($principal))
609
        {
610
            if ($old_principal['id'] != $principal)
611
            {
612
                Event::fire(new AddUserToRoleEvent([ $principal ], $project->key));
613
                Event::fire(new DelUserFromRoleEvent([ $old_principal['id'] ], $project->key));
614
            }
615
        }
616
617
        return Response()->json([ 'ecode' => 0, 'data' => Project::find($id) ]);
618
    }
619
620
    /**
621
     * Remove the specified resource from storage.
622
     *
623
     * @param  int  $id
624
     * @return \Illuminate\Http\Response
625
     */
626
    public function destroy($id)
627
    {
628
    	$project = Project::find($id);
629
        if (!$project)
630
        {
631
            throw new \UnexpectedValueException('the project does not exist.', -14004);
632
        }
633
634
        $project_key = $project->key;
635
        //$related_cols = [ 'version', 'module', 'board', 'epic', 'sprint', 'sprint_log', 'searcher', 'access_project_log', 'access_board_log', 'user_group_project', 'watch', 'acl_role', 'acl_roleactor', 'acl_role_permissions', 'oswf_definition' ];
636
        $unrelated_cols = [ 'system.indexes', 'users', 'persistences', 'throttle', 'project' ];
637
        // delete releted table
638
        $collections = DB::listCollections();
639
        foreach ($collections as $col)
640
        {
641
            $col_name = $col->getName();
642
            if (strpos($col_name, 'issue_') === 0 ||
643
                strpos($col_name, 'activity_') === 0 ||
644
                strpos($col_name, 'comments_') === 0 ||
645
                strpos($col_name, 'document_') === 0 ||
646
                strpos($col_name, 'wiki_') === 0 ||
647
                in_array($col_name, $unrelated_cols))
648
            {
649
                continue;
650
            }
651
    
652
            DB::collection($col_name)->where('project_key', $project_key)->delete();
653
        }
654
655
        // delete the collections
656
        Schema::drop('issue_' . $project_key);
657
        Schema::drop('issue_his_' . $project_key);
658
        Schema::drop('activity_' . $project_key);
659
        Schema::drop('comments_' . $project_key);
660
        Schema::drop('document_' . $project_key);
661
        Schema::drop('wiki_' . $project_key);
662
        // delete from the project table
663
        Project::destroy($id);
664
665
        return Response()->json([ 'ecode' => 0, 'data' => [ 'id' => $id ] ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
666
    }
667
668
    /**
669
     * check if project key has been taken 
670
     *
671
     * @param  string  $key
672
     * @return \Illuminate\Http\Response
673
     */
674
    public function checkKey($key)
675
    {
676
        $isExisted = Project::Where('key', $key)->exists(); 
677
        return Response()->json([ 'ecode' => 0, 'data' => [ 'flag' => $isExisted ? '2' : '1' ] ]);
0 ignored issues
show
Bug introduced by
The method json does only exist in Illuminate\Contracts\Routing\ResponseFactory, but not in Illuminate\Http\Response.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
678
    }
679
}
680