package org.aplikator.server.descriptor;
import java.io.Serializable;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import org.aplikator.server.data.BinaryData;
import org.aplikator.server.data.PersisterTriggers;
import org.aplikator.server.persistence.PersisterFactory;
public abstract class Entity extends LocalizedServerDescriptorBase implements Cloneable {
public static final String TIMESTAMP_NAME = "UPDATE_TIMESTAMP";
private Property<Integer> primaryKey;
// index configuration properties
private boolean indexed = false;
private int indexTraverseLevel = 1;
private boolean indexIncludeCollections = true;
private Property<Date> timeStamp;
private List<Property<? extends Serializable>> properties = new ArrayList<Property<? extends Serializable>>();
private View defaultView;
private PersisterTriggers trigger;
protected Entity(String name) {
this(name, name, "ID", name + "_ID_SQ");
}
protected Entity(String name, String tableName, String primaryKeyName) {
this(name, tableName, primaryKeyName, primaryKeyName + "_SQ");
}
protected Entity(String name, String tableName, String primaryKeyName, String sequenceName) {
super(name);
setLocalizationKey(name);
Property<Integer> pk = new Property<Integer>(this.getId() + "." + "PRIMARY_KEY", Integer.class, 0, true, this, false, null);
primaryKey = pk;
primaryKey.setLocalizationKey("ID");
Property<Date> ts = new Property<Date>(this.getId() + "." + TIMESTAMP_NAME, Date.class, 0, false, this, false, null);
timeStamp = ts;
timeStamp.setLocalizationKey("timeStamp");
PersisterFactory.getPersister().registerEntity(this, tableName);
PersisterFactory.getPersister().registerPrimaryKey(this, primaryKey, primaryKeyName, sequenceName);
PersisterFactory.getPersister().registerTimestamp(this, timeStamp, TIMESTAMP_NAME);
}
public boolean isIndexIncludeCollections() {
return indexIncludeCollections;
}
public void setIndexIncludeCollections(boolean indexIncludeCollections) {
this.indexIncludeCollections = indexIncludeCollections;
}
public int getIndexTraverseLevel() {
return indexTraverseLevel;
}
public void setIndexTraverseLevel(int indexTraverseLevel) {
this.indexTraverseLevel = indexTraverseLevel;
}
public boolean isIndexed() {
return indexed;
}
public void setIndexed(boolean indexed) {
this.indexed = indexed;
}
protected Entity map(String tableName, String primaryKeyName, String sequenceName) {
PersisterFactory.getPersister().registerEntity(this, tableName);
PersisterFactory.getPersister().registerPrimaryKey(this, primaryKey, primaryKeyName, sequenceName);
PersisterFactory.getPersister().registerTimestamp(this, timeStamp, TIMESTAMP_NAME);
return this;
}
public List<Property<? extends Serializable>> getProperties() {
return properties;
}
private <X extends Serializable> Property<X> addProperty(String name, Class<X> type, double size, boolean required, boolean virtual, String formatPattern) {
Property<X> property = new Property<X>(this.getId() + "." + name, type, size, required, this, virtual, formatPattern);
property.setLocalizationKey(this.getId() + "." + name);
properties.add(property);
if (!virtual) {
PersisterFactory.getPersister().registerProperty(this, property, name);
}
return property;
}
public Property<String> stringProperty(String name, int size, boolean required) {
return addProperty(name, String.class, size, required, false, null);
}
public Property<String> stringProperty(String name, boolean required) {
return addProperty(name, String.class, 255, required, false, null);
}
public Property<String> stringProperty(String name, int size) {
return stringProperty(name, size, false);
}
public Property<String> stringProperty(String name) {
return stringProperty(name, 255);
}
public Property<String> virtualStringProperty(String name) {
return addProperty(name, String.class, 30000, false, true, null);
}
public Property<String> virtualTextProperty(String name) {
return addProperty(name, String.class, 0, false, true, null);
}
public Property<String> textProperty(String name) {
return addProperty(name, String.class, 0, false, false, null);
}
public Property<Boolean> booleanProperty(String name, boolean required) {
return addProperty(name, Boolean.class, 0, required, false, null);
}
public Property<Boolean> booleanProperty(String name) {
return booleanProperty(name, false);
}
public Property<Boolean> virtualBooleanProperty(String name) {
return addProperty(name, Boolean.class, 0, false, true, null);
}
public Property<BigDecimal> numericProperty(String name, double size, boolean required) {
return addProperty(name, BigDecimal.class, size, required, false, null);
}
public Property<BigDecimal> numericProperty(String name) {
return numericProperty(name, 10.2, false);
}
public Property<BigDecimal> virtualNumericProperty(String name, double size) {
return addProperty(name, BigDecimal.class, size, false, true, null);
}
public Property<BigDecimal> virtualNumericProperty(String name) {
return virtualNumericProperty(name, 10.2);
}
public Property<Integer> integerProperty(String name, boolean required) {
return addProperty(name, Integer.class, 10.0, required, false, null);
}
public Property<Integer> integerProperty(String name) {
return integerProperty(name, false);
}
public Property<Integer> virtualIntegerProperty(String name) {
return addProperty(name, Integer.class, 10.0, false, true, null);
}
public Property<Date> dateProperty(String name, boolean required, String formatPattern) {
return addProperty(name, Date.class, 0, required, false, formatPattern);
}
public Property<Date> dateProperty(String name, boolean required) {
return dateProperty(name, required, null);
}
public Property<Date> dateProperty(String name) {
return dateProperty(name, false);
}
public Property<Date> virtualDateProperty(String name) {
return addProperty(name, Date.class, 0, false, true, null);
}
public BinaryProperty binaryProperty(String name) {
BinaryProperty property = new BinaryProperty(this.getId() + "." + name, this);
property.setLocalizationKey(this.getId() + "." + name);
properties.add(property);
PersisterFactory.getPersister().registerProperty(this, property, name);
return property;
}
public <T extends Entity> Reference<T> referenceProperty(T referredEntity, String name) {
return referenceProperty(referredEntity, name, name);
}
public <T extends Entity> Reference<T> referenceProperty(T referredEntity, String name, boolean required) {
return referenceProperty(referredEntity, name, name, required);
}
public <T extends Entity> Reference<T> referenceProperty(T referredEntity, String name, String mapping) {
return referenceProperty(referredEntity, name, mapping, null);
}
public <T extends Entity> Reference<T> referenceProperty(T referredEntity, String name, String mapping, boolean required) {
return referenceProperty(referredEntity, name, mapping, null, required);
}
public <T extends Entity> Reference<T> referenceProperty(T referredEntity, String name, String mapping, String indexName) {
return referenceProperty(referredEntity, name, mapping, indexName, false);
}
public <T extends Entity> Reference<T> referenceProperty(T referredEntity, String name, String mapping, String indexName, boolean required) {
Reference<T> property = new Reference<T>(this.getId() + "." + name, referredEntity, this, required);
property.setLocalizationKey(this.getId() + "." + name);
properties.add(property);
if (indexName == null) {
PersisterFactory.getPersister().registerReference(this, property, mapping, referredEntity);
} else {
PersisterFactory.getPersister().registerReference(this, property, mapping, referredEntity, indexName);
}
return property;
}
public <T extends Entity> Collection<T> collectionProperty(T referredEntity, String name) {
return collectionProperty(referredEntity, name, name);
}
public <T extends Entity> Collection<T> collectionProperty(T referredEntity, String name, String mapping) {
return collectionProperty(referredEntity, name, mapping, null);
}
public <T extends Entity> Collection<T> collectionProperty(T referredEntity, String name, String mapping, String indexName) {
Collection<T> property = new Collection<T>(this.getId() + "." + name, referredEntity, this);
property.setLocalizationKey(this.getId() + "." + name);
properties.add(property);
PersisterFactory.getPersister().registerReference(referredEntity, property, mapping, this, indexName);
return property;
}
public <T extends Entity> Collection<T> reverseCollectionProperty(String name, T referredEntity, Reference<? extends Entity> referringColumn) {
Collection<T> property = new Collection<T>(this.getId() + "." + name, referredEntity, this);
property.setLocalizationKey(this.getId() + "." + name);
properties.add(property);
PersisterFactory.getPersister().registerReverseCollection(property, referringColumn);
return property;
}
public Property<Integer> getPrimaryKey() {
return primaryKey;
}
public Property<Date> getTimeStamp() {
return timeStamp;
}
public void addIndex(String name, boolean unique, Property<?>... properties) {
PersisterFactory.getPersister().registerIndex(this, name, unique, properties);
}
public PersisterTriggers getPersisterTriggers() {
if (this.trigger == null) {
this.setPersistersTriggers(new PersisterTriggers.Default());
}
return this.trigger;
}
public Entity setPersistersTriggers(PersisterTriggers triggers) {
this.trigger = triggers;
return this;
}
public synchronized View view() {
if (defaultView == null) {
defaultView = initDefaultView();
}
return defaultView;
}
/**
* Create the default view for this entity. The view contains all properties
* except References, Collections and BinaryData. It has simple form with
* VerticalPanel, containing default widgets for all properties, obtained
* from Property.widget() method
*
* @return The default view
* @see Property
*/
protected View initDefaultView() {
View retval = new View(this);
Form form = new Form(true);
Panel layout = Panel.column();
for (Property<? extends Serializable> prop : properties) {
if (!((prop instanceof Reference) || (prop instanceof Collection) || (prop.getType().equals(BinaryData.class)))) {
retval.addProperty(prop);
}
layout.add(prop.widget());
}
form.setLayout(layout);
retval.setForm(form);
if (retval.getProperties().size() > 0) {
Property<? extends Serializable> prop = retval.getProperties().get(0);
retval.addSortDescriptor("Default", prop.getLocalizationKey(), SortItem.ascending(prop));
}
return retval;
}
public View inheritanceView(View masterView, Property<String> discriminator, Enum<?> value) {
View view = new SubView(masterView, discriminator, value);
PersisterFactory.getPersister().addInheritanceIndex(this, discriminator);
return view;
}
}