/**
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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.apache.metamodel;

import java.io.File;
import java.io.InputStream;
import java.net.URL;
import java.sql.Connection;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;

import javax.sql.DataSource;

import org.apache.metamodel.cassandra.CassandraDataContext;
import org.apache.metamodel.couchdb.CouchDbDataContext;
import org.apache.metamodel.csv.CsvConfiguration;
import org.apache.metamodel.csv.CsvDataContext;
import org.apache.metamodel.elasticsearch.nativeclient.ElasticSearchDataContext;
import org.apache.metamodel.elasticsearch.rest.ElasticSearchRestClient;
import org.apache.metamodel.elasticsearch.rest.ElasticSearchRestDataContext;
import org.apache.metamodel.excel.ExcelConfiguration;
import org.apache.metamodel.excel.ExcelDataContext;
import org.apache.metamodel.fixedwidth.FixedWidthConfiguration;
import org.apache.metamodel.fixedwidth.FixedWidthDataContext;
import org.apache.metamodel.hbase.HBaseConfiguration;
import org.apache.metamodel.hbase.HBaseDataContext;
import org.apache.metamodel.jdbc.JdbcDataContext;
import org.apache.metamodel.json.JsonDataContext;
import org.apache.metamodel.mongodb.mongo3.MongoDbDataContext;
import org.apache.metamodel.openoffice.OpenOfficeDataContext;
import org.apache.metamodel.pojo.PojoDataContext;
import org.apache.metamodel.pojo.TableDataProvider;
import org.apache.metamodel.salesforce.SalesforceDataContext;
import org.apache.metamodel.schema.TableType;
import org.apache.metamodel.sugarcrm.SugarCrmDataContext;
import org.apache.metamodel.util.FileHelper;
import org.apache.metamodel.util.Resource;
import org.apache.metamodel.util.SimpleTableDef;
import org.apache.metamodel.xml.XmlDomDataContext;
import org.ektorp.http.StdHttpClient.Builder;
import org.elasticsearch.client.Client;
import org.xml.sax.InputSource;

import com.datastax.driver.core.Cluster;
import com.google.common.base.Strings;
import com.mongodb.MongoClient;
import com.mongodb.MongoCredential;
import com.mongodb.ServerAddress;
import com.mongodb.client.MongoDatabase;

/**
 * A factory for DataContext objects. This class substantially easens the task
 * of creating and initializing DataContext objects and/or their strategies for
 * reading datastores.
 * 
 * @see DataContext
 */
public class DataContextFactory {

    public static final char DEFAULT_CSV_SEPARATOR_CHAR = CsvConfiguration.DEFAULT_SEPARATOR_CHAR;
    public static final char DEFAULT_CSV_QUOTE_CHAR = CsvConfiguration.DEFAULT_QUOTE_CHAR;

    private DataContextFactory() {
        // Prevent instantiation
    }

    /**
     * Creates a composite DataContext based on a set of delegate DataContexts.
     * 
     * Composite DataContexts enables cross-DataContext querying and unified
     * schema exploration
     * 
     * @param delegates
     *            an array/var-args of delegate DataContexts
     * @return a DataContext that matches the request
     */
    public static DataContext createCompositeDataContext(DataContext... delegates) {
        return new CompositeDataContext(delegates);
    }

    /**
     * Creates a composite DataContext based on a set of delegate DataContexts.
     * 
     * Composite DataContexts enables cross-DataContext querying and unified
     * schema exploration
     * 
     * @param delegates
     *            a collection of delegate DataContexts
     * @return a DataContext that matches the request
     */
    public static DataContext createCompositeDataContext(Collection<DataContext> delegates) {
        return new CompositeDataContext(delegates);
    }

    /**
     * Creates a DataContext that connects to a Salesforce.com instance.
     * 
     * @param username
     *            the Salesforce username
     * @param password
     *            the Salesforce password
     * @param securityToken
     *            the Salesforce security token
     * @return a DataContext object that matches the request
     */
    public static DataContext createSalesforceDataContext(String username, String password, String securityToken) {
        return new SalesforceDataContext(username, password, securityToken);
    }

