/*
 * Copyright (c) 1998, 2021 Oracle and/or its affiliates. All rights reserved.
 * Copyright (c) 2019 IBM Corporation. All rights reserved.
 *
 * This program and the accompanying materials are made available under the
 * terms of the Eclipse Public License v. 2.0 which is available at
 * http://www.eclipse.org/legal/epl-2.0,
 * or the Eclipse Distribution License v. 1.0 which is available at
 * http://www.eclipse.org/org/documents/edl-v10.php.
 *
 * SPDX-License-Identifier: EPL-2.0 OR BSD-3-Clause
 */

// Contributors:
//     Oracle - initial API and implementation from Oracle TopLink
//     Phillip Ross - LIMIT/OFFSET syntax support
//     09/14/2011-2.3.1 Guy Pelletier
//       - 357533: Allow DDL queries to execute even when Multitenant entities are part of the PU
package org.eclipse.persistence.platform.database;

import java.io.*;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.Types;
import java.util.*;

import org.eclipse.persistence.internal.sessions.AbstractRecord;
import org.eclipse.persistence.internal.sessions.AbstractSession;
import org.eclipse.persistence.mappings.structures.ObjectRelationalDatabaseField;
import org.eclipse.persistence.queries.StoredProcedureCall;
import org.eclipse.persistence.exceptions.ValidationException;
import org.eclipse.persistence.expressions.ExpressionOperator;
import org.eclipse.persistence.internal.databaseaccess.DatabaseCall;
import org.eclipse.persistence.internal.databaseaccess.DatasourceCall;
import org.eclipse.persistence.internal.databaseaccess.FieldTypeDefinition;
import org.eclipse.persistence.internal.expressions.ExpressionSQLPrinter;
import org.eclipse.persistence.internal.expressions.RelationExpression;
import org.eclipse.persistence.internal.expressions.SQLSelectStatement;
import org.eclipse.persistence.internal.helper.*;
import org.eclipse.persistence.queries.SQLCall;
import org.eclipse.persistence.queries.ValueReadQuery;
import org.eclipse.persistence.tools.schemaframework.FieldDefinition;

/**
 * <p>
 * <b>Purpose</b>: Provides Postgres specific behavior.
 * <p>
 * <b>Responsibilities</b>:
 * <ul>
 * <li>Native SQL for Date, Time, {@literal &} Timestamp.
 * <li>Native sequencing.
 * <li>Mapping of class types to database types for the schema framework.
 * <li>Pessimistic locking.
 * <li>Platform specific operators.
 * <li>LIMIT/OFFSET query syntax for select statements.
 * </ul>
 *
 * @since OracleAS TopLink 10<i>g</i> (10.1.3)
 */
public class PostgreSQLPlatform extends DatabasePlatform {

    private static final String LIMIT = " LIMIT ";
    private static final String OFFSET = " OFFSET ";

    public PostgreSQLPlatform() {
        super();
        this.cursorCode = 1111; //jdbc.Types.OTHER - PostGreSQL expects this for refCursor types
        this.pingSQL = "SELECT 1";
    }

    /**
     * Return the JDBC type for the Java type. For some reason PostgreSQL does
     * not seem to like the JDBC Blob type (PostgreSQL 8.2).
     */
    @Override
    public int getJDBCType(Class javaType) {
        if (javaType == ClassConstants.BLOB) {
            return Types.LONGVARBINARY;
        }
        return super.getJDBCType(javaType);
    }

    /**
     * Appends a Boolean value. Refer to :
     * http://www.postgresql.org/docs/8.0/static/datatype-boolean.html In
     * PostgreSQL the following are the values that are value for a boolean
     * field Valid literal values for the "true" state are: TRUE, 't', 'true',
     * 'y', 'yes', '1' Valid literal values for the false" state are : FALSE,
     * 'f', 'false', 'n', 'no', '0'
     *
     * To be consistent with the other data platforms we are using the values
     * '1' and '0' for true and false states of a boolean field.
     */
    @Override
    protected void appendBoolean(Boolean bool, Writer writer) throws IOException {
        if (bool) {
            writer.write("\'1\'");
        } else {
            writer.write("\'0\'");
        }
    }

