Skip to content
wiki.fftac.org

Member System - Source Excerpt 02

Back to Member System

Summary

This source excerpt preserves a bounded section of Anti-Christ.net/wp-content/themes/anti-christ-thin-veil/inc/member-system.php so readers can inspect the evidence without opening the full source file.

**Source path:** Anti-Christ.net/wp-content/themes/anti-christ-thin-veil/inc/member-system.php

/**
 * Member submission category choices.
 *
 * @return array
 */
function actv_member_submission_category_choices() {
	$starter = function_exists( 'actv_starter_categories_data' ) ? actv_starter_categories_data() : array();
	$slugs   = array( 'member-submissions', 'journal', 'claim-review', 'religion-and-the-machine', 'civil-liberties', 'socioeconomic-decay', 'the-machine', 'field-guide', 'toolkit', 'source-desk' );
	$choices = array();

	foreach ( $slugs as $slug ) {
		$choices[ $slug ] = isset( $starter[ $slug ][0] ) ? $starter[ $slug ][0] : ucwords( str_replace( '-', ' ', $slug ) );
	}

	return $choices;
}

/**
 * Ensure a starter category exists and return its term ID.
 *
 * @param string $slug Category slug.
 * @return int
 */
function actv_ensure_starter_category( $slug ) {
	$term = get_category_by_slug( $slug );

	if ( $term ) {
		return (int) $term->term_id;
	}

	$starter     = function_exists( 'actv_starter_categories_data' ) ? actv_starter_categories_data() : array();
	$label       = isset( $starter[ $slug ][0] ) ? $starter[ $slug ][0] : ucwords( str_replace( '-', ' ', $slug ) );
	$description = isset( $starter[ $slug ][1] ) ? $starter[ $slug ][1] : '';
	$result      = wp_insert_term(
		sanitize_text_field( $label ),
		'category',
		array(
			'slug'        => sanitize_title( $slug ),
			'description' => sanitize_text_field( $description ),
		)
	);

	if ( is_wp_error( $result ) || empty( $result['term_id'] ) ) {
		return 0;
	}

	return (int) $result['term_id'];
}

/**
 * Redirect after member submission processing.
 *
 * @param string $status Status key.
 */
function actv_member_submission_redirect( $status ) {
	wp_safe_redirect( add_query_arg( 'member_status', sanitize_key( $status ), actv_page_url( 'submit-dispatch' ) ) );
	exit;
}

/**
 * Handle front-end member dispatch submissions.
 */
function actv_handle_member_submission() {
	if ( 'POST' !== strtoupper( isset( $_SERVER['REQUEST_METHOD'] ) ? (string) $_SERVER['REQUEST_METHOD'] : '' ) ) {
		return;
	}

	if ( ! isset( $_POST['actv_member_submission_action'] ) || 'submit' !== sanitize_key( wp_unslash( $_POST['actv_member_submission_action'] ) ) ) {
		return;
	}

	$nonce = isset( $_POST['actv_member_submission_nonce'] ) ? sanitize_text_field( wp_unslash( $_POST['actv_member_submission_nonce'] ) ) : '';

	if ( ! wp_verify_nonce( $nonce, 'actv_member_submission' ) ) {
		actv_member_submission_redirect( 'invalid' );
	}

	if ( ! actv_is_age_verified() ) {
		actv_member_submission_redirect( 'age_required' );
	}

	if ( ! is_user_logged_in() ) {
		actv_member_submission_redirect( 'login_required' );
	}

	$honeypot = isset( $_POST['actv_member_company'] ) ? trim( (string) wp_unslash( $_POST['actv_member_company'] ) ) : '';

	if ( '' !== $honeypot ) {
		actv_member_submission_redirect( 'invalid' );
	}

	$user_id = get_current_user_id();

	if ( get_transient( 'actv_member_submission_lock_' . $user_id ) ) {
		actv_member_submission_redirect( 'rate_limited' );
	}

	$title    = isset( $_POST['actv_submission_title'] ) ? sanitize_text_field( wp_unslash( $_POST['actv_submission_title'] ) ) : '';
	$summary  = isset( $_POST['actv_submission_summary'] ) ? sanitize_textarea_field( wp_unslash( $_POST['actv_submission_summary'] ) ) : '';
	$body     = isset( $_POST['actv_submission_body'] ) ? wp_kses_post( wp_unslash( $_POST['actv_submission_body'] ) ) : '';
	$category = isset( $_POST['actv_submission_category'] ) ? sanitize_title( wp_unslash( $_POST['actv_submission_category'] ) ) : 'member-submissions';
	$choices  = actv_member_submission_category_choices();

	if ( ! isset( $choices[ $category ] ) ) {
		$category = 'member-submissions';
	}

	if ( '' === $title || '' === trim( wp_strip_all_tags( $body ) ) || empty( $_POST['actv_submission_rules'] ) ) {
		actv_member_submission_redirect( 'missing' );
	}

	$category_id = actv_ensure_starter_category( $category );

	if ( ! $category_id ) {
		$category_id = actv_ensure_starter_category( 'member-submissions' );
	}

	$post_data = array(
		'post_type'      => 'post',
		'post_status'    => 'pending',
		'post_author'    => $user_id,
		'post_title'     => $title,
		'post_content'   => $body,
		'post_excerpt'   => $summary,
		'comment_status' => 'closed',
		'ping_status'    => 'closed',
	);

	if ( $category_id ) {
		$post_data['post_category'] = array( $category_id );
	}

	$post_id = wp_insert_post( $post_data, true );

	if ( is_wp_error( $post_id ) || ! $post_id ) {
		actv_member_submission_redirect( 'failed' );
	}

	update_post_meta( $post_id, '_actv_member_submission', '1' );
	update_post_meta( $post_id, '_actv_member_submission_category', $category );
	update_post_meta( $post_id, '_actv_member_submission_received', current_time( 'mysql' ) );
	set_transient( 'actv_member_submission_lock_' . $user_id, '1', 10 * MINUTE_IN_SECONDS );

	actv_member_submission_redirect( 'received' );
}
add_action( 'template_redirect', 'actv_handle_member_submission', 9 );

