Trabalhando com PDO no PHP

PDO (PHP Data Objects) é uma extensão que fornece uma interface padronizada para trabalhar com bancos de dados, cuja finalidade é abstrair a conexão e interações com os bancos, ou seja, independente do banco de dados que estiver sendo utilizado os métodos executados serão os mesmos, mas isso não significa que seu sistema será portável entre diversos bancos de dados, por mais que o uso do PDO facilite a portabilidade, esta interface significa apenas que você se comunicará com qualquer banco de dados através de um determinado conjunto de métodos e classes.

Não é possível executar funções de interação com o banco de dados utilizando somente a extensão PDO, é preciso utilizar um driver específico do PDO para acessar um determinado banco de dados. Cada banco de dados pode prover um driver para PDO, porém nem todos os recursos são suportados em todos os bancos, por exemplo, no MySQL, tabelas do tipo MyISAM não suportam transações, impossibilitando o funcionamento dos métodos PDO::beginTransaction(), PDO::commit() e PDO::rollBack().

PDO não é uma abstração de banco de dados e não reescreve SQL.

Banco de dados, SQL e Joins

Neste artigo não irei focar na criação de bancos de dados, comandos SQL ou Joins, se você tem interesse em ler mais sobre esses assuntos confira os links abaixo.

Se você estiver estudando para certificação não deixe de conferir.

Vantagens de utilizar PDO

  • Abstração de conexão e interação com banco de dados
  • Segurança
  • Suporte a diversos drivers

Ainda hoje muitas pessoas consideram o uso do PDO uma opção, analisando a possibilidade de um determinado projeto mudar de banco, utilizando o PDO somente se essa possibilidade existir. O grande perigo nessa análise superficial é que nem sempre no início de um projeto temos essa visão e se tiver que mudar não adianta lamentar, então em cima disso particularmente recomendo a utilização deste recurso, principalmente se o projeto necessitar trabalhar com mais de um tipo de banco.

Confira todos os drivers suportados pelo PDO.

Manipulando conexões

Toda conexão com banco de dados é realizada ao criar uma instância da classe PDO, ou seja, independente do driver utilizado sempre iremos instanciar a classe PDO.

O construtor da classe PDO recebe as informações do banco como parâmetro obrigatório, conhecido como dsn(Data Source Name), além dos parâmetros opcionais username, password e driver_options.

__construct ( string $dsn [, string $username [, string $password
    [, array $driver_options ]]] )

No exemplo abaixo realizamos uma conexão com o banco de dados mysql.

$conn = new PDO(
    'mysql:host=localhost;dbname=example-pdo', 'diogo', '123456'
);

Também podemos configurar nossa conexão através do parâmetro driver_options.

$conn = new PDO(
    'mysql:host=localhost;dbname=example-pdo', 'diogo', '123456',
    array(
        PDO::ATTR_PERSISTENT => true
    )
);

No exemplo acima, configuramos nossa conexão como persistente. Uma conexão persistente não é fechada no final do script, e sim armazenada em cache sendo reutilizada quando outro script solicitar uma conexão usando as mesmas credenciais.

Após abrir uma conexão podemos interagir com o banco utilizando 3 métodos da classe PDO:

Método Retorno Objetivo
exec int Utilizado para insert, update e delete.
query PDOStatement Utilizado para resultados tabulares, comando select.
prepare PDOStatement Cria um prepared statement, utilizado para dados variáveis.

Normalmente para fechar uma conexão é preciso destruir o objeto, assim como suas referências, para isso atribuimos o valor NULL a variável que contém o objeto. Se isso não for feito o PHP irá fechar automáticamente a conexão quando o script terminar, caso não seja uma conexão persistente.

Prepared statements

Os prepared statements oferecem dois ótimos benefícios:

  • A query só precisa ser preparada uma vez, mas pode ser executada várias vezes.
  • Os parâmetros não precisam ser escapados, pois o driver cuida disso automaticamente.

Esses benefícios significam duas coisas, agilidade e segurança, confira a criação de um prepared statement.

<?php
$stmt = $conn->prepare(
    'INSERT INTO posts (title, content) VALUES (:title, :content)'
);
?>

Com nosso prepared statement criado, precisamos informar os valores para compor a query, confira os métodos que podem ser utilizados.

  • bindValue()
  • bindParam()
<?php
$stmt = $conn->prepare(
    'INSERT INTO posts (title, content) VALUES (:title, :content)'
);

