/**
 * Distributable under LGPL license.
 * See terms of license at gnu.org.
 *
 * Copyright (C)
 * <a href="http://www.inab.org">Spanish National Institute of Bioinformatics (INB)</a>
 * <a href="http://www.bsc.es">Barcelona Supercomputing Center (BSC)</a>
 * <a href="http://inb.bsc.es">Computational Node 6</a>
 */

package org.inb.biomoby.shared.registry;

import java.io.Serializable;
import javax.xml.bind.annotation.XmlAttribute;
import javax.xml.bind.annotation.XmlTransient;

/**
 * <p>
 * An abstract class that represents any Moby Central entity that could be named
 * </p>
 *
 * @author Dmitry Repchevsky
 *
 */

@XmlTransient
public class AbstractEntity<T extends AbstractEntity> implements Comparable<T>, Serializable, Cloneable
{
    protected String name;
    protected String authURI;
    protected String contactEmail;
    protected String title;
    protected String description;
    
    private String lsid;

    public AbstractEntity() {}
    
    public AbstractEntity(String name)
    {
        this.name = name;
    }
    
    public AbstractEntity(String name, String authURI)
    {
        this.name = name;
        this.authURI = authURI;
    }
    
    @XmlAttribute
    public String getName()
    {
        return name == null ? "" : name;
    }

    public void setName(String name)
    {
        this.name = name;
    }

    @XmlAttribute(name="authority_uri")
    public String getAuthURI()
    {
        return authURI;
    }

    public void setAuthURI(String authURI)
    {
        this.authURI = authURI;
    }

    @XmlAttribute(name="contact_email")
    public String getContactEmail()
    {
        return contactEmail;
    }

    public void setContactEmail(String contactEmail)
    {
        this.contactEmail = contactEmail;
    }

    @XmlAttribute
    public String getTitle()
    {
        return title;
    }

    public void setTitle(String title)
    {
        this.title = title;
    }

    @XmlAttribute
    public String getDescription()
    {
        return description;
    }

    public void setDescription(String description)
    {
        this.description = description;
    }
    
    @XmlAttribute
    public String getLsid()
    {
        return lsid;
    }

    public void setLsid(String lsid)
    {
        this.lsid = lsid;
    }
    
    public int compareTo(AbstractEntity entity)
    {
        if (this == entity)
        {
            return 0;
        }
        
        if(this.getName().equals(entity.getName()))
        {
            return this.authURI == null || entity.authURI == null ? 0 : this.authURI.compareTo(entity.authURI);
        }
        
        return this.getName().compareTo(entity.name);
    }

    @Override
    public boolean equals(Object object)
    {
        if (object == this)
        {
            return true;
        }

        if (object != null && object instanceof AbstractEntity)
        {
            AbstractEntity entity = (AbstractEntity)object;

            return this.getName().equals(entity.getName()) &&
                   (this.authURI == null || entity.authURI == null || this.authURI.equals(entity.authURI));
        }

        return false;
    }
    
    @Override
    public int hashCode()
    {
        int hash = 7;
        hash = 59 * hash + (this.name != null ? this.name.hashCode() : 0);
        hash = 59 * hash + (this.authURI != null ? this.authURI.hashCode() : 0);
        return hash;
    }

    @Override
    public AbstractEntity<T> clone()
    {
        AbstractEntity<T> clone;
        
        try
        {
            clone = (AbstractEntity<T>)super.clone();
        }
        catch(CloneNotSupportedException ex)
        {
            clone = null;
        }

        return clone;
    }
}