    /**
     * Create a DataContext that connects to a SugarCRM system.
     * 
     * @param baseUrl
     *            the base URL of the system, e.g. http://localhost/sugarcrm
     * @param username
     *            the SugarCRM username
     * @param password
     *            the SugarCRM password
     * @param applicationName
     *            the name of the application you are connecting with
     * @return a DataContext object that matches the request
     */
    public static DataContext createSugarCrmDataContext(String baseUrl, String username, String password,
            String applicationName) {
        return new SugarCrmDataContext(baseUrl, username, password, applicationName);
    }

    /**
     * Creates a DataContext based on a CSV file
     * 
     * @param file
     *            a CSV file
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createCsvDataContext(File file) {
        return createCsvDataContext(file, DEFAULT_CSV_SEPARATOR_CHAR, DEFAULT_CSV_QUOTE_CHAR);
    }

    /**
     * Creates a DataContext based on a JSON file
     */
    public static DataContext createJsonDataContext(File file) {
        return new JsonDataContext(file);
    }

    /**
     * Creates a DataContext based on a CSV file
     * 
     * @param file
     *            a CSV file
     * @param separatorChar
     *            the char to use for separating values
     * @param quoteChar
     *            the char used for quoting values (typically if they include
     *            the separator char)
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createCsvDataContext(File file, char separatorChar, char quoteChar) {
        return createCsvDataContext(file, separatorChar, quoteChar, FileHelper.DEFAULT_ENCODING);
    }

    /**
     * Creates a DataContext based on a CSV file
     * 
     * @param file
     *            a CSV file
     * @param separatorChar
     *            the char to use for separating values
     * @param quoteChar
     *            the char used for quoting values (typically if they include
     *            the separator char)
     * @param encoding
     *            the character encoding of the file
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createCsvDataContext(File file, char separatorChar, char quoteChar,
            String encoding) {
        final CsvConfiguration configuration = new CsvConfiguration(CsvConfiguration.DEFAULT_COLUMN_NAME_LINE, encoding,
                separatorChar, quoteChar, CsvConfiguration.DEFAULT_ESCAPE_CHAR);
        final CsvDataContext dc = new CsvDataContext(file, configuration);
        return dc;
    }

    /**
     * Creates a DataContext based on a CSV file
     * 
     * @param file
     *            a CSV file
     * @param configuration
     *            the CSV configuration to use
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createCsvDataContext(File file, CsvConfiguration configuration) {
        final CsvDataContext dc = new CsvDataContext(file, configuration);
        return dc;
    }

    /**
     * Creates a DataContext based on CSV-content through an input stream
     * 
     * @param inputStream
     *            the input stream to read from
     * @param separatorChar
     *            the char to use for separating values
     * @param quoteChar
     *            the char used for quoting values (typically if they include
     *            the separator char)
     * @return a DataContext object that matches the request
     */
    public static DataContext createCsvDataContext(InputStream inputStream, char separatorChar, char quoteChar) {
        return createCsvDataContext(inputStream, separatorChar, quoteChar, FileHelper.DEFAULT_ENCODING);
    }

    /**
     * Creates a DataContext based on CSV-content through an input stream
     * 
     * @param inputStream
     *            the input stream to read from
     * @param separatorChar
     *            the char to use for separating values
     * @param quoteChar
     *            the char used for quoting values (typically if they include
     *            the separator char)
     * @return a DataContext object that matches the request
     */
    public static DataContext createCsvDataContext(InputStream inputStream, char separatorChar, char quoteChar,
            String encoding) {
        final CsvConfiguration configuration = new CsvConfiguration(CsvConfiguration.DEFAULT_COLUMN_NAME_LINE, encoding,
                separatorChar, quoteChar, CsvConfiguration.DEFAULT_ESCAPE_CHAR);
        final CsvDataContext dc = new CsvDataContext(inputStream, configuration);
        return dc;
    }

