loadRecords(SQL, [values]) casting issue

I’ve got an interesting problem.
The following code works fine in Developer

controller.loadRecords("SELECT ct_contact.ct_id FROM ct_contact WHERE ct_status=? ORDER BY ct_id;",[2])

But gives the following error in Rich Client:

com.servoy.j2db.dataprocessing.DataException: Can't infer the SQL type to use for an instance of java.lang.Byte. Use setObject() with an explicit Types value to specify the type to use.
	at com.servoy.j2db.c.a.a(Unknown Source)
	at com.servoy.j2db.persistence.Server.translateSQLException(Unknown Source)
	at com.servoy.j2db.dataprocessing.SQLEngine.a(Unknown Source)
	at com.servoy.j2db.dataprocessing.SQLEngine.performQuery(Unknown Source)
	at sun.reflect.GeneratedMethodAccessor192.invoke(Unknown Source)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
	at java.lang.reflect.Method.invoke(Unknown Source)
	at sun.rmi.server.UnicastServerRef.dispatch(Unknown Source)
	at sun.rmi.transport.Transport$1.run(Unknown Source)
	at java.security.AccessController.doPrivileged(Native Method)
	at sun.rmi.transport.Transport.serviceCall(Unknown Source)
	at sun.rmi.transport.tcp.TCPTransport.handleMessages(Unknown Source)
	at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(Unknown Source)
	at java.lang.Thread.run(Unknown Source)
	at sun.rmi.transport.StreamRemoteCall.exceptionReceivedFromServer(StreamRemoteCall.java:247)
	at sun.rmi.transport.StreamRemoteCall.executeCall(StreamRemoteCall.java:223)
	at sun.rmi.server.UnicastRef.invoke(UnicastRef.java:126)
	at com.servoy.j2db.dataprocessing.SQLEngine_Stub.performQuery(Unknown Source)
	at com.servoy.j2db.dataprocessing.FoundSet.loadByQuery(Unknown Source)
	at com.servoy.j2db.FormController.loadData(Unknown Source)
	at com.servoy.j2db.FormController$JSForm.js_loadRecords(Unknown Source)
	at inv7.invoke()
	at org.mozilla.javascript.FunctionObject.doInvoke(FunctionObject.java:550)
	at org.mozilla.javascript.FunctionObject.call(FunctionObject.java:466)
	at org.mozilla.javascript.ScriptRuntime.call(ScriptRuntime.java:1254)
	at org.mozilla.javascript.gen.c36.call(filterRecords:30)
	at com.servoy.j2db.scripting.f.executeFunction(Unknown Source)
	at com.servoy.j2db.FormController.a(Unknown Source)
	at com.servoy.j2db.FormController.executeFunction(Unknown Source)
	at com.servoy.j2db.FormController$a.a(Unknown Source)
	at com.servoy.j2db.dataui.EventExecutor.fireActionCommand(Unknown Source)
	at com.servoy.j2db.dataui.EventExecutor.fireActionCommand(Unknown Source)
	at com.servoy.j2db.dataui.DataComboBox.notifyLastNewValueWasChange(Unknown Source)
	at com.servoy.j2db.dataprocessing.aw.commitEdit(Unknown Source)
	at com.servoy.j2db.dataui.EditProvider.itemStateChanged(Unknown Source)
	at com.servoy.j2db.dataui.DataComboBox.itemStateChanged(Unknown Source)
	at javax.swing.JComboBox.fireItemStateChanged(JComboBox.java:1162)
	at javax.swing.JComboBox.selectedItemChanged(JComboBox.java:1219)
	at javax.swing.JComboBox.contentsChanged(JComboBox.java:1266)
	at javax.swing.AbstractListModel.fireContentsChanged(AbstractListModel.java:100)
	at com.servoy.j2db.util.t.setSelectedItem(Unknown Source)
	at com.servoy.j2db.dataui.DataComboBox.setSelectedItem(Unknown Source)
	at com.servoy.j2db.dataui.DataComboBox.setSelectedIndex(Unknown Source)
	at javax.swing.plaf.basic.BasicComboPopup$Handler.mouseReleased(BasicComboPopup.java:808)
	at java.awt.AWTEventMulticaster.mouseReleased(AWTEventMulticaster.java:232)
	at java.awt.Component.processMouseEvent(Component.java:5554)
	at javax.swing.JComponent.processMouseEvent(JComponent.java:3126)
	at apple.laf.AquaComboBoxUI$AquaComboPopup$1.processMouseEvent(AquaComboBoxUI.java:443)
	at java.awt.Component.processEvent(Component.java:5319)
	at java.awt.Container.processEvent(Container.java:2010)
	at java.awt.Component.dispatchEventImpl(Component.java:4021)
	at java.awt.Container.dispatchEventImpl(Container.java:2068)
	at java.awt.Component.dispatchEvent(Component.java:3869)
	at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4256)
	at java.awt.LightweightDispatcher.processMouseEvent(Container.java:3936)
	at java.awt.LightweightDispatcher.dispatchEvent(Container.java:3866)
	at java.awt.Container.dispatchEventImpl(Container.java:2054)
	at java.awt.Window.dispatchEventImpl(Window.java:1774)
	at java.awt.Component.dispatchEvent(Component.java:3869)
	at java.awt.EventQueue.dispatchEvent(EventQueue.java:463)
	at java.awt.EventDispatchThread.pumpOneEventForHierarchy(EventDispatchThread.java:269)
	at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:190)
	at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:184)
	at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:176)
	at java.awt.EventDispatchThread.run(EventDispatchThread.java:110)

