001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one
003: * or more contributor license agreements. See the NOTICE file
004: * distributed with this work for additional information
005: * regarding copyright ownership. The ASF licenses this file
006: * to you under the Apache License, Version 2.0 (the
007: * "License"); you may not use this file except in compliance
008: * with the License. You may obtain a copy of the License at
009: *
010: * http://www.apache.org/licenses/LICENSE-2.0
011: *
012: * Unless required by applicable law or agreed to in writing,
013: * software distributed under the License is distributed on an
014: * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
015: * KIND, either express or implied. See the License for the
016: * specific language governing permissions and limitations
017: * under the License.
018: */
019: package org.apache.openjpa.jdbc.meta.strats;
020:
021: import java.io.InputStream;
022: import java.io.Reader;
023: import java.sql.SQLException;
024: import java.sql.Types;
025:
026: import org.apache.openjpa.jdbc.kernel.JDBCFetchConfiguration;
027: import org.apache.openjpa.jdbc.kernel.JDBCStore;
028: import org.apache.openjpa.jdbc.meta.FieldMapping;
029: import org.apache.openjpa.jdbc.meta.ValueMappingInfo;
030: import org.apache.openjpa.jdbc.schema.Column;
031: import org.apache.openjpa.jdbc.sql.Result;
032: import org.apache.openjpa.jdbc.sql.Row;
033: import org.apache.openjpa.jdbc.sql.RowManager;
034: import org.apache.openjpa.jdbc.sql.Select;
035: import org.apache.openjpa.kernel.OpenJPAStateManager;
036:
037: /**
038: * Direct mapping from a stream value to a column.
039: *
040: * @author Ignacio Andreu
041: * @since 1.1.0
042: */
043: public class LobFieldStrategy extends AbstractFieldStrategy {
044:
045: private int fieldType;
046:
047: public void map(boolean adapt) {
048: assertNotMappedBy();
049: field.mapJoin(adapt, false);
050: field.getKeyMapping().getValueInfo().assertNoSchemaComponents(
051: field.getKey(), !adapt);
052: field.getElementMapping().getValueInfo()
053: .assertNoSchemaComponents(field.getElement(), !adapt);
054: field.setStream(true);
055: ValueMappingInfo vinfo = field.getValueInfo();
056: vinfo.assertNoJoin(field, true);
057: vinfo.assertNoForeignKey(field, !adapt);
058: Column tmpCol = new Column();
059: tmpCol.setName(field.getName());
060: tmpCol.setJavaType(field.getTypeCode());
061: tmpCol.setType(fieldType);
062: tmpCol.setSize(-1);
063:
064: Column[] cols = vinfo.getColumns(field, field.getName(),
065: new Column[] { tmpCol }, field.getTable(), adapt);
066:
067: field.setColumns(cols);
068: field.setColumnIO(vinfo.getColumnIO());
069: field.mapConstraints(field.getName(), adapt);
070: field.mapPrimaryKey(adapt);
071: }
072:
073: public Boolean isCustomInsert(OpenJPAStateManager sm,
074: JDBCStore store) {
075: return null;
076: }
077:
078: public void insert(OpenJPAStateManager sm, JDBCStore store,
079: RowManager rm) throws SQLException {
080: Object ob = toDataStoreValue(sm.fetchObjectField(field
081: .getIndex()), store);
082: Row row = field.getRow(sm, store, rm, Row.ACTION_INSERT);
083: if (field.getColumnIO().isInsertable(0, ob == null)) {
084: if (ob != null) {
085: if (isBlob()) {
086: store.getDBDictionary().insertBlobForStreamingLoad(
087: row, field.getColumns()[0]);
088: } else {
089: store.getDBDictionary().insertClobForStreamingLoad(
090: row, field.getColumns()[0]);
091: }
092: } else {
093: Column col = field.getColumns()[0];
094: col.setType(Types.OTHER);
095: row.setNull(col);
096: }
097: }
098: }
099:
100: public void customInsert(OpenJPAStateManager sm, JDBCStore store)
101: throws SQLException {
102: Object ob = toDataStoreValue(sm.fetchObjectField(field
103: .getIndex()), store);
104: if (field.getColumnIO().isInsertable(0, ob == null)) {
105: if (ob != null) {
106: Select sel = createSelect(sm, store);
107: if (isBlob()) {
108: store.getDBDictionary().updateBlob(sel, store,
109: (InputStream) ob);
110: } else {
111: store.getDBDictionary().updateClob(sel, store,
112: (Reader) ob);
113: }
114: }
115: }
116: }
117:
118: public void update(OpenJPAStateManager sm, JDBCStore store,
119: RowManager rm) throws SQLException {
120: Object ob = toDataStoreValue(sm.fetchObjectField(field
121: .getIndex()), store);
122: if (field.getColumnIO().isUpdatable(0, ob == null)) {
123: if (ob != null) {
124: Select sel = createSelect(sm, store);
125: if (isBlob()) {
126: store.getDBDictionary().updateBlob(sel, store,
127: (InputStream) ob);
128: } else {
129: store.getDBDictionary().updateClob(sel, store,
130: (Reader) ob);
131: }
132: } else {
133: Row row = field
134: .getRow(sm, store, rm, Row.ACTION_UPDATE);
135: Column col = field.getColumns()[0];
136: col.setType(Types.OTHER);
137: row.setNull(col);
138: }
139: }
140: }
141:
142: public int supportsSelect(Select sel, int type,
143: OpenJPAStateManager sm, JDBCStore store,
144: JDBCFetchConfiguration fetch) {
145: if (type == Select.TYPE_JOINLESS
146: && sel.isSelected(field.getTable()))
147: return 1;
148: return 0;
149: }
150:
151: public int select(Select sel, OpenJPAStateManager sm,
152: JDBCStore store, JDBCFetchConfiguration fetch, int eagerMode) {
153: sel.select(field.getColumns()[0], field.join(sel));
154: return 1;
155: }
156:
157: public void load(OpenJPAStateManager sm, JDBCStore store,
158: JDBCFetchConfiguration fetch, Result res)
159: throws SQLException {
160: Column col = field.getColumns()[0];
161: if (res.contains(col)) {
162: if (isBlob()) {
163: sm.storeObject(field.getIndex(), res
164: .getBinaryStream(col));
165: } else {
166: sm.storeObject(field.getIndex(), res
167: .getCharacterStream(col));
168: }
169: }
170: }
171:
172: protected void assertNotMappedBy() {
173: if (field != null && field.getMappedBy() != null)
174: throw new UnsupportedOperationException();
175: }
176:
177: public void setFieldMapping(FieldMapping owner) {
178: if (owner.getType().isAssignableFrom(InputStream.class)) {
179: fieldType = Types.BLOB;
180: } else if (owner.getType().isAssignableFrom(Reader.class)) {
181: fieldType = Types.CLOB;
182: }
183: field = owner;
184: }
185:
186: private boolean isBlob() {
187: if (fieldType == Types.BLOB)
188: return true;
189: return false;
190: }
191:
192: private Select createSelect(OpenJPAStateManager sm, JDBCStore store) {
193: Select sel = store.getSQLFactory().newSelect();
194: sel.select(field.getColumns()[0]);
195: sel.selectPrimaryKey(field.getDefiningMapping());
196: sel.wherePrimaryKey(sm.getObjectId(), field
197: .getDefiningMapping(), store);
198: sel.setLob(true);
199: return sel;
200: }
201: }
|