2011-09-02 8 views
8

que tienen este procedimiento en la base de datos:¿Por qué me aparece un error que informa que "no se esperaba un resultado" al ejecutar procedimientos almacenados en PostgreSQL desde Java en un lote?

CREATE OR REPLACE FUNCTION replacePageRelevance(id INT, value REAL) RETURNS VOID AS $$ 
BEGIN 
INSERT INTO pageRelevance VALUES (id,value); 
EXCEPTION WHEN unique_violation THEN 
    UPDATE pageRelevance SET relevance = value WHERE pageId = id;  
END 
$$ 
LANGUAGE plpgsql; 

Y este código que llama a esta función:

private final String PAGE_RELEVANCE_SQL = "SELECT replacePageRelevance(?,?::REAL)"; 
try (CallableStatement cstm = conn.prepareCall(PAGE_RELEVANCE_SQL)) { 
     for (Map.Entry<Integer, Double> entry : weightMap.entrySet()) { 
      cstm.setInt(1, entry.getKey()); 
      cstm.setDouble(2, entry.getValue()); 
      cstm.addBatch(); 
     } 
     cstm.executeBatch(); 
    } catch (SQLException e) { 
     LOGGER.error("Error discovering pages relevance: " + e.getNextException()); 
    } 
} 

Cuando ejecuto el lote, los valores se insertan o sustituyen en la tabla, pero después de eso, estoy recibiendo una excepción informando que A result was returned when none was expected.

No sé qué está mal, si la forma en que llamo al procedimiento o al procedimiento en sí. ¿Cuál puede ser el problema y cómo resolverlo?

Llamar a un procedimiento con SELECT es la forma correcta/única?

Respuesta

6

Por lo que puedo decir que está usando SELECT cuando se debe usar call.

Un ejemplo de la PostgreSQL documentation on the JDBC interface:

// Turn transactions off. 
con.setAutoCommit(false); 
// Procedure call. 
CallableStatement upperProc = con.prepareCall("{ ? = call upper(?) }"); 
upperProc.registerOutParameter(1, Types.VARCHAR); 
upperProc.setString(2, "lowercase to uppercase"); 
upperProc.execute(); 
String upperCased = upperProc.getString(1); 
upperProc.close(); 

Tenga en cuenta que la sintaxis ? = call para que el resultado no es necesaria en su caso - que tendrá que usar solo call replacePageRelevance(?,?::REAL)

La razón de que esta sintaxis difiere de la real PostgreSQL es porque esto es parte de JDBC specification.

+1

'CALL' no funciona en PostgreSQL. –

+0

@Renato - ¿Has probado? http://www.postgresql.org/docs/7.4/static/jdbc-callproc.html (could not find docs for 9.0) –

+0

Intenté solo con una llamada en lugar de SELECT. Estoy intentando con este ejemplo, pero mi función devuelve VOID. –

Cuestiones relacionadas