$title = 'Titulo do post';
$content = 'Conteudo do post';

$stmt->bindValue(':title', $title);
$stmt->bindValue(':content', $content);
?>

Após informar os dados necessários para o prepared statement, precisamos executar o método execute() para realizar a query no banco.

Para resgatar resultados de um comando select temos algumas alternativas.

Método Objetivo
fetch() Retorna a próxima linha do resultado.
fetchAll() Retorna um array com todos os resultados.
fetchObject() Retorna a próxima linha do resultado como objeto.
fetchColumn() Retorna uma coluna da próxima linha do resultado.
<?php
$stmt = $conn->prepare("SELECT * FROM posts");
while($row = $stmt->fetch()) {
    print_r($row);
}
?>

Um recurso interessante na hora de resgatar valores é o método bindColumn(), que tem a função de vincular o valor de uma coluna do resultado do prepared statment à uma variável.

Diferença entre bindParam() e bindValue()

A grande diferença entre esses métodos é que o bindParam() recebe o valor do parâmetro por referência, sendo este realmente setado no momento em que o método execute() do prepared statment for chamado, o que pode gerar problemas em alguns casos, mas também pode facilitar em outros, sendo assim dê preferência ao bindValue() para os casos básicos.

Transações

Uma transação é um conjunto de procedimentos executados no banco de dados como uma única operação. Na prática, indicamos o início de uma transação utilizando o comando start transaction ou begin no MySQL, em seguida realizamos algumas tarefas, inserção, alteração ou remoção de registro(s), no termino desses procedimentos caso tudo ocorra bem, informamos através do comando commit que as mudanças podem ser aplicadas de fato no banco, mas caso ocorra algo de errado em algum dos procedimentos podemos utilizar o comando rollback, garantindo que todos os procedimentos realizados desde o início da transação sejam desfeitos.

A integridade de uma transação depende de quatro propriedades, conhecidas como ACID.

1. Atomicidade

Uma transação deve ser uma unidade atômica de trabalho; ou todas as suas modificações de dados são executadas ou nenhuma delas é executada.

2. Consistência

Regras de integridade dos dados são asseguradas, ou seja, as transações não podem quebrar as regras do banco de dados.

3. Isolamento

O resultado de uma transação executada concorrentemente a outra deve ser o mesmo que o de sua execução de forma isolada. Operações exteriores a uma dada transação jamais verão esta transação em estados intermediários.

4. Durabilidade

Depois que uma transação tiver sido concluída, seus efeitos ficam permanentemente no sistema.

No PDO utilizamos três métodos para trabalhar com transações, beginTransaction() para iniciar uma transação, commit() para que as tarefas realizadas sejam mantidas e rollback() para desfazer caso ocorra algum problema.

Alguns bancos de dados não oferecem este recurso, trabalhando apenas em modo autocommit.

Tratamento de erros no PDO

O PDO oferece 3 alternativas para manipulação de erros.

PDO::ERRMODE_SILENT

Esse é o tipo padrão utilizado pelo PDO, basicamente o PDO seta internamente o código de um determinado erro, podendo ser resgatado através dos métodos PDO::errorCode() e PDO::errorInfo().

PDO::ERRMODE_WARNING

Além de armazenar o código do erro, este tipo de manipulação de erro irá enviar uma mensagem E_WARNING, sendo este muito utilizado durante a depuração e/ou teste da aplicação.

PDO::ERRMODE_EXCEPTION

Além de armazenar o código de erro, este tipo de manipulação de erro irá lançar uma exceção PDOException, esta alternativa é recomendada, principalmente por deixar o código mais limpo e legível.

<?php
$dsn = 'mysql:host=localhost;dbname=example-pdo';
$user = 'diogo';
$password = '123456';
try {
    $conn = new PDO($dsn, $user, $password);
    $conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
} catch (PDOException $e) {
    echo $e->getMessage();
}
?>

Trabalhando com PDO

Agora que conhecemos um pouco sobre PDO, vamos praticar, neste exemplo iremos utilizar um banco de dados chamado de “example-pdo”, contendo apenas uma tabela, nomeada de “posts”, confira o script de criação da tabela.

index.php

<?php
include_once('Registry.php');
include_once('dao/PostDAO.php');
include_once('model/Post.php');

