Skip to content
Snippets Groups Projects
Commit 5af43965 authored by Bruce Momjian's avatar Bruce Momjian
Browse files

Update of Java driver from Peter Mount.

parent c17fa36d
No related branches found
No related tags found
No related merge requests found
......@@ -10,15 +10,20 @@ class JDBC_Test
public static void main(String argv[])
{
if(argv.length<3) {
System.err.println("java JDBC_Test jdbc-url user password [debug]");
System.exit(1);
}
String url = new String(argv[0]);
String usr = new String(argv[1]);
String pwd = new String(argv[2]);
Connection db;
Statement s;
ResultSet rs;
// This line outputs debug information to stderr. To enable this, simply
// remove the //
// add an extra parameter to the command line
if(argv.length>3)
DriverManager.setLogStream(System.err);
// Load the driver
......@@ -31,12 +36,15 @@ class JDBC_Test
// Lets do a few things -- it doesn't do everything, but
// it tests out basic functionality
try {
//----------------------------------------
// Connect to database
System.out.println("Connecting to Database URL = " + url);
db = DriverManager.getConnection(url, usr, pwd);
System.out.println("Connected...Now creating a statement");
s = db.createStatement();
// test Date & Warnings
//----------------------------------------
// test DateStyle & Warnings
System.out.println("Ok... now set European date style");
s.executeUpdate("set datestyle='european'");
......@@ -49,30 +57,52 @@ class JDBC_Test
}
db.clearWarnings();
//----------------------------------------
// Creating a table
System.out.println("Ok...now we will create a table");
s.executeUpdate("create table test (a int2, b int2,c timestamp,d date)");
//----------------------------------------
// Simple inserts
System.out.println("Now we will insert some columns");
s.executeUpdate("insert into test values (1, 1,'now','now')");
s.executeUpdate("insert into test values (2, 1,'now','01-11-1997')"); // As we are in european, this should mean 1 November 1997
s.executeUpdate("insert into test values (3, 1,'now','11-01-1997')"); // As we are in european, this should mean 11 January 1997
System.out.println("Inserted some data");
//----------------------------------------
// Now a select (see seperate method at end)
System.out.println("Now lets try a select");
rs = s.executeQuery("select a, b,c,d from test");
System.out.println("Back from the select...the following are results");
System.out.println("row a b c d 'd as string'");
int i = 0;
while (rs.next())
{
int a = rs.getInt("a"); // Example of retriving by column name
int b = rs.getInt("b");
Timestamp c = rs.getTimestamp(3); // Example of by column number
java.sql.Date d = rs.getDate(4); // Note, java.sql.Date here
System.out.println("row " + i + " " + a + " " + b + " " + c + " " + d + " '"+rs.getString(4)+"'");
i++;
select(s,"");
//----------------------------------------
// Now run some tests
runTests(db,s);
//----------------------------------------
// Dropping a table
System.out.println("Ok...dropping the table");
s.executeUpdate("drop table test");
//----------------------------------------
// Closing the connection
System.out.println("Now closing the connection");
s.close();
db.close();
//----------------------------------------
} catch (SQLException e) {
System.out.println("Exception: " + e.toString());
}
}
/**
* This performs some tests - not really part of an example, hence
* they are in a seperate method.
*/
public static void runTests(Connection db, Statement s) throws SQLException
{
//----------------------------------------
// This is a bug at the moment... when you use set datestyle
// it must be followed by show datestyle
System.out.println("Now switch to US date format");
......@@ -80,12 +110,54 @@ class JDBC_Test
s.executeUpdate("show datestyle");
System.out.println("Now lets try a select");
rs = s.executeQuery("select a, b,c,d from test");
System.out.println("Back from the select...the following are results");
//int i = 0;
System.out.println("row a b c d 'd as string'");
while (rs.next())
select(s,"");
//----------------------------------------
// Inserting dates using PreparedStatement
System.out.println("Ok, now a test using PreparedStatement");
Date dt = new Date(97,11,1);
PreparedStatement ps = db.prepareStatement("insert into test values (?,?,'now',?)");
// first insert in US style
s.executeUpdate("set datestyle='US'");
s.executeUpdate("show datestyle");
ps.setInt(1,8);
ps.setInt(2,8);
ps.setDate(3,dt);
ps.executeUpdate();
// second insert in European style
s.executeUpdate("set datestyle='european'");
s.executeUpdate("show datestyle");
ps.setInt(1,9);
ps.setInt(2,9);
ps.setDate(3,dt);
ps.executeUpdate();
System.out.println("Now run the select again - first as European");
select(s,"where a>7");
s.executeUpdate("set datestyle='US'");
s.executeUpdate("show datestyle");
System.out.println("Then as US");
select(s,"where a>7");
}
/**
* This performs a select. It's seperate because the tests use it in
* multiple places.
* @param s Statement to run under
* @throws SQLException
*/
public static void select(Statement s,String sql) throws SQLException
{
sql="select a, b,c,d from test "+sql;
System.out.println("\nQuery: "+sql);
ResultSet rs = s.executeQuery(sql);
System.out.println("row a b c d 'd as string'");
System.out.println("-------------------------------------------------------------------------------");
int i = 0;
while(rs.next()) {
int a = rs.getInt("a"); // Example of retriving by column name
int b = rs.getInt("b");
Timestamp c = rs.getTimestamp(3); // Example of by column number
......@@ -93,15 +165,7 @@ class JDBC_Test
System.out.println("row " + i + " " + a + " " + b + " " + c + " " + d + " '"+rs.getString(4)+"'");
i++;
}
System.out.println("Ok...dropping the table");
s.executeUpdate("drop table test");
System.out.println("Now closing the connection");
s.close();
db.close();
} catch (SQLException e) {
System.out.println("Exception: " + e.toString());
}
rs.close();
}
}
......@@ -121,7 +121,8 @@ or if passing the user & password directly via DriverManager.getConnection():
jdbc:postgresql:database?auth=y
PS: 'y' could be anything, aslong as there is something after the '='
PS: Password authentication is enabled if the value of auth starts with 'y'.
It is case insensitive.
---------------------------------------------------------------------------
......
......
......@@ -36,15 +36,20 @@ public class Connection implements java.sql.Connection
private String PG_PASSWORD;
private String PG_DATABASE;
private boolean PG_STATUS;
private boolean PG_AUTH; // true, then password auth used
public boolean CONNECTION_OK = true;
public boolean CONNECTION_BAD = false;
private static final int STARTUP_LEN = 288; // Length of a startup packet
// These are defined in src/include/libpq/pqcomm.h
private int STARTUP_CODE = STARTUP_USER;
private static final int STARTUP_USER = 7; // User auth
private static final int STARTUP_KRB4 = 10; // Kerberos 4 (unused)
private static final int STARTUP_KRB5 = 11; // Kerberos 5 (unused)
private static final int STARTUP_HBA = 12; // Host Based
private static final int STARTUP_NONE = 13; // Unauthenticated (unused)
private static final int STARTUP_PASS = 14; // Password auth
private static final int STARTUP_LEN = 288; // Length of a startup packet
private boolean autoCommit = true;
private boolean readOnly = false;
......@@ -84,10 +89,22 @@ public class Connection implements java.sql.Connection
PG_HOST = new String(host);
PG_STATUS = CONNECTION_BAD;
if(info.getProperty("auth") != null) {
PG_AUTH=true;
// This handles the auth property. Any value begining with p enables
// password authentication, while anything begining with i enables
// ident (RFC 1413) authentication. Any other values default to trust.
//
// Also, the postgresql.auth system property can be used to change the
// local default, if the auth property is not present.
//
String auth = info.getProperty("auth",System.getProperty("postgresql.auth","trust")).toLowerCase();
if(auth.startsWith("p")) {
// Password authentication
STARTUP_CODE=STARTUP_PASS;
} else if(auth.startsWith("i")) {
// Ident (RFC 1413) authentication
STARTUP_CODE=STARTUP_HBA;
} else {
// Anything else defaults to trust authentication
STARTUP_CODE=STARTUP_USER;
}
......@@ -107,7 +124,7 @@ public class Connection implements java.sql.Connection
pg_stream.Send(PG_USER.getBytes(), len);
// Send the password packet if required
if(PG_AUTH) {
if(STARTUP_CODE == STARTUP_PASS) {
len=STARTUP_LEN;
pg_stream.SendInteger(len, 4); len -= 4;
pg_stream.SendInteger(STARTUP_PASS, 4); len -= 4;
......
......
......@@ -27,7 +27,7 @@ public class Driver implements java.sql.Driver
// These should be in sync with the backend that the driver was
// distributed with
static final int MAJORVERSION = 6;
static final int MINORVERSION = 2;
static final int MINORVERSION = 3;
static
{
......@@ -125,8 +125,22 @@ public class Driver implements java.sql.Driver
*/
public DriverPropertyInfo[] getPropertyInfo(String url, Properties info) throws SQLException
{
return null; // We don't need anything except
// the username, which is a default
Properties p = parseURL(url,info);
// naughty, but its best for speed. If anyone adds a property here, then
// this _MUST_ be increased to accomodate them.
DriverPropertyInfo d,dpi[] = new DriverPropertyInfo[1];
int i=0;
dpi[i++] = d = new DriverPropertyInfo("auth",p.getProperty("auth","default"));
d.description = "determines if password authentication is used";
d.choices = new String[4];
d.choices[0]="default"; // Get value from postgresql.auth property, defaults to trust
d.choices[1]="trust"; // No password authentication
d.choices[2]="password"; // Password authentication
d.choices[3]="ident"; // Ident (RFC 1413) protocol
return dpi;
}
/**
......@@ -168,6 +182,10 @@ public class Driver implements java.sql.Driver
/**
* Constructs a new DriverURL, splitting the specified URL into its
* component parts
* @param url JDBC URL to parse
* @param defaults Default properties
* @return Properties with elements added from the url
* @throws SQLException
*/
Properties parseURL(String url,Properties defaults) throws SQLException
{
......
......
......@@ -7,8 +7,8 @@ import java.text.*;
import java.util.*;
/**
* @version 1.0 15-APR-1997
* @author <A HREF="mailto:adrian@hottub.org">Adrian Hall</A>
* @version 6.3 15-APR-1997
* @author <A HREF="mailto:adrian@hottub.org">Adrian Hall</A><A HREF="mailto:petermount@earthling.net">Peter Mount</A>
*
* A SQL Statement is pre-compiled and stored in a PreparedStatement object.
* This object can then be used to efficiently execute this statement multiple
......@@ -294,9 +294,9 @@ public class PreparedStatement extends Statement implements java.sql.PreparedSta
*/
public void setDate(int parameterIndex, java.sql.Date x) throws SQLException
{
DateFormat df = DateFormat.getDateInstance();
SimpleDateFormat df = new SimpleDateFormat(connection.europeanDates?"''dd-MM-yyyy''":"''MM-dd-yyyy''");
set(parameterIndex, "'" + df.format(x) + "'");
set(parameterIndex, df.format(x));
}
/**
......
......
......@@ -374,27 +374,12 @@ public class ResultSet implements java.sql.ResultSet
public java.sql.Date getDate(int columnIndex) throws SQLException
{
String s = getString(columnIndex);
if (s != null)
{
SimpleDateFormat df = new SimpleDateFormat(connection.europeanDates?"dd-MM-yyyy":"MM-dd-yyyy");
try {
if (s.length() != 10)
throw new NumberFormatException("Wrong Length!");
int mon = Integer.parseInt(s.substring(0,2));
int day = Integer.parseInt(s.substring(3,5));
int yr = Integer.parseInt(s.substring(6));
if(connection.europeanDates) {
// We europeans prefer dd mm yyyy
int t = mon;
mon = day;
day = t;
}
return new java.sql.Date(yr - 1900, mon -1, day);
} catch (NumberFormatException e) {
throw new SQLException("Bad Date Form: " + s);
}
return new java.sql.Date(df.parse(s).getTime());
} catch (ParseException e) {
throw new SQLException("Bad Date Format: at " + e.getErrorOffset() + " in " + s);
}
return null; // SQL NULL
}
/**
......
......
......@@ -190,10 +190,12 @@ public class ResultSetMetaData implements java.sql.ResultSetMetaData
for (i = 0 ; i < rows.size(); ++i)
{
byte[][] x = (byte[][])(rows.elementAt(i));
if(x[column-1]!=null) {
int xl = x[column - 1].length;
if (xl > max)
max = xl;
}
}
return max;
}
......
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment