ExportedKeyConstraint.java :  » Database-DBMS » Quadcap-Embeddable-Database » com » quadcap » sql » Java Open Source

Java Open Source » Database DBMS » Quadcap Embeddable Database 
Quadcap Embeddable Database » com » quadcap » sql » ExportedKeyConstraint.java
package com.quadcap.sql;

/* Copyright 1999 - 2003 Quadcap Software.  All rights reserved.
 *
 * This software is distributed under the Quadcap Free Software License.
 * This software may be used or modified for any purpose, personal or
 * commercial.  Open Source redistributions are permitted.  Commercial
 * redistribution of larger works derived from, or works which bundle
 * this software requires a "Commercial Redistribution License"; see
 * http://www.quadcap.com/purchase.
 *
 * Redistributions qualify as "Open Source" under  one of the following terms:
 *   
 *    Redistributions are made at no charge beyond the reasonable cost of
 *    materials and delivery.
 *
 *    Redistributions are accompanied by a copy of the Source Code or by an
 *    irrevocable offer to provide a copy of the Source Code for up to three
 *    years at the cost of materials and delivery.  Such redistributions
 *    must allow further use, modification, and redistribution of the Source
 *    Code under substantially the same terms as this license.
 *
 * Redistributions of source code must retain the copyright notices as they
 * appear in each source code file, these license terms, and the
 * disclaimer/limitation of liability set forth as paragraph 6 below.
 *
 * Redistributions in binary form must reproduce this Copyright Notice,
 * these license terms, and the disclaimer/limitation of liability set
 * forth as paragraph 6 below, in the documentation and/or other materials
 * provided with the distribution.
 *
 * The Software is provided on an "AS IS" basis.  No warranty is
 * provided that the Software is free of defects, or fit for a
 * particular purpose.  
 *
 * Limitation of Liability. Quadcap Software shall not be liable
 * for any damages suffered by the Licensee or any third party resulting
 * from use of the Software.
 */

import java.io.ByteArrayOutputStream;
import java.io.Externalizable;
import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectOutput;

import java.util.Vector;

import java.sql.ResultSet;
import java.sql.SQLException;

import com.quadcap.sql.index.Btree;
import com.quadcap.sql.index.BCursor;

import com.quadcap.util.Debug;
import com.quadcap.util.Util;

/**
 * A hidden 'ExportedKeyConstraint' is created for tables that
 * are referenced as foreign keys by other tables.
 *
 * @author Stan Bailes
 */
public class ExportedKeyConstraint extends ForeignKeyConstraint
implements Externalizable
{
    transient ImportedKeyConstraint    iConstraint;
    transient String        iConstraintName;

    String          uConstraintName;
    

    /**
     * Default constructor
     */
    public ExportedKeyConstraint() {}

    /**
     * Explicit constructor for matching ImportedKeyConstraint.
     */
    public ExportedKeyConstraint(String name, Vector colNames,
         String fTableName, Vector fColNames,
         ImportedKeyConstraint iConstraint,
         UniqueConstraint uConstraint)
        throws SQLException
    {
  super(name, colNames, fTableName, fColNames);
  this.iConstraint = iConstraint;
  this.iConstraintName = iConstraint.getName();
  this.uConstraintName = uConstraint.getName();
        uConstraint.addExportConstraint(this);
        if (this.colNames == null) {
            this.colNames = uConstraint.getColumnNames();
        }
    }

    public void delete(Session session) throws SQLException, IOException {
  UniqueConstraint uc = 
      (UniqueConstraint)table.getConstraint(uConstraintName);
        if (uc != null) {
            uc.removeExportConstraint(name);
        }
    }

    void setForeignKeyCols(int[] fCols) {
  this.fCols = fCols;
    }
    
    public void checkUpdate(Session session, byte[] oldKey, Row row,
                            Row oldRow, long rowId, Constraint activeIndex)
  throws SQLException, IOException
    {
  getComparator();
  Database db = session.getDatabase();
  byte[] newKey = makeKey(session, row);
  if (activeIndex != this) oldKey = makeKey(session, oldRow);
  if (compare.compare(newKey, oldKey) != 0) {
      ExportedKeys ek = getExportedKeys(session);
      if (isSelfReferencing(db)) {
    byte[] oldfKey = makeFKey(session, oldRow);
    byte[] newfKey = makeFKey(session, row);
    ek.addSelfRefEntry(oldKey, newKey, oldfKey, newfKey);
      } else {
    ek.addEntry(oldKey, newKey);
      }
  }
    }
    
    public void checkDelete(Session session, Row row, long rowId)
  throws SQLException, IOException
    {
        byte[] fkey = getImportedKeyConstraint(session.getDatabase()).makeFKey(session, row);
  if (isSelfReferencing(session.getDatabase())) {
      ExportedKeys ek = getExportedKeys(session);
            byte[] key = makeKey(session, row);
        ek.addDeleteSelfRef(key, fkey);
  } else {
      checkKeyRemoval(session, fkey);
  }
    }

    public void checkKeyRemoval(Session session, byte[] oldkey) 
  throws SQLException, IOException
    {
  getComparator();
  Database db = session.getDatabase();
  Btree fTree = getForeignIndex(db);
  int count = 0;
        boolean match = false;
  BCursor cursor = fTree.getCursor(false);
        try {
            boolean kvalid = cursor.seek(oldkey);
            while (!match && (kvalid || cursor.next())) {
                byte[] key = cursor.getKey();
                int cmp = compare.compare(key, oldkey);
                match = cmp == 0;
                kvalid = false;
            }
        } finally {
            cursor.release();
        }
  if (match) {
      int refSpec = iConstraint.getRefAction(DELETE);
      switch (refSpec) {
      case NOACTION:
    throw new SQLException(
        "Foreign key constraint violation: children exist",
        "23000");

      case CASCADE:
    ExportedKeys ek = getExportedKeys(session);
    ek.removeKey(refSpec, oldkey);
    break;
      case SETNULL:
      case SETDEFAULT:
    // XXX TODO: set null, set default
                throw new SQLException(
        "Foreign key constraint violation and SET " +
        "{NULL|DEFAULT} not implemented", "23000");
      }
  }
    }
    
    /**
     * Utility function to get / lazy-create the session context used
     * to keep track of key additions and removals generated by the current
     * statement.
     */
    ExportedKeys getExportedKeys(Session session) throws IOException {
  ExportedKeys ek =
            (ExportedKeys)session.getContext(this, isDeferred());
  if (ek == null) {
      ek = new ExportedKeys(session, this);
      session.putContext(this, isDeferred(), ek);
  }
  return ek;
    }
    
    ImportedKeyConstraint getImportedKeyConstraint(Database db)
  throws SQLException, IOException
    {
  if (iConstraint == null) {
      getFTable(db);
      iConstraint =
    (ImportedKeyConstraint)fTable.getConstraint(iConstraintName);
  }
  return iConstraint;
    }

    Btree getForeignIndex(Database db) throws SQLException, IOException {
  return getImportedKeyConstraint(db).getIndex(db);
    }

    public void readExternal(ObjectInput in)
  throws IOException, ClassNotFoundException
    {
  super.readExternal(in);
  iConstraintName = (String)in.readObject();
  uConstraintName = (String)in.readObject();
    }
    
    public void writeExternal(ObjectOutput out) throws IOException {
  super.writeExternal(out);
  out.writeObject(iConstraintName);
  out.writeObject(uConstraintName);
    }
}
java2s.com  | Contact Us | Privacy Policy
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.