    /**
     * Creates a DataContext based on CSV-content through an input stream
     * 
     * @param inputStream
     *            the input stream to read from
     * @param configuration
     *            the CSV configuration to use
     * @return a DataContext object that matches the request
     */
    public static DataContext createCsvDataContext(InputStream inputStream, CsvConfiguration configuration) {
        final CsvDataContext dc = new CsvDataContext(inputStream, configuration);
        return dc;
    }

    /**
     * Creates a DataContext based on a fixed width file.
     * 
     * @param file
     *            the file to read from.
     * @param fileEncoding
     *            the character encoding of the file.
     * @param fixedValueWidth
     *            the (fixed) width of values in the file.
     * @return a DataContext object that matches the request
     */
    public static DataContext createFixedWidthDataContext(File file, String fileEncoding, int fixedValueWidth) {
        return createFixedWidthDataContext(file, new FixedWidthConfiguration(
                FixedWidthConfiguration.DEFAULT_COLUMN_NAME_LINE, fileEncoding, fixedValueWidth));
    }

    /**
     * Creates a DataContext based on a fixed width file.
     * 
     * @param file
     *            the file to read from.
     * @param configuration
     *            the fixed width configuration to use
     * @return a DataContext object that matches the request
     */
    public static DataContext createFixedWidthDataContext(File file, FixedWidthConfiguration configuration) {
        final FixedWidthDataContext dc = new FixedWidthDataContext(file, configuration);
        return dc;
    }
    /**
    * Creates a DataContext based on a fixed width file.
    * 
    * @param resource
    *            the resource to read from.
    * @param configuration
    *            the fixed width configuration to use
    * @return a DataContext object that matches the request
    */
   public static DataContext createFixedWidthDataContext(Resource resource, FixedWidthConfiguration configuration) {
       final FixedWidthDataContext dc = new FixedWidthDataContext(resource, configuration);
       return dc;
   }


    /**
     * Creates a DataContext based on a fixed width file.
     * 
     * @param file
     *            the file to read from.
     * @param fileEncoding
     *            the character encoding of the file.
     * @param fixedValueWidth
     *            the (fixed) width of values in the file.
     * @param headerLineNumber
     *            the line number of the column headers.
     * @return a DataContext object that matches the request
     */
    public static DataContext createFixedWidthDataContext(File file, String fileEncoding, int fixedValueWidth,
            int headerLineNumber) {
        return createFixedWidthDataContext(file, new FixedWidthConfiguration(
                FixedWidthConfiguration.DEFAULT_COLUMN_NAME_LINE, fileEncoding, fixedValueWidth));
    }

    /**
     * Creates a DataContet based on an Excel spreadsheet file
     * 
     * @param file
     *            an excel spreadsheet file
     * @param configuration
     *            the configuration with metadata for reading the spreadsheet
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createExcelDataContext(File file, ExcelConfiguration configuration) {
        return new ExcelDataContext(file, configuration);
    }

    /**
     * Creates a DataContext based on an Excel spreadsheet file
     * 
     * @param file
     *            an Excel spreadsheet file
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createExcelDataContext(File file) {
        return createExcelDataContext(file, new ExcelConfiguration());
    }

    /**
     * Creates a DataContext based on XML-content from an input source.
     * 
     * Tables are created by examining the data in the XML file, NOT by reading
     * XML Schemas (xsd/dtd's). This enables compliancy with ALL xml formats but
     * also raises a risk that two XML files with the same format wont
     * nescesarily yield the same table model if some optional attributes or
     * tags are omitted in one of the files.
     * 
     * @param inputSource
     *            an input source feeding XML content
     * @param schemaName
     *            the name to be used for the main schema
     * @param autoFlattenTables
     *            a boolean indicating if MetaModel should flatten very simple
     *            table structures (where tables only contain a single
     *            data-carrying column) for greater usability of the generated
     *            table-based model
     * @return a DataContext object that matches the request
     */
    public static DataContext createXmlDataContext(InputSource inputSource, String schemaName,
            boolean autoFlattenTables) {
        XmlDomDataContext dc = new XmlDomDataContext(inputSource, schemaName, autoFlattenTables);
        return dc;
    }