// Instanciar uma conexão com PDO
$conn = new PDO(
    'mysql:host=localhost;port=3306;dbname=example-pdo', 'user', 'password'
);
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

// Armazenar essa instância no Registry
$registry = Registry::getInstance();
$registry->set('Connection', $conn);

// Instanciar um novo Post e setar informações
$primeiroPost = new Post();
$primeiroPost->setTitle('Primeiro post');
$primeiroPost->setContent('Conteudo!');

// Instanciar um novo Post e setar informações
$segundoPost = new Post();
$segundoPost->setTitle('Segundo post');
$segundoPost->setContent('Conteudo!');

// Instanciar o DAO e trabalhar com os métodos
$postDAO = new PostDAO();
$postDAO->insert($primeiroPost);
$postDAO->insert($segundoPost);

// Resgatar todos os registros e iterar
$results = $postDAO->getAll();
foreach($results as $post) {
    echo $post->getTitle() . '<br />';
    echo $post->getContent() . '<br />';
    echo '<br />';
}
?>

Registry.php

<?php
/**
 * @author João Batista Neto
 */

class Registry {

    private static $instance;
    private $storage;

    protected function __construct() {
        $this->storage = new ArrayObject();
    }

    public function get( $key ) {
        if ( $this->storage->offsetExists( $key ) ) {
            return $this->storage->offsetGet( $key );
        } else {
            throw new RuntimeException( sprintf( 'Não existe um registro para a chave "%s".' , $key ) );
        }
    }

    public static function getInstance() {
        if ( !self::$instance )
            self::$instance = new Registry();

        return self::$instance;
    }

    public function set( $key , $value ) {
        if ( !$this->storage->offsetExists( $key ) ) {
            $this->storage->offsetSet( $key , $value );
        } else {
            throw new LogicException( sprintf( 'Já existe um registro para a chave "%s".' , $key ) );
        }
    }

    public function unregister( $key ) {
        if ( $this->storage->offsetExists( $key ) ) {
            $this->storage->offsetUnset( $key );
        } else {
            throw new RuntimeException( sprintf( 'Não existe um registro para a chave "%s".' , $key ) );
        }
    }

}
?>

dao/PostDAO.php

<?php
include_once('model/Post.php');

class PostDAO {

    private $conn;

    public function __construct() {
        $registry = Registry::getInstance();
        $this->conn = $registry->get('Connection');
    }

    public function insert(Post $post) {
        $this->conn->beginTransaction();

        try {
            $stmt = $this->conn->prepare(
                'INSERT INTO posts (title, content) VALUES (:title, :content)'
            );

            $stmt->bindValue(':title', $post->getTitle());
            $stmt->bindValue(':content', $post->getContent());
            $stmt->execute();

            $this->conn->commit();
        }
        catch(Exception $e) {
            $this->conn->rollback();
        }
    }

    public function getAll() {
        $statement = $this->conn->query(
            'SELECT * FROM posts'
        );

        return $this->processResults($statement);
    }

    private function processResults($statement) {
        $results = array();

        if($statement) {
            while($row = $statement->fetch(PDO::FETCH_OBJ)) {
                $post = new Post();

                $post->setId($row->post_id);
                $post->setTitle($row->title);
                $post->setContent($row->content);

                $results[] = $post;
            }
        }

        return $results;
    }

}
?>

model/Post.php

<?php
class Post {

    private $id;
    private $title;
    private $content;

    public function getId() {
        return $this->id;
    }

    public function setId($id) {
        $this->id = $id;
        return $this;
    }

    public function getTitle() {
        return $this->title;
    }

    public function setTitle($title) {
        $this->title = $title;
        return $this;
    }

    public function getContent() {
        return $this->content;
    }

    public function setContent($content) {
        $this->content = $content;
        return $this;
    }

}
?>

Ao executar este exemplo iremos obter o seguinte resultado:

Resultado PDO
Resultado PDO

Fique a vontade para visualizar ou efetuar download do exemplo.

Referência(s)

http://php.net/manual/en/book.pdo.php

http://www.php.net/manual/en/pdo.drivers.php