/**
 * Render the member hub.
 *
 * @return string
 */
function actv_render_member_home() {
	if ( ! actv_is_age_verified() ) {
		return actv_render_age_gate( __( 'the member desk', 'anti-christ-thin-veil' ) );
	}

	$is_logged_in = is_user_logged_in();
	$user         = $is_logged_in ? wp_get_current_user() : null;

	ob_start();
	?>
	<section class="member-system-grid" aria-label="<?php esc_attr_e( 'Member tools', 'anti-christ-thin-veil' ); ?>">
		<article class="member-card">
			<p class="section-label"><?php esc_html_e( 'Roster', 'anti-christ-thin-veil' ); ?></p>
			<h2><?php esc_html_e( 'Join the member roster', 'anti-christ-thin-veil' ); ?></h2>
			<p><?php esc_html_e( 'Use Participants Database for intake, private roster updates, and recovery of private edit links. Roster signup is separate from WordPress login and never guarantees publication.', 'anti-christ-thin-veil' ); ?></p>
			<a class="button button-primary" href="<?php echo esc_url( actv_page_url( 'join' ) ); ?>"><?php esc_html_e( 'Open roster intake', 'anti-christ-thin-veil' ); ?></a>
		</article>
		<article class="member-card">
			<p class="section-label"><?php esc_html_e( 'Login', 'anti-christ-thin-veil' ); ?></p>
			<h2><?php echo $is_logged_in ? esc_html__( 'You are signed in', 'anti-christ-thin-veil' ) : esc_html__( 'Sign in to post', 'anti-christ-thin-veil' ); ?></h2>
			<?php if ( $is_logged_in && $user instanceof WP_User ) : ?>
				<p>
					<?php
					printf(
						/* translators: %s is the logged-in user's display name. */
						esc_html__( 'Active WordPress account: %s. Dispatches you submit enter pending editorial review.', 'anti-christ-thin-veil' ),
						esc_html( $user->display_name ? $user->display_name : $user->user_login )
					);
					?>
				</p>
				<a class="button button-primary" href="<?php echo esc_url( actv_page_url( 'submit-dispatch' ) ); ?>"><?php esc_html_e( 'Submit dispatch', 'anti-christ-thin-veil' ); ?></a>
				<a class="button button-ghost" href="<?php echo esc_url( wp_logout_url( actv_page_url( 'members' ) ) ); ?>"><?php esc_html_e( 'Log out', 'anti-christ-thin-veil' ); ?></a>
			<?php else : ?>
				<p><?php esc_html_e( 'Posting requires a WordPress account. Public WordPress registration is currently request-based; use the roster intake if you need access and expect editorial review.', 'anti-christ-thin-veil' ); ?></p>
				<a class="button button-primary" href="<?php echo esc_url( actv_page_url( 'member-login' ) ); ?>"><?php esc_html_e( 'Open login', 'anti-christ-thin-veil' ); ?></a>
			<?php endif; ?>
		</article>
		<article class="member-card">
			<p class="section-label"><?php esc_html_e( 'Record', 'anti-christ-thin-veil' ); ?></p>
			<h2><?php esc_html_e( 'Update your private record', 'anti-christ-thin-veil' ); ?></h2>
			<p><?php esc_html_e( 'Use the private link emailed by Participants Database to edit your roster record. No public directory is exposed by this theme.', 'anti-christ-thin-veil' ); ?></p>
			<a class="button button-ghost" href="<?php echo esc_url( actv_page_url( 'member-record' ) ); ?>"><?php esc_html_e( 'Open record page', 'anti-christ-thin-veil' ); ?></a>
		</article>
	</section>
	<?php
	return ob_get_clean();
}

/**
 * Render the member login page body.
 *
 * @return string
 */
function actv_render_member_login_panel() {
	if ( ! actv_is_age_verified() ) {
		return actv_render_age_gate( __( 'member login', 'anti-christ-thin-veil' ) );
	}