    /**
     * INTERNAL: Use the JDBC maxResults and firstResultIndex setting to compute
     * a value to use when limiting the results of a query in SQL. These limits
     * tend to be used in two ways.
     *
     * 1. MaxRows is the index of the last row to be returned (like JDBC
     * maxResults) 2. MaxRows is the number of rows to be returned
     *
     * PostGreSQL uses case #2 and therefore the maxResults has to be altered
     * based on the firstResultIndex
     *
     * @see org.eclipse.persistence.platform.database.MySQLPlatform
     */
    @Override
    public int computeMaxRowsForSQL(int firstResultIndex, int maxResults) {
        return maxResults - ((firstResultIndex >= 0) ? firstResultIndex : 0);
    }

    /**
     * INTERNAL: Initialize any platform-specific operators
     */
    @Override
    protected void initializePlatformOperators() {
        super.initializePlatformOperators();
        addOperator(ExpressionOperator.simpleLogicalNoParens(ExpressionOperator.Concat, "||"));
        addOperator(ExpressionOperator.simpleTwoArgumentFunction(ExpressionOperator.Nvl, "COALESCE"));
        addOperator(operatorLocate());
        addOperator(operatorLocate2());
        addOperator(toNumberOperator());
        addOperator(regexpOperator());
    }

    /**
     * INTERNAL:
     * Create the ~ operator.
     * REGEXP allows for comparison through regular expression.
     */
    public static ExpressionOperator regexpOperator() {
        ExpressionOperator result = new ExpressionOperator();
        result.setSelector(ExpressionOperator.Regexp);
        result.setType(ExpressionOperator.FunctionOperator);
        List<String> v = new ArrayList<>(3);
        v.add("");
        v.add(" ~ ");
        v.add("");
        result.printsAs(v);
        result.bePrefix();
        result.setNodeClass(ClassConstants.FunctionExpression_Class);
        v = new ArrayList<>(2);
        v.add(".regexp(");
        v.add(")");
        result.printsJavaAs(v);
        return result;
    }

    /**
     * INTERNAL: Postgres to_number has two arguments, as fix format argument.
     */
    protected ExpressionOperator toNumberOperator() {
        ExpressionOperator exOperator = new ExpressionOperator();
        exOperator.setType(ExpressionOperator.FunctionOperator);
        exOperator.setSelector(ExpressionOperator.ToNumber);
        List<String> v = new ArrayList<>(2);
        v.add("TO_NUMBER(");
        v.add(", '999999999.9999')");
        exOperator.printsAs(v);
        exOperator.bePrefix();
        exOperator.setNodeClass(ClassConstants.FunctionExpression_Class);
        return exOperator;
    }

    /**
     * INTERNAL: This method returns the query to select the timestamp from the
     * server for Postgres.
     */
    @Override
    public ValueReadQuery getTimestampQuery() {
        if (this.timestampQuery == null) {
            this.timestampQuery = new ValueReadQuery();
            this.timestampQuery.setSQLString("SELECT NOW()");
            this.timestampQuery.setAllowNativeSQLQuery(true);
        }
        return this.timestampQuery;

    }

    /**
     * This method is used to print the output parameter token when stored
     * procedures are called
     */
    @Override
    public String getInOutputProcedureToken() {
        return "OUT";
    }

    /**
     * This is required in the construction of the stored procedures with output
     * parameters
     */
    @Override
    public boolean shouldPrintOutputTokenAtStart() {
        // TODO: Check with the reviewer where this is used
        return true;
    }

    /**
     * Calling a stored procedure query on PostgreSQL with no output parameters
     * always returns true from an execute call regardless if a result set is
     * returned or not. This flag will help avoid throwing a JPA mandated
     * exception on an executeUpdate call (which calls jdbc execute and checks
     * the return value to ensure no results sets are returned (true))
     *
     * @see PostgreSQLPlatform
     */
    @Override
    public boolean isJDBCExecuteCompliant() {
        return false;
    }

    /**
     * INTERNAL: Answers whether platform is Postgres.
     */
    @Override
    public boolean isPostgreSQL() {
        return true;
    }

