<?php
if ( ! defined( 'ABSPATH' ) ) {
    exit;
}

/**
 * @return float
 */
function elementsell_billing_get_fee_percent() {
    return 1.0;
}

/**
 * @return int
 */
function elementsell_billing_get_fee_max() {
    return 990;
}

/**
 * Počet produkčních prodejů zdarma před požadavkem na kartu.
 *
 * @return int
 */
function elementsell_billing_get_required_sales_count() {
    return 10;
}

/**
 * @return int Částka v haléřích (1 Kč).
 */
function elementsell_billing_get_card_verification_amount() {
    return 100;
}

/**
 * @return string
 */
function elementsell_billing_get_parent_payment_uid() {
    return (string) get_option( 'elementsell_parent_payment_uid', '' );
}

/**
 * @param string $uid
 * @return void
 */
function elementsell_billing_set_parent_payment_uid( $uid ) {
    update_option( 'elementsell_parent_payment_uid', sanitize_text_field( (string) $uid ) );
}

/**
 * @return bool
 */
function elementsell_billing_has_saved_card() {
    return elementsell_billing_get_parent_payment_uid() !== '';
}

/**
 * @return bool
 */
function elementsell_billing_is_payment_failed() {
    return get_option( 'payment_failed', 'ne' ) === 'ano';
}

/**
 * SQL podmínka: pouze produkční objednávky (ne demo).
 *
 * @param string $orders_alias
 * @return string
 */
function elementsell_billing_get_production_orders_sql( $orders_alias = '' ) {
    global $wpdb;

    $prefix = $orders_alias !== '' ? $orders_alias . '.' : '';
    $fields_table = $wpdb->prefix . 'elementsell_order_fields';

    return " AND {$prefix}id NOT IN (
        SELECT order_id
        FROM {$fields_table}
        WHERE ( field_name = 'environment' AND field_value = 'demo' )
           OR ( field_name = 'billing_test' AND field_value = '1' )
           OR ( field_name = 'landing_lead' AND field_value = '1' )
           OR ( field_name = 'landing_demo' AND field_value = '1' )
           OR ( field_name = 'fio_test' AND field_value = '1' )
           OR ( field_name = 'invoice_sample' AND field_value = '1' )
           OR ( field_name = 'invoice_bulk_sample' AND field_value = '1' )
           OR ( field_name = 'invoice_hist_sample' AND field_value = '1' )
           OR ( field_name = 'api_url' AND field_value LIKE '%demo.%' )
           OR ( field_name = 'gate_url' AND field_value LIKE '%demo.%' )
    )";
}

/**
 * @return int
 */
function elementsell_get_legacy_paid_orders_count_only() {
    global $wpdb;

    $table = $wpdb->prefix . 'zakaznici';

    if ( $wpdb->get_var( $wpdb->prepare( 'SHOW TABLES LIKE %s', $table ) ) !== $table ) {
        return 0;
    }

    return (int) $wpdb->get_var(
        "SELECT COUNT(*) FROM {$table} WHERE payment_status = 'paid' AND api_url NOT LIKE '%demo%'"
    );
}

/**
 * @return int
 */
function elementsell_get_production_paid_orders_count() {
    $cached = get_transient( 'elementsell_paid_orders_count' );

    if ( false !== $cached ) {
        return (int) $cached;
    }

    global $wpdb;

    $orders_table = $wpdb->prefix . 'elementsell_orders';
    $production   = elementsell_billing_get_production_orders_sql();

    $count = (int) $wpdb->get_var(
        "SELECT COUNT(*) FROM {$orders_table} WHERE payment_status = 'paid' {$production}"
    );

    $count += elementsell_get_legacy_paid_orders_count_only();

    set_transient( 'elementsell_paid_orders_count', $count, 5 * MINUTE_IN_SECONDS );

    return $count;
}

/**
 * Zpětná kompatibilita.
 *
 * @return int
 */
function elementsell_get_legacy_paid_orders_count() {
    return elementsell_get_production_paid_orders_count();
}

