<?php
/** Contact Form 7 create, update, duplicate and delete abilities. */

if ( ! defined( 'ABSPATH' ) ) {
	exit;
}

/** @return array<string,mixed> */
function wpagent_cf7_write_output_schema(): array {
	return wpagent_forms_public_object_schema( array( 'form' => wpagent_cf7_form_output_schema(), 'verified' => array( 'type' => 'boolean' ) ), array( 'form', 'verified' ) );
}

/**
 * Compensates only a just-created candidate whose complete state still exactly
 * matches our own expected hash. Existing forms stay on the manual-only path.
 */
function wpagent_cf7_delete_owned_candidate( int $form_id, string $candidate_hash ): bool {
	if ( $form_id <= 0 || 1 !== preg_match( '/^[a-f0-9]{64}$/', $candidate_hash ) ) {
		return false;
	}
	$fresh = wpcf7_contact_form( $form_id );
	if ( ! $fresh instanceof WPCF7_ContactForm || ! hash_equals( $candidate_hash, wpagent_cf7_state_hash( $fresh ) ) ) {
		return false;
	}
	return $fresh->delete() && ! wpcf7_contact_form( $form_id );
}

function wpagent_ability_create_contact_form(): array {
	return array(
		'label' => __( 'Kontaktformular erstellen', 'wp-agent-companion' ),
		'description' => __( 'Erstellt ein Contact-Form-7-Formular über dessen native API mit begrenzter Mailkonfiguration, vollständiger Validierung und exaktem Read-back. Nicht verifizierte eigene Neuanlagen werden nur nach einem frischen Zustandsabgleich entfernt.', 'wp-agent-companion' ),
		'category' => 'wp-agent',
		'input_schema' => array( 'type' => 'object', 'properties' => wpagent_cf7_write_properties_schema(), 'required' => array( 'title' ), 'additionalProperties' => false ),
		'output_schema' => wpagent_cf7_write_output_schema(),
		'execute_callback' => 'wpagent_exec_create_contact_form',
		'permission_callback' => 'wpagent_perm_cf7_edit',
		'meta' => array( 'show_in_rest' => true, 'annotations' => array( 'readonly' => false, 'destructive' => false, 'idempotent' => false ) ),
	);
}

/** @param mixed $input @return array|WP_Error */
function wpagent_exec_create_contact_form( $input ) {
	if ( ! wpagent_cf7_available() ) {
		return wpagent_cf7_missing_error();
	}
	return wpagent_cf7_create_safe( is_array( $input ) ? $input : array() );
}

function wpagent_ability_update_contact_form(): array {
	$properties = array_merge(
		array(
			'form_id' => array( 'type' => 'integer', 'minimum' => 1 ),
			'expected_hash' => array( 'type' => 'string', 'pattern' => '^[a-f0-9]{64}$' ),
		),
		wpagent_cf7_write_properties_schema()
	);
	return array(
		'label' => __( 'Kontaktformular aktualisieren', 'wp-agent-companion' ),
		'description' => __( 'Aktualisiert nur sichere Eigenschaften eines Contact-Form-7-Formulars mit Zustands-Hash, Lock, nativer Validierung und exaktem Read-back. Nicht bestätigte Teiländerungen erfordern eine manuelle Prüfung.', 'wp-agent-companion' ),
		'category' => 'wp-agent',
		'input_schema' => array( 'type' => 'object', 'properties' => $properties, 'required' => array( 'form_id', 'expected_hash' ), 'additionalProperties' => false ),
		'output_schema' => wpagent_cf7_write_output_schema(),
		'execute_callback' => 'wpagent_exec_update_contact_form',
		'permission_callback' => 'wpagent_perm_cf7_edit',
		'meta' => array( 'show_in_rest' => true, 'annotations' => array( 'readonly' => false, 'destructive' => false, 'idempotent' => false ) ),
	);
}

/** @param mixed $input @return array|WP_Error */
function wpagent_exec_update_contact_form( $input ) {
	$input = is_array( $input ) ? $input : array();
	$form = wpagent_cf7_get_authorized_form( $input, 'wpcf7_edit_contact_form' );
	if ( is_wp_error( $form ) ) {
		return $form;
	}
	return wpagent_cf7_update_safe( $input, $form );
}

