could not read column value from result set in Hibernate Native Query - java

SELECT
CONCAT(CREG.FIRSTNAME, ' ', CREG.LASTNAME) AS NAME,
CASE WHEN CR.CAMPAIGNTYPE = 'NPS'
THEN NPSSCORE
ELSE CSATSCORE END AS SCORE,
IFNULL(cast(CC.TEXT AS CHAR(255)), '') AS COMMENTS,
CREG.ID AS CLIENTID,
CR.ID AS CAMPAIGNRESPONSEID,
CI.ID AS ISSUEID
FROM CUSTOMER_ISSUES CI INNER JOIN (SELECT DISTINCT ISSUEID
FROM ISSUE_DEPARTMENT_MAPPING
WHERE CUSTOMERUSERID = 91 AND ISSUE_STATUS = 'New') IDM
ON CAST(CI.FEEDBACK_DATE AS DATE) BETWEEN '2016-06-05' AND '2016-06-11' AND IDM.ISSUEID = CI.ID
INNER JOIN CAMPAIGN_RESPONSE CR ON CR.ID = CI.CAMPAIGN_RESPONSE_ID
INNER JOIN CLIENT_REGISTRATION CREG ON CREG.ID = CR.RESPONSECUSTOMERID
LEFT OUTER JOIN CAMPAIGN_COMMENTS CC ON CC.CAMPAIGN_RESPONSE_ID = CR.ID;
The above query is running in the mysql-console properly ,but when I am integrating with the Hibernate,following error is thrown by Hibernate.
[BigIntegerType] could not read column value from result set: ID; Column 'ID' not found.

Try getting rid of the alias names in your SQL query.
Basically what happens here is when you run
SELECT
CONCAT(CREG.FIRSTNAME, ' ', CREG.LASTNAME) AS NAME,
CASE WHEN CR.CAMPAIGNTYPE = 'NPS'
THEN NPSSCORE
ELSE CSATSCORE END AS SCORE,
IFNULL(cast(CC.TEXT AS CHAR(255)), '') AS COMMENTS,
CREG.ID AS CLIENTID,
CR.ID AS CAMPAIGNRESPONSEID,
CI.ID AS ISSUEID
in JDBC it returns the column as CREG.ID instead of ClientID.
So try running the query without the aliases, typically, there is a problem in JDBC with this. If you still insist on using aliases,add the following entry to JDBC URL in configuration file
[useOldAliasMetadataBehavior=true]

Related

Java: Problems while setting an array as parameter name in DB2 SQL query