    /**
     * Creates a DataContext based on XML-content from a File.
     * 
     * Tables are created by examining the data in the XML file, NOT by reading
     * XML Schemas (xsd/dtd's). This enables compliancy with ALL xml formats but
     * also raises a risk that two XML files with the same format wont
     * nescesarily yield the same table model if some optional attributes or
     * tags are omitted in one of the files.
     * 
     * @param file
     *            the File to use for feeding XML content
     * @param autoFlattenTables
     *            a boolean indicating if MetaModel should flatten very simple
     *            table structures (where tables only contain a single
     *            data-carrying column) for greater usability of the generated
     *            table-based model
     * @return a DataContext object that matches the request
     */
    public static DataContext createXmlDataContext(File file, boolean autoFlattenTables) {
        XmlDomDataContext dc = new XmlDomDataContext(file, autoFlattenTables);
        return dc;
    }

    /**
     * Creates a DataContext based on XML-content from a URL.
     * 
     * Tables are created by examining the data in the XML file, NOT by reading
     * XML Schemas (xsd/dtd's). This enables compliancy with ALL xml formats but
     * also raises a risk that two XML files with the same format wont
     * nescesarily yield the same table model if some optional attributes or
     * tags are omitted in one of the files.
     * 
     * @param url
     *            the URL to use for feeding XML content
     * @param autoFlattenTables
     *            a boolean indicating if MetaModel should flatten very simple
     *            table structures (where tables only contain a single
     *            data-carrying column) for greater usability of the generated
     *            table-based model
     * @return a DataContext object that matches the request
     */
    public static DataContext createXmlDataContext(URL url, boolean autoFlattenTables) {
        XmlDomDataContext dc = new XmlDomDataContext(url, autoFlattenTables);
        return dc;
    }

    /**
     * Creates a DataContext based on an OpenOffice.org database file.
     * 
     * @param file
     *            an OpenOffice.org database file
     * @return a DataContext object that matches the request
     */
    public static DataContext createOpenOfficeDataContext(File file) {
        return new OpenOfficeDataContext(file);
    }

