How can I generate response after insert query in wso2dss? - insert

I am using wso2dss.
I just insert one row.
Table has only one field and it is not the unique and it is not a key.
I can't use the "GenerateKeys" option.
However, I need to generate response after insert query is success in the wso2dss.
I created table as below.
create table SAMPLETABLE (My_VALUE VARCHAR (100));
<data name="MyTESTSERVICE">
<config id="testconfig">
<property name="username">sa</property>
<property name="password">sa</property>
<property name="url">jdbc:h2:tcp://localhost/~/test;MODE=Oracle</property>
<property name="driverClassName">org.h2.Driver</property>
</config>
<query id="insertMyValue" useConfig="testconfig">
<sql>INSERT INTO SAMPLETABLE (My_VALUE) VALUES (:MyValue)</sql>
<param name="MyValue" sqlType="STRING"/>
</query>
<operation name="insertOP">
<call-query href="insertMyValue">
<with-param name="MyValue" query-param="MyValue"/>
</call-query>
</operation>
</data>
It was working without any response.
But I need customized response after inserting is successful. How can I do?

You can try stored procedures that return value. ie you can write sp which is insert values in database and returns the status of transaction, in dss it returns that whether your query ran on DB or not.

Related

mybatis batch insert generating duplicate uuid primary key

when i insert single record:
<insert id="add" parameterType="SysUser">
<selectKey keyProperty="id" resultType="String" order="BEFORE">
select replace(uuid(),'-','') from dual
</selectKey>
insert into sys_user(id,user_name,user_email,user_info,user_password,create_time)
values
(#{id,jdbcType=VARCHAR},
#{userName,jdbcType=VARCHAR},
#{userEmail,jdbcType=VARCHAR},
#{userInfo,jdbcType=VARCHAR},
#{userPassword,jdbcType=VARCHAR},
#{createTime,jdbcType=TIMESTAMP})
</insert>
but i want to insert a list, how can i generate the uuid like the single insert above???
<insert id="addSysUsers" parameterType="List" useGeneratedKeys="true" keyProperty="id">
INSERT INTO sys_user(user_name,user_password,user_email)
VALUES
<foreach collection="sysUsers" item="sysUser" separator=",">
(#{sysUser.userName,jdbcType=VARCHAR},#{sysUser.userPassword,jdbcType=VARCHAR},#{sysUser.userEmail,jdbcType=VARCHAR})
</foreach>
</insert>
The simplest way to do it is put the UUID generator in the values block:
<insert id="add" parameterType="SysUser">
insert into sys_user(id,user_name,user_email,user_info,user_password,create_time)
values
(replace(uuid(),'-',''), <!-- create uuid directly here --->
#{userName,jdbcType=VARCHAR},
#{userEmail,jdbcType=VARCHAR},
#{userInfo,jdbcType=VARCHAR},
#{userPassword,jdbcType=VARCHAR},
#{createTime,jdbcType=TIMESTAMP})
</insert>

ORA-00933: SQL command not properly ended In Spring batch Item Writer

I am writing one spring batch based application in which i have to write a consolidated xml file data into multiple tables of database.
bean id="mysqlItemWriter"
class="org.springframework.batch.item.database.JdbcBatchItemWriter">
<property name="dataSource" ref="dataSource" />
<property name="sql">
<value>
<![CDATA[
INSERT INTO LEASE (LEASE_ID, CONTRACT_TYPE, CONTRACT_NUMBER, LEASE_AMOUNT, DESCRIPTION, CREATE_DATE, REGISTER_DATE)
VALUES ( :leaseId, :contractType, :contactNumber, :leaseAmount, :description, :leaseCreateDate, :leaseUpdateDate)
INSERT INTO CUSTOMER (CUSTOMER_ID ,FIRST_NAME, LAST_NAME, SURNAME, CUSTOMER_NUMBER, RECORD_CODE,
SOURCE_SYSTEM, BIRTH_DATE,CREATE_DATE, UPDATE_DATE,ADDRESS,STREET,HOUSE_NUMBER,
STATE, POSTAL_CODE, COUNTRY_CODE )
VALUES ( :customerId , :firstname, :lastName ,:surname, :customerNumber, :recordCode, :SourceSystem,
:birthDate, :leaseCreateDate, :leaseUpdateDate, :address, :houseNumber, :city, :state, :postalcode,
:countryCode)
]]>
</value>
In the above code when only one SQL statement is there it is working fine but for two insert statements it is not working fine. It is giving the error as
"ORA-00933: SQL command not properly ended" .
When i am inserting ; after first insert statement it is showing the same error
I am not able to resolve this..
You can always try wrapping your 2 statements inside a PL/SQL anonymous block (Make sure you don't forget any of the required semi colons).
begin
insert into ...;
insert into ...;
end;
Technically, it should then be treated as a single statement and should work.
bean id="mysqlItemWriter"
class="org.springframework.batch.item.database.JdbcBatchItemWriter">
<property name="dataSource" ref="dataSource" />
<property name="sql">
<value>
<![CDATA[
begin
INSERT INTO LEASE (LEASE_ID, CONTRACT_TYPE, CONTRACT_NUMBER, LEASE_AMOUNT, DESCRIPTION, CREATE_DATE, REGISTER_DATE)
VALUES ( :leaseId, :contractType, :contactNumber, :leaseAmount, :description, :leaseCreateDate, :leaseUpdateDate);
INSERT INTO CUSTOMER (CUSTOMER_ID ,FIRST_NAME, LAST_NAME, SURNAME, CUSTOMER_NUMBER, RECORD_CODE,
SOURCE_SYSTEM, BIRTH_DATE,CREATE_DATE, UPDATE_DATE,ADDRESS,STREET,HOUSE_NUMBER,
STATE, POSTAL_CODE, COUNTRY_CODE )
VALUES ( :customerId , :firstname, :lastName ,:surname, :customerNumber, :recordCode, :SourceSystem,
:birthDate, :leaseCreateDate, :leaseUpdateDate, :address, :houseNumber, :city, :state, :postalcode,
:countryCode);
end;
]]>
</value>
There is a good description of the issue here:
http://forum.liquibase.org/topic/formatted-sql-enddelimiter-issue
I suggest adding the "/" to see if that works in combination with
endDelimiter:/ or using splitStatement:false

How to get Oracle next sequence value in liqiibase 1.9.5 for insert

How to get Oracle next sequence value in liqiibase 1.9.5 for insert
<changeSet author="MIGRATE" id="070214010049877">
<insert tableName="MYTABLE">
<column name="ID" valueNumeric=" nextval( 'MYTABLE_SEQ' ) "/>
<column name="NUMBER" value="5"/>
</insert>
</changeSet>
it is trying to put the value of ID " nextval( 'MYTABLE_SEQ' )" in table so it gives error
With Liquibase 1.9.5, there is no support for finding the next sequence value with the <insert> tag. You will have to either drop back to using <sql> or use <modifySql> assuming that existed in 1.9.5.

Cannot retrieve the id of the last inserted row in Hibernate using Oracle

I'm using Hibernate Tools 3.2.1.GA with the Spring version 3.0.2. I'm trying to retrieve the id of the last inserted row into the Oracle(10g) database as follows.
Session session=NewHibernateUtil.getSessionFactory().getCurrentSession();
session.beginTransaction();
Country c=new Country();
c.setCountryId(new BigDecimal(0));
c.setCountryName(request.getParameter("txtCountryName"));
c.setCountryCode(request.getParameter("txtCountryCode"));
Zone z=(Zone) session.get(Zone.class, new BigDecimal(request.getParameter("zoneId")));
c.setZone(z);
session.save(c);
session.flush();
System.out.println(c.getCountryId());
session.getTransaction().commit();
This statement System.out.println(c.getCountryId()); is expected to return the currently inserted id after the data is serialized to the database and before the transaction is committed but it doesn't because of the following line in the preceding code snippet (as it presumably appears to me).
c.setCountryId(new BigDecimal(0));
I'm not sure why this statement is required in my case (while inserting). I saw this statement nowhere. Omission of this line causes the following exception to be thrown.
org.hibernate.id.IdentifierGenerationException: ids for this class
must be manually assigned before calling save(): model.Country
Is this statement c.setCountryId(new BigDecimal(0)); really required during insertion? It's a sequence generated primary key in the Oracle database and because of that line, this statement System.out.println(c.getCountryId()); always returns 0 which is actually expected to return the currently inserted id in the current session.
So, how can I get the last generated id in this case? Am I following a wrong way, is there a different way?
EDIT:
CREATE TABLE "COUNTRY"
(
"COUNTRY_ID" NUMBER(35,0) NOT NULL ENABLE,
"COUNTRY_CODE" VARCHAR2(10),
"COUNTRY_NAME" VARCHAR2(50),
"ZONE_ID" NUMBER(35,0),
CONSTRAINT "COUNTRY_PK" PRIMARY KEY ("COUNTRY_ID") ENABLE,
CONSTRAINT "COUNTRY_FK" FOREIGN KEY ("ZONE_ID")
REFERENCES "ZONE" ("ZONE_ID") ON DELETE CASCADE ENABLE
)
/
CREATE OR REPLACE TRIGGER "BI_COUNTRY"
before insert on "COUNTRY"
for each row
begin
select "COUNTRY_SEQ".nextval into :NEW.COUNTRY_ID from dual;
end;
/
ALTER TRIGGER "BI_COUNTRY" ENABLE
/
The exception 'ids for this class must be manually assigned before calling save()' means that you are using the identifier generation strategy of 'Assigned'.
assigned
lets the application assign an identifier to the object before save() is called. This is the default strategy if no element is specified.
If you do not define any strategy, hibernate defaults to 'assigned'. 'assigned' strategy implies that hibernate expects that the application supplies it's own ids.
If you want to use a sequence id generator in Oracle, you can do so with the following configuration -
If you are using xml -
<id name="countryId" type="java.lang.Integer">
<column name="Country_Id" />
<generator class="sequence">
<param name="sequence">Country_Id_Seq</param>
</generator>
</id>
If you are using annotations -
#Id
#GeneratedValue(strategy=GenerationType.SEQUENCE, generator="Country_Id_Seq")
#SequenceGenerator(name="Country_Id_Seq", sequenceName="Country_Id_Seq" )
private Integer sequence;
And your code should look like so -
Country c=new Country();
c.setCountryName(request.getParameter("txtCountryName"));
c.setCountryCode(request.getParameter("txtCountryCode"));
Zone z=(Zone) session.get(Zone.class, new BigDecimal(request.getParameter("zoneId")));
c.setZone(z);
session.save(c);
session.flush();
System.out.println(c.getCountryId());
When 'session.save(c)' executes, hibernate makes the following sql call to Oracle, retrieves the id and sets it in Country object.
select Country_Id_Seq.nextVal from dual;
Problem with trigger
Since you are using a trigger to increment the id when a row is inserted, this will cause a problem with hibernate sequence. Hibernate is using the sequence to generate an id and the database is using the trigger to increment the id. This is resulting in the id being incremented twice.
You have a three options to resolve this.
Delete the trigger because it's not necessary.
If you still need the trigger because the table could be updated outside the application, you could update the trigger such that the id is generated only if the id is not set in the insert statement
HIbernate issue with Oracle Trigger for generating id from a sequence
Create a custom id generator that uses the trigger to set the id in the data before it is saved to db. Check out the following link - https://forum.hibernate.org/viewtopic.php?t=973262
If the values into an ID column generated by a sequence, then you should associate that sequence with your ID column in the entity definition so that the attribute is filled in with the ID value by Hibernate during insertion.
Using annotations:
#Id
#GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "CountryIdSequence")
#SequenceGenerator(name = "CountryIdSequence", sequenceName = "COUNTRY_ID_SEQUENCE")
#Column(name = "COUNTRY_ID")
private BigDecimal countryId;
Using hbm:
<id name="countryId" type="big_decimal">
<column name="COUNTRY_ID" />
<generator class=""sequence">
<param name="sequence">COUNTRY_ID_SEQUENCE</param>
</generator>
</id>
Then, it will be available after the save.
Any changes made to the entity at the database layer are not reflected in the hibernate entity layer until you refresh the object.
session.save(c);
session.flush();
// Refresh the object for columns modified in the DB by IDENTITY / SEQUENCE / Triggers.
session.refresh(c);
System.out.println(c.getCountryId());

RETURNING ... INTO ... clause throwing an error with Oracle and ColdFusion

Here is the query I am running.
<cfquery name="myquery" datasource="mydatasource">
INSERT INTO
myTable (myfield)
VALUES
(<cfqueryparam cfsqltype="cf_sql_varchar" value="#ARGUMENTS.myValue#" />)
RETURNING
id INTO <cfqueryparam cfsqltype="cf_sql_varchar" value="#LOCAL.myid#" />
</cfquery>
The error I am getting is ORA-00439: feature not enabled: RETURNING clause from this client type
I've run across a feature in cfquery called GENERATEDKEY, I think this can be used to mitigate any database server settings, which I don't have access to. However I can't seem to get GENERATEDKEY to return my primary key instead I get something like AAFO9cAAEAAB8vYAAH, which is the Oracle rowid...
According to the docs you linked, there isn't a generatedkey member of the query result. there's a generated_key for mySQL, but for oracle it's ROWID, although the docs say this "Oracle only. The ID of an inserted row. This is not the primary key of the row, although you can retrieve rows based on this ID." I'm not sure how to map from one to the other though. If you leave out the RETURNING part of the statement, do you get anything for ROWID?
I'm not familiar with coldfusion, and there may be some simple solution.
But if not, a workaround could be to create a stored procedure that is using the returning clause and retuns it.
This way you can call the stored procedure instead.
create or replace function insert_my_table(my_value varchar2) return number is
i number;
begin
insert into my_table (value_col_name) values (my_value) returning id into i;
return i;
end insert_my_table;

Resources