/*
 * Copyright (c) 2007, 2009, Oracle and its affiliates. All rights reserved.
 * ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
 */

/*
 * $Id: ClientFactory.java 62602 2011-04-21 14:51:41Z kgrucci $
 */

/* Copyright (c) 2003 Oracle Corporation.  All rights reserved.  */
package com.sun.ts.tests.jaxws.sharedclients;

import java.lang.reflect.Constructor;
import java.util.Properties;

import com.sun.ts.lib.harness.EETest;
import com.sun.ts.lib.harness.ServiceEETest;
import com.sun.ts.lib.util.TestUtil;
import com.sun.ts.tests.jaxws.wsi.utils.PropertyUtils;

import javax.xml.ws.Service;

public class ClientFactory {

    public static SOAPClient getClient(Class clazz, Properties properties) throws EETest.Fault {
	return getClient(clazz, properties, null, null);
    }

    public static SOAPClient getClient(Class clazz, Properties properties, ServiceEETest theTest, Service theService) throws EETest.Fault {
        int mode;
        String property = properties.getProperty("platform.mode");
        if (property == null) {
            throw new EETest.Fault("The 'platform.mode' property value is not defined");
        }
        if (property.equalsIgnoreCase("standalone")) {
            mode = SOAPClient.MODE_STANDALONE;
        } else if (property.equalsIgnoreCase("javaEE")) {
            mode = SOAPClient.MODE_JavaEE;
	    
        } else {
            throw new EETest.Fault("The 'platform.mode' property value '" + property + "' is invalid");
        }
        String webServerHost = PropertyUtils.getProperty(properties, "webServerHost");
        int webServerPort;
        if (SecureClient.class.isAssignableFrom(clazz)) {
            webServerPort = PropertyUtils.getIntegerProperty(properties, "secureWebServerPort");
        } else {
            webServerPort = PropertyUtils.getIntegerProperty(properties, "webServerPort");
        }
        try {
	    if (mode == SOAPClient.MODE_STANDALONE) {
                Constructor ctr = clazz.getConstructor(new Class[] {String.class, int.class, int.class});
                return (SOAPClient)ctr.newInstance(new Object[] {webServerHost, Integer.valueOf(webServerPort), Integer.valueOf(mode)});
	    }
	    else {
                Constructor ctr = clazz.getConstructor(new Class[] {String.class, int.class, int.class, javax.xml.ws.Service.class});
                return (SOAPClient)ctr.newInstance(new Object[] {webServerHost, Integer.valueOf(webServerPort), Integer.valueOf(mode), getWebServiceRef(theTest, theService)});
	    }
        } catch (NoSuchMethodException e) {
            throw new EETest.Fault("Client '" + clazz.getName() + "' does not have required constructor", e);
        } catch (ClassCastException e) {
            throw new EETest.Fault("Client '" + clazz.getName() + "' does not extend '" + SOAPClient.class.getName() + "'", e);
        } catch (Exception e) {
            TestUtil.printStackTrace(e);
            throw new EETest.Fault("Unable to instantiate '" + clazz.getName() + "'", e);
        }
    }

    private static javax.xml.ws.Service getWebServiceRef(ServiceEETest theTest, Service theService)
    {
	Service service = theService;
	TestUtil.logMsg("WebServiceRef is not set in Client (get it from specific vehicle)");
	service = (Service) theTest.getSharedObject();
	TestUtil.logMsg("service="+service);
	return service;
    }
        
    private ClientFactory() {
        super();
    }
}
