| /* |
| * Copyright (c) 1998, 2021 Oracle and/or its affiliates. All rights reserved. |
| * |
| * This program and the accompanying materials are made available under the |
| * terms of the Eclipse Public License v. 2.0 which is available at |
| * http://www.eclipse.org/legal/epl-2.0, |
| * or the Eclipse Distribution License v. 1.0 which is available at |
| * http://www.eclipse.org/org/documents/edl-v10.php. |
| * |
| * SPDX-License-Identifier: EPL-2.0 OR BSD-3-Clause |
| */ |
| |
| // Contributors: |
| // Mike Norman - from Proof-of-concept, become production code |
| package dbws.testing.shadowddlgeneration.oldjpub; |
| |
| import static dbws.testing.shadowddlgeneration.oldjpub.Util.ALL_ARGUMENTS; |
| import static dbws.testing.shadowddlgeneration.oldjpub.Util.DATA_LEVEL; |
| import static dbws.testing.shadowddlgeneration.oldjpub.Util.OBJECT_NAME; |
| import static dbws.testing.shadowddlgeneration.oldjpub.Util.OVERLOAD; |
| import static dbws.testing.shadowddlgeneration.oldjpub.Util.OWNER; |
| import static dbws.testing.shadowddlgeneration.oldjpub.Util.PACKAGE_NAME; |
| import static dbws.testing.shadowddlgeneration.oldjpub.Util.SEQUENCE; |
| |
| //javase imports |
| import java.sql.SQLException; |
| import java.util.ArrayList; |
| import java.util.Iterator; |
| import java.util.List; |
| |
| public class PlsqlRecordType extends SqlTypeWithFields { |
| |
| // Locating PL/SQL RECORD, esp., ROWTYPE in ALL_ARGUMENTS |
| protected List<FieldInfo> m_fieldInfo; |
| protected List<RowtypeInfo> m_rowtypeInfo; |
| |
| public PlsqlRecordType(SqlName sqlName, List<FieldInfo> fieldInfo, List<AttributeField> fields, |
| List<RowtypeInfo> rowtypeInfo, boolean generateMe, SqlType parentType, SqlReflector reflector) |
| throws SQLException { |
| super(sqlName, OracleTypes.PLSQL_RECORD, generateMe, parentType, reflector); |
| m_rowtypeInfo = rowtypeInfo; |
| m_fieldInfo = fieldInfo; |
| m_fields = fields; |
| } |
| |
| @Override |
| public List<AttributeField> getDeclaredFields(boolean publishedOnly) throws SQLException, |
| PublisherException { |
| if (!publishedOnly) { |
| return m_fields; |
| } |
| else if (m_fieldsPublishedOnly != null) { |
| return m_fieldsPublishedOnly; |
| } |
| else { |
| ArrayList<AttributeField> fieldsCS = new ArrayList<AttributeField>(); |
| PLSQLMap map = new PLSQLMap(m_parentType, m_reflector); |
| for (int i = 0; i < m_fields.size(); i++) { |
| if (map.getMemberName(m_fields.get(i).getName()) != null) { |
| fieldsCS.add(m_fields.get(i)); |
| } |
| } |
| m_fieldsPublishedOnly = new ArrayList<AttributeField>(fieldsCS); |
| return m_fieldsPublishedOnly; |
| } |
| } |
| |
| /** |
| * Returns an array of Field objects reflecting all the accessible fields of this Type object. |
| * Returns an array of length 0 if this Type object has no accesible fields. |
| */ |
| @Override |
| public List<AttributeField> getFields(boolean publishedOnly) throws SecurityException, |
| SQLException, PublisherException { |
| return getDeclaredFields(publishedOnly); |
| } |
| |
| @Override |
| protected List<FieldInfo> getFieldInfo() { |
| return m_fieldInfo; |
| } |
| |
| public static List<FieldInfo> getFieldInfo(String schema, String packageName, String methodName, String methodNo, |
| int sequence, SqlReflector reflector) throws SQLException { |
| |
| int data_level = -1; |
| int next_rec_sequence = -1; |
| |
| // Although package_name and type_name derived from getPlsqlTypeName() |
| // can be used for the queries, we use method and sequence |
| // to be more general. If this type is defined via CURSOR%ROWTYPE, |
| // for which method, method_no and sequence has to be used to |
| // identify this type in ALL_ARGUMENTS. |
| |
| ViewCache viewCache = reflector.getViewCache(); |
| Iterator<ViewRow> iter = viewCache.getRows(ALL_ARGUMENTS, new String[0], new String[]{ |
| OWNER, PACKAGE_NAME, OBJECT_NAME, OVERLOAD}, new Object[]{schema, packageName, |
| methodName, methodNo}, new String[]{SEQUENCE}); |
| ArrayList<ViewRow> viewRows = new ArrayList<ViewRow>(); |
| while (iter.hasNext()) { |
| UserArguments item = (UserArguments)iter.next(); |
| viewRows.add(item); |
| } |
| PlsqlTypeInfo[] info = PlsqlTypeInfo.getPlsqlTypeInfo(viewRows); |
| if (info != null) { |
| for (int i = 0; i < info.length; i++) { |
| if (data_level == -1 && (sequence == -1 || sequence == info[i].sequence)) { |
| data_level = info[i].dataLevel; // Data level for the record |
| } |
| if (data_level > -1 && data_level == info[i].dataLevel && next_rec_sequence == -1 |
| && sequence < info[i].sequence) { |
| next_rec_sequence = info[i].sequence; |
| break; |
| } |
| } |
| } |
| data_level++; |
| iter = viewCache.getRows(ALL_ARGUMENTS, new String[0], new String[]{OWNER, PACKAGE_NAME, |
| OBJECT_NAME, OVERLOAD, DATA_LEVEL}, new Object[]{schema, packageName, |
| methodName, methodNo, data_level}, new String[]{SEQUENCE}); |
| viewRows = new ArrayList<ViewRow>(); |
| while (iter.hasNext()) { // DISTINCT |
| UserArguments item = (UserArguments)iter.next(); |
| if ((sequence == -1 || item.sequence > sequence) |
| && (next_rec_sequence == -1 || item.sequence < next_rec_sequence)) { |
| viewRows.add(item); |
| } |
| } |
| return FieldInfo.getFieldInfo(viewRows); |
| } |
| |
| public List<RowtypeInfo> getRowtypeInfo() { |
| return m_rowtypeInfo; |
| } |
| } |