Last active
September 16, 2016 13:25
-
-
Save akirk/9e1d51edce273c93ed89a6bbe71ecf0a to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/** | |
* Plugin Name: Cross-Locale PTE | |
* Plugin URI: https://meta.trac.wordpress.org/ticket/2000 | |
* Description: Implements a user that can approve and import translations in all | |
* translation-sets of a project but cannot overwrite current translations by others. | |
*/ | |
// This is re-implemented in the following filter. | |
remove_filter( 'gp_pre_can_user', 'gp_route_translation_set_permissions_to_validator_permissions' ); | |
/* | |
* A Cross-Locale PTE is defined through an entry in the permission table 'cross-pte' with the | |
* object_id referring to a project id. | |
* A user with this permission will have 'approve' rights for all translation-sets within this | |
* project. Usually having approval rights for a translation-set also means that the user has | |
* approval rights for all translations, but not a Cross-Locale PTE: | |
* If a current translation exists by another user then overwriting (through UI or import) is not | |
* possible. | |
*/ | |
add_filter( 'gp_pre_can_user', function( $verdict, $args ) { | |
if ( 'cross-pte' === $args['action'] ) { | |
if ( GP::$permission->user_can( $args['user'], 'admin' ) ) { | |
// Admins shouldn't have this because it will end up restricting them. | |
return false; | |
} | |
if ( 'translation-set' === $args['object_type'] ) { | |
if ( isset( $args['extra']['set']->id ) && $args['extra']['set']->id == $args['object_id'] ) { | |
$set = $args['extra']['set']; | |
} else { | |
$set = GP::$translation_set->get( $args['object_id'] ); | |
} | |
// Allow on all translation-sets within the project. | |
if ( $set ) { | |
return GP::$permission->user_can( $args['user'], 'cross-pte', 'project', $set->project_id ); | |
} | |
} | |
} | |
if ( 'approve' === $args['action'] ) { | |
if ( 'translation' === $args['object_type'] ) { | |
if ( isset( $args['extra']['translation']->translation_set_id ) && $args['extra']['translation']->id == $args['object_id'] ) { | |
$translation = $args['extra']['translation']; | |
} else { | |
$translation = GP::$translation->get( $args['object_id'] ); | |
} | |
if ( $translation ) { | |
static $current_translation_by_user; | |
$cache_key = $args['user']->ID . '_' . $translation->original_id; | |
if ( isset( $current_translation_by_user[ $cache_key ] ) ) { | |
return $current_translation_by_user[ $cache_key ]; | |
} | |
if ( GP::$permission->user_can( $args['user'], 'cross-pte', 'translation-set', $translation->translation_set_id ) ) { | |
$current_translation = GP::$translation->find_one( array( 'translation_set_id' => $translation->translation_set_id, 'original_id' => $translation->original_id, 'status' => 'current' ) ); | |
if ( $current_translation && intval( $current_translation->user_id ) !== $args['user']->ID ) { | |
// Current translation was authored by someone else. Disallow setting to current. | |
return $current_translation_by_user[ $cache_key ] = false; | |
} | |
// No current translation exists or it was translated by me: allow. | |
return $current_translation_by_user[ $cache_key ] = true; | |
} else { | |
// Allows usage of the re-implementation below. | |
if ( GP::$permission->user_can( $args['user'], 'approve', 'translation-set', $translation->translation_set_id ) ) { | |
return true; | |
} | |
} | |
} | |
} elseif ( 'translation-set' === $args['object_type'] ) { | |
// Re-implementation of gp_route_translation_set_permissions_to_validator_permissions(). | |
if ( isset( $args['extra']['set']->id ) && $args['extra']['set']->id == $args['object_id'] ) { | |
$set = $args['extra']['set']; | |
} else { | |
$set = GP::$translation_set->get( $args['object_id'] ); | |
} | |
if ( $set ) { | |
if ( GP::$permission->user_can( $args['user'], 'cross-pte', 'project', $set->project_id ) ) { | |
return true; | |
} | |
return GP::$permission->user_can( $args['user'], 'approve', GP::$validator_permission->object_type, | |
GP::$validator_permission->object_id( $set->project_id, $set->locale, $set->slug ) ); | |
} | |
} | |
} | |
return $verdict; | |
}, 2, 2 ); | |
/* | |
* Enforce not-overwriting current translation by others while importing. | |
*/ | |
add_filter( 'gp_translation_set_import_status', function( $status, $new_translation, $old_translation ) { | |
if ( ! isset( $old_translation->translation_set_id ) ) { | |
return $status; | |
} | |
if ( 'current' !== $old_translation->status ) { | |
return $status; | |
} | |
if ( GP::$permission->current_user_can( 'cross-pte', 'translation-set', $old_translation->translation_set_id ) ) { | |
// Set to waiting if a current translation exists by another user. | |
if ( intval( $old_translation->user_id ) !== intval( get_current_user_id() ) ) { | |
return 'waiting'; | |
} | |
} | |
return $status; | |
}, 2, 3 ); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment