/* ======================================================================
   Parts Copyright 2006 University of Leeds, Oxford University, University of the Highlands and Islands.

   Licensed under the Apache License, Version 2.0 (the "License");
   you may not use this file except in compliance with the License.
   You may obtain a copy of the License at

       http://www.apache.org/licenses/LICENSE-2.0

   Unless required by applicable law or agreed to in writing, software
   distributed under the License is distributed on an "AS IS" BASIS,
   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   See the License for the specific language governing permissions and
   limitations under the License.

====================================================================== */

package org.bodington.server.events;

import java.io.PrintWriter;
import java.sql.Timestamp;
import java.text.MessageFormat;
import java.util.Enumeration;
import java.util.ResourceBundle;

import org.apache.log4j.Logger;
import org.bodington.database.PrimaryKey;
import org.bodington.server.BuildingServerException;
import org.bodington.util.IntStringEnum;


/**
 * Navigation Events are used to track users moving around the site through the
 * various resources.
 * @author buckett
 */
public class NavigationEvent extends org.bodington.server.events.Event
	{
    private static Logger log = Logger.getLogger(NavigationEvent.class);
    private static ResourceBundle resourceBundle = ResourceBundle.getBundle(NavigationEvent.class.getName());
    
    
	PrimaryKey navigation_event_id;
	String url;
    
    public static class NavigationEventType extends IntStringEnum
    {
        protected NavigationEventType(String name)
        {
            super(name, NavigationEventType.class);
        }
        
        public static NavigationEventType getMapping(int index)
        {
            return (NavigationEventType)getConst(index,NavigationEventType.class);
        }
        
        public static NavigationEventType getMapping(String name)
        {
            return (NavigationEventType)getConst(name, NavigationEventType.class);
        }
        
    }
    
	public static final NavigationEventType EVENT_PAGE_ACCESS = new NavigationEventType("event.page");
    public static final NavigationEventType EVENT_RESOURCE_ACCESS = new NavigationEventType("event.resource");
    public static final NavigationEventType EVENT_FAILED_ACCESS = new NavigationEventType("event.failed");
    
    public static Event findEvent( PrimaryKey key )
    throws BuildingServerException
    {
        return (Event)findPersistentObject( key, "org.bodington.server.events.NavigationEvent" );
    }
    
    public static Event findEvent( String where )
    throws BuildingServerException
    {
        return (Event)findPersistentObject( where, "org.bodington.server.events.NavigationEvent" );
    }
    
    public static Enumeration findEvents( String where )
    throws BuildingServerException
    {
        return findPersistentObjects( where, "org.bodington.server.events.NavigationEvent" );
    }
    
    public static Enumeration findEvents( String where, String order )
    throws BuildingServerException
    {
        return findPersistentObjects( where, order, "org.bodington.server.events.NavigationEvent" );
    }
    
    public static Enumeration findEventPrimaryKeys( String where, String order )
    throws BuildingServerException
    {
        return findPrimaryKeys( where, order, "org.bodington.server.events.NavigationEvent" );
    }
    
    /**
     * Find events for a resource after a particular date. The results are sorted
     * by the time the event occurred.
     * @param resourceId The resource ID to find events for.
     * @param from The time to start looking from.
     * @return An Enumeration of Events.
     */
    public static Enumeration findEvents( PrimaryKey resourceId, long from )
    throws BuildingServerException
    {
        return findEvents("resource_id = "+ resourceId+ " AND event_time > {ts '"+ new Timestamp(from)+ "'}", "event_time");
    }
    
	public NavigationEvent()
		{
		super();
		url=null;
		}
	
	public NavigationEvent( NavigationEventType event_code, PrimaryKey resource_id, PrimaryKey user_id, String url )
		{
		super();
		
		this.event_code = event_code.getId(); 
		this.importance = Event.IMPORTANCE_MANAGEMENT_MIN;
			
		this.resource_id=resource_id;
		active_user_id=user_id;
		passive_user_id=null;
		
		this.url = url;
		}
	
	
	
	
    public PrimaryKey getPrimaryKey()
	    {
        return getNavigationEventId();
    	}

    public void setPrimaryKey( PrimaryKey key )
    	{
    	setNavigationEventId( key );
    	}

	public PrimaryKey getNavigationEventId()
		{
		return navigation_event_id;
		}
		
    public void setNavigationEventId(PrimaryKey key)
    	{
    	navigation_event_id = key;
    	setEventId( key );
    	setUnsaved();
    	}


	public void setUrl( String u )
		{
        if ( u == null )
            url = null;
        else
        {
            if ( u.length()<=128 )
                url = u;
            else
                url = u.substring( 128 );
        }
    	setUnsaved();
		}
		
	public String getUrl()
		{
		return url;
		}
		
	public void printProperties( PrintWriter writer, boolean html )
		{
		super.printProperties( writer, html );
		
		if ( html )
			writer.println( "<PRE>" );
		writer.print( "Url           : " );   writer.println( url==null?"no url":url );
		if ( html )
			writer.println( "</PRE>" );
		}

    public String messageTitle()
    {
        String params[] = {"Someone", "Someone"};
        return MessageFormat.format(resourceBundle
            .getString(NavigationEventType.getMapping(event_code).getName()),
            params);
    }
    
    public void printMessage(PrintWriter out, boolean html)
    {
        Object params[] = { "Someone", "Someone", url };
        try
        {
            params[0] = getActiveUser();
            params[1] = getPassiveUser();
        }
        catch (BuildingServerException bse)
        {}
        out.write(MessageFormat.format(resourceBundle
            .getString(NavigationEventType.getMapping(event_code).getName()),
            params));
    }
	}
	
