/*
 * @(#)IAnalysisModuleUTestI.java
 *
 * Copyright (C) 2002-2003 Matt Albrecht
 * groboclown@users.sourceforge.net
 * http://groboutils.sourceforge.net
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public License
 * as published by the Free Software Foundation; either version 2
 * of the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 */

package net.sourceforge.groboutils.codecoverage.v2;

import java.io.IOException;

import net.sourceforge.groboutils.autodoc.v1.AutoDoc;
import net.sourceforge.groboutils.junit.v1.iftc.ImplFactory;
import net.sourceforge.groboutils.junit.v1.iftc.InterfaceTestCase;
import net.sourceforge.groboutils.junit.v1.iftc.InterfaceTestSuite;

import org.apache.bcel.classfile.JavaClass;
import org.apache.bcel.classfile.LineNumberTable;
import org.apache.bcel.classfile.Method;
import org.apache.bcel.generic.ConstantPoolGen;
import org.apache.bcel.generic.Instruction;
import org.apache.bcel.generic.MethodGen;


/**
 * Tests the IAnalysisModule interface.
 *
 * @author    Matt Albrecht <a href="mailto:groboclown@users.sourceforge.net">groboclown@users.sourceforge.net</a>
 * @version   $Date: 2004/04/15 05:48:27 $
 * @since     December 28, 2002
 */
public class IAnalysisModuleUTestI extends InterfaceTestCase
{
    //-------------------------------------------------------------------------
    // Standard JUnit Class-specific declarations
    
    private static final Class THIS_CLASS = IAnalysisModuleUTestI.class;
    private static final AutoDoc DOC = new AutoDoc( THIS_CLASS );
    
    public IAnalysisModuleUTestI( String name, ImplFactory f )
    {
        super( name, IAnalysisModule.class, f );
    }

    
    public IAnalysisModule createIAnalysisModule()
    {
        return (IAnalysisModule)createImplObject();
    }


    //-------------------------------------------------------------------------
    // Tests
    
    public void testGetMeasureName1()
    {
        IAnalysisModule am = createIAnalysisModule();
        String s = am.getMeasureName();
        assertNotNull(
            "Null measure name.",
            s );
        assertTrue(
            "Empty measure name.",
            s.length() > 0 );
    }
    
    
    public void testGetMeasureUnit1()
    {
        IAnalysisModule am = createIAnalysisModule();
        String s = am.getMeasureUnit();
        assertNotNull(
            "Null measure Unit.",
            s );
        assertTrue(
            "Empty measure Unit.",
            s.length() > 0 );
    }
    
    
    public void testGetMimeEncoding1()
    {
        IAnalysisModule am = createIAnalysisModule();
        String s = am.getMimeEncoding();
        assertNotNull(
            "Null mime encoding.",
            s );
        assertTrue(
            "Empty mime encoding.",
            s.length() > 0 );
        int pos = s.indexOf( '/' );
        assertTrue(
            "No '/' in mime encoding: invalid encoding type.",
            pos > 0 );
        assertTrue(
            "Multiple mime encoding types are not allowed.",
            s.indexOf( ';' ) < 0 );
    }
    
    
    private static class MockMethodCode implements IMethodCode
    {
        private Method meth;
        private Instruction[] instrL;
        private String className;
        public MockMethodCode( Class c, int methodIndex )
                throws IOException
        {
            if (c == null)
            {
                c = this.getClass();
            }
            JavaClass jc = loadBytecode( c.getName() );
            this.className = jc.getClassName();
            this.meth = jc.getMethods()[ methodIndex ];
            MethodGen mg = new MethodGen( this.meth, this.className,
                new ConstantPoolGen( jc.getConstantPool() ) );
            this.instrL = mg.getInstructionList().getInstructions();
        }
        
        public Method getOriginalMethod() { return this.meth; }
        public String getMethodName() { return this.meth.getName(); }
        public String getClassName() { return this.className; }
        public int getInstructionCount() { return this.instrL.length; }
        public Instruction getInstructionAt( int index )
        {
            if (index < 0 || index >= getInstructionCount())
            {
                throw new IndexOutOfBoundsException( ""+index );
            }
            return this.instrL[ index ];
        }
        public void markInstruction( int index, IAnalysisMetaData meta )
        {
            if (index < 0 || index >= getInstructionCount())
            {
                throw new IndexOutOfBoundsException( ""+index );
            }
            // ignore mark.
        }
        public LineNumberTable getLineNumberTable()
        { return this.meth.getLineNumberTable(); }
    }
    
    
    
    public void testAnalyze1() throws Exception
    {
        IAnalysisModule am = createIAnalysisModule();
        am.analyze( new MockMethodCode( null, 0 ) );
    }
    
    
    //-------------------------------------------------------------------------
    
    protected static JavaClass loadBytecode( String className )
            throws IOException
    {
        return BytecodeLoaderUtil.loadJavaClass( className );
    }
    
    
    
    //-------------------------------------------------------------------------
    // Standard JUnit declarations
    
    
    public static InterfaceTestSuite suite()
    {
        InterfaceTestSuite suite = new InterfaceTestSuite( THIS_CLASS );
        
        return suite;
    }
    
    public static void main( String[] args )
    {
        String[] name = { THIS_CLASS.getName() };
        
        // junit.textui.TestRunner.main( name );
        // junit.swingui.TestRunner.main( name );
        
        junit.textui.TestRunner.main( name );
    }
    
    
    /**
     * 
     * @exception Exception thrown under any exceptional condition.
     */
    protected void setUp() throws Exception
    {
        super.setUp();
        
        // set ourself up
    }
    
    
    /**
     * 
     * @exception Exception thrown under any exceptional condition.
     */
    protected void tearDown() throws Exception
    {
        // tear ourself down
        
        
        super.tearDown();
    }
}

