Completed
Push — master ( 761efc...53b1ea )
by Reginaldo
28:04
created

ProdutoController::validar_estoque()   A

Complexity

Conditions 4
Paths 3

Size

Total Lines 11
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 4
eloc 6
c 0
b 0
f 0
nc 3
nop 1
dl 0
loc 11
rs 9.2
1
<?php
2
3
ini_set('max_execution_time', 300);
4
5
require_once(ROOT . DS . 'vendor' . DS . 'autoload.php');
6
7
use Dompdf\Dompdf;
8
9
10
class ProdutoController extends AppController{		
11
12
	public function listar_cadastros() {
13
		$this->layout = 'wadmin';
14
	}
15
16
	public function listar_cadastros_ajax() {
0 ignored issues
show
Coding Style introduced by
listar_cadastros_ajax uses the super-global variable $_GET which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
17
		$this->layout = 'ajax';
18
19
		$aColumns = array( 'sku', 'imagem', 'nome', 'preco', 'estoque' );
20
		
21
		$conditions = array('conditions' =>
22
			array(
23
				'ativo' => 1,
24
				'id_usuario' => $this->instancia
25
			)
26
		);
27
28
		$allProdutos = $this->Produto->find('all', $conditions);
29
		
30 View Code Duplication
		if ( isset( $_GET['iDisplayStart'] ) && $_GET['iDisplayLength'] != '-1' )
31
		{
32
			$conditions['offset'] = $_GET['iDisplayStart'];
33
			$conditions['limit'] = $_GET['iDisplayLength'];
34
		}
35
36 View Code Duplication
		if ( isset( $_GET['iSortCol_0'] ) )
37
		{
38
			for ( $i=0 ; $i < intval( $_GET['iSortingCols'] ) ; $i++ )
39
			{
40
				if ( $_GET[ 'bSortable_' . intval($_GET['iSortCol_' . $i]) ] == "true" )
41
				{
42
					$conditions['order'] = array('Produto.' . $aColumns[intval($_GET['iSortCol_' . $i])] => $_GET['sSortDir_'.$i]);
43
				}
44
			}
45
		}
46
47 View Code Duplication
		if ( isset( $_GET['sSearch'] ) && !empty( $_GET['sSearch'] ) )
48
		{
49
			$conditions['conditions']['Produto.nome LIKE '] = '%' . $_GET['sSearch'] . '%';
50
		}
51
		
52
		$produtos = $this->Produto->find('all', $conditions);
53
54
		$output = array(
55
			"sEcho" => intval($_GET['sEcho']),
56
			"iTotalDisplayRecords" => count($allProdutos),
57
			"iTotalRecords" => count($produtos),
58
			"aaData" => array()
59
		);
60
61 View Code Duplication
		foreach ( $produtos as $i => $produto )
62
		{
63
			$row = array();
64
65
			for ( $i=0 ; $i < count($aColumns) ; $i++ )
0 ignored issues
show
Performance Best Practice introduced by
It seems like you are calling the size function count() as part of the test condition. You might want to compute the size beforehand, and not on each iteration.

If the size of the collection does not change during the iteration, it is generally a good practice to compute it beforehand, and not on each iteration:

for ($i=0; $i<count($array); $i++) { // calls count() on each iteration
}

// Better
for ($i=0, $c=count($array); $i<$c; $i++) { // calls count() just once
}
Loading history...
66
			{
67
				$value = $produto['Produto'][$aColumns[$i]];
68
69
				if ($aColumns[$i] == "imagem")
70
				{
71
					$value = '<img src="/uploads/produto/imagens/' . $produto['Produto'][$aColumns[$i]] . '" width="120" height="120">';
72
73
					if (!isset($produto['Produto'][$aColumns[$i]]) || empty($produto['Produto'][$aColumns[$i]]))
74
					{
75
						$value = '<img src="/images/no_image.png" width="120" height="120">';
76
					}
77
				}
78
				
79
				$row[] = $value;
80
			}
81
82
			$output['aaData'][] = $row;
83
		}
84
		
85
		echo json_encode($output);
86
		exit;
0 ignored issues
show
Coding Style Compatibility introduced by
The method listar_cadastros_ajax() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
87
	}
88
89
	public function listar_cadastros_estoque_minimo(){
90
		$this->layout = 'wadmin';
91
	}
92
93
	public function listar_cadastros_estoque_minimo_ajax(){
0 ignored issues
show
Coding Style introduced by
listar_cadastros_estoque_minimo_ajax uses the super-global variable $_GET which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
94
95
		$this->layout = 'ajax';
96
97
		$aColumns = array( 'sku', 'imagem', 'nome', 'preco', 'estoque' );
98
99
		$this->loadModel('Usuario');
100
101
		$usuario = $this->Usuario->find('all', array('conditions' =>
102
				array(
103
					'Usuario.id' => $this->instancia
104
				)
105
			)
106
		)[0]['Usuario'];
107
		
108
		$conditions = array('conditions' =>
109
			array(
110
				'ativo' => 1,
111
				'id_usuario' => $this->instancia,
112
				'Produto.quantidade_minima <= ' => 'Produto.estoque',
113
				'Produto.estoque <= ' => $usuario['estoque_minimo']
114
			)
115
		);
116
117
		$allProdutos = $this->Produto->find('all', $conditions);
118
		
119 View Code Duplication
		if ( isset( $_GET['iDisplayStart'] ) && $_GET['iDisplayLength'] != '-1' )
120
		{
121
			$conditions['offset'] = $_GET['iDisplayStart'];
122
			$conditions['limit'] = $_GET['iDisplayLength'];
123
		}
124
125 View Code Duplication
		if ( isset( $_GET['iSortCol_0'] ) )
126
		{
127
			for ( $i=0 ; $i < intval( $_GET['iSortingCols'] ) ; $i++ )
128
			{
129
				if ( $_GET[ 'bSortable_' . intval($_GET['iSortCol_' . $i]) ] == "true" )
130
				{
131
					$conditions['order'] = array('Produto.' . $aColumns[intval($_GET['iSortCol_' . $i])] => $_GET['sSortDir_'.$i]);
132
				}
133
			}
134
		}
135
136 View Code Duplication
		if ( isset( $_GET['sSearch'] ) && !empty( $_GET['sSearch'] ) )
137
		{
138
			$conditions['conditions']['Produto.nome LIKE '] = '%' . $_GET['sSearch'] . '%';
139
		}
140
		
141
		$produtos = $this->Produto->find('all', $conditions);
142
143
		$output = array(
144
			"sEcho" => intval($_GET['sEcho']),
145
			"iTotalDisplayRecords" => count($allProdutos),
146
			"iTotalRecords" => count($produtos),
147
			"aaData" => array()
148
		);
149
150 View Code Duplication
		foreach ( $produtos as $i => $produto )
151
		{
152
			$row = array();
153
154
			for ( $i=0 ; $i < count($aColumns) ; $i++ )
0 ignored issues
show
Performance Best Practice introduced by
It seems like you are calling the size function count() as part of the test condition. You might want to compute the size beforehand, and not on each iteration.

If the size of the collection does not change during the iteration, it is generally a good practice to compute it beforehand, and not on each iteration:

for ($i=0; $i<count($array); $i++) { // calls count() on each iteration
}

// Better
for ($i=0, $c=count($array); $i<$c; $i++) { // calls count() just once
}
Loading history...
155
			{
156
				$value = $produto['Produto'][$aColumns[$i]];
157
158
				if ($aColumns[$i] == "imagem")
159
				{
160
					$value = '<img src="/uploads/produto/imagens/' . $produto['Produto'][$aColumns[$i]] . '" width="120" height="120">';
161
162
					if (!isset($produto['Produto'][$aColumns[$i]]) || empty($produto['Produto'][$aColumns[$i]]))
163
					{
164
						$value = '<img src="/images/no_image.png" width="120" height="120">';
165
					}
166
				}
167
				
168
				$row[] = $value;
169
			}
170
171
			$output['aaData'][] = $row;
172
		}
173
		
174
		echo json_encode($output);
175
		exit;
0 ignored issues
show
Coding Style Compatibility introduced by
The method listar_cadastros_estoque_minimo_ajax() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
176
	}
177
178
	public function baixar_estoque_minimo_pdf() {
179
		$this->loadModel('Produto');
180
		$this->loadModel('Usuario');
181
182
		$dompdf = new Dompdf();
183
184
		$usuario = $this->Usuario->find('all', array('conditions' =>
185
				array(
186
					'Usuario.id' => $this->instancia
187
				)
188
			)
189
		)[0]['Usuario'];
190
191
		$conditions = array('conditions' =>
192
			array(
193
				'ativo' => 1,
194
				'id_usuario' => $this->instancia,
195
				'Produto.quantidade_minima <= ' => 'Produto.estoque',
196
				'Produto.estoque <= ' => $usuario['estoque_minimo']
197
			)
198
		);
199
200
		$produtos = $this->Produto->find('all', $conditions);
201
202
		$html = $this->getProdutosEstoqueMinimoComoHtml($produtos);
203
204
		$dompdf->loadHtml($html);
205
206
		$dompdf->setPaper('A4');
207
208
		$dompdf->render();
209
210
		$dompdf->stream();
211
212
		exit;
0 ignored issues
show
Coding Style Compatibility introduced by
The method baixar_estoque_minimo_pdf() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
213
	}
214
215
	public function getProdutosEstoqueMinimoComoHtml($produtos) {
216
		$html = '';
217
		$html .= '<html>';
218
		$html .= '<head>';
219
		$html .= '	<title></title>';
220
		$html .= '</head>';
221
		$html .= '<body>';
222
		$html .= '';
223
		$html .= '	<table style="background-color: #cacaca;"  width="100%" valign="center" align="center">';
224
		$html .= '		<tr align="center">';
225
		$html .= '			<td>';
226
		$html .= '				<h2>Produtos com quantidade de estoque minimo</h2>';
227
		$html .= '			</td>';
228
		$html .= '		</tr> ';
229
		$html .= '	</table>';
230
		$html .= '	<br>';
231
		$html .= '	<br>';
232
		$html .= '	<table  width="100%" valign="center" align="center">';
233
		$html .= '		<tr style="background-color: #cacaca;" align="center">';
234
		$html .= '			<td>';
235
		$html .= '				<h2>Produtos</h2>';
236
		$html .= '			</td>';
237
		$html .= '		</tr> ';
238
		$html .= '	</table>';
239
		$html .= '	<br>';
240
		$html .= '	<table  width="100%" valign="center" align="center">';
241
		$html .= '		<tr>';
242
		$html .= '			<td>';
243
		$html .= '				<table width="100%" valign="center" align="center">';
244
		$html .= '					<tr style="background-color: #cacaca;">';
245
		$html .= '						<td>Nome Produto</td>';
246
		$html .= '						<td>Quantidade</td>';
247
		$html .= '					</tr>';
248
		$html .= '';
249
250
		foreach ($produtos as $i => $produto) {
251
252
			$html .= '					<tr>';
253
			$html .= '						<td>' . $produto['Produto']['nome'] . '</td>';
254
			$html .= '						<td>' . $produto['Produto']['estoque'] . '</td>';
255
			$html .= '					</tr>';
256
		}
257
258
		$html .= '				</table>';
259
		$html .= '			</td>';
260
		$html .= '		</tr>';
261
		$html .= '	</table>';
262
		$html .= '	<br>';
263
		$html .= '';
264
		$html .= '</body>';
265
		$html .= '</html>';
266
267
		return $html;
268
	}
269
270 View Code Duplication
	public function adicionar_cadastro() {
271
		$this->loadModel('Categoria');
272
273
		$this->set('categorias', $this->Categoria->find('all', 
274
				array('conditions' => 
275
					array('ativo' => 1,
276
						  'usuario_id' => $this->instancia
277
					)
278
				)
279
			)
280
		);	
281
282
		$this->layout = 'wadmin';
283
	}
284
285
	public function s_adicionar_cadastro() {
0 ignored issues
show
Coding Style introduced by
s_adicionar_cadastro uses the super-global variable $_FILES which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
286
		$dados  = $this->request->data('dados');
287
288
		$variacoes = $this->request->data('variacao');
289
290
		$image  = $_FILES['imagem'];
291
292
		$retorno = $this->uploadImage($image);
293
294
		if (!$retorno['status']) 
295
			$this->Session->setFlash('Não foi possivel salvar a imagem tente novamente');
296
297
		$dados['imagem'] = $retorno['nome'];
298
		$dados['id_usuario'] = $this->instancia;
299
		$dados['ativo'] = 1;
300
		$dados['id_alias'] = $this->id_alias();
301
302
		if($this->Produto->save($dados)) {
303
			$produto_id = $this->Produto->getLastInsertId();
304
			
305
			require 'VariacaoController.php';
306
307
			$objVariacaoController = new VariacaoController();
308
309
			$objVariacaoController->s_adicionar_variacao($variacoes, $produto_id, $this->instancia);			
310
311
			$this->Session->setFlash('Produto salvo com sucesso!');
312
            
313
            return $this->redirect('/produto/listar_cadastros');
314
		} else {
315
			$this->Session->setFlash('Ocorreu um erro ao salva o produto!');
316
            
317
            return $this->redirect('/produto/listar_cadastros');
318
		}
319
	}
320
321
	public function editar_cadastro($id) {
322
		$this->layout = 'wadmin';
323
324
		$this->loadModel('Variacao');
325
326
		$query = array (
327
			'joins' => array(
328
				    array(
329
				        'table' => 'produtos',
330
				        'alias' => 'Produto',
331
				        'type' => 'LEFT',
332
				        'conditions' => array(
333
				            'Variacao.produto_id = Produto.id',
334
				        ),
335
				    )
336
				),
337
	        'conditions' => array('Variacao.produto_id' => $id, 'Variacao.ativo' => 1),
338
	        'fields' => array('Produto.id, Variacao.*'),
339
		);
340
341
		$variacoes = $this->set('variacoes', $this->Variacao->find('all', $query));
0 ignored issues
show
Bug introduced by
Are you sure the assignment to $variacoes is correct as $this->set('variacoes', ...o->find('all', $query)) (which targets Controller::set()) seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
342
343
		$this->set('produto', $this->Produto->find('all', 
344
				array('conditions' => 
345
					array('ativo' => 1,
346
						  'id' => $id
347
					)
348
				)
349
			)[0]
350
		);
351
352
		$this->loadModel('Categoria');
353
354
		$this->set('categorias', $this->Categoria->find('all', 
355
				array('conditions' => 
356
					array('ativo' => 1,
357
						  'usuario_id' => $this->instancia
358
					)
359
				)
360
			)
361
		);	
362
	}
363
364
	public function s_editar_cadastro($id) {
0 ignored issues
show
Coding Style introduced by
s_editar_cadastro uses the super-global variable $_FILES which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
365
		$dados = $this->request->data('dados');
366
367
		$variacoes = $this->request->data('variacao');
368
369
		$image  = $_FILES['imagem'];
370
		
371 View Code Duplication
		if (!empty($image['name'])) {
372
			$retorno = $this->uploadImage($image);
373
			
374
			if (!$retorno['status']) 
375
				$this->Session->setFlash('Não foi possivel salvar a imagem tente novamente');
376
			
377
			$dados['imagem'] = $retorno['nome'];
378
		}
379
380
381
		$dados['id_usuario'] = $this->instancia;
382
		$dados['ativo'] = 1;
383
		$dados['id_alias'] = $this->id_alias();
384
385
		$this->Produto->id = $id;
386
		
387
		if ($this->Produto->save($dados)) {
388
389
			require 'VariacaoController.php';
390
			$objVariacaoController = new VariacaoController();
391
			$objVariacaoController->desativar_variacoes($id);
392
			$objVariacaoController->s_adicionar_variacao($variacoes, $id, $this->instancia);	
393
394
			$this->Session->setFlash('Produto editado com sucesso!','default','good');
395
            return $this->redirect('/produto/listar_cadastros');
396
		} else {
397
			$this->Session->setFlash('Ocorreu um erro ao editar o produto!','default','good');
398
            return $this->redirect('/produto/listar_cadastros');
399
		}
400
	}
401
402 View Code Duplication
	public function excluir_cadastro() {
403
		$this->layout = 'ajax';
404
405
		$id = $this->request->data('id');
406
407
		$dados = array('ativo' => '0');
408
		$parametros = array('id' => $id);
409
410
		if ($this->Produto->updateAll($dados, $parametros)) {
411
			echo json_encode(true);
412
		} else {
413
			echo json_encode(false);
414
		}
415
	}
416
417
	public function id_alias() {
418
		$id_alias = $this->Produto->find('first', array(
419
				'conditions' => array('Produto.ativo' => 1),
420
				'order' => array('Produto.id' => 'desc')
421
			)
422
		);
423
424
		return $id_alias['Produto']['id_alias'] + 1;
425
	}
426
427
	public function carregar_dados_venda_ajax() {
428
		$this->layout = 'ajax';
429
430
		$retorno = $this->Produto->find('first', 
431
			array('conditions' => 
432
				array('Produto.ativo' => 1,
433
					  'Produto.id_usuario' => $this->instancia,
434
					  'Produto.id' => $this->request->data('id')
435
				)
436
			)
437
		);
438
439
		if (!$this->validar_estoque($retorno)) {
440
			return false;
441
		}
442
443
		$retorno['Produto']['total'] = $this->calcular_preco_produto_venda($retorno['Produto']['preco'], $this->request->data('qnt'));
444
445
		$retorno['Produto']['preco'] = number_format($retorno['Produto']['preco'], 2, ',', '.');
446
		
447
		echo json_encode($retorno);
448
	}
449
450
	public function validar_estoque($produto) {
451
		if (empty($produto) && !isset($produto)) {
452
			return false;
453
		}
454
		
455
		if ($produto['Produto']['estoque'] <= 0) {
456
			return false;
457
		}
458
459
		return true;
460
	}
461
462
	public function calcular_preco_produto_venda($preco, $qnt) {
463
		if (empty($preco) || !isset($preco)) {
464
			return false;
465
		}
466
467
		if (!is_numeric($qnt)) {
468
			return false;
469
		}
470
471
		$retorno = $preco * $qnt;
472
473
		return number_format($retorno, 2, ',', '.');
474
	}
475
476 View Code Duplication
	public function uploadImage(&$image) {
477
		$type = substr($image['name'], -4);
478
		$nameImage = uniqid() . md5($image['name']) . $type;
479
		$dir = APP . 'webroot/uploads/produto/imagens/';
480
		
481
		$returnUpload = move_uploaded_file($image['tmp_name'], $dir . $nameImage);
482
483
		if (!$returnUpload)
484
			return array('nome' => null, 'status' => false);
485
486
		return array('nome' => $nameImage, 'status' => true);
487
	}
488
489
	public function visualizar_cadastro($id) {
490
		$this->layout = 'wadmin';
491
492
		$produto = $this->Produto->find('all', 
493
			array('conditions' => 
494
				array('ativo' => 1,
495
					  'id' => $id
496
				)
497
			)
498
		);
499
500
		if (empty($produto)) {
501
			$this->Session->setFlash("Produto não encotrado, tente novamente");
502
			$this->redirect("/produto/listar_cadastros");
503
		}
504
505
		$this->set('produto', $produto[0]);
506
	}
507
508
	public function exportar_excel_exemplo() {
509
		include(APP . 'Vendor/PHPExcel/PHPExcel.php');
510
		include(APP . 'Vendor/PHPExcel/PHPExcel/IOFactory.php');
511
512
        $objPHPExcel = new PHPExcel();
513
        // Definimos o estilo da fonte
514
        $objPHPExcel->getActiveSheet()->getStyle('A1')->getFont()->setBold(true);
515
516
        $objPHPExcel->getActiveSheet()->getRowDimension('1')->setRowHeight(40);
517
518
        // Criamos as colunas
519
        $objPHPExcel->setActiveSheetIndex(0)
0 ignored issues
show
Bug introduced by
The method setCellValue does only exist in PHPExcel_Worksheet, but not in PHPExcel_Cell.

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...
520
                    ->setCellValue('A1', "Nome do Produto")
521
                    ->setCellValue('B1', "Preço ")
522
                    ->setCellValue("C1", "Peso Bruto")
523
                    ->setCellValue("D1", "Peso Liquido")
524
                    ->setCellValue("E1", "Estoque")
525
                    ->setCellValue("F1", "Descrição");
526
527
        // Podemos renomear o nome das planilha atual, lembrando que um único arquivo pode ter várias planilhas
528
        $objPHPExcel->getActiveSheet()->setTitle('Listagem de produtos');
529
530
        // Cabeçalho do arquivo para ele baixar
531
        header('Content-Type: application/vnd.ms-excel');
532
        header('Content-Disposition: attachment;filename="planilha_importacao_exemplo.xls"');
533
        header('Cache-Control: max-age=0');
534
        // Se for o IE9, isso talvez seja necessário
535
        header('Cache-Control: max-age=1');
536
537
        // Acessamos o 'Writer' para poder salvar o arquivo
538
        $objWriter = PHPExcel_IOFactory::createWriter($objPHPExcel, 'Excel5');
539
540
        // Salva diretamente no output, poderíamos mudar arqui para um nome de arquivo em um diretório ,caso não quisessemos jogar na tela
541
        $objWriter->save('php://output'); 
542
543
        exit;
0 ignored issues
show
Coding Style Compatibility introduced by
The method exportar_excel_exemplo() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
544
    }
545
546
    public function importar_produtos_planilha() {
0 ignored issues
show
Coding Style introduced by
importar_produtos_planilha uses the super-global variable $_FILES which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
547
        if (!isset($_FILES['arquivo']['tmp_name']) && empty($_FILES['arquivo']['tmp_name']))
548
        {
549
			$this->Session->setFlash("Erro ao subir a planilha, tente novamente.");
550
			$this->redirect("/produto/listar_cadastros");        	
551
        }
552
553
        $typesPermissions = ['application/vnd.ms-excel'];
554
555
        if (!in_array($_FILES['arquivo']['type'], $typesPermissions))
556
        {
557
			$this->Session->setFlash("O arquivo deve ser no formato .xls.");
558
			$this->redirect("/produto/listar_cadastros");                	
559
        }
560
561
        $caminho = APP . 'webroot/uploads/produto/planilhas/' . uniqid() . '.xls';
562
563
        $inputFileName = $_FILES['arquivo']['tmp_name'];
564
565
        move_uploaded_file($inputFileName, $caminho);
566
567
        $data = [
568
        	'caminho' => $caminho,
569
        	'usuario_id' => $this->instancia,
570
        	'processado' => 0,
571
        	'ativo' => 1
572
        ];
573
574
        $this->loadModel('QueueProduct');
575
576
        if ($this->QueueProduct->save($data))
577
        {
578
			$this->Session->setFlash("O arquivo está na fila para ser importado, iremos enviar um e-mail quando terminar.");
579
			$this->redirect("/produto/listar_cadastros");  
580
        }
581
        else 
582
        {
583
			$this->Session->setFlash("Ocorreu um erro, tente novamente.");
584
			$this->redirect("/produto/listar_cadastros");          	
585
        }
586
    }
587
588
    public function processar_planilhas_na_fila() {
589
    	$this->loadModel('QueueProduct');
590
591
    	$planilhas = $this->QueueProduct->loadPlanilhasNotProcesseds();
592
593
    	$response = [];
594
    	foreach ($planilhas as $planilha) {
595
    		$response[] = $this->processar_planilhas($planilha['caminho'], $planilha['usuario_id'], $planilha['id']);
0 ignored issues
show
Bug introduced by
Are you sure the assignment to $response[] is correct as $this->processar_planilh..._id'], $planilha['id']) (which targets ProdutoController::processar_planilhas()) seems to always return null.

This check looks for function or method calls that always return null and whose return value is assigned to a variable.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
$object = $a->getObject();

The method getObject() can return nothing but null, so it makes no sense to assign that value to a variable.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
596
    	}
597
598
    	return $response;
599
    }
600
601
    public function processar_planilhas($inputFileName, $usuarioId, $planilhaId) {
602
		include(APP . 'Vendor/PHPExcel/PHPExcel.php');
603
		include(APP . 'Vendor/PHPExcel/PHPExcel/IOFactory.php');
604
    	
605
        $objPHPExcel = new PHPExcel();
606
607
		try {
608
		    $inputFileType 	= PHPExcel_IOFactory::identify($inputFileName);
609
		    $objReader 		= PHPExcel_IOFactory::createReader($inputFileType);
610
		    $objPHPExcel 	= $objReader->load($inputFileName);
611
		} catch(Exception $e) {
612
		    die('Error loading file "' . pathinfo($inputFileName, PATHINFO_BASENAME) . '": ' . $e->getMessage());
0 ignored issues
show
Coding Style Compatibility introduced by
The method processar_planilhas() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
613
		}
614
615
		$dados = [];
616
617
		$rows = $objPHPExcel->setActiveSheetIndex(0)->getHighestRow();
618
619
		for ($row = 2; $row <= $rows; $row++) {
620
			
621
			$rowInterator = $objPHPExcel->getActiveSheet()->getRowIterator($row)->current();
622
623
			$cellIterator = $rowInterator->getCellIterator();
624
			$cellIterator->setIterateOnlyExistingCells(false);
625
626
			foreach ($cellIterator as $i => $cell) {
627
				switch ($i) {
628
					case 0: //Codigo/SKU
629
						$dados[$row]['sku'] = $cell->getValue();
630
					break; 
631
					case 1: // Nome/Descrição 
632
						$dados[$row]['nome'] = $cell->getValue();						
633
					break;
634
					case 2: // QtdAtual
635
						//$dados[$row]['sku'] = $cell->getValue();						
636
					break;
637
					case 3: // QtdMinima  
638
						$dados[$row]['quantidade_minima'] = $cell->getValue();						
639
					break;
640
					case 4: // QtdTotal
641
						$dados[$row]['estoque'] = $cell->getValue();						
642
					break;
643
					case 5: // ValCusto
644
						$dados[$row]['custo'] = $cell->getValue();						
645
					break;
646
					case 6:  // ValVenda
647
						$dados[$row]['preco'] = $cell->getValue();						
648
					break;
649
				}
650
			}
651
652
			$dados[$row]['id_usuario'] = $usuarioId;	
653
			$dados[$row]['ativo'] = 1;
654
655
		}
656
657
		$errors = $this->processar_lista_produtos($dados);
658
659
		if (isset($errors) && !empty($errors))
660
		{
661
			$this->QueueProduct->planilhaProcessedIncomplete($planilhaId);
662
		}
663
664
		$this->QueueProduct->planilhaProcessedComplete($planilhaId);
665
666
		echo json_encode(array('sucess' => true));
667
		exit;
0 ignored issues
show
Coding Style Compatibility introduced by
The method processar_planilhas() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
668
    }
669
670
    public function processar_lista_produtos($dados) {
671
    	$errors = [];
672
673
    	foreach ($dados as $dado) {
674
    		$this->loadModel('Produto');
675
    		
676
    		$existProduto = $this->Produto->find('all',
677
    			array(
678
    				'conditions' => array(
679
    					'Produto.sku' => $dado['sku'],
680
    					'Produto.ativo' => 1
681
    				)
682
    			)
683
    		);
684
685
    		if (isset($existProduto) && !empty($existProduto))
686
    		{
687
    			$this->Produto->id = $existProduto[0]['Produto']['id'];
688
    			$this->Produto->save($dado);
689
    			continue;
690
    		}
691
692
			$this->Produto->create();
693
694
    		if (!$this->Produto->save($dado))
695
    		{
696
    			$errors[] = $dado;
697
    		}
698
    	}
699
700
    	return $errors;
701
    }
702
703
}
704