http://www.slideshare.net/wezfurlong/php-data-objects

  • Léo Rodrigues Biscassi

    27/06/2012 às 10:00

    Muito bom o artigo! :)

  • Marcos Ferreira

    27/07/2012 às 23:24

    De muitos que encontrei, esse foi o melhor, bem explicativo e detalhado. Obrigado!

    Gostaria de saber se tem como trabalhar usando PDO e matriz de array, não acho nenhuma referencia que possa me ajudar nesse sentido.

    e parabens pelo artigo.

  • Diogo Matheus

    28/08/2012 às 21:45

    Obrigado pelo comentário Marcos,

    Poderia explicar melhor o que você quer fazer?

    Boa sorte, abraço.

  • França Web Developer

    18/09/2012 às 19:51

    Sem dúvida PDO é incrível, desde do dia que a conhece nunca mais larguei. Fácil e prático! Usuo em todos os meus projetos.

  • França Web Developer

    18/09/2012 às 19:54

    Para iniciantes vai ai um exemplo:

    // INSERIR DADOS
    public function inserir($tabela, $dados){

    try{

    // Pegar chaves
    $arrCampo = array_keys( $dados );
    // Pegar valores
    $arrValor = array_values( $dados );
    // Contar campo
    $numCampo = count( $arrCampo );
    // Contar valor
    $numValor = count( $arrValor );
    // Validando campos
    if($numCampo == $numValor){

    // Montar Query
    $SQL = “INSERT INTO ” . $tabela . ” (“;

    // Concatenando os campos da coluna da $tabela
    foreach($arrCampo as $campo){
    $SQL .= “$campo, “;
    }
    // Data Time Automatico
    $SQL .= ‘criado, ‘;

    // Retirando a “,” concatenado no final do $campo, e substituibdo por “)”
    $SQL = substr_replace($SQL,”)”,-2,1);
    $SQL .= ” VALUES (“;

    // Concatenando os ponto-chave para o bindParam
    foreach($arrCampo as $pontoChave){
    $SQL .= “:”.$pontoChave.”, “;
    }
    // Aplicando automaticamente Data Time
    $SQL .= ‘NOW(), ‘;

    // Retirando a “,” concatenado no final do $pontoChave, e substituibdo por “)”
    $SQL = substr_replace($SQL,”)”,-2,1);
    }

    // $SQL .= ‘ LAST_INSERT_ID()’;

    # print $SQL; // Retire a cerquilha do comentário em caso de ERROR para imprimir a SQL, e comente o que está abaixo.

    // Preparando a queryString
    $stmt = $this->pdo->prepare($SQL);
    // Relacionao os pontos chaves via bindParam
    for($i = 0; $i bindParam(‘:’.$arrCampo[$i],$arrValor[$i],$this->obterPDOConstanteTipo($arrValor[$i]));
    }

    $stmt->execute();
    $this->UltimoInsertID($this->pdo->lastInsertId());

    return true;

    }catch(PDOException $e){
    // Antes de verificar o ERROR, analise obterPDOConstanteTipo(), se está convertendos os dados correto.
    print “#Inserir: ERROR AO INSERIR DADOS! Consulte o programador(a) do seu site.”;
    $e->getMessage();
    }

    }

  • Diogo Matheus

    11/11/2012 às 10:51

    Obrigado pelos comentários pessoal.

  • Laércio

    11/02/2013 às 19:14

    Primeiramente parabéns pelo artigo Diogo.
    Eu queria saber se tem como usar reflection abordado num outro artigo seu para criar um DAO genérico, Já que possibilita percorrer os métodos das classe. Se é possível, teria como apresentar um piqueno exemplo o resto me viro aqui.
    Desde já agradeço pela atenção.

  • Eduardo

    21/02/2013 às 16:58

    Oi Diogo, estou com uma duvida e se possivel me ajudar agradeco desde ja.
    Bom estou usando teu exemplo num projeto pessoal, pesquisei muito sobre PDO e o artigo que mais me agradou nestas pesquisas foi o teu.

    Minha duvida e o seguinte. Como seria a adaptacao do seu exemplo na situacao. Preciso buscar uma linha especifica do banco passando um parametro, exemplo um id.
    Exemplificando, um usuario clica no link de um produto e com esse id carrego em outra pagina informacoes do produto em especifico.

    No teu exemplo voce carrega varios resultados do banco, gostaria de buscar um unico resultado entao como ficaria o controller nessa situacao.

    Obrigado.

  • Felipe

    20/04/2013 às 10:59

    Oi Diogo
    gostei do seu exemplo eu só dei uma melhorada nele
    tirei os includes e usei autoload e namespaces

    ah e seu registry.php ta identico ao do Joao Batista Neto Admnistrador do forum imasters foi um CTRL +C CTRL + V nem os creditos voce citou, mas blz acho que o Joao nao liga para esses detalhes

    t+

  • Diogo Matheus

    20/04/2013 às 12:27

    Olá Felipe,

    Obrigado pelo comentário, não foquei em autoload/namespaces para não confundir quem está iniciando.

    Realmente essa parte do exemplo, Registry, veio do João Batista, fórum do imasters, na correria deixei passar, vou providenciar esse ajuste, muito obrigado por lembrar essa parte.

    UPDATE: Adicionei autor da classe.

    Abraço e boa sorte

  • Renato Donizete

    20/04/2013 às 22:53

    Otimo material, é dificil achar material avançado e de qualidade na internet parabens

    gostaria de fazer uma humilde contribuição no seu codigo

    no registry.php fiz assim:
    class Registry extends \ArrayObject {
    dai eliminei todo __construct e a $torage, ficou o $this
    exemplo $this->offsetExists(), $this->offsetGet(), o codigo ficou bem mais clean, abraços

  • Diogo Matheus

    22/04/2013 às 19:48

    Obrigado pela sugestão Renato,

    Realmente é uma boa para simplificar, Zend Framework trabalhava dessa forma.

    Abraço e boa sorte

  • xbno

    16/10/2013 às 15:31

    uma dica para esse teu exemplo

    não a necessidade do uso de um novo método para criação do array, no metodo:

    public function getAll()
    {
    $statement = $this->conn->query(‘SELECT * FROM posts’);
    return $this->processResults($statement);
    }

    elimine o metodo processResults($statement) e use o fetchAll()
    só que na classe Post que vc criou deve conter os atributos iguais a da tabela criada, no caso troque o atributo id para post_id como na tabela, ai conservara os atributos private e poderá usar os métodos gets da classe Post no view
    ficando assim assim:

    require_once(‘model/Post.php’);

    class PostDAO
    {

    // lembrando de configurara o fetchAll() com PDO::FETCH_CLASS
    // como no exemplo a baixo

    public function getAll()
    {
    $statement = $this->conn->query(‘SELECT * FROM posts’);
    return $statement->fetchAll(PDO::FETCH_CLASS,”Post”);
    }

    }

    sendo que o PDO já foi feito para criar arrays assim trabalhando com classes.
    ganha mais praticidade e performance.

  • Carlos Anders

    06/11/2013 às 23:33

    Parabéns pelo artigo, é muito bom poder ver como o php aos poucos têm ganhado espaço e tem amadurecido com a orientação a objetos, ainda mais com o zend framework.

  • fckruz

    11/01/2014 às 01:42

    Olá, irmão! poderia dar uma luz, queria uma confirmação de que os dados foram inseridos com sucesso no bd, pensei em implementar function insert, mas não estou fazendo de modo correto!

  • Tiago Farias

    19/01/2014 às 22:50

    Muito agradecido Sir Diogo!
    Sou estudande de php e outras linguagens de programação, e passarei a acompanhar seu trabalho.

  • Bruce

    14/03/2014 às 19:48

    Olá!
    Alguém poderia me explicar qual a finalidade do Registry.php?

    grato!

  • Daniel

    17/05/2014 às 02:07

    Valeu mesmo!! Muito bom!

  • omor

    02/06/2014 às 16:24

    Olá Diogo tudo bem?
    Estou desenvolvendo um projeto e está dando esses erros
    Notice: Undefined variable: conecta in D:\Program Files\wamp\www\Portal_Imobiliario\funcoes.php on line 16

    Fatal error: Call to a member function prepare() on a non-object in D:\Program Files\wamp\www\Portal_Imobiliario\funcoes.php on line 16

    meu arquivo de conexao está assim
    setAttribute(PDO::ATTR_ERRMODE,PDO::ERRMODE_EXCEPTION);

    }catch(PDOException $error_conecta){
    echo ‘Erro ao conectar, informe no email contato@srimoveis.com.br ‘.$error_conecta->getMessage();;

    }

    ?>

    arquivo funcões está assim
    = :dataVal ORDER BY imovelID DESC LIMIT 5’;

    try{
    $query = $conecta->prepare($sql);
    $query->bindValue(‘:dataVal’,$dataVal,PDO::PARAM_STR);
    $query->bindValue(‘:imovelStatus’,$imovelStatus,PDO::PARAM_STR);
    $query->execute();

    $resultado = $query->fetchAll(PDO::FETCH_ASSOC);

    }catch(PDOexception $error_Sql){
    echo ‘Erro ao selecionar Imóveis ‘.$error_Sql->getMessage();

    }
    foreach($resultado as $res){

    $imovelID = $res[‘imovelID’];
    $tipo = $res[‘imovelTipo’];
    $negocio = $res[‘imovelNegocio’];
    $valor = $res[‘imovelValor’];
    $thumb = $res[‘imovelThumb’];
    $titulo = $res[‘imovelTitulo’];

    echo ”;
    echo ‘‘;
    echo ‘‘.$tipo.’ à ‘.$negocio.’‘;
    echo ‘Valor ‘.$valor.’‘;
    echo ‘Veja mais‘;
    echo ”;

    }
    }

    se faço o include do arquivo config aparece os seguintes erros

    Notice: Constant HOST already defined in D:\Program

    Notice: Constant DB already defined in D:\Program

    Notice: Constant USER already defined in D:\Program

    Notice: Constant HOST already defined in D:\Program Files\wamp\www\Portal_Imobiliario\Connections\config.php on line 3

    Notice: Constant DB already defined in D:\Program Files\wamp\www\Portal_Imobiliario\Connections\config.php on line 4

    Notice: Constant USER already defined in D:\Program Files\wamp\www\Portal_Imobiliario\Connections\config.php on line 5

    Notice: Constant PASS already defined in D:\Program Files\wamp\www\Portal_Imobiliario\Connections\config.php on line 6

  • Rogério

    21/01/2015 às 20:54

    Gostei da explicação, mas se eu quisesse conectar a dois bancos mysql ao mesmo tempo. Como ficaria?

  • Sandro

    28/10/2015 às 08:22

    Fiz questão de deixar meus parabéns aqui! Jogou duro! rsrsrs

  • Cairo Ramos

    28/10/2015 às 10:06

    Excelente artigo, explicativo e não tem enrolação…rsrs…, continue colocando mais posts…

  • Garnizé

    02/11/2015 às 10:51

    xou de bolá o seu artigo, muito bom, me ajudou muuuuito, valeu camarada.

  • Diogo Matheus

    02/11/2015 às 20:35

    Pessoal,
    Obrigado pelos comentários, infelizmente não tenho como ajudar em todos os casos mas irei adicionar novos artigos sobre PHP.

  • Marcus

    09/01/2016 às 10:29

    Obrigado pela ajuda. simples e Didático.

  • Mauricio

    24/10/2016 às 06:18

    preciso de ajuda meu codigo é o seguinte:
    prepare(“SELECT * FROM adminstrador WHERE admistador_login=? AND admistador_senha=? AND admistador_nivel=’1′”);

    $logar->bindValue(1, $login,PDO::PARAM_STR);
    $logar->bindValue(2, $senha,PDO::PARAM_STR);
    $logar->execute();

    if ($logar->rowCount()==1) {
    return true;
    } else {
    return false;
    }

    }catch(PDOException $e){
    echo $e->getMessage();
    }

    }

    e o erro é erro

    ( ! ) Fatal error: Call to a member function prepare() on a non-object in C:\wamp\www\F\login.php on line 8
    Call Stack
    #TimeMemoryFunctionLocation
    10.0026136168{main}( )..\controller.php:0
    20.0303143968login( )..\controller.php:15

  • Mauricio

    24/10/2016 às 06:20

    eu não tenho nenhuma resposta, mas estou iniciando com programação web, e to precisando ai de ajuda para resolver esse erro… e se houver uma comunidade de programadores eu gostaria de ingressar…

  • José Miguel Arede Carvalho Silvestre

    22/11/2016 às 10:46

    Olá Bom dia!

    Tenho um projecto para fazer e tenho algumas dúvidas sobre o uso de crud e PDO.
    Para fazer o projecto com PDO tenho de realizar uma página class para cada tabela?
    Ou seja para cada tabela eu crio um ficheiro class-nomedatabela.php e dentro desse ficheiro passo as funções ou é possível ter funções genéricas para poder user por várias tabelas, tendo por exemplo o ficheiro class-crud.php e dentro dele ter funções que podem ser usadas a qualquer momento.

  • Thalysson

    26/12/2016 às 00:21

    É incrível a facildiade do PDO pra fazer CRUD. Obrigado pelo artigo, de longe, um dos melhores que já li.

  • Marcello Caetano

    09/01/2017 às 12:52

    Artigo muito bom.
    Parabéns!

  • Ricardo Kady Aoun

    29/01/2017 às 09:03

    Muito bom o seu artigo, parabéns e obrigado!
    Venho da escola antiga de PHP e tenho alguma dificuldade com POD, porém vc me ajudou a entender bastante coisa.

  • Claudia Andrade

    03/03/2017 às 23:43

    Muito bom seu artigo, aprendi muito… E estou aprendendo diariamente…
    Porém queria saber se consegue me ajudar. Me deparei com um SELECT de duas tabelas, e não estou conseguindo apresentar o resultado esperado, que seria os campos atraves da busca das duas tabelas.

    $sql = “SELECT a.idEnc, a.idCliente, a.encDtCad, a.idSitEnc, b.cadNome, b.cadSobreNome ”
    . ” FROM encomenda a JOIN cadastro b ”
    . ” ON a.idCliente=b.idCadastro ”
    . ” AND a.idSitEnc=”.$idSitEnc
    . ” AND a.encDtCad=”.$dataHoje
    . ” AND b.idCadastro=”.$idCadastro;

    Devo estar muito errada, mas me retorna erro de sintaxe.
    Conforme Abaixo.

    Fatal error: Uncaught exception ‘PDOException’ with message ‘SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near ”2017-03-03″ AND b.idCadastro=13′ at line 1’ in C:\xampp\htdocs\EncomendasPao\SiteAcesso\Encomenda\carregaClienteId.php:20 Stack trace: #0 C:\xampp\htdocs\EncomendasPao\SiteAcesso\Encomenda\carregaClienteId.php(20): PDO->query(‘SELECT a.idEnc,…’) #1 C:\xampp\htdocs\EncomendasPao\SiteAcesso\Encomenda\add.php(22): include(‘C:\\xampp\\htdocs…’) #2 {main} thrown in C:\xampp\htdocs\EncomendasPao\SiteAcesso\Encomenda\carregaClienteId.php on line 20

    Porém replicando o sql no banco mysql, me retorna os valores corretos.
    Será que pode me ajudar?

  • Miguel

    22/04/2017 às 19:42

    Nossa que post interessante!!..parabéns!

  • cleimar

    16/06/2017 às 15:54

    estou com esse erro nao consigo arrumar.
    Fatal error: Uncaught PDOException: SQLSTATE[HY093]: Invalid parameter number: parameter was not defined in C:\xampp\htdocs\cadastros\action_cliente2.php:112 Stack trace: #0 C:\xampp\htdocs\cadastros\action_cliente2.php(112): PDOStatement->execute() #1 {main} thrown in C:\xampp\htdocs\cadastros\action_cliente2.php on line 112

  • joao silva

    05/07/2017 às 11:20

    .òtimo post.
    eu sou iniciante em programação php e faço o uso do pdo. eu gostaria de saber como testar o fim de uma tabela mysql com PDO. Preciso fazer um relatorio com quebra e preciso saber como testar se o FIM da tabela foi alcançado.

    vai pro inicio da tabela
    enquanto nao for fim da tabela

    var_nome = campo_nome
    enquando campo_nome = var_nome e nao for fim da tabela

    var_acumulo =+ campo_valor

    fim-enquanto
    imprimi var_nome
    imprime var_acumulo
    var_acumulo = 0

    fim-do enquanto

  • Cristiano Soares

    11/08/2017 às 18:56

    Obrigado, foi muito útil essa explicação!!!

  • Cosme

    27/06/2018 às 16:49

    Muito bom, estou procurando um assim porém com a necessidade de ter uma aplicação conectando em vários bancos diferentes. Isso é possível do PHP e PDO? Daria um ótimo conteúdo. Obrigado!

  • Douglas Fernando Ferreira Braga

    13/09/2018 às 10:46

    Obrigado por seu conteúdo, só não entendi a diferença entre BindValue() para o BindParam, tem como colocar um exemplo para ficar mais claro ?

    Desde já agradeço.

  • Sandré Cardoso

    18/07/2019 às 01:30

    como instalo o PDO ou ele já vem com o wamp

Deixe uma resposta

O seu endereço de e-mail não será publicado.. Campos obrigatórios são marcados com *