Java/SQL - executeUpdate() зависает и вызывает OutOfMemoryException

Я пытаюсь выполнить относительно простую вставку в свою таблицу, но метод executeUpdate() зависает до тех пор, пока программа не вылетает с OutOfMemoryException. Я успешно выполнял вставки в SQL Server Management Studio и переводил базу данных в автономный режим и обратно в оперативный режим, поэтому я не думаю, что таблица может быть заблокирована каким-либо образом. Я также распечатываю свои токены, и ни один из них не является нулевым.

Что-нибудь выглядит подозрительным в моем коде?

if(commandCode.equals("RV")){
    StringTokenizer tokens = new StringTokenizer(fullLine,"^");

    String itemCallNumber=null;
    String itemCurrentLocation=null;
    String itemFormat=null;
    String itemHomeLocation=null;
    String itemLibrary=null;
    String itemType=null;
    String itemCat1=null;
    String itemCat2=null;
    String itemCat3=null;
    Integer itemPubYear=null;
    String stationLibrary=null;
    String userProfileName=null;
    String userCat1=null;
    String userCat2=null;       
    String userZipCode=null;
    String userLibrary=null;
    java.sql.Date userBirthdate=null;
    String clientType = null;


    while(tokens.hasMoreTokens()){
        String token = tokens.nextToken();
        System.out.println(token);
        if(token.startsWith("UZ")){
            String dateString = token.substring(2);
            SimpleDateFormat format = new SimpleDateFormat("M/d/yyyy");
            Date date = format.parse(dateString);

            userBirthdate=new java.sql.Date(date.getTime());;
        }
        if(token.startsWith("PG")){
            userCat1=token.substring(2);
        }
        if(token.startsWith("PH")){
            userCat2=token.substring(2);
        }

        if(token.startsWith("PE")){
            userProfileName=token.substring(2);
        }

        if(token.startsWith("UM")){
            userLibrary=token.substring(2);
        }
        if(token.startsWith("UB")){
            userZipCode=token.substring(2);
        }

        if(token.startsWith("IQ")){
            itemCallNumber=token.substring(2);
        }
        if(token.startsWith("IL")){
            itemCurrentLocation=token.substring(2);
        }
        if(token.startsWith("IK")){
            itemFormat=token.substring(2);
        }
        if(token.startsWith("IN")){
            itemHomeLocation=token.substring(2);
        }
        if(token.startsWith("NS")){
            itemLibrary=token.substring(2);
        }
        if(token.startsWith("IG")){
            itemType=token.substring(2);
        }
        if(token.startsWith("NX")){
            itemCat1=token.substring(2);
        }
        if(token.startsWith("NY")){
            itemCat2=token.substring(2);
        }
        if(token.startsWith("0A")){
            itemCat3=token.substring(2);
        }
        if(token.startsWith("IF")){
            itemPubYear=Integer.parseInt(token.substring(2));
        }
        if(token.startsWith("FE")){
            stationLibrary=token.substring(2);
        }

        if(token.startsWith("dC")){
            clientType=token.substring(2);
        }

    }


    String insert = "INSERT INTO dbo.RenewItem Values(?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)";
    PreparedStatement insertPS = connection.prepareStatement(insert);

    //These come from earlier in the code and are verified to be correct
    insertPS.setInt(1, id);
    insertPS.setTimestamp(2, ts);

    insertPS.setString(3, itemCallNumber);
    insertPS.setString(4, itemCurrentLocation);
    insertPS.setString(5, itemFormat);
    insertPS.setString(6, itemHomeLocation);
    insertPS.setString(7, itemLibrary);
    insertPS.setString(8, itemType);
    insertPS.setString(9, itemCat1);
    insertPS.setString(10, itemCat2);
    insertPS.setString(11, itemCat3);
    insertPS.setInt(12, itemPubYear);
    insertPS.setString(13, stationLibrary);
    insertPS.setString(14, userProfileName);
    insertPS.setString(15,userCat1);
    insertPS.setString(16, userCat2);
    insertPS.setString(17, userZipCode);
    insertPS.setString(18, userLibrary);
    insertPS.setDate(19, userBirthdate);
    insertPS.setString(20,clientType);

    insertPS.executeUpdate();

EDIT: мне удалось значительно изолировать проблему. Это связано с окружающим SELECT * на большой таблице. В приведенном ниже коде selectPS.close() достигается, но метод никогда не возвращается.

        final Connection connection = DriverManager.getConnection(url);

        String select = "SELECT * FROM dbo.SirsiStat";
        PreparedStatement selectPS = connection.prepareStatement(select);
        ResultSet rs = selectPS.executeQuery();
        System.out.println("here");
        selectPS.close();

person James Harpe    schedule 29.01.2015    source источник
comment
Я не уверен, но я думаю, вам нужно указать столбцы, например dbo.RenewItem('col1','col2'.....,'col20')   -  person Titus    schedule 29.01.2015
comment
@Titus: это был бы недопустимый SQL. 'col1' — это символьный литерал, а не имя столбца (col1 — это имя столбца). Но я согласен, что это хороший стиль кодирования, чтобы явно перечислить имена столбцов для оператора insert.   -  person a_horse_with_no_name    schedule 29.01.2015


Ответы (1)


Прежде всего, вы должны распорядиться ресурсами JDBC, а во-вторых, попытаться изучить правильное использование или назначение PreparedStatement.

Используйте синтаксис попытки с ресурсом. Этот синтаксис гарантирует вызов метода close() даже после исключения.

try(Connection cn=DriverManager.getConnection(url,user,pass)) {
  //statements

   String sql = "insert into tableName (columnOne, columnTwo) values (?,?)";
   try(PreparedStatement ps = cn.prepareStatement(sql)) {

      while(tokens.hasMoreTokens()) {
         //statements
        ps.setInt(1,valueForColumn1);
        ps.setString(2,valueForColumn2);
      }
   }
}

Справочная ветка - Как правильно удалять объекты Connection, ResultSet и Statement в цикле while?

person kv-prajapati    schedule 29.01.2015
comment
Это не относится к моему вопросу. - person James Harpe; 29.01.2015
comment
Я думаю, что неправильно прочитал ваш ответ. Я извиняюсь. Я удалю свой отрицательный голос, когда смогу. Пожалуйста, взгляните на мое редактирование. - person James Harpe; 29.01.2015
comment
@JamesHarpe Я думаю, проблема связана с API драйвера. - person kv-prajapati; 30.01.2015