    /**
     * Creates a DataContext based on a JDBC connection
     * 
     * @param connection
     *            a JDBC connection
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createJdbcDataContext(Connection connection) {
        return new JdbcDataContext(connection);
    }

    /**
     * Creates a DataContext based on a JDBC datasource
     * 
     * @param ds
     *            a JDBC datasource
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createJdbcDataContext(DataSource ds) {
        return new JdbcDataContext(ds);
    }

    /**
     * Creates a DataContext based on a JDBC connection
     * 
     * @param connection
     *            a JDBC connection
     * @param catalogName
     *            a catalog name to use
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createJdbcDataContext(Connection connection, String catalogName) {
        return new JdbcDataContext(connection, TableType.DEFAULT_TABLE_TYPES, catalogName);
    }

    /**
     * Creates a DataContext based on a JDBC connection
     * 
     * @param connection
     *            a JDBC connection
     * @param tableTypes
     *            the types of tables to include in the generated schemas
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createJdbcDataContext(Connection connection, TableType... tableTypes) {
        return new JdbcDataContext(connection, tableTypes, null);
    }

    /**
     * Creates a DataContext based on a JDBC connection
     * 
     * @param connection
     *            a JDBC connection
     * @param catalogName
     *            a catalog name to use
     * @param tableTypes
     *            the types of tables to include in the generated schemas
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createJdbcDataContext(Connection connection, String catalogName,
            TableType[] tableTypes) {
        return new JdbcDataContext(connection, tableTypes, catalogName);
    }

    /**
     * Creates a DataContext based on a JDBC datasource
     * 
     * @param ds
     *            a JDBC datasource
     * @param tableTypes
     *            the types of tables to include in the generated schemas
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createJdbcDataContext(DataSource ds, TableType... tableTypes) {
        return new JdbcDataContext(ds, tableTypes, null);
    }

    /**
     * Creates a DataContext based on a JDBC datasource
     * 
     * @param ds
     *            a JDBC datasource
     * @param catalogName
     *            a catalog name to use
     * @param tableTypes
     *            the types of tables to include in the generated schemas
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createJdbcDataContext(DataSource ds, String catalogName,
            TableType[] tableTypes) {
        return new JdbcDataContext(ds, tableTypes, catalogName);
    }

    /**
     * Creates a DataContext based on a JDBC datasource
     * 
     * @param ds
     *            a JDBC datasource
     * @param catalogName
     *            a catalog name to use
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createJdbcDataContext(DataSource ds, String catalogName) {
        return new JdbcDataContext(ds, TableType.DEFAULT_TABLE_TYPES, catalogName);
    }

    /**
     * Creates a new MongoDB datacontext.
     * 
     * @param hostname
     *            The hostname of the MongoDB instance
     * @param port
     *            the port of the MongoDB instance, or null if the default port
     *            should be used.
     * @param databaseName
     *            the name of the database
     * @param username
     *            the username, or null if unauthenticated access should be used
     * @param password
     *            the password, or null if unathenticated access should be used
     * @param tableDefs
     *            an array of table definitions, or null if table definitions
     *            should be autodetected.
     * @return a DataContext object that matches the request
     */
    @SuppressWarnings("resource")
    public static UpdateableDataContext createMongoDbDataContext(String hostname, Integer port, String databaseName,
            String username, char[] password, SimpleTableDef[] tableDefs) {
        try {
            final ServerAddress serverAddress;
            if (port == null) {
                serverAddress = new ServerAddress(hostname);
            } else {
                serverAddress = new ServerAddress(hostname, port);
            }
            final MongoClient mongoClient;
            final MongoDatabase mongoDb;
            if (Strings.isNullOrEmpty(username)) {
                mongoClient = new MongoClient(serverAddress);
            } else {
                final MongoCredential credential = MongoCredential.createCredential(username, databaseName, password);
                mongoClient = new MongoClient(serverAddress, Arrays.asList(credential));
            }
            mongoDb = mongoClient.getDatabase(databaseName);

            if (tableDefs == null || tableDefs.length == 0) {
                return new MongoDbDataContext(mongoDb);
            }
            return new MongoDbDataContext(mongoDb, tableDefs);
        } catch (Exception e) {
            if (e instanceof RuntimeException) {
                throw (RuntimeException) e;
            }
            throw new IllegalStateException(e);
        }
    }

    /**
     * Creates a new MongoDB datacontext.
     * 
     * @param hostname
     *            The hostname of the MongoDB instance
     * @param port
     *            the port of the MongoDB instance, or null if the default port
     *            should be used.
     * @param databaseName
     *            the name of the database
     * @param username
     *            the username, or null if unauthenticated access should be used
     * @param password
     *            the password, or null if unathenticated access should be used
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createMongoDbDataContext(String hostname, Integer port, String databaseName,
            String username, char[] password) {
        return createMongoDbDataContext(hostname, port, databaseName, username, password, null);
    }

    /**
     * Creates a new CouchDB datacontext.
     * 
     * @param hostname
     *            The hostname of the CouchDB instance
     * @param port
     *            the port of the CouchDB instance, or null if the default port
     *            should be used.
     * @param username
     *            the username, or null if unauthenticated access should be used
     * @param password
     *            the password, or null if unathenticated access should be used
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createCouchDbDataContext(String hostname, Integer port, String username,
            String password) {
        return createCouchDbDataContext(hostname, port, username, password, null);
    }

    /**
     * Creates a new CouchDB datacontext.
     * 
     * @param hostname
     *            The hostname of the CouchDB instance
     * @param port
     *            the port of the CouchDB instance, or null if the default port
     *            should be used.
     * @param username
     *            the username, or null if unauthenticated access should be used
     * @param password
     *            the password, or null if unathenticated access should be used
     * @param tableDefs
     *            an array of table definitions, or null if table definitions
     *            should be autodetected.
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createCouchDbDataContext(String hostname, Integer port, String username,
            String password, SimpleTableDef[] tableDefs) {

        final Builder httpClientBuilder = new Builder();
        httpClientBuilder.host(hostname);
        if (port != null) {
            httpClientBuilder.port(port);
        }
        if (username != null) {
            httpClientBuilder.username(username);
        }
        if (password != null) {
            httpClientBuilder.password(password);
        }

        // increased timeouts (20 sec) - metamodel typically does quite some
        // batching so it might take a bit of time to provide a connection.
        httpClientBuilder.connectionTimeout(20000);
        httpClientBuilder.socketTimeout(20000);

        if (tableDefs == null || tableDefs.length == 0) {
            return new CouchDbDataContext(httpClientBuilder);
        }
        return new CouchDbDataContext(httpClientBuilder, tableDefs);
    }

    /**
     * Creates a new JSON-based ElasticSearch datacontext.
     * @param client
     *       The Jest client
     * @param indexName
     *       The ElasticSearch index name
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createElasticSearchDataContext(final ElasticSearchRestClient client,
            final String indexName) {
        return new ElasticSearchRestDataContext(client, indexName);
    }

    /**
     * Creates a new ElasticSearch datacontext.
     * 
     * @param client
     *            The ElasticSearch client
     * @param indexName
     *            The ElasticSearch index name
     * @return a DataContext object that matches the request
     */
    public static UpdateableDataContext createElasticSearchDataContext(Client client, String indexName) {
        return new ElasticSearchDataContext(client, indexName);
    }

