<?php
/**
 * WordPress registered post and page metadata schemas.
 *
 * @package ScheduledChanges
 */

namespace ScheduledChanges\Discovery;

/**
 * Normalizes access to WordPress registered metadata.
 */
final class RegisteredMetadataRegistry {
	/**
	 * @return array<string,array<string,mixed>>
	 */
	public function forSubtype( string $subtype ): array {
		$registered = get_registered_meta_keys( 'post', $subtype );
		ksort( $registered );

		return $registered;
	}

	/**
	 * @return array<string,mixed>|null
	 */
	public function get( string $subtype, string $key ): ?array {
		return $this->forSubtype( $subtype )[ $key ] ?? null;
	}

	/**
	 * @param array<string,mixed> $registration Registered metadata arguments.
	 * @return array<string,mixed>
	 */
	public function schema( array $registration ): array {
		$schema = array(
			'type'        => $registration['type'] ?? 'string',
			'description' => (string) ( $registration['description'] ?? '' ),
			'default'     => $registration['default'] ?? null,
		);
		$rest   = $registration['show_in_rest'] ?? false;

		if ( is_array( $rest ) && is_array( $rest['schema'] ?? null ) ) {
			$schema = array_merge( $schema, $rest['schema'] );
		}

		return $schema;
	}

	public function versionFingerprint(): string {
		$summary = array();

		foreach ( array( 'post', 'page' ) as $subtype ) {
			foreach ( $this->forSubtype( $subtype ) as $key => $registration ) {
				$summary[ $subtype ][ $key ] = array(
					'type'          => $registration['type'] ?? 'string',
					'single'        => (bool) ( $registration['single'] ?? false ),
					'show_in_rest'  => false !== ( $registration['show_in_rest'] ?? false ),
					'label'         => (string) ( $registration['label'] ?? '' ),
					'description'   => (string) ( $registration['description'] ?? '' ),
					'has_sanitizer' => is_callable( $registration['sanitize_callback'] ?? null ),
					'has_auth'      => is_callable( $registration['auth_callback'] ?? null ),
				);
			}
		}

		return substr( hash( 'sha256', (string) wp_json_encode( $summary ) ), 0, 12 );
	}
}