    /**
     * INTERNAL:
     */
    @Override
    protected String getCreateTempTableSqlSuffix() {
        return " ON COMMIT DROP";
    }

    /**
     * INTERNAL: Indicates whether locking OF clause should print alias for
     * field. Example: on Oracle platform (method returns false): SELECT
     * ADDRESS_ID, ... FROM ADDRESS T1 WHERE (T1.ADDRESS_ID = ?) FOR UPDATE OF
     * T1.ADDRESS_ID on Postgres platform (method returns true): SELECT
     * ADDRESS_ID, ... FROM ADDRESS T1 WHERE (T1.ADDRESS_ID = ?) FOR UPDATE OF
     * T1
     */
    @Override
    public boolean shouldPrintAliasForUpdate() {
        return true;
    }

    /**
     * INTERNAL: Indicates whether the platform supports identity.
     */
    @Override
    public boolean supportsIdentity() {
        return true;
    }

    /**
     * INTERNAL: Returns query used to read back the value generated by
     * Identity. This method is called when identity NativeSequence is
     * connected, the returned query used until the sequence is disconnected. If
     * the platform supportsIdentity then (at least) one of
     * buildSelectQueryForIdentity methods should return non-null query.
     */
    @Override
    public ValueReadQuery buildSelectQueryForIdentity() {
        ValueReadQuery selectQuery = new ValueReadQuery();
        selectQuery.setSQLString("select lastval()");
        return selectQuery;
    }

    /**
     * INTERNAL: Indicates whether the platform supports sequence objects.
     */
    @Override
    public boolean supportsSequenceObjects() {
        return true;
    }

    /**
     * INTERNAL: Returns query used to read value generated by sequence object
     * (like Oracle sequence). This method is called when sequence object
     * NativeSequence is connected, the returned query used until the sequence
     * is disconnected. If the platform supportsSequenceObjects then (at least)
     * one of buildSelectQueryForSequenceObject methods should return non-null
     * query.
     */
    @Override
    public ValueReadQuery buildSelectQueryForSequenceObject(String qualifiedSeqName, Integer size) {
        return new ValueReadQuery("select nextval(\'" + qualifiedSeqName + "\')");
    }

    /**
     * INTERNAL: Append the receiver's field 'identity' constraint clause to a
     * writer.
     */
    @Override
    public void printFieldIdentityClause(Writer writer) throws ValidationException {
        try {
            writer.write(" SERIAL");
        } catch (IOException ioException) {
            throw ValidationException.fileError(ioException);
        }
    }

    @Override
    protected Hashtable<Class<?>, FieldTypeDefinition> buildFieldTypes() {
        Hashtable<Class<?>, FieldTypeDefinition> fieldTypeMapping = new Hashtable<>();

        fieldTypeMapping.put(Boolean.class, new FieldTypeDefinition("BOOLEAN", false));

        fieldTypeMapping.put(Integer.class, new FieldTypeDefinition("INTEGER", false));
        fieldTypeMapping.put(Long.class, new FieldTypeDefinition("BIGINT", false));
        fieldTypeMapping.put(Float.class, new FieldTypeDefinition("FLOAT", false));
        fieldTypeMapping.put(Double.class, new FieldTypeDefinition("FLOAT", false));
        fieldTypeMapping.put(Short.class, new FieldTypeDefinition("SMALLINT", false));
        fieldTypeMapping.put(Byte.class, new FieldTypeDefinition("SMALLINT", false));
        fieldTypeMapping.put(java.math.BigInteger.class, new FieldTypeDefinition("BIGINT", false));
        fieldTypeMapping.put(java.math.BigDecimal.class, new FieldTypeDefinition("DECIMAL", 38));
        fieldTypeMapping.put(Number.class, new FieldTypeDefinition("DECIMAL", 38));

        fieldTypeMapping.put(String.class, new FieldTypeDefinition("VARCHAR", DEFAULT_VARCHAR_SIZE));
        fieldTypeMapping.put(Character.class, new FieldTypeDefinition("CHAR", 1));

        fieldTypeMapping.put(Byte[].class, new FieldTypeDefinition("BYTEA", false));
        fieldTypeMapping.put(Character[].class, new FieldTypeDefinition("TEXT", false));
        fieldTypeMapping.put(byte[].class, new FieldTypeDefinition("BYTEA", false));
        fieldTypeMapping.put(char[].class, new FieldTypeDefinition("TEXT", false));
        fieldTypeMapping.put(java.sql.Blob.class, new FieldTypeDefinition("BYTEA"));
        fieldTypeMapping.put(java.sql.Clob.class, new FieldTypeDefinition("TEXT", false));

        fieldTypeMapping.put(java.sql.Date.class, new FieldTypeDefinition("DATE", false));
        fieldTypeMapping.put(java.sql.Time.class, new FieldTypeDefinition("TIME", false));
        fieldTypeMapping.put(java.sql.Timestamp.class, new FieldTypeDefinition("TIMESTAMP", false));

        fieldTypeMapping.put(java.time.LocalDate.class, new FieldTypeDefinition("DATE", false));
        fieldTypeMapping.put(java.time.LocalDateTime.class, new FieldTypeDefinition("TIMESTAMP", false));
        fieldTypeMapping.put(java.time.LocalTime.class, new FieldTypeDefinition("TIME", false));
        fieldTypeMapping.put(java.time.OffsetDateTime.class, new FieldTypeDefinition("TIMESTAMP", false));
        fieldTypeMapping.put(java.time.OffsetTime.class, new FieldTypeDefinition("TIME", false));

        return fieldTypeMapping;
    }

    /**
     * INTERNAL: Override the default locate operator.
     */
    protected ExpressionOperator operatorLocate() {
        ExpressionOperator result = new ExpressionOperator();
        result.setSelector(ExpressionOperator.Locate);
        Vector<String> v = new Vector<>(3);
        v.addElement("STRPOS(");
        v.addElement(", ");
        v.addElement(")");
        result.printsAs(v);
        result.bePrefix();
        result.setNodeClass(RelationExpression.class);
        return result;
    }

    /**
     * INTERNAL: Override the default locate operator.
     */
    protected ExpressionOperator operatorLocate2() {
        ExpressionOperator operator = new ExpressionOperator();
        operator.setSelector(ExpressionOperator.Locate2);
        List<String> v = new ArrayList<>(2);
        v.add("COALESCE(NULLIF(STRPOS(SUBSTRING(");
        v.add(" FROM ");
        v.add("), ");
        v.add("), 0) - 1 + ");
        v.add(", 0)");
        operator.printsAs(v);
        operator.bePrefix();
        int[] argumentIndices = new int[4];
        argumentIndices[0] = 0;
        argumentIndices[1] = 2;
        argumentIndices[2] = 1;
        argumentIndices[3] = 2;
        operator.setArgumentIndices(argumentIndices);
        operator.setNodeClass(RelationExpression.class);
        return operator;
    }

    /**
     * INTERNAL:
     */
    @Override
    public boolean supportsLocalTempTables() {
        return true;
    }

    /**
     * INTERNAL:
     */
    @Override
    protected String getCreateTempTableSqlPrefix() {
        return "CREATE LOCAL TEMPORARY TABLE ";
    }

    /**
     * INTERNAL: returns the maximum number of characters that can be used in a
     * field name on this platform.
     */
    @Override
    public int getMaxFieldNameSize() {
        // The system uses no more than NAMEDATALEN-1 characters of an
        // identifier; longer names can be written in commands,
        // but they will be truncated. By default, NAMEDATALEN is 64 so the
        // maximum identifier length is 63 (but at the time PostgreSQL
        // is built, NAMEDATALEN can be changed in src/include/postgres_ext.h).
        // http://www.postgresql.org/docs/7.3/interactive/sql-syntax.html#SQL-SYNTAX-IDENTIFIERS
        return 63;
    }

    // http://www.postgresql.org/docs/8.1/interactive/plpgsql-declarations.html
    /**
     * INTERNAL: Used for sp calls.
     */
    @Override
    public String getProcedureBeginString() {
        return "AS $$  BEGIN ";
    }

