Trabalhos com uma classe de conexão a banco de dados chamada BD

Cordiais saudações.

Com a ajuda do meu colega Staroski (que fez umas modificações criando um objeto chamado instance) tenho uma classe BD que faz conexão com banco de dados empresa de MySQL.

Dentro dos programas que fazem uso de tabelas eu uso a classe BD para abrir conexão ou fechar.

Veja os comandos para abrir e para fechar, respectivamente:

abrir:
public ForDAO() {
bd = BD.getInstance();
fornecedor = new Fornecedores();
}

fechar:
BD.getInstance().close();

O comando para abrir conexão se encontra em todos os arquivos de classes DAO e o comando para fechar se encontra em todas classes de manipulação de cadastros e tabelas abertas pelo DAO.

No programa BD que é a classe onde está o método getInstance() e close() há uma verificação se existe uma conexão se não houver ao ser solicitada pelos DAO a classe BD é criada.

Gostaria de saber porque não posso fazer a referência difereta BD.close(), onde close() é o método de BD que fecha a conexão e torna nulo o objeto instance. Veja o programa BD abaixo:

package empresaiv;

import java.sql.*;

/**
 * @author Ronaldo R. Godoi, contibuição de Staroski
 */
public final class BD {
    
    private static final String DRIVER = "com.mysql.cj.jdbc.Driver";
    private static final String DBNAME = "empresa";
    private static final String URL = "jdbc:mysql://localhost:3306/" + DBNAME;
    private static final String LOGIN = "root";
    private static final String SENHA = "04latosensu10";
    
    /**
     * Única instância desta classe
     */
    private static BD instance;
    
    /**
     * Obtém a única instância desta classe
     */
    public static synchronized BD getInstance() {
        if (instance == null) {
            System.out.println("Criando objeto da classe BD");
            instance = new BD();
        }
        System.out.println("Retornando objeto existente da classe BD");
        return instance;
    }
    
    public final Connection connection;
    
    /**
     * Construtor privado
     */
    private BD() {
        try {
            Class.forName(DRIVER);
            connection = DriverManager.getConnection(URL, LOGIN, SENHA);
            System.out.println("Conectou! ");
        } catch (Throwable t) {
            throw new RuntimeException("Erro ao inicializar BD", t);
        }
    }

    /**
     * Fecha a conexão com o banco
     */
    public void close() {
        try {
            connection.close();
            instance = null;
            System.out.println("Desconectou...");
        } catch(Throwable t) {
            throw new RuntimeException("Erro ao fechar BD", t);
        }
    }
}

Eu gostaria de saber porque deve fazer a referência BD.getInstance().close(), se o método close pertence a BD. Não posso dizer simplesmente BD.close(). Porque?
Também gostaria de saber se o método que esta sendo executado quando chamo BD.getInstance().close() é realmente o método close da classe BD, e então é ele?

Atenciosamente,
Ronaldo

Usa essa classe
/*

  • To change this license header, choose License Headers in Project Properties.
  • To change this template file, choose Tools | Templates
  • and open the template in the editor.
    */
    package br.com.comissaovendas.controle.conexao;

import java.sql.*;

/**
*

  • @author DiegoFeitoza
    */
    public class Conexao_Local {
    public static String status = “”;

    public static Connection abrirConexao() {
    Connection con = null;
    try {
    Class.forName(“com.mysql.jdbc.Driver”).newInstance();
    String url = “jdbc:mysql://localhost:3306/progmanutencao?zeroDateTimeBehavior=convertToNull”;
    //String url = “jdbc:mysql://192.168.5.3:3306/progmanutencao?zeroDateTimeBehavior=convertToNull”;
    String usuario = “diego”;
    String senha = “SdjYcpDuk@2020”;
    con = DriverManager.getConnection(url, usuario, senha);
    //System.out.println(“Conexao com Banco de Dados estabelecida.”);
    } catch (SQLException erroSQL) {
    System.out.println("Erro na conexão com o Banco " + erroSQL.getMessage());
    } catch (ClassNotFoundException erroClass) {
    System.out.println("Erro ao carregar o Driver " + erroClass.getMessage());
    } catch (Exception e) {
    System.out.println("Ocoreru um erro: " + e.getMessage());
    }
    //VOCÊ ESQUECEU QUE RETORNAR A VARIÁVEL CONECTION AQUI (CORRIGIDO)
    return con;
    }
    /*
    public static Connection ObterConexao() {
    Connection con = null;
    try {
    Class.forName(“com.mysql.jdbc.Driver”).newInstance();
    String url = “jdbc:mysql://bolsonave.com.br:3306/bolso273_projet_fornecedores”;
    String usuario = “bolso273_spdiego”;
    String senha = “SdjYcpDuk@87”;
    con = DriverManager.getConnection(url, usuario, senha);
    status = “Conexao aberta!”;
    System.out.println(status);
    } catch (Exception e) {
    status = e.getMessage();
    System.out.println(status);
    }
    return con;
    }*/

    public static void fecharConexao(Connection con) {
    try {
    con.close();
    //System.out.println(“Conexao com o Banco de Dados fechada.”);
    } catch (SQLException erroSQL) {
    System.out.println("Erro na comunicação com o Banco " + erroSQL.getMessage());
    } catch (Exception e) {
    System.out.println("Ocorreu um erro: " + e.getMessage());
    }
    }

    public static void main(String[] args) {
    Connection con = null;
    con = Conexao_Local.abrirConexao();
    String sql = “SELECT * FROM df_usuario WHERE codusur = 1”;
    try {
    Statement st = con.createStatement();
    ResultSet rs = st.executeQuery(sql);
    if (rs.next()) {
    System.out.println(rs.getString(“login”));
    }
    } catch (Exception e) {
    System.out.println(e);
    } finally {
    Conexao_Local.fecharConexao(con);
    }
    }
    }

Tens de rever o conceito de métodos e variáveis static para entender isso facilmente.

O método close() não é static, é de instância, logo ele só pode ser chamado sobre uma instância e não diretamente na classe.

O getInstance funciona quase como um new só que está sempre a usar a mesma instância (vê sobre o pattern Singleton).

Assim, imagina que terias

   BD objeto = new Bd();
   //... faz algo
   objeto.close(); // E não BD.close()

Aqui é semelhante, mas tens

   BD objeto = BD.getInstance();
   //... faz algo
   objeto.close();
1 curtida

O método close() não é static, isso significa que ele só pode ser acessado a partir de um objeto da classe BD, neste caso o objeto é obtido através do método getInstance().

1 curtida