function wpagent_ability_duplicate_contact_form(): array {
	return array(
		'label' => __( 'Kontaktformular duplizieren', 'wp-agent-companion' ),
		'description' => __( 'Dupliziert einen unveränderten Contact-Form-7-Zustand über dessen copy()-API unter Konfliktschutz, Validierung und exaktem Read-back.', 'wp-agent-companion' ),
		'category' => 'wp-agent',
		'input_schema' => array(
			'type' => 'object',
			'properties' => array(
				'form_id' => array( 'type' => 'integer', 'minimum' => 1 ),
				'expected_hash' => array( 'type' => 'string', 'pattern' => '^[a-f0-9]{64}$' ),
				'title' => array( 'type' => 'string', 'minLength' => 1, 'maxLength' => WPAGENT_CF7_MAX_TITLE_BYTES ),
			),
			'required' => array( 'form_id', 'expected_hash' ),
			'additionalProperties' => false,
		),
		'output_schema' => wpagent_cf7_write_output_schema(),
		'execute_callback' => 'wpagent_exec_duplicate_contact_form',
		'permission_callback' => 'wpagent_perm_cf7_edit',
		'meta' => array( 'show_in_rest' => true, 'annotations' => array( 'readonly' => false, 'destructive' => false, 'idempotent' => false ) ),
	);
}

/** @param mixed $input @return array|WP_Error */
function wpagent_exec_duplicate_contact_form( $input ) {
	$input = is_array( $input ) ? $input : array();
	$form = wpagent_cf7_get_authorized_form( $input, 'wpcf7_edit_contact_form' );
	if ( is_wp_error( $form ) ) {
		return $form;
	}
	foreach ( array_keys( $input ) as $key ) {
		if ( ! in_array( $key, array( 'form_id', 'expected_hash', 'title' ), true ) ) {
			return new WP_Error( 'wpagent_cf7_property', __( 'Die Anfrage enthält eine nicht erlaubte CF7-Eigenschaft.', 'wp-agent-companion' ), array( 'status' => 400 ) );
		}
	}
	$expected = wpagent_cf7_expected_hash( $input['expected_hash'] ?? '' );
	if ( is_wp_error( $expected ) ) {
		return $expected;
	}
	if ( array_key_exists( 'title', $input ) ) {
		$valid = wpagent_cf7_validate_text( $input['title'], 'title', WPAGENT_CF7_MAX_TITLE_BYTES, false, true );
		if ( is_wp_error( $valid ) || trim( $input['title'] ) !== $input['title'] ) {
			return is_wp_error( $valid ) ? $valid : new WP_Error( 'wpagent_cf7_title_whitespace', __( 'Der Titel darf keine führenden oder abschließenden Leerzeichen enthalten.', 'wp-agent-companion' ), array( 'status' => 400 ) );
		}
	}
	$form_id = (int) $form->id();
	$lock = wpagent_cf7_acquire_lock( $form_id );
	if ( is_wp_error( $lock ) ) {
		return $lock;
	}
	try {
		$current = wpcf7_contact_form( $form_id );
		$current_hash = $current instanceof WPCF7_ContactForm ? wpagent_cf7_state_hash( $current ) : '';
		if ( ! $current || ! hash_equals( $current_hash, $expected ) ) {
			return new WP_Error( 'wpagent_cf7_conflict', __( 'Das Formular wurde seit dem Lesen verändert.', 'wp-agent-companion' ), array( 'status' => 409, 'current_hash' => $current_hash ) );
		}
		$copy = $current->copy();
		if ( ! $copy instanceof WPCF7_ContactForm ) {
			return new WP_Error( 'wpagent_cf7_copy_failed', __( 'Das Formular konnte nicht dupliziert werden.', 'wp-agent-companion' ), array( 'status' => 500 ) );
		}
		if ( array_key_exists( 'title', $input ) ) {
			$copy->set_title( $input['title'] );
		}
		$valid = wpagent_cf7_validate_candidate( $copy, array( 'form' => (string) $copy->prop( 'form' ) ), true );
		if ( is_wp_error( $valid ) ) {
			return $valid;
		}
		$expected_copy = wpagent_cf7_state_hash( $copy );
		$id = $copy->save();
		$fresh = $id ? wpcf7_contact_form( (int) $id ) : null;
		$verified = $fresh instanceof WPCF7_ContactForm && (int) $fresh->id() !== $form_id && hash_equals( $expected_copy, wpagent_cf7_state_hash( $fresh ) );
		if ( ! $verified ) {
			$rolled_back = $id > 0 && wpagent_cf7_delete_owned_candidate( (int) $id, $expected_copy );
			return new WP_Error(
				'wpagent_cf7_recovery_required',
				$rolled_back
					? __( 'Die Formularkopie konnte nicht verifiziert werden und wurde als unveränderter, eigener Kandidat entfernt.', 'wp-agent-companion' )
					: __( 'Die Formularkopie konnte nicht verifiziert werden. Ihr aktueller Zustand muss vor einer manuellen Bereinigung geprüft werden.', 'wp-agent-companion' ),
				array( 'status' => 409, 'recovery_required' => ! $rolled_back, 'rollback_succeeded' => $rolled_back, 'form_id' => absint( $id ) )
			);
		}
		$payload = wpagent_cf7_form_payload( $fresh );
		return is_wp_error( $payload ) ? $payload : array( 'form' => $payload, 'verified' => true );
	} finally {
		wpagent_cf7_release_lock( $form_id, $lock );
	}
}

