Pledge: Count number of confirmed contributors instead of using arbitrary number input (#52)

This will be more accurate and avoid confusion that could arise if the self-reported "Number of Employees Being Sponsored" didn't match the number of confirmed contributors listed on the pledge.

Having that counted number stored in post meta is still useful, though, so this also adds/updates that number for a pledge whenever a Contributor post changes its status.

Fixes #48
This commit is contained in:
Corey McKrill 2019-10-25 13:39:13 -07:00 committed by GitHub
parent 553247cbf7
commit 838a490776
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 60 additions and 30 deletions

View file

@ -139,6 +139,20 @@ function create_new_contributor( $wporg_username, $pledge_id ) {
return wp_insert_post( $args, true ); return wp_insert_post( $args, true );
} }
/**
* Remove a contributor post from a pledge.
*
* This wrapper function ensures we have a standardized way of removing a contributor that will still
* transition a post status (see PledgeMeta\update_confirmed_contributor_count).
*
* @param int $contributor_post_id
*
* @return false|WP_Post|null
*/
function remove_contributor( $contributor_post_id ) {
return wp_trash_post( $contributor_post_id );
}
/** /**
* Get the contributor posts associated with a particular pledge post. * Get the contributor posts associated with a particular pledge post.
* *

View file

@ -15,10 +15,11 @@ defined( 'WPINC' ) || die();
const META_PREFIX = FiveForTheFuture\PREFIX . '_'; const META_PREFIX = FiveForTheFuture\PREFIX . '_';
add_action( 'init', __NAMESPACE__ . '\register_pledge_meta' ); add_action( 'init', __NAMESPACE__ . '\register_pledge_meta' );
add_action( 'admin_init', __NAMESPACE__ . '\add_meta_boxes' ); add_action( 'admin_init', __NAMESPACE__ . '\add_meta_boxes' );
add_action( 'save_post', __NAMESPACE__ . '\save_pledge', 10, 2 ); add_action( 'save_post', __NAMESPACE__ . '\save_pledge', 10, 2 );
add_action( 'admin_enqueue_scripts', __NAMESPACE__ . '\enqueue_assets' ); add_action( 'admin_enqueue_scripts', __NAMESPACE__ . '\enqueue_assets' );
add_action( 'transition_post_status', __NAMESPACE__ . '\update_confirmed_contributor_count', 10, 3 );
// Both hooks must be used because `updated` doesn't fire if the post meta didn't previously exist. // Both hooks must be used because `updated` doesn't fire if the post meta didn't previously exist.
add_action( 'updated_postmeta', __NAMESPACE__ . '\update_generated_meta', 10, 4 ); add_action( 'updated_postmeta', __NAMESPACE__ . '\update_generated_meta', 10, 4 );
@ -31,49 +32,48 @@ add_action( 'added_post_meta', __NAMESPACE__ . '\update_generated_meta', 10, 4
*/ */
function get_pledge_meta_config( $context = '' ) { function get_pledge_meta_config( $context = '' ) {
$user_input = array( $user_input = array(
'org-description' => array( 'org-description' => array(
'single' => true, 'single' => true,
'sanitize_callback' => 'sanitize_text_field', 'sanitize_callback' => 'sanitize_text_field',
'show_in_rest' => true, 'show_in_rest' => true,
'php_filter' => FILTER_SANITIZE_STRING, 'php_filter' => FILTER_SANITIZE_STRING,
), ),
'org-name' => array( 'org-name' => array(
'single' => true, 'single' => true,
'sanitize_callback' => 'sanitize_text_field', 'sanitize_callback' => 'sanitize_text_field',
'show_in_rest' => true, 'show_in_rest' => true,
'php_filter' => FILTER_SANITIZE_STRING, 'php_filter' => FILTER_SANITIZE_STRING,
), ),
'org-url' => array( 'org-url' => array(
'single' => true, 'single' => true,
'sanitize_callback' => 'esc_url_raw', 'sanitize_callback' => 'esc_url_raw',
'show_in_rest' => true, 'show_in_rest' => true,
'php_filter' => FILTER_VALIDATE_URL, 'php_filter' => FILTER_VALIDATE_URL,
), ),
'org-pledge-email' => array( 'org-pledge-email' => array(
'single' => true, 'single' => true,
'sanitize_callback' => 'sanitize_email', 'sanitize_callback' => 'sanitize_email',
'show_in_rest' => false, 'show_in_rest' => false,
'php_filter' => FILTER_VALIDATE_EMAIL, 'php_filter' => FILTER_VALIDATE_EMAIL,
), ),
'org-number-employees' => array(
'single' => true,
'sanitize_callback' => 'absint',
'show_in_rest' => false,
'php_filter' => FILTER_VALIDATE_INT,
),
); );
$generated = array( $generated = array(
'org-domain' => array( 'org-domain' => array(
'single' => true, 'single' => true,
'sanitize_callback' => 'sanitize_text_field', 'sanitize_callback' => 'sanitize_text_field',
'show_in_rest' => false, 'show_in_rest' => false,
), ),
'pledge-email-confirmed' => array( 'pledge-email-confirmed' => array(
'single' => true, 'single' => true,
'sanitize_callback' => 'wp_validate_boolean', 'sanitize_callback' => 'wp_validate_boolean',
'show_in_rest' => false, 'show_in_rest' => false,
), ),
'pledge-confirmed-contributors' => array(
'single' => true,
'sanitize_callback' => 'absint',
'show_in_rest' => false,
),
); );
switch ( $context ) { switch ( $context ) {
@ -285,6 +285,36 @@ function update_generated_meta( $meta_id, $object_id, $meta_key, $_meta_value )
} }
} }
/**
* Update the cached count of confirmed contributors for a pledge when a contributor post changes statuses.
*
* Note that contributor posts should always be trashed instead of deleted completely when a contributor is
* removed from a pledge.
*
* @param string $new_status
* @param string $old_status
* @param WP_Post $post
*
* @return void
*/
function update_confirmed_contributor_count( $new_status, $old_status, WP_Post $post ) {
if ( Contributor\CPT_ID !== get_post_type( $post ) ) {
return;
}
if ( $new_status === $old_status ) {
return;
}
$pledge = get_post( $post->post_parent );
if ( $pledge instanceof WP_Post ) {
$confirmed_contributors = Contributor\get_pledge_contributors( $pledge->ID, 'publish' );
update_post_meta( $pledge->ID, META_PREFIX . 'pledge-confirmed-contributors', count( $confirmed_contributors ) );
}
}
/** /**
* Check that an array contains values for all required keys. * Check that an array contains values for all required keys.
* *

View file

@ -60,17 +60,3 @@ namespace WordPressDotOrg\FiveForTheFuture\View;
echo esc_html( $data['org-description'] ); echo esc_html( $data['org-description'] );
/* phpcs:ignore */ ?></textarea> /* phpcs:ignore */ ?></textarea>
</div> </div>
<div class="form-field">
<label for="5ftf-org-number-employees">
<?php esc_html_e( 'Number of Employees Being Contributed', 'wordpressorg' ); ?>
</label>
<input
type="number"
id="5ftf-org-number-employees"
name="org-number-employees"
value="<?php echo esc_attr( $data['org-number-employees'] ); ?>"
required
<?php echo $readonly ? 'readonly' : ''; ?>
/>
</div>