/*
 * Copyright (C) 2013 The Android Open Source Project
 *
 * 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 com.android.contacts.common.extensions;

import android.content.Context;
import android.util.Log;

import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;


/*
 * A framework for adding extensions to Dialer. This class reads a property file from
 * assets/contacts_extensions.properties and loads extension classes that an app has defined. If
 * an extension class was not defined, null is returned.
 */
public class ExtensionsFactory {

    private static String TAG = "ExtensionsFactory";

    // Config filename for mappings of various class names to their custom
    // implementations.
    private static final String EXTENSIONS_PROPERTIES = "contacts_extensions.properties";

    private static final String EXTENDED_PHONE_DIRECTORIES_KEY = "extendedPhoneDirectories";

    private static Properties sProperties = null;
    private static ExtendedPhoneDirectoriesManager mExtendedPhoneDirectoriesManager = null;

    public static void init(Context context) {
        if (sProperties != null) {
            return;
        }
        try {
            final InputStream fileStream = context.getAssets().open(EXTENSIONS_PROPERTIES);
            sProperties = new Properties();
            sProperties.load(fileStream);
            fileStream.close();

            final String className = sProperties.getProperty(EXTENDED_PHONE_DIRECTORIES_KEY);
            if (className != null) {
                mExtendedPhoneDirectoriesManager = createInstance(className);
            } else {
                Log.d(TAG, EXTENDED_PHONE_DIRECTORIES_KEY + " not found in properties file.");
            }

        } catch (FileNotFoundException e) {
            // No custom extensions. Ignore.
            Log.d(TAG, "No custom extensions.");
        } catch (IOException e) {
            Log.d(TAG, e.toString());
        }
    }

    private static <T> T createInstance(String className) {
        try {
            Class<?> c = Class.forName(className);
            //noinspection unchecked
            return (T) c.newInstance();
        } catch (ClassNotFoundException e) {
            Log.e(TAG, className + ": unable to create instance.", e);
        } catch (IllegalAccessException e) {
            Log.e(TAG, className + ": unable to create instance.", e);
        } catch (InstantiationException e) {
            Log.e(TAG, className + ": unable to create instance.", e);
        }
        return null;
    }

    public static ExtendedPhoneDirectoriesManager getExtendedPhoneDirectoriesManager() {
        return mExtendedPhoneDirectoriesManager;
    }
}