function wpagent_ability_delete_contact_form(): array {
	return array(
		'label' => __( 'Kontaktformular manuell löschen', 'wp-agent-companion' ),
		'description' => __( 'Die Fernlöschung bestehender Contact-Form-7-Formulare ist ohne atomare Provider-Prüfung nicht verfügbar. Lösche das Formular manuell in WordPress.', 'wp-agent-companion' ),
		'category' => 'wp-agent',
		'input_schema' => array(
			'type' => 'object',
			'properties' => array(
				'form_id' => array( 'type' => 'integer', 'minimum' => 1 ),
				'expected_hash' => array( 'type' => 'string', 'pattern' => '^[a-f0-9]{64}$' ),
				'confirm' => array( 'type' => 'boolean' ),
			),
			'required' => array( 'form_id', 'expected_hash', 'confirm' ),
			'additionalProperties' => false,
		),
		'output_schema' => wpagent_forms_public_object_schema( array( 'form_id' => array( 'type' => 'integer', 'minimum' => 1 ), 'deleted' => array( 'type' => 'boolean' ) ), array( 'form_id', 'deleted' ) ),
		'execute_callback' => 'wpagent_exec_delete_contact_form',
		'permission_callback' => 'wpagent_perm_cf7_edit',
		'meta' => array( 'show_in_rest' => true, 'annotations' => array( 'readonly' => false, 'destructive' => true, 'idempotent' => false, 'manual_only' => true ) ),
	);
}

/** @param mixed $input @return array|WP_Error */
function wpagent_exec_delete_contact_form( $input ) {
	$input = is_array( $input ) ? $input : array();
	foreach ( array_keys( $input ) as $key ) {
		if ( ! in_array( $key, array( 'form_id', 'expected_hash', 'confirm' ), true ) ) {
			return new WP_Error( 'wpagent_cf7_property', __( 'Die Anfrage enthält eine nicht erlaubte CF7-Eigenschaft.', 'wp-agent-companion' ), array( 'status' => 400 ) );
		}
	}
	if ( true !== ( $input['confirm'] ?? false ) ) {
		return new WP_Error( 'wpagent_confirmation_required', __( 'Dauerhaftes Löschen erfordert confirm=true.', 'wp-agent-companion' ), array( 'status' => 400 ) );
	}
	$form = wpagent_cf7_get_authorized_form( $input, 'wpcf7_delete_contact_form' );
	if ( is_wp_error( $form ) ) {
		return $form;
	}
	$form_id = (int) $form->id();
	$expected = wpagent_cf7_expected_hash( $input['expected_hash'] ?? '' );
	if ( is_wp_error( $expected ) ) {
		return $expected;
	}
	$lock = wpagent_cf7_acquire_lock( $form_id );
	if ( is_wp_error( $lock ) ) {
		return $lock;
	}
	try {
		$current = wpcf7_contact_form( $form_id );
		$current_hash = $current instanceof WPCF7_ContactForm ? wpagent_cf7_state_hash( $current ) : '';
		if ( ! $current || ! hash_equals( $current_hash, $expected ) ) {
			return new WP_Error( 'wpagent_cf7_conflict', __( 'Das Formular wurde seit dem Lesen verändert.', 'wp-agent-companion' ), array( 'status' => 409, 'current_hash' => $current_hash ) );
		}
		return new WP_Error( 'wpagent_cf7_delete_manual_only', __( 'Das dauerhafte Löschen bestehender Contact-Form-7-Formulare kann ohne atomare Provider-Prüfung nicht sicher gegen parallele Änderungen abgesichert werden. Lösche das Formular in WordPress manuell.', 'wp-agent-companion' ), array( 'status' => 409, 'form_id' => $form_id ) );
	} finally {
		wpagent_cf7_release_lock( $form_id, $lock );
	}
}