DB2 Driver version: 4.19.66
DB2 installed version: DB2 v11.5.7.0
Java version: 1.8_121
I'm trying to set a parameter on a DB2 SQL query:
SELECT distinct object_id AS oid
FROM myschema.package p
INNER JOIN myschema.package_item pi ON p.machine_id = pi.machine_id
AND p.package_id = pi.package_id
INNER JOIN main_schema.item i ON i.item_id = pi.id_articulo
WHERE p.package_status_id = 5 AND p.machine_id IN (:machineIdsParam)
I must say that p.machine_id is an INTEGER field in the DB2 database.
I prepare the connection like this:
Properties properties = new Properties(); // Create Properties object
properties.put("user", config.getDbUser()); // Set user ID for connection
properties.put("password", bdPassword); // Set password for connection
properties.put("enableNamedParameterMarkers", 1);
connection = (DB2Connection) DriverManager.getConnection(config.getDbUrl(), properties);
And then I try to set the parameter on this query:
DB2PreparedStatement ps = connection.getPreparedStatement(sqlString);
List<Integer> machineIds = Array.asList(new Integer[] { 1, 5, 7, 9});
Array machineIdArray = connection.createArrayOf("INTEGER", machineIds.toArray(new Integer[idInstalaciones.length]));
ps.setJccArrayAtName("machineIdsParam", machineIdArray);
But I'm getting this error:
com.ibm.db2.jcc.am.SqlSyntaxErrorException: [jcc][1091][10417][4.19.66] Invalid data conversion: Parameter instance com.ibm.db2.jcc.am.o#36fc695d is invalid for the requested conversion.
I couldn't find an example on how to use this setJccArrayAtName(), only documentation where I'm unable to find the cause of this error. I'm only guessing that it has something to do with the data type but I don't know how to make this work.
For Db2 for LUW:
... IN
(
SELECT TOK
FROM XMLTABLE
(
'for $id in tokenize($s, ",") return <i>{string($id)}</i>'
PASSING CAST (:machineIdsParam AS VARCHAR (100)) AS "s"
COLUMNS
TOK INT PATH '.'
)
)
You pass a string like '1,2,3' for the :machineIdsParam parameter. That is: int values separated by comma.
I don't believe any family of Db2 supports arrays with the IN predicate..
What's normally needed is separate parameters
SELECT distinct object_id AS oid
FROM myschema.package p
INNER JOIN myschema.package_item pi ON p.machine_id = pi.machine_id
AND p.package_id = pi.package_id
INNER JOIN main_schema.item i ON i.item_id = pi.id_articulo
WHERE p.package_status_id = 5 AND p.machine_id IN (:machineId1
,:machineId2
,:machineId3
,:machineId4
)
That of course requires you to know how many values you'll need ahead of time, or at least some maximum number. (You can always load the last value in any remaining parameters.)
The other option is to pass a delimited string that get's split out into individual values. Something like so (assuming a comma separated list)
SELECT distinct object_id AS oid
FROM myschema.package p
INNER JOIN myschema.package_item pi ON p.machine_id = pi.machine_id
AND p.package_id = pi.package_id
INNER JOIN main_schema.item i ON i.item_id = pi.id_articulo
WHERE p.package_status_id = 5 AND p.machine_id IN (select int(element)
from table (systools.split(:machineIds, ' '))
)
systools.split() may be specific to Db2 for IBM i, other platforms may have it in a different schema.
If nothing else, you can write your own User Defined Function (UDF) to do the split.

Incorrect Syntax near WHERE error in generated SQL

I am generating the below SQL. From my code I am using a where condition list to collect all the Where logic and insert it after the Join logic is set-up. However, I am getting a very generic syntax error and I can't figure out why. I am pretty sure the logic is properly organized however, when inserting the where statement it throws the syntax error
Incorrect Syntax near WHERE
The {h-schema} are just generated database and table names.
The code:
SELECT count(*) AS ID
FROM (
SELECT 'PREAPPROVAL' AS type, pa.id AS id FROM {h-schema}preapproval AS pa
LEFT JOIN {h-schema}risk_limit AS lim ON pa.limit_id = lim.id
LEFT JOIN {h-schema}desk AS d ON lim.desk_enterprise_id = d.enterprise_id AND CAST(pa.creation_date_time AS date) BETWEEN d.start_date AND d.end_date
WHERE pa.status = 'APPROVED' AND pd.end_date = NULL <-------------------------SYNTAX ERR HERE
OR pa.status = 'DECLINED' AND pa.completion_date_time > '2021-01-28 13:02:13'
OR pa.status = 'IN_PROGRESS'
OR pa.creation_date_time > '2021-01-28 13:02:13'
AND COALESCE(lim.policy_enterprise_id, d.policy_enterprise_id) IN (6)
UNION
SELECT 'BREACH' AS type, br.id AS id FROM {h-schema}breach AS br
LEFT JOIN {h-schema}risk_limit AS lim ON br.limit_id = lim.id
LEFT JOIN {h-schema}desk AS d ON lim.desk_enterprise_id = d.enterprise_id
AND br.reporting_date BETWEEN d.start_date AND d.end_date
LEFT JOIN {h-schema}valid_breach_recommendation AS vbr_approve ON vbr_approve.id = (SELECT TOP(1) id FROM {h-schema}valid_breach_recommendation
WHERE breach_id = br.id AND outcome = 'APPROVE'
ORDER BY creation_date_time DESC, id DESC)
LEFT JOIN {h-schema}valid_breach_decision AS vbd
ON vbd.id = (SELECT TOP(1) id FROM {h-schema}valid_breach_decision
WHERE breach_id = br.id
ORDER BY creation_date_time DESC, id DESC)
LEFT JOIN {h-schema}breach AS child_br ON br.id = child_br.parent_breach_id
WHERE br.status = 'APPROVED' AND vbd.end_date = NULL <--------------------SYNTAX ERR HERE
OR br.status = 'DECLINED' AND br.completion_date_time > '2021-01-28 13:02:14'
OR br.status = 'IN_PROGRESS'
OR br.creation_date_time > '2021-01-28 13:02:14'
AND child_br.id IS NULL
AND CASE br.status
WHEN 'IN_PROGRESS' THEN vbr_approve.start_date
WHEN 'APPROVED' THEN vbd.start_date
WHEN 'CANCELLED' THEN vbd.start_date
ELSE NULL
END IS NOT NULL AND COALESCE(lim.policy_enterprise_id, d.policy_enterprise_id) IN (6)
) AS issue
This is actually version issue. In latest version of SQL support like
create procedure sp_name
(
#name varchar(50) NULL
)
...
But the older version of SQL doesn't support with this way. For older version we need to provide '=NULL'
There is some syntax error due to {h-schema}, remove {h-schema} and your code has no syntax error. Remove {h-schema} and your code works fine.

