<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>pot Archives - Alexandros Georgiou</title>
	<atom:link href="https://www.alexgeorgiou.gr/tag/pot/feed/" rel="self" type="application/rss+xml" />
	<link>https://www.alexgeorgiou.gr/tag/pot/</link>
	<description>Balancing brackets for a living</description>
	<lastBuildDate>Wed, 20 Dec 2023 10:30:39 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	

<image>
	<url>https://www.alexgeorgiou.gr/wp-content/uploads/2021/07/cropped-alexgeorgiou-icon-32x32.png</url>
	<title>pot Archives - Alexandros Georgiou</title>
	<link>https://www.alexgeorgiou.gr/tag/pot/</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>😛 How to make pot with WordPress</title>
		<link>https://www.alexgeorgiou.gr/make-pot-wordpress/</link>
					<comments>https://www.alexgeorgiou.gr/make-pot-wordpress/#respond</comments>
		
		<dc:creator><![CDATA[alexg]]></dc:creator>
		<pubDate>Thu, 29 Mar 2018 18:08:46 +0000</pubDate>
				<category><![CDATA[Blog]]></category>
		<category><![CDATA[grunt]]></category>
		<category><![CDATA[grunt-po2mo]]></category>
		<category><![CDATA[grunt-pot]]></category>
		<category><![CDATA[grunt-wp-i18n]]></category>
		<category><![CDATA[i18n]]></category>
		<category><![CDATA[l10n]]></category>
		<category><![CDATA[plugin]]></category>
		<category><![CDATA[pot]]></category>
		<category><![CDATA[translation]]></category>
		<category><![CDATA[wordpress]]></category>
		<guid isPermaLink="false">https://www.alexgeorgiou.gr/?p=241</guid>

					<description><![CDATA[<p>Build translation files to localize a WordPress plugin using grunt. Create separate translation files for the front-end and back-end.</p>
<p>The post <a href="https://www.alexgeorgiou.gr/make-pot-wordpress/">😛 How to make pot with WordPress</a> appeared first on <a href="https://www.alexgeorgiou.gr">Alexandros Georgiou</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p><em>In this article I will detail how to use grunt to build translation files to <a href="https://developer.wordpress.org/plugins/internationalization/localization/" target="_blank" rel="noopener">localize a WordPress plugin</a>. We&#8217;ll create separate translation files for the front-end and back-end (admin area), potentially allowing a translator to translate only one or the other.</em></p>
<h2>Have you tried POT?</h2>
<p>Hopefully you&#8217;ve already used the i18n functions in your PHP code. For example, a simple translatable string would look like:</p>
<pre>$text = <a href="https://developer.wordpress.org/reference/functions/__/" target="_blank" rel="noopener">__</a>( 'Text to internationalize', 'language-domain-slug' );</pre>
<p>The purpose of this article is not to list all the relevant functions, you can look them up <a href="https://developer.wordpress.org/plugins/internationalization/how-to-internationalize-your-plugin/" target="_blank" rel="noopener">here</a>. These are all wrappers to <a href="https://www.gnu.org/software/gettext/" target="_blank" rel="noopener">gettext</a>.</p>
<p>The important thing to note is that you need to run something to generate your <em>Portable Object Template</em> files. These <code>.pot</code> files can then be copied to <em>Portable Object</em> <code>.po</code> files, then translated to <em>Machine Object</em> <code>.mo</code> files. These <code>.mo</code> binaries are finally loaded by the end user&#8217;s WordPress installation to provide the translated strings to the plugin, or theme. No surprises up to here, all of this is standard.</p>
<h2>Grow your own with Grunt!</h2>
<p>What I will present today is an easy way to use <a href="https://gruntjs.com" target="_blank" rel="noopener">grunt</a> to generate the following:</p>
<ol>
<li>Two <code>.pot</code> files, one with the front-end strings and one with the admin area strings, and</li>
<li><code>.mo</code> files for any <code>.po</code> files in your project</li>
</ol>
<p>You will still need to copy the <code>.pot</code> files to <code>.po</code> files manually and provide the translations. Let&#8217;s get started:</p>
<p>The first thing to add to our <code>Gruntfile.js</code> is <a href="https://www.npmjs.com/package/grunt-wp-i18n" target="_blank" rel="noopener">grunt-wp-i18n</a>. This is a grunt plugin that I have found to be a little more flexible than the alternative, <a href="https://www.npmjs.com/package/grunt-pot" target="_blank" rel="noopener">grunt-pot</a>. So, as usual, add this grunt plugin to your dev toolbox:</p>
<div class="highlight shell">
<pre class="line"><span class="source shell">npm install grunt-wp-i18n --save-dev</span></pre>
<div class="line">and then add the following into your Gruntfile, to get the plugin loaded:</div>
<div class="line">
<div class="highlight js">
<pre class="line"><span class="source js"><span class="variable other object js">grunt</span><span class="meta js"><span class="meta delimiter method period js">.</span><span class="entity name function js">loadNpmTasks</span><span class="punctuation definition begin round js">(</span> <span class="string quoted single js"><span class="punctuation definition string begin js">'</span>grunt-wp-i18n<span class="punctuation definition string end js">'</span></span> <span class="punctuation definition end round js">)</span></span><span class="punctuation terminator statement js">;</span></span></pre>
<div class="line">Now we need to configure this build task. We will hide our pot in our usual stash, the <code>/languages</code> directory of our WordPress plugin. I like to keep my source code in version control under <code>/src</code> and copy it over to assemble the build under <code>/build</code>. I keep any <code>.po</code> translations under <code>/src/languages</code>, and auto-generate <code>.pot</code> files into the <code>/build/languages</code> dir. Any <code>.po</code> files are simply copied from the <code>/src</code> to the <code>/build</code> directory. This is a good practice that keeps our pot always fresh!</div>
<pre class="line">makepot: {
    front: {
        options: {
            cwd: 'build',
            potFilename: 'myplugin-front.pot',
            include: [ '/path/to/files', '/more/files', '/etc' ],
            domainPath: 'languages/',
            type: 'wp-plugin'
        }
    },
    admin: {
        options: {
            cwd: 'build',
            potFilename: 'myplugin.pot',
            include: [ '.*' ],
            exclude: [ '/path/to/files', '/more/files', '/etc' ],
            domainPath: 'languages/',
            type: 'wp-plugin'
    }
}</pre>
<div class="line">Notice that in this example there are two files: The <code>myplugin-front.pot</code> file pulls strings from a list of files that make up the front-end, while the <code>myplugin.pot</code> pulls strings from every other thing in my plugin, which would be the admin area.</div>
<blockquote>
<div class="line">Now a translator is free to only translate the front-end, leaving the back-end, which may contain a lot more strings, to its default (English?) language.</div>
</blockquote>
<div class="line">In functions such as <a href="https://developer.wordpress.org/reference/functions/__/" target="_blank" rel="noopener">__()</a>, the second argument is a <em>language domain</em>. People usually set here the plugin&#8217;s slug, but this is not strictly necessary: You can use different domains for e.g. the front-end and the back-end. Here we will use <code>myplugin-front</code> for the front-end and <code>myplugin</code> for the back-end. This has to be done in the PHP code, wherever the i18n functions are used.</div>
</div>
</div>
</div>
<h2 class="line">Make pot</h2>
<div class="line">If all is set up correctly, you can now easily make pot with:</div>
<pre class="line">grunt makepot</pre>
<p class="line">This will make two files in your project, <code>/build/languages/myplugin.pot</code> and <code>/build/languages/myplugin-frontend.pot</code>. Do not commit these files, we&#8217;ll let them auto-generate every time. The <code>/build</code> directory is in my <code>.gitignore</code> list.</p>
<h2 class="line">Using pot</h2>
<div class="line">For your plugin to actually use this, you need to copy the <code>.pot</code> files into <code>.po</code> files. Depending on your language, you will have to use the correct <em>language code</em> in your filename. See the <a href="https://www.gnu.org/software/gettext/manual/gettext.html#Language-Codes" target="_blank" rel="noopener">gettext list of language codes</a> or simply the <a href="https://en.wikipedia.org/wiki/List_of_ISO_639-1_codes" target="_blank" rel="noopener">Wikipedia list of ISO 639-1 language codes</a>. For instance, to do a German translation in our example, you would need to copy the following:</div>
<pre class="line">cp build/languages/myplugin-front.pot src/languages/myplugin-front-de_DE.po
cp build/languages/myplugin.pot src/languages/myplugin-de_DE.po</pre>
<div class="line">or to do a translation to Arabic:</div>
<div class="line">
<pre class="line">cp build/languages/myplugin-front.pot src/languages/myplugin-front-ar.po
cp build/languages/myplugin.pot src/languages/myplugin-ar.po</pre>
<div class="line">You will need to check to make sure whether you need to use a <em>country code</em> along with your language code.</div>
<div class="line">Once you have your <code>.po</code> files you can load them up in <a href="https://poedit.net/" target="_blank" rel="noopener">poedit</a> and start translating. Once the translations are ready you can commit them to your source tree.</div>
<h2 class="line">Packaging it all together for shipment</h2>
<div class="line">WordPress will not use your <code>.pot</code> or <code>.po</code> files. You only include these in your plugin so as to help future translators. To actually enable translation you need to convert the <code>.po</code> files to <code>.mo</code> files.</div>
</div>
<p>We&#8217;ll use another grunt plugin, <a href="https://www.npmjs.com/package/grunt-po2mo" target="_blank" rel="noopener">grunt-po2mo</a>. First add it to your project:</p>
<div class="highlight shell">
<pre class="line"><span class="source shell">npm install grunt-po2mo --save-dev</span></pre>
</div>
<p>And add the following into your Gruntfile to load it:</p>
<div class="highlight js">
<pre class="line"><span class="source js"><span class="variable other object js">grunt</span><span class="meta js"><span class="meta delimiter method period js">.</span><span class="entity name function js">loadNpmTasks</span><span class="punctuation definition begin round js">( </span><span class="string quoted single js"><span class="punctuation definition string begin js">'</span>grunt-po2mo<span class="punctuation definition string end js">' </span></span><span class="punctuation definition end round js">)</span></span><span class="punctuation terminator statement js">;</span></span></pre>
</div>
<p>This one requires very little configuration. Add the following target into your Gruntfile:</p>
<pre>po2mo: {
    plugin: {
        cwd: 'src',
        src: 'languages/*.po',
        dest: 'build',
        expand: true
    }
},</pre>
<p>This config expects that the <code>.po</code> files are in the <code>/src/languages</code> directory where we placed them earlier. It places the <code>.mo</code> files in the <code>/build/languages</code> dir. All you need to do for this is:</p>
<pre>grunt po2mo</pre>
<p>You will also need to tell your plugin to actually go and use these <code>.mo</code> files. Easy. Just hook to the <code>plugins_loaded</code> action and load the text domains:</p>
<pre>function action_plugins_loaded() {
    load_plugin_textdomain( 'myplugin', false, dirname( plugin_basename( __FILE__ ) ) . '/languages/' );
    load_plugin_textdomain( 'myplugin-front', false, dirname( plugin_basename( __FILE__ ) ) . '/languages/' );
} // end function action_plugins_loaded

add_action( 'plugins_loaded', 'action_plugins_loaded' );</pre>
<h2>That&#8217;s it!</h2>
<p>Make sure to include the <code>makepot</code> and <code>po2mo</code> targets in your build task. Finally use <code>grunt-contrib-compress</code> or another plugin to compress your entire build directory to a <code>.zip</code> file that is ready to be installed into WordPress!</p>
<p>Pass it on.</p>
<p>&nbsp;</p>
<p>The post <a href="https://www.alexgeorgiou.gr/make-pot-wordpress/">😛 How to make pot with WordPress</a> appeared first on <a href="https://www.alexgeorgiou.gr">Alexandros Georgiou</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://www.alexgeorgiou.gr/make-pot-wordpress/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