    /**
     * INTERNAL: Used for sp calls.
     */
    @Override
    public String getProcedureEndString() {
        return "; END ; $$ LANGUAGE plpgsql;";
    }

     /**
     * INTERNAL: Used for sp calls.  PostGreSQL uses a different method for executing StoredProcedures than other platforms.
     */
    @Override
    public String buildProcedureCallString(StoredProcedureCall call, AbstractSession session, AbstractRecord row) {
        StringWriter tailWriter = new StringWriter();
        StringWriter writer = new StringWriter();
        boolean outParameterFound = false;

        tailWriter.write(call.getProcedureName());
        tailWriter.write("(");

        int indexFirst = call.getFirstParameterIndexForCallString();
        int size = call.getParameters().size();
        String nextBindString = "?";

        for (int index = indexFirst; index < size; index++) {
             String name = call.getProcedureArgumentNames().get(index);
             Object parameter = call.getParameters().get(index);
             Integer parameterType = call.getParameterTypes().get(index);
             // If the argument is optional and null, ignore it.
             if (!call.hasOptionalArguments() || !call.getOptionalArguments().contains(parameter) || (row.get(parameter) != null)) {
                  if (!DatasourceCall.isOutputParameterType(parameterType)) {
                       tailWriter.write(nextBindString);
                       nextBindString = ", ?";
                  } else {
                       if (outParameterFound) {
                            //multiple outs found
                            throw ValidationException.multipleOutParamsNotSupported(Helper.getShortClassName(this), call.getProcedureName());
                       }
                       outParameterFound = true; //PostGreSQL uses a very different header to execute when there are out params
                  }
             }
        }
        tailWriter.write(")");

        if (outParameterFound) {
             writer.write("{?= CALL ");
             tailWriter.write("}");
        } else {
             writer.write("SELECT * FROM ");
        }
        writer.write(tailWriter.toString());

        return writer.toString();
    }
    /**
     * INTERNAL Used for stored function calls.
     */
    @Override
    public String getAssignmentString() {
        return ":= ";
    }

    /**
     * Allows DROP TABLE to cascade dropping of any dependent constraints if the database supports this option.
     */
    @Override
    public String getDropCascadeString() {
        return " CASCADE";
    }

    @Override
    public void printFieldTypeSize(Writer writer, FieldDefinition field, FieldTypeDefinition fieldType, boolean shouldPrintFieldIdentityClause) throws IOException {
        if (!shouldPrintFieldIdentityClause) {
            super.printFieldTypeSize(writer, field, fieldType, shouldPrintFieldIdentityClause);
        }
    }

    @Override
    public void printFieldUnique(Writer writer, boolean shouldPrintFieldIdentityClause) throws IOException {
        if (!shouldPrintFieldIdentityClause) {
            super.printFieldUnique(writer, shouldPrintFieldIdentityClause);
        }
    }

    /**
     * JDBC defines and outer join syntax, many drivers do not support this. So
     * we normally avoid it.
     */
    @Override
    public boolean shouldUseJDBCOuterJoinSyntax() {
        return false;
    }

    /**
     * INTERNAL: Override this method if the platform supports sequence objects
     * and it's possible to alter sequence object's increment in the database.
     */
    @Override
    public boolean isAlterSequenceObjectSupported() {
        return true;
    }

    /**
     * Print the pagination SQL using Postgres syntax
     * " LIMIT {@literal <max> OFFSET <first>}".
     */
    @Override
    public void printSQLSelectStatement(DatabaseCall call, ExpressionSQLPrinter printer, SQLSelectStatement statement) {
        int max = 0;
        if (statement.getQuery() != null) {
            max = statement.getQuery().getMaxRows();
        }
        if (max <= 0 || !(this.shouldUseRownumFiltering())) {
            super.printSQLSelectStatement(call, printer, statement);
            return;
        }
        statement.setUseUniqueFieldAliases(true);
        call.setFields(statement.printSQL(printer));
        printer.printString(LIMIT);
        printer.printParameter(DatabaseCall.MAXROW_FIELD);
        printer.printString(OFFSET);
        printer.printParameter(DatabaseCall.FIRSTRESULT_FIELD);
        call.setIgnoreFirstRowSetting(true);
        call.setIgnoreMaxResultsSetting(true);
    }