/**
 * @param int $year
 * @param int $month
 * @return float
 */
function elementsell_get_production_revenue_for_month( $year, $month ) {
    global $wpdb;

    $orders_table = $wpdb->prefix . 'elementsell_orders';
    $production   = elementsell_billing_get_production_orders_sql();

    $total = (float) $wpdb->get_var(
        $wpdb->prepare(
            "SELECT COALESCE(SUM(amount), 0)
             FROM {$orders_table}
             WHERE payment_status = 'paid'
             {$production}
             AND YEAR(created_at) = %d
             AND MONTH(created_at) = %d",
            (int) $year,
            (int) $month
        )
    );

    $legacy_table = $wpdb->prefix . 'zakaznici';

    if ( $wpdb->get_var( $wpdb->prepare( 'SHOW TABLES LIKE %s', $legacy_table ) ) === $legacy_table ) {
        $legacy_total = (float) $wpdb->get_var(
            $wpdb->prepare(
                "SELECT COALESCE(SUM(amount), 0)
                 FROM {$legacy_table}
                 WHERE payment_status = 'paid'
                 AND api_url NOT LIKE '%%demo%%'
                 AND YEAR(date) = %d
                 AND MONTH(date) = %d",
                (int) $year,
                (int) $month
            )
        );

        $total += $legacy_total;
    }

    return $total;
}

/**
 * @param float $revenue_czk
 * @return float
 */
function elementsell_calculate_billing_fee( $revenue_czk ) {
    $revenue_czk = max( 0, (float) $revenue_czk );

    if ( $revenue_czk <= 0 ) {
        return 0.0;
    }

    $fee = $revenue_czk * ( elementsell_billing_get_fee_percent() / 100 );

    return min( (float) elementsell_billing_get_fee_max(), $fee );
}

/**
 * ThePay vyžaduje město, PSČ a ulici jako samostatná neprázdná pole.
 * Z textarea faktury se pokusíme město oddělit, jinak použijeme výchozí hodnoty.
 *
 * @return \ThePay\ApiClient\Model\Address
 */
function elementsell_billing_create_thepay_address() {
    $address_text = trim( (string) get_option( 'faktury_adresa', '' ) );
    $street       = $address_text;
    $city         = 'Praha';
    $zip          = '110 00';

    if ( $address_text !== '' && false !== strpos( $address_text, ',' ) ) {
        $parts = array_map( 'trim', explode( ',', $address_text ) );

        if ( count( $parts ) >= 2 ) {
            $city   = (string) end( $parts );
            $street = implode( ', ', array_slice( $parts, 0, -1 ) );
        }
    }

    if ( preg_match( '/^(\d{3}\s?\d{2})\s+(.+)$/u', $city, $matches ) ) {
        $zip  = $matches[1];
        $city = trim( $matches[2] );
    }

    if ( $street === '' ) {
        $street = $address_text !== '' ? $address_text : '-';
    }

    return new \ThePay\ApiClient\Model\Address( 'CZ', $city, $zip, $street );
}

/**
 * @return bool
 */
function elementsell_billing_are_invoice_details_complete() {
    $name  = trim( (string) get_option( 'faktury_jmeno', '' ) );
    $addr  = trim( (string) get_option( 'faktury_adresa', '' ) );
    $email = function_exists( 'elementsell_get_invoice_supplier_email' )
        ? elementsell_get_invoice_supplier_email()
        : trim( (string) get_option( 'faktury_email', '' ) );

    return $name !== '' && $addr !== '' && $email !== '' && is_email( $email );
}

/**
 * @return bool
 */
function elementsell_is_billing_blocked() {
    if ( elementsell_billing_has_saved_card() ) {
        return false;
    }

    return elementsell_get_production_paid_orders_count() >= elementsell_billing_get_required_sales_count();
}

/**
 * @return bool
 */
function elementsell_billing_should_prompt_for_card() {
    return ! elementsell_billing_has_saved_card()
        && (
            elementsell_is_billing_blocked()
            || elementsell_billing_is_payment_failed()
        );
}

