Ir para conteúdo

POWERED BY:

Arquivado

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

Marcelo Diniz

POO - Iniciante

Recommended Posts

Pessoa, antes de mais nada Boa tarde.

 

Estou começando agora a mudar a minha visão de programação, estou querendo e vou conseguir entrar nesse mundo de POO, mas estou iniciando agora com isso, sempre programei na forma proceidural.

 

Vamos la. Tenho uma classe de conexão ao banco de dados.

 

para chamar ela faço assim

$conn = new clsMysql();
$conn->open();//abre a conexão e seleciona a base de dados a ser utilizada.
$conn->query("SELECT * FROM TABELA");
$conn->close();

até ai legal.

 

agora eu tenho uma outra classe de autenticação do usuário onde faço uma query nessa classe, mas gostaria de usar a clsMysql nessa outra classe, como posso fazer isso?

 

Valew

Compartilhar este post


Link para o post
Compartilhar em outros sites

Você deve fazer herança de classes.

Por exemplo:

Tenho uma classe chamada Calculo.

class calculo{ 
function soma($a=null,$b=null){  
$somar=$a+$b;  
return $somar; }
}
class subtrair extends calculo{  
function subtrai($a,$B){ 
 $sub=$a-$b; 
 $somar=$this->soma(2,$sub); 
 return $somar;  }
}
Note que na classe subtrair eu usei a instrução extends que faz com que eu ligue a classe subtrair na classe soma. Isso me possibilita usar todas as funções publicas da classe soma dentro da classe subtrair.

Pesquise sobre metodos ´public, private e protected para ter mais respaldo disso.

Espero ter ajudado.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Marcelo Diniz, seja bem vindo ao mundo de POO. Para uma melhor participação no fórum de PHP, sugiro que leia o tópico de orientações para uma boa participação.

 

Sobre a sua dúvida, eu sugiro que você leia um pouco sobre design patterns, em especial ao padrão singleton.

 

Não utilize herança neste caso. Na classe que faz a autenticação, apenas faça a criação de uma instância da classe clsMysql dentro da classe de autenticação.

 

Carlos Eduardo

Compartilhar este post


Link para o post
Compartilhar em outros sites

Entendi,

 

vamos la.

 

 

//mysql.class.php

<?php
class clsMysql {
    var $dbi;
    var $query;
	
    function open() {
        $this->dbi = mysql_connect('host', 'user', 'pwd');
        if (!$this->dbi) {
            echo "Erro na conexão!";
        }
        if (!mysql_select_db(DB_BASE, $this->dbi)) {
            echo "Erro na seleção do banco de dados!";
        }
    }	
	
    function close() {
        mysql_close($this->dbi);
    }

    function query($sql) {
        $this->query = mysql_query($sql, $this->dbi);
        return $this->query;
    }

    function linhas() {
        return mysql_num_rows($this->query);
    }
?>

 

 

valida.class.php

<?php
require_once("mysql.class.php");

class Login extends clsMysql{

	function ValidaLogin($User,$Pwd) {
		$strSQL= "Select id, nome, pwd, login from usuarios where login = '".$User."' AND  pwd = '".$Pwd."'";
		$this->open();
		$resultado = $this->query($strSQL);
		
		if ($this->linhas($resultado) > 0) {
			while ($rs= $this->farray($resultado)) {
				return $rs['id'];
			}
			return $nOk = 0;
		} else {
			return -1;
		}
	}
}
?>

acho que é isso, mas não funciona

 

olah os erros que estão dando

 

Warning: mysql_num_rows(): supplied argument is not a valid MySQL result resource in...on line 44

Warning: session_destroy() [function.session-destroy]: Trying to destroy uninitialized session in...on line 18

Warning: Cannot modify header information - headers already sent by (output started at...on line 19

Compartilhar este post


Link para o post
Compartilhar em outros sites

pode ser que sua query não esteja executando devido algum erro na instrução SQL..pode ser que valores passados nas variaveis da função estão sendo passados vazios...

Compartilhar este post


Link para o post
Compartilhar em outros sites

Mário, a query esta rodando ok, já imprimi ela na tela e os valores tbm estão ok, quanto a isso tenho certeza que não é, infelizmente, pois se fosse seria mais simples, beeemmmmm mais simples....

E Fabyo, valew pela dica, mas infelizmente tbm não mudou em nada....

 

Mas valew, se souberem de algo será bem vindo.....

Compartilhar este post


Link para o post
Compartilhar em outros sites

Vamos lá...

- Não utilize var, utilize public, private ou protected - http://br.php.net/manual/pt_BR/language.oop5.visibility.php

- Utilize mysqli - http://br.php.net/mysqli

- Não utilize herança neste caso (não é a causa do problema, mas não é o correto). Faça assim:

<?php
require_once("mysql.class.php");

class Login{

        function ValidaLogin($User,$Pwd) {
        		
        		
                $strSQL= "Select id, nome, pwd, login from usuarios where login = '".$User."' AND  pwd = '".$Pwd."'";
                $mysql = new clsMysql();
                $mysql->open();
                $resultado = $mysql->query($strSQL);
                
                if ($mysql->linhas($resultado) > 0) {
                        while ($rs= $this->farray($resultado)) {
                                return $rs['id'];
                        }
                        return $nOk = 0;
                } else {
                        return -1;
                }
        }
}
?>

Mais ou menos por aí. Não corrigi toda a sua classe, foi só para dar uma idéia.

 

Carlos Eduardo

Compartilhar este post


Link para o post
Compartilhar em outros sites

Onde está a parte que executa o mysql_num_rows?

 

Vamos lá...

- Não utilize var, utilize public, private ou protected - http://br.php.net/manual/pt_BR/language.oop5.visibility.php

- Utilize mysqli - http://br.php.net/mysqli

- Não utilize herança neste caso (não é a causa do problema, mas não é o correto). Faça assim:

 

Mais ou menos por aí. Não corrigi toda a sua classe, foi só para dar uma idéia.

 

Carlos Eduardo

 

Carlos, só para agregar no meu conhecimento, por que usar herança nesse casso não é correto?

Compartilhar este post


Link para o post
Compartilhar em outros sites

hehe concordo com que o fabyo flw..

 

usa mysqli

isso quanto a classe de conexao ... claro dai da pra faze uma classe de login e uma de autencificacao .. ^^ como preferir

mass acho que voce vai caba dexando autentificacao como metodo da classe login assim so existindo uma nao havera nessesidade de heranças e talz .. mas caso tenha algum problema semelhante mais tarde seria interessante (eu acho :P tambem to estudando isso.. ainda nao posso afirma) usa abstract e interface =] defini a visibilidade de acordo com o foco do metodo e dexa eles mais genericos pra pode implementa depois em ambas saka ^^

 

valwww

Compartilhar este post


Link para o post
Compartilhar em outros sites

Matias, estou tentando algo aqui e não sai do erro.

 

Mário, a parte do num_rows é essa

    function linhas() {
        return mysql_num_rows($this->query);
    }

os outros erros já vi que podem esquecer, pois tem a ver com a outra parte que depende disso para rodar, então vai ficar dando erro mesmo...

 

Não se mais o que fazer......

 

e vcs falaram para usar mysqli ao invés de mysql

 

seria só alterar todos os mysql_alguma_coisa por mysqli_alguma_coisa? Mas não é isso que esta ferrando o código é?

 

valew

Compartilhar este post


Link para o post
Compartilhar em outros sites

A herança deve ser utilizada quando a classe filha (que vai herdar) vai especializar a classe pai. Não é o caso, já que a classe Login (que não é a forma correta) não especializa a classe Mysql, apenas utiliza-a em um de seus métodos. O correto seria ter uma classe Usuario, que faria todas as manipulações com usuários.

 

Carlos Eduardo

Compartilhar este post


Link para o post
Compartilhar em outros sites

Finalmente funcionou, e exatamente da forma que o Matias falou.

 

Agora me diga uma coisa Matias.

 

Na function ValidaLogin eu instancio a classe, legal, funcionou, agora se eu tiver outra function dentro da classe Login tenho que instanciar a classe clsMysql novamente ou tem outro meio de fazer?

 

exemplo

 


<?php
require_once("mysql.class.php");

class Login{