Getting "SQL command not properly ended" error

Why i am getting below error while running this query in eclipse?
java.sql.SQLException: ORA-00933: SQL command not properly ended
Code:
String policy = "select p.policy_id,i.insurance_type,c.reason,i.insured_amount,i.max_claim_amount,c.claim_status from claim as c join policy as p on c.policy_id=p.policy_id join insurance as i on p.insurance_id=i.insurance_id where c.user_id=?";
PreparedStatement policyst = con.prepareStatement(policy);
policyst.setString(1, userId);
ResultSet policyrs = policyst.executeQuery();
Oracle does not support as for table aliasing; you should remove them:
SELECT p.policy_id,
i.insurance_type,
c.reason,
i.insured_amount,
i.max_claim_amount,
c.claim_status
FROM claim c
JOIN policy p ON c.policy_id = p.policy_id
JOIN insurance i ON p.insurance_id = i.insurance_id
WHERE c.user_id = ?
Remove word "AS" from your statement

Error when changing datatype of column in SQL Server DB - Java

I made a query in Java which changes one column's datatype in another. It works fine until it tries to change type. It finds all columns in DB with specified datatype, but cannt change it.
Here is my code:
st = conn.createStatement();
rs = st.executeQuery("SELECT a.name as ColName, o.name AS TableName"
+ "FROM sys.syscolumns AS a"
+ "INNER JOIN sys.systypes AS b ON a.xtype = b.xtype AND b.name = 'char' AND a.length = 255"
+ "INNER JOIN sys.objects AS o ON a.id = o.object_id WHERE (o.type = 'u') AND (o.schema_id = 1)");
ResultSet rsPom;
while (rs.next()){
String tName=rs.getString("TableName");
String cName=rs.getString("ColName");
System.out.println(tName+" "+cName);
rsPom=st.executeQuery("ALTER TABLE "+ tName+" ALTER COLUMN "+cName+" nvarchar(255)");
}
And here is my Exception:
com.microsoft.sqlserver.jdbc.SQLServerException: The object 'CK_TimeInstant_frame_default' is dependent on column 'frame'.
at com.microsoft.sqlserver.jdbc.SQLServerException.makeFromDatabaseError(SQLServerException.java:216)
at com.microsoft.sqlserver.jdbc.SQLServerStatement.getNextResult(SQLServerStatement.java:1515)
at com.microsoft.sqlserver.jdbc.SQLServerStatement.doExecuteStatement(SQLServerStatement.java:792)
at com.microsoft.sqlserver.jdbc.SQLServerStatement$StmtExecCmd.doExecute(SQLServerStatement.java:689)
at com.microsoft.sqlserver.jdbc.TDSCommand.execute(IOBuffer.java:5696)
at com.microsoft.sqlserver.jdbc.SQLServerConnection.executeCommand(SQLServerConnection.java:1715)
at com.microsoft.sqlserver.jdbc.SQLServerStatement.executeCommand(SQLServerStatement.java:180)
at com.microsoft.sqlserver.jdbc.SQLServerStatement.executeStatement(SQLServerStatement.java:155)
at com.microsoft.sqlserver.jdbc.SQLServerStatement.executeQuery(SQLServerStatement.java:616)
at DataTypeChanger.changeDataType(DataTypeChanger.java:50)
at DataTypeChanger.main(DataTypeChanger.java:36)
Does anyone knows what is all about, and what can I do?
Firstly, my apologies about the sarky comment above.
The reason you receive this error is because your alter script isn't taking any action with respect to constraints. Columns which are the target of constraints (Unique, Foreign Key, Default, etc) can't be modified unless the constraint is first dropped. In which case you'll probably need to add the constraints back afterwards.
I've assumed your earlier (deleted) comment still holds, viz that you do not require to create the constraints again after they have been dropped.
Re : How do I drop all constraints
Disclaimer : Back up your database before you try this, but the following MIGHT work. It is a destructive one way operation.
declare #sql nvarchar(2000);
while(exists(select 1 from sys.objects WHERE type_desc LIKE '%CONSTRAINT%'))
begin
BEGIN TRY
SELECT TOP 1 #sql=('ALTER TABLE ' + SCHEMA_NAME(schema_id) + '.[' + OBJECT_NAME(parent_object_id)
+ '] DROP CONSTRAINT [' + OBJECT_NAME(OBJECT_ID) + ']')
FROM sys.objects
WHERE type_desc LIKE '%CONSTRAINT%'
ORDER BY NEWID();
exec (#sql);
END TRY
BEGIN CATCH
END CATCH
end;
GO
Rationale: The TRY CATCH is required because there is no guarantee that we will get the order of dependencies correct when dropping constraints (e.g. FK dependent on PK), so we basically squash the error and try drop another random constraint (ORDER BY NEWID())
Reference : Based on this query here, but extended to all constraints
SqlFiddle Here

OpenJPA: how to construct a GROUP BY query with a group count

In JPQL I want to construct the equivalent query to this:
select *, count(*) as finger_count from page_delta_summary
where delta_history_id = ? and change_type = ? group by fingerprint;
where fingerprint is a varchar field in table page_delta_summary. What I have is this:
select d, count(d) as finger_count from PageDeltaSummary d
where d.deltaHistoryId = :deltaHistoryId and d.type = :pageDeltaType
GROUP BY d.fingerprint"
where PageDeltaSummary is my entity. But I'm getting the following exception:
org.apache.openjpa.persistence.ArgumentException: Your query on type "class com.su3analytics.sitedelta.model.PageDeltaSummary" with filter "select d, count(d) from PageDeltaSummary d where d.deltaHistoryId = :deltaHistoryId and d.type = :pageDeltaType GROUP BY d.fingerprint" is invalid. Your select and having clauses must only include aggregates or values that also appear in your grouping clause.
The query works fine if I remove either count(d) as finger_count or the GROUP BY.
Any suggestions?
Thanks
Your original SQL query doesn't make sense, therefore you can't convert in into JPQL.
I guess you want to get count of page_delta_summary rows satisfying where conditions for each fingerprint. If so, the SQL query looks like this:
select fingerprint, count(*) as finger_count from page_delta_summary
where delta_history_id = ? and change_type = ? group by fingerprint;
and JPQL - like this:
select d.fingerprint, count(d) from PageDeltaSummary d
where d.deltaHistoryId = :deltaHistoryId and d.type = :pageDeltaType
GROUP BY d.fingerprint
These queries return pairs <fingerprint, finger_count> instead of full page_delta_summary rows (or entities).

Categories