1/*- 2 * See the file LICENSE for redistribution information. 3 * 4 * Copyright (c) 2002,2008 Oracle. All rights reserved. 5 * 6 * $Id: ClassMetadata.java,v 1.1 2008/02/07 17:12:28 mark Exp $ 7 */ 8 9package com.sleepycat.persist.model; 10 11import java.io.Serializable; 12import java.util.List; 13import java.util.Map; 14 15/** 16 * The metadata for a persistent class. A persistent class may be specified 17 * with the {@link Entity} or {@link Persistent} annotation. 18 * 19 * <p>{@code ClassMetadata} objects are thread-safe. Multiple threads may 20 * safely call the methods of a shared {@code ClassMetadata} object.</p> 21 * 22 * <p>This and other metadata classes are classes rather than interfaces to 23 * allow adding properties to the model at a future date without causing 24 * incompatibilities. Any such property will be given a default value and 25 * its use will be optional.</p> 26 * 27 * @author Mark Hayes 28 */ 29public class ClassMetadata implements Serializable { 30 31 private static final long serialVersionUID = -2520207423701776679L; 32 33 private String className; 34 private int version; 35 private String proxiedClassName; 36 private boolean entityClass; 37 private PrimaryKeyMetadata primaryKey; 38 private Map<String,SecondaryKeyMetadata> secondaryKeys; 39 private List<FieldMetadata> compositeKeyFields; 40 41 /** 42 * Used by an {@code EntityModel} to construct persistent class metadata. 43 */ 44 public ClassMetadata(String className, 45 int version, 46 String proxiedClassName, 47 boolean entityClass, 48 PrimaryKeyMetadata primaryKey, 49 Map<String,SecondaryKeyMetadata> secondaryKeys, 50 List<FieldMetadata> compositeKeyFields) { 51 this.className = className; 52 this.version = version; 53 this.proxiedClassName = proxiedClassName; 54 this.entityClass = entityClass; 55 this.primaryKey = primaryKey; 56 this.secondaryKeys = secondaryKeys; 57 this.compositeKeyFields = compositeKeyFields; 58 } 59 60 /** 61 * Returns the name of the persistent class. 62 */ 63 public String getClassName() { 64 return className; 65 } 66 67 /** 68 * Returns the version of this persistent class. This may be specified 69 * using the {@link Entity#version} or {@link Persistent#version} 70 * annotation. 71 */ 72 public int getVersion() { 73 return version; 74 } 75 76 /** 77 * Returns the class name of the proxied class if this class is a {@link 78 * PersistentProxy}, or null otherwise. 79 */ 80 public String getProxiedClassName() { 81 return proxiedClassName; 82 } 83 84 /** 85 * Returns whether this class is an entity class. 86 */ 87 public boolean isEntityClass() { 88 return entityClass; 89 } 90 91 /** 92 * Returns the primary key metadata for a key declared in this class, or 93 * null if none is declared. This may be specified using the {@link 94 * PrimaryKey} annotation. 95 */ 96 public PrimaryKeyMetadata getPrimaryKey() { 97 return primaryKey; 98 } 99 100 /** 101 * Returns an unmodifiable map of field name to secondary key metadata for 102 * all secondary keys declared in this class, or null if no secondary keys 103 * are declared in this class. This metadata may be specified using {@link 104 * SecondaryKey} annotations. 105 */ 106 public Map<String,SecondaryKeyMetadata> getSecondaryKeys() { 107 return secondaryKeys; 108 } 109 110 /** 111 * Returns an unmodifiable list of metadata for the fields making up a 112 * composite key, or null if this is a not a composite key class. The 113 * order of the fields in the returned list determines their stored order 114 * and may be specified using the {@link KeyField} annotation. When the 115 * composite key class does not implement {@link Comparable}, the order of 116 * the fields is the relative sort order. 117 */ 118 public List<FieldMetadata> getCompositeKeyFields() { 119 return compositeKeyFields; 120 } 121 122 @Override 123 public boolean equals(Object other) { 124 if (other instanceof ClassMetadata) { 125 ClassMetadata o = (ClassMetadata) other; 126 return version == o.version && 127 entityClass == o.entityClass && 128 nullOrEqual(className, o.className) && 129 nullOrEqual(proxiedClassName, o.proxiedClassName) && 130 nullOrEqual(primaryKey, o.primaryKey) && 131 nullOrEqual(secondaryKeys, o.secondaryKeys) && 132 nullOrEqual(compositeKeyFields, o.compositeKeyFields); 133 } else { 134 return false; 135 } 136 } 137 138 @Override 139 public int hashCode() { 140 return version + 141 (entityClass ? 1 : 0) + 142 hashCode(className) + 143 hashCode(proxiedClassName) + 144 hashCode(primaryKey) + 145 hashCode(secondaryKeys) + 146 hashCode(compositeKeyFields); 147 } 148 149 static boolean nullOrEqual(Object o1, Object o2) { 150 if (o1 == null) { 151 return o2 == null; 152 } else { 153 return o1.equals(o2); 154 } 155 } 156 157 static int hashCode(Object o) { 158 if (o != null) { 159 return o.hashCode(); 160 } else { 161 return 0; 162 } 163 } 164} 165