org.postgresql.largeobject.LargeObjectManager Maven / Gradle / Ivy
Show all versions of mogdb-jdbc Show documentation
/*
* Copyright (c) 2003, PostgreSQL Global Development Group
* See the LICENSE file in the project root for more information.
*/
package io.mogdb.largeobject;
import io.mogdb.core.BaseConnection;
import io.mogdb.fastpath.Fastpath;
import io.mogdb.fastpath.FastpathArg;
import io.mogdb.util.GT;
import io.mogdb.util.PSQLException;
import io.mogdb.util.PSQLState;
import io.mogdb.log.Logger;
import io.mogdb.log.Log;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
/**
* This class implements the large object interface to io.mogdb.
*
* It provides methods that allow client code to create, open and delete large objects from the
* database. When opening an object, an instance of io.mogdb.largeobject.LargeObject is
* returned, and its methods then allow access to the object.
*
* This class can only be created by {@link BaseConnection}
*
* To get access to this class, use the following segment of code:
*
*
* import io.mogdb.largeobject.*;
*
* Connection conn;
* LargeObjectManager lobj;
*
* ... code that opens a connection ...
*
* lobj = ((io.mogdb.PGConnection)myconn).getLargeObjectAPI();
*
*
* Normally, client code would use the getAsciiStream, getBinaryStream, or getUnicodeStream methods
* in ResultSet, or setAsciiStream, setBinaryStream, or setUnicodeStream methods in
* PreparedStatement to access Large Objects.
*
* However, sometimes lower level access to Large Objects are required, that are not supported by
* the JDBC specification.
*
* Refer to io.mogdb.largeobject.LargeObject on how to manipulate the contents of a Large
* Object.
*
* @see java.sql.ResultSet#getAsciiStream
* @see java.sql.ResultSet#getBinaryStream
* @see java.sql.ResultSet#getUnicodeStream
* @see java.sql.PreparedStatement#setAsciiStream
* @see java.sql.PreparedStatement#setBinaryStream
* @see java.sql.PreparedStatement#setUnicodeStream
*/
public class LargeObjectManager {
// the fastpath api for this connection
private Fastpath fp;
private BaseConnection conn;
/**
* This mode indicates we want to write to an object.
*/
public static final int WRITE = 0x00020000;
/**
* This mode indicates we want to read an object.
*/
public static final int READ = 0x00040000;
/**
* This mode is the default. It indicates we want read and write access to a large object.
*/
public static final int READWRITE = READ | WRITE;
/**
* This prevents us being created by mere mortals.
*/
private LargeObjectManager() {
}
/**
* Constructs the LargeObject API.
*
* Important Notice
* This method should only be called by {@link BaseConnection}
*
* There should only be one LargeObjectManager per Connection. The {@link BaseConnection} class
* keeps track of the various extension API's and it's advised you use those to gain access, and
* not going direct.
*
* @param conn connection
* @throws SQLException if something wrong happens
*/
public LargeObjectManager(BaseConnection conn) throws SQLException {
this.conn = conn;
// We need Fastpath to do anything
this.fp = conn.getFastpathAPI();
// Now get the function oid's for the api
//
// This is an example of Fastpath.addFunctions();
//
String sql;
if (conn.getMetaData().supportsSchemasInTableDefinitions()) {
sql = "SELECT p.proname,p.oid "
+ " FROM pg_catalog.pg_proc p, pg_catalog.pg_namespace n "
+ " WHERE p.pronamespace=n.oid AND n.nspname='pg_catalog' AND (";
} else {
sql = "SELECT proname,oid FROM pg_proc WHERE ";
}
sql += " proname = 'lo_open'"
+ " or proname = 'lo_close'"
+ " or proname = 'lo_creat'"
+ " or proname = 'lo_unlink'"
+ " or proname = 'lo_lseek'"
+ " or proname = 'lo_lseek64'"
+ " or proname = 'lo_tell'"
+ " or proname = 'lo_tell64'"
+ " or proname = 'loread'"
+ " or proname = 'lowrite'"
+ " or proname = 'lo_truncate'"
+ " or proname = 'lo_truncate64'";
if (conn.getMetaData().supportsSchemasInTableDefinitions()) {
sql += ")";
}
Statement stmt = conn.createStatement();
ResultSet res = stmt.executeQuery(sql);
if (res == null) { // NOSONAR
throw new PSQLException(GT.tr("Failed to initialize LargeObject API"),
PSQLState.SYSTEM_ERROR);
}
fp.addFunctions(res);
res.close();
stmt.close();
conn.getLogger().debug("Large Object initialised");
}
/**
* This opens an existing large object, based on its OID. This method assumes that READ and WRITE
* access is required (the default).
*
* @param oid of large object
* @return LargeObject instance providing access to the object
* @throws SQLException on error
* @deprecated As of 8.3, replaced by {@link #open(long)}
*/
@Deprecated
public LargeObject open(int oid) throws SQLException {
return open((long) oid, false);
}
/**
* This opens an existing large object, same as previous method, but commits the transaction on
* close if asked. This is useful when the LOB is returned to a caller which won't take care of
* transactions by itself.
*
* @param oid of large object
* @param commitOnClose commit the transaction when this LOB will be closed
* @return LargeObject instance providing access to the object
* @throws SQLException on error
*/
public LargeObject open(int oid, boolean commitOnClose) throws SQLException {
return open((long) oid, commitOnClose);
}
/**
* This opens an existing large object, based on its OID. This method assumes that READ and WRITE
* access is required (the default).
*
* @param oid of large object
* @return LargeObject instance providing access to the object
* @throws SQLException on error
*/
public LargeObject open(long oid) throws SQLException {
return open(oid, READWRITE, false);
}
/**
* This opens an existing large object, same as previous method, but commits the transaction on
* close if asked.
*
* @param oid of large object
* @param commitOnClose commit the transaction when this LOB will be closed
* @return LargeObject instance providing access to the object
* @throws SQLException on error
*/
public LargeObject open(long oid, boolean commitOnClose) throws SQLException {
return open(oid, READWRITE, commitOnClose);
}
/**
* This opens an existing large object, based on its OID.
*
* @param oid of large object
* @param mode mode of open
* @return LargeObject instance providing access to the object
* @throws SQLException on error
* @deprecated As of 8.3, replaced by {@link #open(long, int)}
*/
@Deprecated
public LargeObject open(int oid, int mode) throws SQLException {
return open((long) oid, mode, false);
}
/**
* This opens an existing large object, same as previous method, but commits the transaction on
* close if asked.
*
* @param oid of large object
* @param mode mode of open
* @param commitOnClose commit the transaction when this LOB will be closed
* @return LargeObject instance providing access to the object
* @throws SQLException on error
*/
public LargeObject open(int oid, int mode, boolean commitOnClose) throws SQLException {
return open((long) oid, mode, commitOnClose);
}
/**
* This opens an existing large object, based on its OID.
*
* @param oid of large object
* @param mode mode of open
* @return LargeObject instance providing access to the object
* @throws SQLException on error
*/
public LargeObject open(long oid, int mode) throws SQLException {
return open(oid, mode, false);
}
/**
* This opens an existing large object, based on its OID.
*
* @param oid of large object
* @param mode mode of open
* @param commitOnClose commit the transaction when this LOB will be closed
* @return LargeObject instance providing access to the object
* @throws SQLException on error
*/
public LargeObject open(long oid, int mode, boolean commitOnClose) throws SQLException {
if (conn.getAutoCommit()) {
throw new PSQLException(GT.tr("Large Objects may not be used in auto-commit mode."),
PSQLState.NO_ACTIVE_SQL_TRANSACTION);
}
return new LargeObject(fp, oid, mode, conn, commitOnClose);
}
/**
* This creates a large object, returning its OID.
*
* It defaults to READWRITE for the new object's attributes.
*
* @return oid of new object
* @throws SQLException on error
* @deprecated As of 8.3, replaced by {@link #createLO()}
*/
@Deprecated
public int create() throws SQLException {
return create(READWRITE);
}
/**
* This creates a large object, returning its OID.
*
* It defaults to READWRITE for the new object's attributes.
*
* @return oid of new object
* @throws SQLException if something wrong happens
*/
public long createLO() throws SQLException {
return createLO(READWRITE);
}
/**
* This creates a large object, returning its OID.
*
* @param mode a bitmask describing different attributes of the new object
* @return oid of new object
* @throws SQLException on error
*/
public long createLO(int mode) throws SQLException {
if (conn.getAutoCommit()) {
throw new PSQLException(GT.tr("Large Objects may not be used in auto-commit mode."),
PSQLState.NO_ACTIVE_SQL_TRANSACTION);
}
FastpathArg[] args = new FastpathArg[1];
args[0] = new FastpathArg(mode);
return fp.getOID("lo_creat", args);
}
/**
* This creates a large object, returning its OID.
*
* @param mode a bitmask describing different attributes of the new object
* @return oid of new object
* @throws SQLException on error
* @deprecated As of 8.3, replaced by {@link #createLO(int)}
*/
@Deprecated
public int create(int mode) throws SQLException {
long oid = createLO(mode);
return (int) oid;
}
/**
* This deletes a large object.
*
* @param oid describing object to delete
* @throws SQLException on error
*/
public void delete(long oid) throws SQLException {
FastpathArg[] args = new FastpathArg[1];
args[0] = Fastpath.createOIDArg(oid);
fp.fastpath("lo_unlink", args);
}
/**
* This deletes a large object.
*
* It is identical to the delete method, and is supplied as the C API uses unlink.
*
* @param oid describing object to delete
* @throws SQLException on error
* @deprecated As of 8.3, replaced by {@link #unlink(long)}
*/
@Deprecated
public void unlink(int oid) throws SQLException {
delete((long) oid);
}
/**
* This deletes a large object.
*
* It is identical to the delete method, and is supplied as the C API uses unlink.
*
* @param oid describing object to delete
* @throws SQLException on error
*/
public void unlink(long oid) throws SQLException {
delete(oid);
}
/**
* This deletes a large object.
*
* @param oid describing object to delete
* @throws SQLException on error
* @deprecated As of 8.3, replaced by {@link #delete(long)}
*/
@Deprecated
public void delete(int oid) throws SQLException {
delete((long) oid);
}
}