        function ValidaLogin($User,$Pwd) {
                $strSQL= "Select id, nome, pwd, login from usuarios where login = '".$User."' AND  pwd = '".$Pwd."'";
                $mysql = new clsMysql();
                $mysql->open();
                $resultado = $mysql->query($strSQL);
                
                if ($mysql->linhas($resultado) > 0) {
                        while ($rs= $this->farray($resultado)) {
                                return $rs['id'];
                        }
                        return $nOk = 0;
                } else {
                        return -1;
                }
        }

	function InitSession($id) {
		session_start();
		$strSQL= "select * from tab_usuarios where cd_usuario= ".$id;
                $mysql = new clsMysql();
                $mysql->open();
                $resultado = $mysql->query($strSQL);
                $rs = farray($resultado);
		$_SESSION['logado']= TRUE;
		$_SESSION['login']= $rs['NM_LOGIN'];
		$_SESSION['nome']= ucwords(strtolower($rs['NM_USUARIO']));
		$_SESSION['usr_ip']= $_SERVER['REMOTE_ADDR'];
		
	}
}
?>

Compartilhar este post


Link para o post
Compartilhar em outros sites

É assim mesmo, mas para evitar abrir duas conexões com o banco de dados, você utiliza singleton na classe Mysql. Tem uma classe do Fabyo muito boa.

 

http://forum.imasters.com.br/index.php?/topic/353635-classe-mysqli-mais-uma/

 

Usa mysqli.

 

Carlos Eduardo

Compartilhar este post


Link para o post
Compartilhar em outros sites

você utiliza singleton na classe Mysql.

Especificamente no caso de banco de dados, não é correto usar Singleton.

 

Você usa Singleton quando estiver trabalhando com DOM por exemplo, onde deverá existir de fato apenas 1, com banco de dados poderá existir situações onde você precisará usar duas ou mais conexões com servidores de banco de dados diferentes e, nessa situação, ter mais que 1 Singleton é POG.

 

Usando Registry ficaria assim:

 

Em algum lugar da sua aplicação você cria o registro:

//...
Registry::register( 'pdo' , new PDO( 'mysql:host=127.0.0.1;dbname=nomedobanco' , 'usuario' , 'senha' ) );
//...

 

Login.php

class Login {
private $pdo;

public function setPDO( PDO $pdo ){
	$this->pdo =& $pdo;
}

public function validaLogin( &$user , &$pswd ){
	if ( $this->pdo ){
		$ret	= false;
		$stmt	= $this->pdo->prepare( 'SELECT `id` FROM `usuarios` WHERE `login`=:user AND `pwd`=:pswd' );
		$stmt->bindParam( ':user' , $user , PDO::PARAM_STR );
		$stmt->bindParam( ':pswd' , $pswd , PDO::PARAM_STR );

		if ( $stmt->execute() ){
			if ( ( $obj = $stmt->fetch( PDO::FETCH_OBJ ) ) !== false )
				$ret =& $obj->id;
		}

		return $ret;
	} else throw new RuntimeException( 'Instância de PDO não definida' );
}
}

 

Ai, quando você precisar:

 

$login = new Login();
$login->setPDO( Registry::get( 'pdo' ) );

if ( ( $id = $login->validaLogin( $_POST[ 'user' ] , $_POST[ 'senha' ] ) ) !== false ){
echo 'Login aceito';
} else {
echo 'Acesso negado';
}

 

Exemplo de Registry: http://joaobatistaneto.com.br/source/Registry.php

Compartilhar este post


Link para o post
Compartilhar em outros sites

A questão do Singleton é a forma que ele é escrito, se você escrever uma aplicação pensando nos seus objetos de banco de dados como Singleton você pode vir a ter problemas no futuro.

 

O Registry é, vamos dizer, uma extensão de Singleton, ele faz um mapeamento das instâncias permitindo que você possa localizar uma instância de um objeto conhecido e dessa forma recuperá-lo.

 

Basicamente Registry é um Map:

 

class Map {
	private $storage = array();

	public function __get( $name ){
		if ( isset( $this->storage[ $name ] ) )
			return $this->storage[ $name ];
		else throw new UnexpectedValueException( sprintf( 'Undefined map: "%s"' , $name ) );
	}

	public function __isset( $name ){
		return isset( $this->storage[ $name ] );
	}

	public function __set( $name , $value ){
		$this->storage[ $name ] =& $value;
	}

	public function __unset( $name ){
		unset( $this->storage[ $name ] );
	}
}

 

Um Map é um objeto onde se guarda dados para serem recuperados posteriormente, e só pode existir uma instância daquele registro:

 

$conexoes = new Map();
$conexoes->mysql = new PDO( 'mysql:host=127.0.0.1;dbname=nomedobanco' , 'usuario' , 'senha' );
$conexoes->sqlserver = new PDO( 'mssql:host=sqlserver;dbname=database' , 'usuario' , 'senha' );

 

A vantagem no uso do Registry para banco de dados é justamente não engessar a aplicação, por exemplo:

class MySQLSingleton extends PDO {
	private static $pdo;

	final public function __construct( $host , $dbname , $user , $pswd ){
		if ( self::$pdo instanceOf PDO ) throw new LogicException( 'There can be only one' );
		else {
			parent::__construct( sprintf( 'mysql:host=%s;dbname=%s' , $host , $dbname ) , $user , $pswd );
			self::$pdo = $this;
		}
	}
}

 

Se amanhã sua aplicação precisar conectar com outro servidor ou outro banco de dados você terá um problema já que a construção da classe de conexão é engessada.

 

Com o Registry você ainda terá uma única instância e esse objeto que está registrado será visível de forma global, porém, sem ter que construir a classe engessada.

 

abstract class Registry {
	private static $map = array();

	public static function &get( $key ){
		if ( isset( self::$map[ $key ] ) ) return self::$map[ $key ];
		else throw new RuntimeException( 'Registro não encontrado' );
	}

	public static function isRegistered( $key ){
		return isset( self::$map[ $key ] );
	}

	public static function register( $key , &$value ){
		self::$map[ $key ] =& $value;
	}

	public static function unregister( $key ){
		if ( isset( self::$map[ $key ] ) ) unset( self::$map[ $key ] );
		else throw new RuntimeException( 'Registro não encontrado' );
	}
}

 

//Registro do banco de dados de origem
Registry::register( 'dbo' , new PDO( 'mysql:host=127.0.0.2;dbname=bancoantigo' , 'usuario' , 'senha' ) );

//Registro do banco de dados de destino
Registry::register( 'dbd' , new PDO( 'mysql:host=127.0.0.1;dbname=novobanco' , 'usuario' , 'senha' ) );

$migration = new MigrationFacade();
$migration->migrateApplicationData();

 

 

;)

Compartilhar este post


Link para o post
Compartilhar em outros sites

Caras, sinceramente, consegui como disse, de uma forma, imagino eu que você diriam, "um tanto quanto porca", mas esta funcionando.

Eu provavelmente vou ver de usar a classe mysqli, mas gostaria de uma dica, tenho que acessar 3 bases de dados no mysql diferentes, qual a melhor forma para eu estar fazendo, sendo que em uma classe chamo uma base, na outra chamo outra base, e por ai vai.

 

Eu faria mais ou menos assim, quando eu for instanciar a classe para conectar.

 

no arquivo que precisar usar a db01

$mysqli = new mysqli("localhost", "my_user", "my_password", "db01");

 

no arquivo que precisar usar a db02

$mysqli = new mysqli("localhost", "my_user", "my_password", "db02");

estou certo fazendo assim?

 

É, acho que estou um pouco perdido ainda, até normal para quem esta tentando sair da forma procedural para a forma POO.

 

Mas já vi uma coisa, que aqui posso contar com a ajuda de muitos mesmo.

 

Obrigado

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.