    /**
     * INTERNAL: May need to override this method if the platform supports
     * temporary tables and the generated sql doesn't work. Write an sql string
     * for updating the original table from the temporary table. Precondition:
     * supportsTempTables() == true. Precondition: pkFields and assignFields
     * don't intersect.
     *
     * @param writer for writing the sql
     * @param table is original table for which temp table is
     *            created.
     * @param pkFields - primary key fields for the original
     *            table.
     * @param assignedFields - fields to be assigned a new value.
     */
    @Override
    public void writeUpdateOriginalFromTempTableSql(Writer writer, DatabaseTable table, Collection pkFields, Collection assignedFields) throws IOException {
        writer.write("UPDATE ");
        String tableName = table.getQualifiedNameDelimited(this);
        writer.write(tableName);
        writer.write(" SET ");

        String tempTableName = getTempTableForTable(table).getQualifiedNameDelimited(this);
        boolean isFirst = true;
        Iterator itFields = assignedFields.iterator();
        while (itFields.hasNext()) {
            if (isFirst) {
                isFirst = false;
            } else {
                writer.write(", ");
            }
            DatabaseField field = (DatabaseField) itFields.next();
            String fieldName = field.getNameDelimited(this);
            writer.write(fieldName);
            writer.write(" = (SELECT ");
            writer.write(fieldName);
            writer.write(" FROM ");
            writer.write(tempTableName);
            writeAutoJoinWhereClause(writer, null, tableName, pkFields, this);
            writer.write(")");
        }

        writer.write(" WHERE EXISTS(SELECT ");
        writer.write(((DatabaseField) pkFields.iterator().next()).getNameDelimited(this));
        writer.write(" FROM ");
        writer.write(tempTableName);
        writeAutoJoinWhereClause(writer, null, tableName, pkFields, this);
        writer.write(")");
    }

    /**
     * INTERNAL:
     * Postgres has a returning clause.
     */
    @Override
    public boolean canBuildCallWithReturning() {
        return true;
    }

    /**
     * INTERNAL:
     * Uses the returning clause on Postgres.
     */
    @Override
    public DatabaseCall buildCallWithReturning(SQLCall sqlCall, Vector returnFields) {
        SQLCall call = new SQLCall();
        call.setParameters(sqlCall.getParameters());
        call.setParameterTypes(sqlCall.getParameterTypes());
        call.returnOneRow();
        Writer writer = new CharArrayWriter(sqlCall.getSQLString().length() + 32);
        try {
            writer.write(sqlCall.getSQLString());
            writer.write(" RETURNING ");
            for (int i = 0; i < returnFields.size(); i++) {
                DatabaseField field = (DatabaseField)returnFields.elementAt(i);
                writer.write(field.getNameDelimited(this));
                if ((i + 1) < returnFields.size()) {
                    writer.write(", ");
                }
            }
            call.setQueryString(writer.toString());
        } catch (IOException exception) {
            throw ValidationException.fileError(exception);
        }
        return call;
    }

    @Override
    protected void setNullFromDatabaseField(DatabaseField databaseField, PreparedStatement statement, int index) throws SQLException {
        // Substituted null value for the corresponding DatabaseField.
        // Cannot bind null through set object, so we must compute the type, this is not good.
        // Fix for bug 2730536: for ARRAY/REF/STRUCT types must pass in the
        // user defined type to setNull as well.
        if (databaseField instanceof ObjectRelationalDatabaseField) {
            ObjectRelationalDatabaseField field = (ObjectRelationalDatabaseField)databaseField;
            //Fix for bug 537657: Inserting empty or null varchar arrays doesn't work with PostgreSQL since driver version 42.2.4
            if (field.getSqlType() == Types.ARRAY) {
                statement.setNull(index, field.getSqlType());
            } else {
                statement.setNull(index, field.getSqlType(), field.getSqlTypeName());
            }
        } else {
            int jdbcType = getJDBCTypeForSetNull(databaseField);
            statement.setNull(index, jdbcType);
        }
    }
}
