2017-08-20 14 views
-1

この問題を解決する方法とこのコードで何が間違っていますか?私は質問をする前に頼まれましたが、私は問題com.mysql.jdbc.exception.jdbc4.MySQLNonTransientConnectionException:接続が閉じられた後に操作が許可されない

private void cb_categoriesPopupMenuWillBecomeVisible(javax.swing.event.PopupMenuEvent evt) {               
    cb_categories.removeAllItems(); 
    try { 
     String sql_c = "SELECT * FROM inventory.categories"; 
     cc.pst = cc.c.prepareStatement(sql_c); 
     cc.rs = cc.pst.executeQuery(); 
     while (cc.rs.next()) { 
      String c_name = cc.rs.getString("CategoryName"); 
      cb_categories.addItem(c_name); 

     } 
    } catch (Exception e) { 
     JOptionPane.showMessageDialog(null, e); 
    } finally { 
     try { 
      cc.rs.close(); 
      cc.pst.close(); 
     } catch (Exception e) { 

     } 
    } 
}   
+0

問題は何ですか?出力とあなたの希望の結果は何ですか? – Noob

+0

コンボボックスが見えるようになると、データベースからのリストが表示されます –

+0

あなたの質問は私にとってはっきりしないので、あなたの質問を編集してください! – Noob

答えて

1

あなたのResultSetやPreparedStatementを解決傾けることを知っている は、メソッドのスコープ内で宣言されていないので、私はあなたが他の場所でそれらを宣言したことを想定しなければなりません。

これは大きな間違いです。

StatementおよびResultSetをメソッドscopeに宣言する必要があります。

リソースをクローズしようとしましたが、個々のtry/catchブロックでラップする必要があります。あなたは閉鎖され、閉鎖されたものを危険にさらすことはできません。

あなたのコードについて批判していることが他にもあります(たとえば、SELECT *、UIとデータベースコードが1つのクラスにまとめられています)が、これで十分です。インターフェースと

スタート:

package persistence; 

import java.util.List; 

/** 
* Created by Michael 
* Creation date 8/20/2017. 
* @link https://stackoverflow.com/questions/45787151/com-mysql-jdbc-exception-jdbc4-mysqlnontransientconnectionexception-no-operatio/45787321?noredirect=1#comment78532554_45787321 
*/ 
public interface CategoryDao { 
    List<String> findAllCategories(); 
} 

が次に具体的な実装を記述します。

package database; 

import database.util.DatabaseUtils; 
import org.apache.commons.logging.Log; 
import org.apache.commons.logging.LogFactory; 

import javax.sql.DataSource; 
import java.sql.PreparedStatement; 
import java.sql.ResultSet; 
import java.sql.SQLException; 
import java.util.ArrayList; 
import java.util.List; 

/** 
* Created by Michael 
* Creation date 8/20/2017. 
* @link https://stackoverflow.com/questions/45787151/com-mysql-jdbc-exception-jdbc4-mysqlnontransientconnectionexception-no-operatio/45787321?noredirect=1#comment78532554_45787321 
*/ 
public class CategoryDaoImpl implements CategoryDao { 

    private static final Log LOGGER = LogFactory.getLog(CategoryDaoImpl.class); 
    private static String SELECT_CATEGORIES = "SELECT CategoryName from inventory.Categories "; 

    private DataSource dataSource; 

    public CategoryDaoImpl(DataSource dataSource) { 
     this.dataSource = dataSource; 
    } 

    @Override 
    public List<String> findAllCategories() { 
     List<String> categories = new ArrayList<>(); 
     PreparedStatement ps = null; 
     ResultSet rs = null; 
     try { 
      ps = this.dataSource.getConnection().prepareStatement(SELECT_CATEGORIES); 
      rs = ps.executeQuery(); 
      while (rs.next()) { 
       categories.add(rs.getString("CategoryName")); 
      } 
     } catch (SQLException e) { 
      LOGGER.error(String.format("Exception caught while selecting all category names"), e); 
     } finally { 
      DatabaseUtils.close(rs); 
      DatabaseUtils.close(ps); 
     } 
     return categories; 
    } 
} 

これは、あなたが側にオフのJUnitでテストすることができますものです。それを完全に実行してから、あなたのUIコードへの参照を与えてください。それは、UIとデータベースコードを別々に保つでしょう。このDAOは、SwingやWeb UIを気にすることなく、どのアプリケーションでも使用できます。

+1

+1また、接続のインスタンスである 'cc'が存在していますクローズされ、(コード共有の観点から)閉じた状態で再び再利用されます。 CollectionPoolingメカニズムを使用することをお勧めします。 –

+1

はい、接続は、独自に作成してテストする必要がある別のデータアクセスクラスに渡す必要があります。あなたのコントローラにそのインタフェースベースのクラスのインスタンスを与え、そのメソッドを呼び出します。 – duffymo

+0

あなたは私のためのコードを編集できますか? –

関連する問題