When I cast the value 2 as a number then this works without problems:

controller.loadRecords("SELECT ct_contact.ct_id FROM ct_contact WHERE ct_status=? ORDER BY ct_id;",[Number(2)])

I would think this is a JDBC issue but since it does work fine in Developer I am not certain.

Servoy version 3.1.5-build 409, repository version 29

JDK Information
java.vm.name=Java HotSpot™ Client VM
java.vm.version=1.5.0_11-b03
java.vm.info=mixed mode, sharing
java.vm.vendor=Sun Microsystems Inc.

Operating System Information
os.name=Windows 2003
os.version=5.2
os.arch=x86

Database is PostgreSQL 8.2.4 with latest JDBC driver (on same server)

Anyone seen this ?

Hi Robert,

for now you could force a cast in postgreSQL by adding something like

controller.loadRecords("SELECT ct_contact.ct_id FROM ct_contact WHERE ct_status=?::int4 ORDER BY ct_id;",[2])

Hi Christian,

Thanks for the suggestion but this is not a database error. The error comes from Servoy telling me that the value 2 is considered to be of the type Byte and doesn’t know what to do with it. Looking at the error it looks like a JDBC error but I am not sure.
Casting the value 2 to a Number, as shown in the above post, fixes it but it strikes me as odd that the original code does work in Developer but not in Rich Client.

Doesn’t [2] create an array with a lenght of two, without any value attached to the positions, instead of an array with the length of one, where the the first position contains a “2”?

Paul

No, [2] is an array with the value 2 at the first (0) index.

This a[2] will create a variable array ‘a’ with 2 positions.

A typical problem is when you do something like

var a = new Array(aField)

where aField is an integer. Then you create an empty array with the length of aField. Doing [aField] is fine.

right… :-) tnx for correcting…

Robert, could you create a case in the support system? Basically, when something works in Developer, but not in the Client, it calls for a case in the support system, because that shouldn’t happen: Either it work or it doesn’t. (I sort of missed that part in your first post)

Paul

Hi,

It appears to be a combination of quirks in our javascript compiler and the postgres jdbc driver.

When javascript is interpreted, numbers are passed on as doubles.
In the compiled javascript runtime (what we use in the client) small numbers are returned as bytes.

The postgresql jdbc driver recognizes all java datatypes, except Byte, I think this is a bug in the driver.

These 2 together cause this problem.
We have included a workaround in next release for both 3.1 and 3.5 Servoy version and will try to get it fixed in the postgresql driver.

Rob

Hadn’t filed a bugreport yet and it’s (gonna be) fixed already!
Thanks!

Servoy ROCKS!

Postgres accepted my fix.

Fix applied to 8.0, 8.1, 8.2, and HEAD CVS and will be in the next release.

Rob