/**
 * @return string
 */
function elementsell_billing_get_token_start_url() {
    return wp_nonce_url(
        admin_url( 'admin-post.php?action=elementsell_billing_start' ),
        'elementsell_billing_start'
    );
}

/**
 * @param int $year
 * @param int $month
 * @return string
 */
function elementsell_billing_get_revenue_option_key( $year, $month ) {
    return 'paid_' . (int) $year . '_' . str_pad( (string) (int) $month, 2, '0', STR_PAD_LEFT );
}

/**
 * @param int $year
 * @param int $month
 * @return string
 */
function elementsell_billing_get_fee_paid_option_key( $year, $month ) {
    return 'poplatek_zaplacen_' . (int) $year . '_' . str_pad( (string) (int) $month, 2, '0', STR_PAD_LEFT );
}

/**
 * @return void
 */
function elementsell_billing_flush_paid_orders_cache() {
    delete_transient( 'elementsell_paid_orders_count' );
}

add_action( 'elementsell_order_paid', 'elementsell_billing_flush_paid_orders_cache' );

/**
 * @return void
 */
function elementsell_billing_reset_card_required_email_state() {
    delete_option( 'elementsell_billing_card_email_count' );
    delete_option( 'elementsell_billing_card_email_last_sent' );
}

/**
 * @return string
 */
function elementsell_get_support_email() {
    return 'info@elementsell.cz';
}

/**
 * @return string
 */
function elementsell_get_brand_url() {
    return 'https://elementsell.cz';
}

/**
 * @return string
 */
function elementsell_get_billing_admin_url() {
    return admin_url( 'admin.php?page=elementsell' );
}

/**
 * @return void
 */
function elementsell_render_payment_form_byline() {
    ?>
    <p class="elementsell-payment-byline">
        Platbu zajišťuje <a href="<?php echo esc_url( elementsell_get_brand_url() ); ?>" target="_blank" rel="noopener noreferrer">ElementSell</a>
    </p>
    <?php
}

/**
 * @return bool
 */
function elementsell_should_show_billing_form_hint() {
    return current_user_can( 'manage_options' )
        && ( elementsell_is_billing_blocked() || elementsell_billing_is_payment_failed() );
}

/**
 * @return void
 */
function elementsell_render_billing_form_attention_notice() {
    if ( ! elementsell_should_show_billing_form_hint() ) {
        return;
    }

    $label = elementsell_billing_is_payment_failed()
        ? 'Aktualizujte platební kartu'
        : 'Uložte platební kartu';
    ?>
    <a class="elementsell-billing-form-hint" href="<?php echo esc_url( elementsell_get_billing_admin_url() ); ?>">
        <?php echo esc_html( $label ); ?>
    </a>
    <?php
}

/**
 * @return string
 */
function elementsell_get_server_public_ip_for_display() {
    $cached = get_transient( 'elementsell_server_public_ip' );

    return is_string( $cached ) && $cached !== '' ? $cached : '—';
}

/**
 * @return void
 */
function elementsell_refresh_server_public_ip() {
    $response = wp_remote_get(
        'https://api.ipify.org',
        [
            'timeout' => 3,
        ]
    );

    if ( is_wp_error( $response ) ) {
        return;
    }

    $ip = trim( (string) wp_remote_retrieve_body( $response ) );

    if ( $ip !== '' ) {
        set_transient( 'elementsell_server_public_ip', $ip, DAY_IN_SECONDS );
    }
}

/**
 * @return void
 */
function elementsell_maybe_refresh_server_public_ip() {
    if ( ! is_admin() || ! current_user_can( 'manage_options' ) ) {
        return;
    }

    if ( isset( $_GET['action'] ) && $_GET['action'] === 'elementor' ) {
        return;
    }

    if ( get_transient( 'elementsell_server_public_ip' ) !== false ) {
        return;
    }

    elementsell_refresh_server_public_ip();
}

add_action( 'admin_init', 'elementsell_maybe_refresh_server_public_ip', 99 );