    /**
     * Creates a new Cassandra datacontext.
     * 
     * @param cluster
     *            The Cassandra client
     * @param keySpaceName
     *            The Cassandra key space name
     * @return a DataContext object that matches the request
     */
    public static DataContext createCassandraDataContext(Cluster cluster, String keySpaceName) {
        return new CassandraDataContext(cluster, keySpaceName);
    }
    
	/**
	 * Creates a new HBase datacontext.
	 * 
	 * @param configuration
	 *            {@code HBaseConfiguration} object containing detailed HBase
	 *            configuration properties.
	 * 
	 * @return a DataContext object that matches the request
	 */
    public static DataContext createHBaseDataContext(HBaseConfiguration configuration){
    	return new HBaseDataContext(configuration);
    }
    
	/**
	 * Creates a new HBase datacontext.
	 * 
	 * @param configuration
	 *            {@code HBaseConfiguration} object containing detailed HBase
	 *            configuration properties.
	 * 
	 * @param connection
	 *            A cluster connection encapsulating lower level individual
	 *            connections to actual servers and a connection to zookeeper.
	 * 
	 * @return a DataContext object that matches the request
	 */
	public static DataContext createHBaseDataContext(HBaseConfiguration configuration,org.apache.hadoop.hbase.client.Connection connection) {
		return new HBaseDataContext(configuration, connection);
	}
	
	/**
	 * Creates a new POJO data context that is empty but can be populated at
	 * will.
	 * 
	 * @return a DataContext object that matches the request
	 * 
	 */
	public static DataContext createPojoDataContext() {
		return new PojoDataContext();
	}

	/**
	 * Creates a new POJO data context based on the provided
	 * {@link TableDataProvider}s.
	 * 
	 * @param tables
	 *            list of tables
	 * 
	 * @return DataContext object that matches the request
	 */
	public static DataContext createPojoDataContext(List<TableDataProvider<?>> tables) {
		return new PojoDataContext(tables);
	}

	/**
	 * Creates a new POJO data context based on the provided
	 * {@link TableDataProvider}s.
	 * 
	 * @param schemaName
	 *            the name of the created schema
	 * 
	 * @param tables
	 *            table information
	 * 
	 * @return DataContext object that matches the request
	 * 
	 */
	public static DataContext createPojoDataContext(String schemaName,TableDataProvider<?>[] tables) {
		return new PojoDataContext(schemaName, tables);
	}

	/**
	 * Creates a new POJO data context based on the provided
	 * {@link TableDataProvider}s.
	 * 
	 * @param schemaName
	 *            the name of the created schema
	 * 
	 * @param tables
	 *            list of tables
	 * 
	 * @return DataContext object that matches the request
	 */
	public static DataContext createPojoDataContext(String schemaName,List<TableDataProvider<?>> tables) {
		return new PojoDataContext(schemaName, tables);
	}
}