Skip to content

Instantly share code, notes, and snippets.

@balbuf
Last active May 10, 2016 13:40
Show Gist options
  • Save balbuf/2b4da509aed1ae32db4b to your computer and use it in GitHub Desktop.
Save balbuf/2b4da509aed1ae32db4b to your computer and use it in GitHub Desktop.
Add or update text domain of all WP i18n functions in a file
<?php
/**
* Console application, which adds textdomain argument
* to all i18n function calls
*
* Adapted from:
* http://develop.svn.wordpress.org/trunk/tools/i18n/add-textdomain.php
*
* Extended such that all text domains are replaced if found or added otherwise.
* Also, double-quoted strings are replaced by single-quoted strings.
*/
error_reporting(E_ALL);
class AddTextdomain {
var $modified_contents = '';
var $rules = array(
'_' => array('string'),
'__' => array('string'),
'_e' => array('string'),
'_c' => array('string'),
'_n' => array('singular', 'plural'),
'_n_noop' => array('singular', 'plural'),
'_nc' => array('singular', 'plural'),
'__ngettext' => array('singular', 'plural'),
'__ngettext_noop' => array('singular', 'plural'),
'_x' => array('string', 'context'),
'_ex' => array('string', 'context'),
'_nx' => array('singular', 'plural', null, 'context'),
'_nx_noop' => array('singular', 'plural', 'context'),
'_n_js' => array('singular', 'plural'),
'_nx_js' => array('singular', 'plural', 'context'),
'esc_attr__' => array('string'),
'esc_html__' => array('string'),
'esc_attr_e' => array('string'),
'esc_html_e' => array('string'),
'esc_attr_x' => array('string', 'context'),
'esc_html_x' => array('string', 'context'),
'comments_number_link' => array('string', 'singular', 'plural'),
);
function usage() {
$usage = "Usage: php add-textdomain.php [-i] <domain> <file>\n\nAdds the string <domain> as a last argument to all i18n function calls in <file>\nand prints the modified php file on standard output.\n\nOptions:\n -i Modifies the PHP file in place, instead of printing it to standard output.\n";
fwrite(STDERR, $usage);
exit(1);
}
function process_token($token_text, $inplace) {
if ($inplace)
$this->modified_contents .= $token_text;
else
echo $token_text;
}
function process_file($domain, $source_filename, $inplace) {
$this->modified_contents = '';
$domain = addslashes($domain);
$source = file_get_contents($source_filename);
$tokens = token_get_all($source);
$in_func = false;
$args_started = false;
$arg_num = 0;
$num_args = 0;
$parens_balance = 0;
$found_domain = false;
foreach($tokens as $token) {
$string_success = false;
if (is_array($token)) {
list($id, $text) = $token;
if (T_STRING == $id && isset( $this->rules[ $text ] ) ) {
$in_func = true;
$parens_balance = 0;
$args_started = false;
$found_domain = false;
// number of args the function accepts, including the domain
$num_args = count( $this->rules[ $text ] ) + 1;
} elseif ( T_CONSTANT_ENCAPSED_STRING == $id && $in_func && $args_started ) {
// is this the last arg, corresponding to the text domain arg?
if ( ++$arg_num === $num_args ) {
$found_domain = true;
// replace the domain with our domain
$text = "'$domain' ";
} else {
// unwrap double quoted strings
$text = preg_replace( '#^"(.+)"\s*#s', '$1', $text, -1, $count );
// if we did, fix the embedded escaping and rewrap with single quotes
if ( $count ) {
//escape singles, unescape doubles
$text = '\'' . str_replace( array( '\'', '\\"' ), array( '\\\'', '"' ), $text ) . '\'';
} else {
$text = rtrim( $text );
}
}
}
$token = $text;
} elseif ('(' == $token){
$args_started = true;
$arg_num = 0;
++$parens_balance;
} elseif (')' == $token) {
--$parens_balance;
if ($in_func && 0 == $parens_balance) {
$token = $found_domain? ')' : ", '$domain' )";
$in_func = false;
$args_started = false;
$found_domain = false;
$num_args = 0;
}
}
$this->process_token($token, $inplace);
}
if ($inplace) {
$f = fopen($source_filename, 'w');
fwrite($f, $this->modified_contents);
fclose($f);
}
}
}
// run the CLI only if the file
// wasn't included
$included_files = get_included_files();
if ($included_files[0] == __FILE__) {
$adddomain = new AddTextdomain;
if (!isset($argv[1]) || !isset($argv[2])) {
$adddomain->usage();
}
$inplace = false;
if ('-i' == $argv[1]) {
$inplace = true;
if (!isset($argv[3])) $adddomain->usage();
array_shift($argv);
}
$adddomain->process_file($argv[1], $argv[2], $inplace);
}
?>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment