Ir para conteúdo

Arquivado

Este tópico foi arquivado e está fechado para novas respostas.

Carcleo

Padrão Singleton

Recommended Posts

Olá, estou tentando fazer com que haja apenas 1 instancia do objeto da minha classe Carrinho.

Mas por mais que eu tente, não dá certo!

Classe CarrinhoDao.php



<?php

class CarrinhoDao {
private $carrinhoProdutos = Array();
private $cont = 0;
private static $instancia = null;

private function __construct() {
}

public function insereProduto($_produto, $_qtde) {

if($this->encontrou($_produto) == false) {

$this->carrinhoProdutos[$this->cont][0] = $_produto;
$this->carrinhoProdutos[$this->cont][1] = $_qtde;
$this->cont++;
}
}

public static function getInstancia() {
if (is_null(CarrinhoDao::$instancia)) {
CarrinhoDao::$instancia = new CarrinhoDao();
}
return CarrinhoDao::$instancia;
}

private function encontrou ($_produto) {
$encontrou = false;
foreach ($this->carrinhoProdutos as $produto) {
if($produto[0]->getIdProdutos() == $_produto->getIdProdutos()) {
$encontrou = true;
break;
}
}
return $encontrou;
}

public function getCarrinho () {
return $this->carrinhoProdutos;
}

public function removeItem ($_item) {
unset($this->carrinhoProdutos[$_item]);
}

public function alteraItem ($_item, $qde) {
$this->carrinhoProdutos[$_item][1] = $qde;
}
}
?>


CarrinhoConteudo.php




<h1 class="h1Centralizado">
Carrinho
</h1>

<?php
require_once "controlls/util/Conexao.php";
require_once "controlls/models/Produtos.php";
require_once "controlls/models/Carrinho.php";
require_once "controlls/daos/ProdutosDao.php";
require_once "controlls/daos/CarrinhoDao.php";
require_once "controlls/util/PhpUtil.php";

$connection = new Conexao();
$conexao = $connection->abreConexao();
$produtoDao = new ProdutosDao($conexao);
$phpUtil = new PhpUtil();

//Verificando se a variavel de sessão foi criada
if(!isset($_SESSION["MeuCarrinho"])) {
$CarrinhoDaoO = CarrinhoDao::getInstancia();
$_SESSION["MeuCarrinho"] = serialize($CarrinhoDaoO);
}

$CarrinhoDao = unserialize($_SESSION["MeuCarrinho"]);

session_write_close();

print "<pre>";
print_r($CarrinhoDao->getCarrinho());
print "</pre>";

?>

<?php
if(isset($_GET["acao"]) && $_GET["acao"] == "adicionar") {
$novoProduto = $produtoDao->pesquisaProdutoEdicao($_GET["idProduto"]);

if($novoProduto != null) {
$CarrinhoDao->insereProduto($novoProduto, 1);
}
//header("Location: ?");
}
?>

<?php
if(isset($_GET["acao"]) && $_GET["acao"] == "excluir") {
$CarrinhoDao->removeItem($_GET["indice"]);
//header("Location: ?");
}
?>

<?php
/*
f$CarrinhoDao->alteraItem(2, 123);
*/
$mensagem = "Deseja excluir este Produto?";
$imagem = "<img src='_img/bloquear.png' height=30px title='Excluir Produto' />";

echo "<table style='width:800px'";
echo " <tr>";
echo " <th>Produto</th>";
echo " <th>Tamanho</th>";
echo " <th>Preço Unitário</th>";
echo " <th>Quantidade</th>";
echo " <th>Preço Total</th>";
echo " <th>Remover</th>";
echo " </tr>";

foreach ($CarrinhoDao->getCarrinho() as $k=>$produto) {
echo " <tr>";
echo " <td style='text-align:left'>".$produto[0]->getNome()."</td>";
echo " <td style='text-align:center'>".$produto[0]->getTamanho()."</td>";
echo " <td style='text-align:right'>".$phpUtil->formataMoeda($produto[0]->getPreco())."</td>";
echo " <td style='text-align:center'><input type='text' id='qtde' name='qtde' class='typetextpequeno' style='text-align:right' value='".$produto[1]."'></td>";
echo " <td style='text-align:right'>".$phpUtil->formataMoeda($produto[0]->getPreco() * $produto[1])."</td>";
echo " <td style='text-align:center'><a href='?acao=remove&indice=".$k."' onclick=\"return verifica('".$mensagem."')\" '>".$imagem."</a>";
echo " </tr>";
}

echo "</table>";



print "<pre>";
print_r($CarrinhoDao->getCarrinho());
print "</pre>";
?>


Página de produtos



<h1 class="h1Centralizado">
Listagem de Produtos
</h1>

<?php
require_once "controlls/util/Conexao.php";
require_once "controlls/models/Produtos.php";
require_once "controlls/daos/ProdutosDao.php";
require_once "controlls/util/PhpUtil.php";

$connection = new Conexao();
$conexao = $connection->abreConexao();

$produtoDao = new ProdutosDao($conexao);
$phpUtil = new PhpUtil();

$imagemAdd = "<img src='_img/add.png' style='height:30px;'";

echo "<table style='width:800px'";
echo " <tr>";
echo " <th>Produto</th>";
echo " <th>Tamanho</th>";
echo " <th>Preço Unitário</th>";
echo " <th>Adicionar</th>";
echo " </tr>";

foreach ($produtoDao->pesquisaProdutos() as $k=>$produto) {
echo " <tr>";
echo " <td style='text-align:left'>".$produto->getNome()."</td>";
echo " <td style='text-align:center'>".$produto->getTamanho()."</td>";
echo " <td style='text-align:right'>".$phpUtil->formataMoeda($produto->getPreco())."</td>";
echo " <td style='text-align:center'><a href='carrinho.php?acao=adicionar&idProduto=".$produto->getIdProdutos()."'>".$imagemAdd."</a>";
echo " </tr>";
}

echo "</table>";
?>

<?php
if(isset($_GET["acao"]) && $_GET["acao"] == "adicionar") {
$CarrinhoDao->removeItem($_GET["indice"]);
header("Location: ?");
}
?>



Tudo funciona bem, a listagem dos produtos e tudo mais. Porem, assim que adiciona um produto ao carrinho, ele é adidionado. Ao adicionar o segundo produto ao carrinho, parece que o Objeto CarrinhoDao é perdido e criado um novo.

E, nesse caso, não consigo ter 2 produtos no carrinho.

Onde estou errando?

Sim,na primeira linha de todas as páginas tem session_start();

Compartilhar este post


Link para o post
Compartilhar em outros sites

Já. A sessão reclama a falta de serialização!

 

O que esta pegando é que parece que esta apagando a instancia e crando outra

 

O primeiro iten vai bem, já o segundo dá esse erro:[

 

 

Fatal error: main(): The script tried to execute a method or access a property of an incomplete object. Please ensure that the class definition "CarrinhoDao" of the object you are trying to operate on was loaded _before_ unserialize() gets called or provide a __autoload() function to load the class definition in C:\xampp\htdocs\php\andre\revenda\carrinhoConteudo.php on line 31
 

Compartilhar este post


Link para o post
Compartilhar em outros sites

Já pensei nisso. Mas estou tentando descobrir o porque que não esta funcionando de gravar 2 produtos:

 

O atributo cont esta incrementando normal. Mas o objeto da classe CarrinhoDao.php esta se recriando!

 

E mesmo assim não deu certo!

Compartilhar este post


Link para o post
Compartilhar em outros sites

Pra vc manter o estado do objeto inalterado com php, teria que usar websocket e manter a conexão em keep alive forever!

Salvar um objeto singleton em uma Session acho que não seria a abordagem correta (Alem de não ser uma pratica segura)!

 

Parece algum problema com autoload . Talvez tenha que usar métodos: magicos __sleep e __wakeup, pra contornar isso.

 

Enfim, acho que armazenar strings com os dados da compra nas session seria mais simples!

 

Compartilhar este post


Link para o post
Compartilhar em outros sites
Sabe, gostaria de uma opinião.


Minha ideia era de guardar o objeto na sessão para todas as modificações que ele sofrer ( delete, add, update, unset).


E no final gravar no BD não a Sessão, mas sim o objeto usando seus métodos.


Mas não está funcionando.


Então estou agora gravando direto na SESSAO["MeuCarrinho"] os dados do Objeto Produto.



<h1 class="h1Centralizado">
Pedido
</h1>

<?php
require_once "controlls/util/Conexao.php";
require_once "controlls/models/Produtos.php";
require_once "controlls/daos/ProdutosDao.php";
require_once "controlls/util/PhpUtil.php";

$connection = new Conexao();
$conexao = $connection->abreConexao();
$produtoDao = new ProdutosDao($conexao);
$phpUtil = new PhpUtil();

//Verificando se a variavel de sessão foi criada
if (!isset($_SESSION["MeuCarrinho"])) {
$_SESSION["MeuCarrinho"] = array();
}
if (!isset($_SESSION["cont"])) {
$_SESSION["cont"] = 0;
}
?>

<?php
if(isset($_GET["acao"])) {
if($_GET["acao"] == "adicionar") {
$novoProduto = $produtoDao->pesquisaProdutoEdicao($_GET["idProduto"]);

if($novoProduto != null) {

$achou = false;
$chave = "";

foreach ($_SESSION["MeuCarrinho"] as $key=>$produtoC) {
if($produtoC["idProdutos"] == $novoProduto->getIdProdutos()) {
$achou = true;
$chave = $key;
break;
}
}

if($achou == true) {
$_SESSION["MeuCarrinho"][$chave]["quantidade"] += 1;
} else {
$_SESSION["MeuCarrinho"][$_SESSION["cont"]]["quantidade"]=1;
$_SESSION["MeuCarrinho"][$_SESSION["cont"]]["idProdutos"]=$novoProduto->getIdProdutos();
$_SESSION["MeuCarrinho"][$_SESSION["cont"]]["nome"]=$novoProduto->getNome();
$_SESSION["MeuCarrinho"][$_SESSION["cont"]]["preco"]=$novoProduto->getPreco();
$_SESSION["MeuCarrinho"][$_SESSION["cont"]]["tamanho"]=$novoProduto->getTamanho();
$_SESSION["cont"]++;
}


}
header("Location: ?");
}
if($_GET["acao"] == "remove") {
$achou = false;
$chave = "";

foreach ($_SESSION["MeuCarrinho"] as $key=>$produtoC) {
if($produtoC["idProdutos"] == $_GET["indice"]) {
$achou = true;
$chave = $key;
break;
}
}

if($achou == true) {
unset ($_SESSION["MeuCarrinho"][$chave]);
}

header("Location: ?");
}

if($_GET["acao"] == "atualizar") {

foreach ($_POST["idProdutos"] as $keyForm => $produtoForm) {
foreach ($_SESSION["MeuCarrinho"] as $keySession => $produtoSession) {
//print $produtoForm ."==". $produtoSession["idProdutos"]."Key: $keySession"."<br>";
if ($produtoForm == $produtoSession["idProdutos"]) {
if($_POST["quantidade"][$keyForm]!= "" && $_POST["quantidade"][$keyForm] != 0) {
$_SESSION["MeuCarrinho"][$keySession]["quantidade"] = $_POST["quantidade"][$keyForm];
} else {
unset ($_SESSION["MeuCarrinho"][$keySession]);
}
break;
}
}
}
}
}

?>

<?php
$mensagem = "Deseja excluir este Produto?";
$imagem = "<img src='_img/excluir.jpg' height=30px title='Excluir Produto' />";
?>
<table style="width:800px">
<thead>
<tr>
<th>Produto</th>
<th>Tamanho</th>
<th>Preço Unitário</th>
<th>Quantidade</th>
<th>Preço Total</th>
<th>Remover</th>
</tr>
</thead>

<form action="?acao=atualizar" method="post">
<tfoot>
<tr><td colspan="6" style="height:30px;"></td></tr>
<tr>
<td colspan=2 style="text-align:center"><input type="submit" value="Atualizar Carrinho" /></td>
<td colspan=2 style="text-align:center"><a href="index.php"><img src='_img/continuar_comprando.gif' height=50px title='Continuar Comprando' /></a></td>
<td colspan=2 style="text-align:center"><a href="fechamento.php?acao=form"><img src='_img/finlizar-pedido.png' height=50px title='Continuar Comprando' /></a></td>
</tr>
</tfoot>
<?php
echo "<tbody>";

foreach ($_SESSION["MeuCarrinho"] as $k=>$produto) {
$campoQuantidade = "quantidade".$produto["idProdutos"];
echo " <tr>";
echo " <td style='text-align:left'>".$produto["nome"]."</td>";
echo " <td style='text-align:center'>".$produto["tamanho"]."</td>";
echo " <td style='text-align:right'>".$phpUtil->formataMoeda($produto["preco"])."</td>";
echo " <td style='text-align:center'><input type='text' id='".$campoQuantidade."' name='quantidade[".$produto["idProdutos"]."]' class='typetextpequeno' onkeypress='return SomenteNumero(event)' style='text-align:right' value='".$produto["quantidade"]."'></td>";
echo " <td style='text-align:right'>".$phpUtil->formataMoeda($produto["preco"] * $produto["quantidade"])."</td>";
echo " <td style='text-align:center'><a href='?acao=remove&indice=".$produto["idProdutos"]."' onclick=\"return verifica('".$mensagem."')\" '>".$imagem."</a>";
echo " </tr>";

echo "<input type='hidden' name='idProdutos[".$produto["idProdutos"]."]' value='".$produto["idProdutos"]."' />";
echo "<input type='hidden' name='nome[".$produto["idProdutos"]."]' value='".$produto["nome"]."' />";
echo "<input type='hidden' name='preco[".$produto["idProdutos"]."]' value='".$produto["nome"]."' />";
echo "<input type='hidden' name='tamanho[".$produto["idProdutos"]."]' value='".$produto["idProdutos"]."' />";
}

echo "</tbody>";
?>
</form>

</table>
<br /><br />



Será que é seguro assim?

Note que já não uso mais a classe Carrinho

Compartilhar este post


Link para o post
Compartilhar em outros sites

Bom, agora ficou mais simples.

 

Quando me referi a segurança, foi no sentido, em guardar um objeto serialize, poderia expor trechos do seu Código fonte. Caso sofra ataques de XSS.

 

Não sei bem como funciona segurança de e-commerces, porem, se seu codigo estiver imune a ataques de XSS e usar ssl, acho que não há problemas em salvar o carrinho em uma session.

Compartilhar este post


Link para o post
Compartilhar em outros sites

×

Informação importante

Ao usar o fórum, você concorda com nossos Termos e condições.