Package com.sleepycat.je.log

Source Code of com.sleepycat.je.log.LogEntryType$UserLNLogEntryType

/*-
* See the file LICENSE for redistribution information.
*
* Copyright (c) 2002, 2011 Oracle and/or its affiliates.  All rights reserved.
*
*/

package com.sleepycat.je.log;

import java.util.HashSet;
import java.util.Set;

import com.sleepycat.je.DatabaseException;
import com.sleepycat.je.log.entry.BINDeltaLogEntry;
import com.sleepycat.je.log.entry.DeletedDupLNLogEntry;
import com.sleepycat.je.log.entry.FileHeaderEntry;
import com.sleepycat.je.log.entry.INLogEntry;
import com.sleepycat.je.log.entry.LNLogEntry;
import com.sleepycat.je.log.entry.LogEntry;
import com.sleepycat.je.log.entry.NameLNLogEntry;
import com.sleepycat.je.log.entry.SingleItemEntry;

/**
* LogEntryType is an  enumeration of all log entry types.
*
* <p>Log entries are versioned. When changing the persistent form of a log
* entry in any way that is incompatible with prior releases, make sure the
* LogEntry instance is capable of reading in older versions from the log and
* be sure to increment LOG_VERSION.  The LogEntry.readEntry and
* Loggable.readFromLog methods should check the actual version of the entry.
* If it is less than LOG_VERSION, the old version should be converted to the
* current version.
*
* <p>Prior to LOG_VERSION 6, each log entry type had a separate version number
* that was incremented only when that log version changed.  From LOG_VERSION 6
* onward, all types use the same version, the LOG_VERSION constant.  For
* versions prior to 6, the readEntry and readFromLog methods will be checking
* the old per-type version.  There is no overlap between the old per-type
* versions and the LOG_VERSION values, because the per-type values are all
* below 6. [#15365]</p>

* <p>The LogEntry instance must be sure that older versions are converted in
* memory into a correct instance of the newest version, so when that LogEntry
* object is written again as the result of migration, eviction, the resulting
* new log entry conforms to the requirements of the new version.  If context
* objects are required for data conversion, the conversion can be done in the
* Node.postFetchInit method.</p>
*/
public class LogEntryType {

    /**
     * Version of the file header, which identifies the version of all entries
     * in that file.
     *
     * Changes to log entries for each version are:
     *
     * Version 3
     * ---------
     * [12328] Add main and dupe tree fanout values for DatabaseImpl.
     * [12557] Add IN LSN array compression.
     * [11597] Add a change to FileSummaryLNs: obsolete offset tracking was
     * added and multiple records are stored for a single file rather than a
     * single record.  Each record contains the offsets that were tracked since
     * the last record was written.
     * [11597] Add the full obsolete LSN in LNLogEntry.
     *
     * Version 4
     * ---------
     * [#14422] Bump MapLN version from 1 to 2.  Instead of a String for the
     * comparator class name, store either a serialized string or Comparator.
     *
     * Version 5
     * ---------
     * [#15195] FileSummaryLN version 3.  Add FileSummary.obsoleteLNSize and
     * obsoleteLNSizeCounted fields.
     *
     * Version 6 (in JE 3.3.X)
     * ---------
     * [#15365] From this point onward, all log entries have the same version,
     * LOG_VERSION, rather than using per-type versions.
     * [#15365] DatabaseImpl stores a map of DbFileSummaries.
     *
     * [#13467] Convert duplicatesAllowed boolean to DUPS_ALLOWED_BIT flag in
     * DatabaseImpl. Add REPLICATED_BIT flag to DatabaseImpl.
     * [#13467] Add REPLICATED_BIT to DbTree.
     * [#13467] Add ReplicatedDatabaseConfig to NameLN_TX to support
     * replication of database operations.
     *
     * [#15581] Add lastAllocateReplicatedDbId to DbTree
     * [#16083] Add replication master node ID to txn commit/abort
     *
     * Version 7 (in JE 4.0)
     * ---------------------
     * Add the invisible bit in the entry header version field.
     * Add the RollbackStart log entry type
     * Add the RollbackEnd log entry type
     * Add the Matchpoint log entry type.
     *
     * Version 8 (in JE 5.0)
     * ---------------------
     * Made provisions for storing Triggers in a DatabaseImpl.
     *
     * Database IDs enlarged from int or packed int, to long or packed long
     * (note that packed int and packed long are compatible).  [#18540]
     *
     * Add new log entry types for LN delete, insert and update. [#18055]
     *
     * Apply optimization to omit key size for some internal LNs, in addition
     * to user LNs. [#18055]
     *
     * LN no longer has node ID. [#18633]
     *
     * Add FileSummary.maxLNSize. [#18633]
     *
     * VLSN is optionally maintained in LogEntryHeader for cleaner migrated LNs
     * and a new VLSN_PRESENT entry header flag is used to signify the presence
     * of the VLSN.  PRESERVE_VLSN_BIT was added to DbTree to correspond to the
     * je.env.preserveRecordVersion environment config param. [#19476]
     *
     * Dup tree representation changed to use two-part keys. Deprecated: DIN,
     * DBIN, DupCountLN, INDeleteInfo, INDupDeleteInfo.  Removed
     * DatabaseImpl.maxDupTreeEntriesPerNode.  [#19165]
     */
    public static final int LOG_VERSION = 8;

    public static final int FIRST_LOG_VERSION = 1;

    /**
     * Should be used for reading the entry header of the file header, since
     * the actual version is not known until the FileHeader item is read.
     */
    public static final int UNKNOWN_FILE_HEADER_VERSION = -1;

    /*
     * Collection of log entry type classes, used to read the log.  Note that
     * this must be declared before any instances of LogEntryType, since the
     * constructor uses this map. Each statically defined LogEntryType should
     * register itself with this collection.
     */
    private static final int MAX_TYPE_NUM = 36;
    private static LogEntryType[] LOG_TYPES = new LogEntryType[MAX_TYPE_NUM];

    /*
     * Enumeration of log entry types. The log entry type represents the 2 byte
     * field that starts every log entry. The top byte is the log type, the
     * bottom byte holds the version value, provisional bit, replicated bit,
     * and invisible bit.
     *
     * Log type(8 bits)
     * Provisional(2 bits) Replicated(1 bit) Invisible(1 bit) Version(5 bits)
     *
     * The top byte (log type) identifies the type and can be used to lookup
     * the LogEntryType object, while the bottom byte has information about the
     * entry (instance) of this type.  The bottom byte is effectively entry
     * header information that is common to all types and is managed by methods
     * in LogEntryHeader. See LogEntryHeader.java
     */

    /*  Node types */

    /*
     * Deprecated transactional LN entry type, use LOG_DEL_LN_TRANSACTIONAL,
     * LOG_INS_LN_TRANSACTIONAL, LOG_UPD_LN_TRANSACTIONAL instead according to
     * the operation type.
     */
    public static final LogEntryType LOG_OLD_LN_TRANSACTIONAL =
        new LogEntryType
        ((byte) 1, "LN_TX",
         new LNLogEntry(com.sleepycat.je.tree.LN.class),
         Txnal.TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_NO_MATCH,
         NodeType.LN_USER);

    /*
     * Deprecated LN entry type, use LOG_DEL_LN, LOG_INS_LN, LOG_UPD_LN instead
     * according to the operation type.
     */
    public static final LogEntryType LOG_OLD_LN =
        new LogEntryType
        ((byte) 2, "LN",
         new LNLogEntry(com.sleepycat.je.tree.LN.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_NO_MATCH,
         NodeType.LN_USER);

    public static final LogEntryType LOG_MAPLN_TRANSACTIONAL =
        new LogEntryType
        ((byte) 3, "MapLN_TX",
         new LNLogEntry(com.sleepycat.je.tree.MapLN.class),
         Txnal.TXNAL,
         Marshall.INSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.LN_INTERNAL);

    public static final LogEntryType LOG_MAPLN =
        new LogEntryType
        ((byte) 4, "MapLN",
         new LNLogEntry(com.sleepycat.je.tree.MapLN.class),
         Txnal.NON_TXNAL,
         Marshall.INSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.LN_INTERNAL);

    public static final LogEntryType LOG_NAMELN_TRANSACTIONAL =
        new LogEntryType
        ((byte) 5, "NameLN_TX",
         new NameLNLogEntry(),
         Txnal.TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_NO_MATCH,
         NodeType.LN_INTERNAL);

    public static final LogEntryType LOG_NAMELN =
        new LogEntryType
        ((byte) 6, "NameLN",
         new NameLNLogEntry(),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_NO_MATCH,
         NodeType.LN_INTERNAL);

    /* Obsolete in version 8, only used by some log readers. */
    public static final LogEntryType LOG_DEL_DUPLN_TRANSACTIONAL =
        new LogEntryType
        ((byte) 7, "DelDupLN_TX",
         new DeletedDupLNLogEntry(),
         Txnal.TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_NO_MATCH,
         NodeType.LN_USER);

    /* Obsolete in version 8, only used by some log readers. */
    public static final LogEntryType LOG_DEL_DUPLN =
        new LogEntryType
        ((byte) 8, "DelDupLN",
         new DeletedDupLNLogEntry(),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_NO_MATCH,
         NodeType.LN_USER);

    /* Obsolete in version 8, only used by DupConvert and some log readers. */
    public static final LogEntryType LOG_DUPCOUNTLN_TRANSACTIONAL =
        new LogEntryType
        ((byte) 9, "DupCountLN_TX",
         new LNLogEntry(com.sleepycat.je.tree.dupConvert.DupCountLN.class),
         Txnal.TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.OLD_DUP);

    /* Obsolete in version 8, only used by DupConvert and some log readers. */
    public static final LogEntryType LOG_DUPCOUNTLN =
        new LogEntryType
        ((byte) 10, "DupCountLN",
         new LNLogEntry(com.sleepycat.je.tree.dupConvert.DupCountLN.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.OLD_DUP);

    public static final LogEntryType LOG_FILESUMMARYLN =
        new LogEntryType
        ((byte) 11, "FileSummaryLN",
         new LNLogEntry(com.sleepycat.je.tree.FileSummaryLN.class),
         Txnal.NON_TXNAL,
         Marshall.INSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.LN_INTERNAL);

    public static final LogEntryType LOG_IN =
        new LogEntryType
        ((byte) 12, "IN",
         new INLogEntry(com.sleepycat.je.tree.IN.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.IN);

    public static final LogEntryType LOG_BIN =
        new LogEntryType
        ((byte) 13, "BIN",
         new INLogEntry(com.sleepycat.je.tree.BIN.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.IN);

    /* Obsolete in version 8, only used by DupConvert and some log readers. */
    public static final LogEntryType LOG_DIN =
        new LogEntryType
        ((byte) 14, "DIN",
         new INLogEntry(com.sleepycat.je.tree.dupConvert.DIN.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.OLD_DUP);

    /* Obsolete in version 8, only used by DupConvert and some log readers. */
    public static final LogEntryType LOG_DBIN =
        new LogEntryType
        ((byte) 15, "DBIN",
         new INLogEntry(com.sleepycat.je.tree.dupConvert.DBIN.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.OLD_DUP);

    /*
     * The root entry of the DbTree, it saves the root information for name
     * and id database.
     */
    public static final LogEntryType LOG_DBTREE =
        new LogEntryType
        ((byte) 16, "DbTree",
         new SingleItemEntry
         (com.sleepycat.je.dbi.DbTree.class),
         Txnal.NON_TXNAL,
         Marshall.INSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    /* Transactional entries */
    public static final LogEntryType LOG_TXN_COMMIT =
        new LogEntryType
        ((byte) 17, "Commit",
         new SingleItemEntry
         (com.sleepycat.je.txn.TxnCommit.class),
         Txnal.TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_MATCH,
         NodeType.NONE);

    public static final LogEntryType LOG_TXN_ABORT =
        new LogEntryType
        ((byte) 18, "Abort",
         new SingleItemEntry
         (com.sleepycat.je.txn.TxnAbort.class),
         Txnal.TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_MATCH,
         NodeType.NONE);

    public static final LogEntryType LOG_CKPT_START =
        new LogEntryType
        ((byte) 19, "CkptStart",
         new SingleItemEntry
         (com.sleepycat.je.recovery.CheckpointStart.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    public static final LogEntryType LOG_CKPT_END =
        new LogEntryType
        ((byte) 20, "CkptEnd",
         new SingleItemEntry
         (com.sleepycat.je.recovery.CheckpointEnd.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    /* Obsolete in version 8, only used by some log readers. */
    public static final LogEntryType LOG_IN_DELETE_INFO =
        new LogEntryType
        ((byte) 21, "INDelete",
         new SingleItemEntry
         (com.sleepycat.je.tree.dupConvert.INDeleteInfo.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    public static final LogEntryType LOG_BIN_DELTA =
        new LogEntryType
        ((byte) 22, "BINDelta",
         new BINDeltaLogEntry
         (com.sleepycat.je.tree.BINDelta.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    /* Obsolete in version 8, only used by some log readers. */
    public static final LogEntryType LOG_DUP_BIN_DELTA =
        new LogEntryType
        ((byte) 23, "DupBINDelta",
         new BINDeltaLogEntry
         (com.sleepycat.je.tree.BINDelta.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    /* Administrative entries */
    public static final LogEntryType LOG_TRACE =
        new LogEntryType
        ((byte) 24, "Trace",
         new SingleItemEntry
         (com.sleepycat.je.log.Trace.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_NO_MATCH,
         NodeType.NONE);

    /* File header */
    public static final LogEntryType LOG_FILE_HEADER =
        new LogEntryType
        ((byte) 25, "FileHeader",
         new FileHeaderEntry
         (com.sleepycat.je.log.FileHeader.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    /* Obsolete in version 8, only used by some log readers. */
    public static final LogEntryType LOG_IN_DUPDELETE_INFO =
        new LogEntryType
        ((byte) 26, "INDupDelete",
         new SingleItemEntry
         (com.sleepycat.je.tree.dupConvert.INDupDeleteInfo.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    public static final LogEntryType LOG_TXN_PREPARE =
        new LogEntryType
        ((byte) 27, "Prepare",
         new SingleItemEntry
         (com.sleepycat.je.txn.TxnPrepare.class),
         Txnal.TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    public static final LogEntryType LOG_ROLLBACK_START =
        new LogEntryType
        ((byte) 28, "RollbackStart",
         new SingleItemEntry
         (com.sleepycat.je.txn.RollbackStart.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    public static final LogEntryType LOG_ROLLBACK_END =
        new LogEntryType
        ((byte) 29, "RollbackEnd",
         new SingleItemEntry
         (com.sleepycat.je.txn.RollbackEnd.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.LOCAL,
         NodeType.NONE);

    public static final LogEntryType LOG_MATCHPOINT =
        new LogEntryType
        ((byte) 30, "Matchpoint",
         new SingleItemEntry
         (com.sleepycat.je.utilint.Matchpoint.class),
         Txnal.NON_TXNAL,
         Marshall.OUTSIDE_LATCH,
         Replicable.REPLICABLE_MATCH,
         NodeType.NONE);

    public static final LogEntryType LOG_DEL_LN_TRANSACTIONAL =
        new UserLNLogEntryType((byte) 31, "DEL_LN_TX", Txnal.TXNAL);

    public static final LogEntryType LOG_DEL_LN =
        new UserLNLogEntryType((byte) 32, "DEL_LN", Txnal.NON_TXNAL);

    public static final LogEntryType LOG_INS_LN_TRANSACTIONAL =
        new UserLNLogEntryType((byte) 33, "INS_LN_TX", Txnal.TXNAL);

    public static final LogEntryType LOG_INS_LN =
        new UserLNLogEntryType((byte) 34, "INS_LN", Txnal.NON_TXNAL);

    public static final LogEntryType LOG_UPD_LN_TRANSACTIONAL =
        new UserLNLogEntryType((byte) 35, "UPD_LN_TX", Txnal.TXNAL);

    public static final LogEntryType LOG_UPD_LN =
        new UserLNLogEntryType((byte) 36, "UPD_LN", Txnal.NON_TXNAL);

    /*** If you add new types, be sure to update MAX_TYPE_NUM at the top.***/

    /* Persistent fields */
    private final byte typeNum; // persistent value for this entry type

    /* Transient fields */
    private final String displayName;
    private final LogEntry logEntry;

    /*
     * Attributes
     */

    /* Whether the log entry holds a transactional information. */
    private Txnal isTransactional;

    /*
     * Does this log entry be marshalled outside or inside the log write
     * latch.
     */
    private Marshall marshallBehavior;

    /* Can this log entry be put in the replication stream? */
    private Replicable replicationPossible;

    private NodeType nodeType;

    /*
     * Constructors
     */

    /**
     * For base class support.
     */

    /*
     * This constructor only used when the LogEntryType is being used as a key
     * for a map. No log types can be defined outside this package.
     */
    LogEntryType(byte typeNum) {
        this.typeNum = typeNum;
        displayName = null;
        logEntry = null;
    }

    /**
     * Create the static log types.
     * @param isTransactional true if this type of log entry holds data
     * involved in a transaction. For example, transaction commit and LN data
     * records are transactional, but INs are not.
     * @param marshallOutsideLatch true if this type of log entry may be
     * serialized outside the log write latch. This is true of the majority of
     * types. Certain types like the FileSummaryLN rely on the log write latch
     * to enforce serial semantics.
     * @param replicationPossible true if this type of log entry can be shared
     * with a replication group.
     */
    private LogEntryType(byte typeNum,
                         String displayName,
                         LogEntry logEntry,
                         Txnal isTransactional,
                         Marshall marshallBehavior,
                         Replicable replicationPossible,
                         NodeType nodeType) {

        this.typeNum = typeNum;
        this.displayName = displayName;
        this.logEntry = logEntry;
        this.isTransactional = isTransactional;
        this.marshallBehavior = marshallBehavior;
        this.replicationPossible = replicationPossible;
        this.nodeType = nodeType;
        logEntry.setLogType(this);
        LOG_TYPES[typeNum - 1] = this;
    }

    /**
     * @return the static version of this type
     */
    public static LogEntryType findType(byte typeNum) {
        if (typeNum <= 0 || typeNum > MAX_TYPE_NUM) {
            return null;
        }
        return LOG_TYPES[typeNum - 1];
    }

    /**
     * Get a copy of all types for unit testing.
     */
    public static Set<LogEntryType> getAllTypes() {
        HashSet<LogEntryType> ret = new HashSet<LogEntryType>();

        for (int i = 0; i < MAX_TYPE_NUM; i++) {
            ret.add(LOG_TYPES[i]);
        }
        return ret;
    }

    /**
     * @return the log entry type owned by the shared, static version
     */
    public LogEntry getSharedLogEntry() {
        return logEntry;
    }

    /**
     * @return a clone of the log entry type for a given log type.
     */
    public LogEntry getNewLogEntry()
        throws DatabaseException {

        return logEntry.clone();
    }

    public byte getTypeNum() {
        return typeNum;
    }

    /**
     * @return true if type number is valid.
     */
    static boolean isValidType(byte typeNum) {
        return typeNum > 0 && typeNum <= MAX_TYPE_NUM;
    }

    public String toStringNoVersion() {
        return displayName;
    }

    @Override
    public String toString() {
        return displayName;
    }

    /**
     * Check for equality without making a new object.
     */
    public boolean equalsType(byte type) {
        return (this.typeNum == type);
    }

    /*
     * Override Object.equals. Ignore provisional bit when checking for
     * equality.
     */
    @Override
    public boolean equals(Object obj) {
        /* Same instance? */
        if (this == obj) {
            return true;
        }

        /* Is it the right type of object? */
        if (!(obj instanceof LogEntryType)) {
            return false;
        }

        return typeNum == ((LogEntryType) obj).typeNum;
    }

    /**
     * This is used as a hash key.
     */
    @Override
    public int hashCode() {
        return typeNum;
    }

    static enum Txnal {
        TXNAL(true),
        NON_TXNAL(false);

        private final boolean isTxnal;

        Txnal(boolean isTxnal) {
            this.isTxnal = isTxnal;
        }

        boolean isTransactional() {
            return isTxnal;
        }
    }

    /**
     * Return true if this log entry has transactional information in it,
     * like a commit or abort record, or a transactional LN.
     */
    public boolean isTransactional() {
        return isTransactional.isTransactional();
    }

    static enum Marshall {
        OUTSIDE_LATCH(true),
        INSIDE_LATCH(false);

        private final boolean marshallOutsideLatch;

        Marshall(boolean marshallOutsideLatch) {
            this.marshallOutsideLatch = marshallOutsideLatch;
        }

        boolean marshallOutsideLatch() {
            return marshallOutsideLatch;
        }
    }

    /**
     * Return true if this log entry should be marshalled into a buffer outside
     * the log write latch. Currently, only the FileSummaryLN and MapLN (which
     * contains DbFileSummary objects) need to be logged inside the log write
     * latch.
     */
    public boolean marshallOutsideLatch() {
        return marshallBehavior.marshallOutsideLatch();
    }

    /**
     * Return true if the type of this LogEntryType is equivalent to typeB.
     * Version is used as a factor in the comparison when new log entry types
     * are introduced in one release, which supercede existing types.
     */
    public boolean compareTypeAndVersion(int verionA,
                                         int versionB,
                                         byte typeB) {
        return typeNum == typeB;
    }

    /*
     * Indicates whether this type of log entry is shared in a replicated
     * environment or not, and whether it can be used as a replication
     * matchpoint.
     */
    static enum Replicable {
        REPLICABLE_MATCH(true, true),
        REPLICABLE_NO_MATCH(true, false),
        LOCAL(false, false);

        private final boolean isReplicable;
        private final boolean isMatchable;

        Replicable(boolean isReplicable, boolean isMatchable) {
            this.isReplicable = isReplicable;
            this.isMatchable = isMatchable;
        }

        boolean isReplicable() {
            return isReplicable;
        }

        boolean isMatchable() {
            return isMatchable;
        }
    }

    /**
     * Return true if this type of log entry can be part of the replication
     * stream. For example, INs can never be replicated, while LNs are
     * replicated only if their owning database is replicated.
     */
    public boolean isReplicationPossible() {
        return replicationPossible.isReplicable();
    }

    /**
     * Return true if this type of log entry can serve as the synchronization
     * matchpoint for the replication stream. That generally means that this
     * log entry contains an replication node ID.
     */
    public boolean isSyncPoint() {
        return replicationPossible.isMatchable();
    }

    /**
     * Return true if this type of log entry can serve as the synchronization
     * matchpoint for the replication stream.
     */
    public static boolean isSyncPoint(byte entryType) {
        return findType(entryType).isSyncPoint();
    }

    /* Type of Btree node. */
    static enum NodeType {

        /* Not a Btree node. */
        NONE,

        /* Internal node. Does not include old-format DIN/DBIN. */
        IN,

        /* DIN/DBIN/DupCountLN in old-format duplicates database. */
        OLD_DUP,

        /* LNs representing records in internal databases. */
        LN_INTERNAL,

        /* LNs representing ordinary user records.  */
        LN_USER;
    }

    public boolean isNodeType() {
        return nodeType != NodeType.NONE;
    }

    public boolean isUserLNType() {
        return nodeType == NodeType.LN_USER;
    }

    public boolean isLNType() {
        return nodeType == NodeType.LN_INTERNAL || isUserLNType();
    }

    public boolean isINType() {
        return nodeType == NodeType.IN;
    }

    public boolean isOldDupType() {
        return nodeType == NodeType.OLD_DUP;
    }

    /**
     * Return true if the two types are equal. Handles the situation where new
     * log entry types were introduced in one release, that are actually
     * equivalent to old, deprecated types.
     */
    public static boolean compareTypeAndVersion(int versionA,
                                                byte typeA,
                                                int versionB,
                                                byte typeB) {
        LogEntryType entryA = findType(typeA);
        return entryA.compareTypeAndVersion(versionA, versionB, typeB);
    }

    private static class UserLNLogEntryType extends LogEntryType {
        public UserLNLogEntryType(byte typeNum,
                                  String displayName,
                                  Txnal txnal) {
            super(typeNum, displayName,
                  new LNLogEntry(com.sleepycat.je.tree.LN.class),
                  txnal, Marshall.OUTSIDE_LATCH,
                  Replicable.REPLICABLE_NO_MATCH, NodeType.LN_USER);
        }

        @Override
        public boolean compareTypeAndVersion(int versionA,
                                             int versionB,
                                             byte typeB) {
            /* If the other entry is newer, the types should match. */
            if (versionA <= versionB && getTypeNum() == typeB) {
                return true;
            }

            /*
             * If the other entry is older, the type might be an old,
             * deprecated, equivalent type.
             */
            if ((versionA > versionB) && isEquivalentOldType(typeB)) {
                return true;
            }

            /*
             * In this case, the other entry's version is older or newer but it
             * doesn't matter -- it's completely the wrong type.
             */
            return false;
        }

        private boolean isEquivalentOldType(byte typeB) {
            if ((!isTransactional() && (typeB == LOG_OLD_LN.getTypeNum())) ||
                (isTransactional() &&
                 (typeB == LOG_OLD_LN_TRANSACTIONAL.getTypeNum()))) {
                return true;
            }

            return false;
        }
    }
}
TOP

Related Classes of com.sleepycat.je.log.LogEntryType$UserLNLogEntryType

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.