<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[13541] sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events: Translate: Sync "Translation Events" from GitHub</title>
</head>
<body>
<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; }
#msg dl a { font-weight: bold}
#msg dl a:link { color:#fc3; }
#msg dl a:active { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { white-space: pre-line; overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta" style="font-size: 105%">
<dt style="float: left; width: 6em; font-weight: bold">Revision</dt> <dd><a style="font-weight: bold" href="http://meta.trac.wordpress.org/changeset/13541">13541</a><script type="application/ld+json">{"@context":"http://schema.org","@type":"EmailMessage","description":"Review this Commit","action":{"@type":"ViewAction","url":"http://meta.trac.wordpress.org/changeset/13541","name":"Review Commit"}}</script></dd>
<dt style="float: left; width: 6em; font-weight: bold">Author</dt> <dd>amieiro</dd>
<dt style="float: left; width: 6em; font-weight: bold">Date</dt> <dd>2024-04-16 12:41:37 +0000 (Tue, 16 Apr 2024)</dd>
</dl>
<pre style='padding-left: 1em; margin: 2em 0; border-left: 2px solid #ccc; line-height: 1.25; font-size: 105%; font-family: sans-serif'>Translate: Sync "Translation Events" from GitHub</pre>
<h3>Modified Paths</h3>
<ul>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsassetscsstranslationeventscss">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/assets/css/translation-events.css</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsautoloadphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/autoload.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesattendeeattendeerepositoryphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/attendee/attendee-repository.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludeseventeventformhandlerphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/event/event-form-handler.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludeseventeventphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/event/event.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesrouteseventdetailsphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/event/details.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesrouteseventeditphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/event/edit.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesroutesuserattendeventphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/user/attend-event.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesroutesuserhosteventphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/user/host-event.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesupgradephp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/upgrade.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventstemplateseventphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/event.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventstemplateseventsheaderphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/events-header.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventstemplateseventsmyeventsphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/events-my-events.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventswporggptranslationeventsphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/wporg-gp-translation-events.php</a></li>
</ul>
<h3>Added Paths</h3>
<ul>
<li>sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/</li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatsstatscalculatorphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-calculator.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatsstatsimporterphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-importer.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatsstatslistenerphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-listener.php</a></li>
</ul>
<h3>Removed Paths</h3>
<ul>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatscalculatorphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats-calculator.php</a></li>
<li><a href="#sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatslistenerphp">sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats-listener.php</a></li>
</ul>
</div>
<div id="patch">
<h3>Diff</h3>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsassetscsstranslationeventscss"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/assets/css/translation-events.css</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/assets/css/translation-events.css 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/assets/css/translation-events.css 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -100,7 +100,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> margin-bottom: 0;
</span><span class="cx" style="display: block; padding: 0 10px"> }
</span><span class="cx" style="display: block; padding: 0 10px">
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">-span.event-creator, span.event-you {
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+span.event-not-attending {
</ins><span class="cx" style="display: block; padding: 0 10px"> display: block;
</span><span class="cx" style="display: block; padding: 0 10px"> margin-left: 55px;
</span><span class="cx" style="display: block; padding: 0 10px"> margin-top: 1em;
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsautoloadphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/autoload.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/autoload.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/autoload.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -18,6 +18,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> require_once __DIR__ . '/includes/event/event-repository.php';
</span><span class="cx" style="display: block; padding: 0 10px"> require_once __DIR__ . '/includes/event/event-repository-cached.php';
</span><span class="cx" style="display: block; padding: 0 10px"> require_once __DIR__ . '/includes/event/event-form-handler.php';
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">-require_once __DIR__ . '/includes/stats-calculator.php';
-require_once __DIR__ . '/includes/stats-listener.php';
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+require_once __DIR__ . '/includes/stats/stats-calculator.php';
+require_once __DIR__ . '/includes/stats/stats-importer.php';
+require_once __DIR__ . '/includes/stats/stats-listener.php';
</ins><span class="cx" style="display: block; padding: 0 10px"> require_once __DIR__ . '/includes/event-text-snippet.php';
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesattendeeattendeerepositoryphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/attendee/attendee-repository.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/attendee/attendee-repository.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/attendee/attendee-repository.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -119,7 +119,9 @@
</span><span class="cx" style="display: block; padding: 0 10px"> * Get the hosts' users for an event.
</span><span class="cx" style="display: block; padding: 0 10px"> *
</span><span class="cx" style="display: block; padding: 0 10px"> * @param int $event_id The id of the event.
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- * @return array[Attendee] The hosts of the event.
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ *
+ * @return Attendee[] The hosts of the event.
+ * @throws Exception
</ins><span class="cx" style="display: block; padding: 0 10px"> */
</span><span class="cx" style="display: block; padding: 0 10px"> public function get_hosts( int $event_id ): array {
</span><span class="cx" style="display: block; padding: 0 10px"> global $wpdb, $gp_table_prefix;
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -127,10 +129,10 @@
</span><span class="cx" style="display: block; padding: 0 10px"> // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
</span><span class="cx" style="display: block; padding: 0 10px"> // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
</span><span class="cx" style="display: block; padding: 0 10px"> // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- $host_ids = $wpdb->get_col(
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ $rows = $wpdb->get_results(
</ins><span class="cx" style="display: block; padding: 0 10px"> $wpdb->prepare(
</span><span class="cx" style="display: block; padding: 0 10px"> "
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- select user_id
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ select event_id, user_id
</ins><span class="cx" style="display: block; padding: 0 10px"> from {$gp_table_prefix}event_attendees
</span><span class="cx" style="display: block; padding: 0 10px"> where event_id = %d and is_host = 1
</span><span class="cx" style="display: block; padding: 0 10px"> ",
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -142,8 +144,10 @@
</span><span class="cx" style="display: block; padding: 0 10px"> // phpcs:enable
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> $hosts = array();
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- foreach ( $host_ids as $host_id ) {
- $hosts[] = $this->get_attendee( $event_id, $host_id );
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ foreach ( $rows as $row ) {
+ $host = new Attendee( $row->event_id, $row->user_id );
+ $host->mark_as_host();
+ $hosts[] = $host;
</ins><span class="cx" style="display: block; padding: 0 10px"> }
</span><span class="cx" style="display: block; padding: 0 10px"> return $hosts;
</span><span class="cx" style="display: block; padding: 0 10px"> }
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludeseventeventformhandlerphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/event/event-form-handler.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/event/event-form-handler.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/event/event-form-handler.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -9,7 +9,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> use WP_Error;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Attendee\Attendee;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Attendee\Attendee_Repository;
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">-use Wporg\TranslationEvents\Stats_Calculator;
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use Wporg\TranslationEvents\Stats\Stats_Calculator;
</ins><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> class Event_Form_Handler {
</span><span class="cx" style="display: block; padding: 0 10px"> private Event_Repository_Interface $event_repository;
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludeseventeventphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/event/event.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/event/event.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/event/event.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -2,6 +2,7 @@
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> namespace Wporg\TranslationEvents\Event;
</span><span class="cx" style="display: block; padding: 0 10px">
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use DateTimeImmutable;
</ins><span class="cx" style="display: block; padding: 0 10px"> use DateTimeZone;
</span><span class="cx" style="display: block; padding: 0 10px"> use Exception;
</span><span class="cx" style="display: block; padding: 0 10px"> use Throwable;
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -86,6 +87,15 @@
</span><span class="cx" style="display: block; padding: 0 10px"> return $this->end;
</span><span class="cx" style="display: block; padding: 0 10px"> }
</span><span class="cx" style="display: block; padding: 0 10px">
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ public function is_active(): bool {
+ $now = new DateTimeImmutable( 'now', new DateTimeZone( 'UTC' ) );
+ return $now >= $this->start->utc() && $now < $this->end->utc();
+ }
+
+ public function is_past(): bool {
+ return $this->end->is_in_the_past();
+ }
+
</ins><span class="cx" style="display: block; padding: 0 10px"> public function timezone(): DateTimeZone {
</span><span class="cx" style="display: block; padding: 0 10px"> return $this->timezone;
</span><span class="cx" style="display: block; padding: 0 10px"> }
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesrouteseventdetailsphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/event/details.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/event/details.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/event/details.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -8,7 +8,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Attendee\Attendee_Repository;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event_Repository_Interface;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Routes\Route;
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">-use Wporg\TranslationEvents\Stats_Calculator;
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use Wporg\TranslationEvents\Stats\Stats_Calculator;
</ins><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Translation_Events;
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> /**
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesrouteseventeditphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/event/edit.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/event/edit.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/event/edit.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -6,7 +6,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Attendee\Attendee_Repository;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event_Repository_Interface;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Routes\Route;
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">-use Wporg\TranslationEvents\Stats_Calculator;
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use Wporg\TranslationEvents\Stats\Stats_Calculator;
</ins><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Translation_Events;
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> /**
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesroutesuserattendeventphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/user/attend-event.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/user/attend-event.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/user/attend-event.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -6,6 +6,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Attendee\Attendee_Repository;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event_Repository_Interface;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Routes\Route;
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use Wporg\TranslationEvents\Stats\Stats_Importer;
</ins><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Translation_Events;
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> /**
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -12,15 +13,20 @@
</span><span class="cx" style="display: block; padding: 0 10px"> * Toggle whether the current user is attending an event.
</span><span class="cx" style="display: block; padding: 0 10px"> * If the user is not currently marked as attending, they will be marked as attending.
</span><span class="cx" style="display: block; padding: 0 10px"> * If the user is currently marked as attending, they will be marked as not attending.
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ *
+ * If the user is marked as attending, and the event is active at that moment, stats for the translations the user
+ * created since the event started are imported.
</ins><span class="cx" style="display: block; padding: 0 10px"> */
</span><span class="cx" style="display: block; padding: 0 10px"> class Attend_Event_Route extends Route {
</span><span class="cx" style="display: block; padding: 0 10px"> private Event_Repository_Interface $event_repository;
</span><span class="cx" style="display: block; padding: 0 10px"> private Attendee_Repository $attendee_repository;
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ private Stats_Importer $stats_importer;
</ins><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> public function __construct() {
</span><span class="cx" style="display: block; padding: 0 10px"> parent::__construct();
</span><span class="cx" style="display: block; padding: 0 10px"> $this->event_repository = Translation_Events::get_event_repository();
</span><span class="cx" style="display: block; padding: 0 10px"> $this->attendee_repository = Translation_Events::get_attendee_repository();
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ $this->stats_importer = new Stats_Importer();
</ins><span class="cx" style="display: block; padding: 0 10px"> }
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> public function handle( int $event_id ): void {
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -28,6 +34,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> if ( ! $user ) {
</span><span class="cx" style="display: block; padding: 0 10px"> $this->die_with_error( esc_html__( 'Only logged-in users can attend events', 'gp-translation-events' ), 403 );
</span><span class="cx" style="display: block; padding: 0 10px"> }
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ $user_id = $user->ID;
</ins><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> $event = $this->event_repository->get_event( $event_id );
</span><span class="cx" style="display: block; padding: 0 10px"> if ( ! $event ) {
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -34,15 +41,22 @@
</span><span class="cx" style="display: block; padding: 0 10px"> $this->die_with_404();
</span><span class="cx" style="display: block; padding: 0 10px"> }
</span><span class="cx" style="display: block; padding: 0 10px">
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- $attendee = $this->attendee_repository->get_attendee( $event->id(), $user->ID );
- if ( $attendee instanceof Attendee && $attendee->is_host() && ( 1 === count( $this->attendee_repository->get_hosts( $event_id ) ) ) ) {
- $this->die_with_error( esc_html__( 'The event needs a host. Add a new host before stopping to attend the event.', 'gp-translation-events' ), 403 );
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ if ( $event->is_past() ) {
+ $this->die_with_error( esc_html__( 'Cannot attend or un-attend a past event', 'gp-translation-events' ), 403 );
</ins><span class="cx" style="display: block; padding: 0 10px"> }
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+
+ $attendee = $this->attendee_repository->get_attendee( $event->id(), $user_id );
</ins><span class="cx" style="display: block; padding: 0 10px"> if ( $attendee instanceof Attendee ) {
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- $this->attendee_repository->remove_attendee( $event->id(), $user->ID );
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ $this->attendee_repository->remove_attendee( $event->id(), $user_id );
</ins><span class="cx" style="display: block; padding: 0 10px"> } else {
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- $attendee = new Attendee( $event->id(), $user->ID );
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ $attendee = new Attendee( $event->id(), $user_id );
</ins><span class="cx" style="display: block; padding: 0 10px"> $this->attendee_repository->insert_attendee( $attendee );
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+
+ // If the event is active right now,
+ // import stats for translations the user created since the event started.
+ if ( $event->is_active() ) {
+ $this->stats_importer->import_for_user_and_event( $user_id, $event );
+ }
</ins><span class="cx" style="display: block; padding: 0 10px"> }
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> wp_safe_redirect( gp_url( "/events/{$event->slug()}" ) );
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesroutesuserhosteventphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/user/host-event.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/user/host-event.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/routes/user/host-event.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -50,9 +50,6 @@
</span><span class="cx" style="display: block; padding: 0 10px"> }
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> $affected_attendee = $this->attendee_repository->get_attendee( $event_id, $user_id );
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- if ( $affected_attendee instanceof Attendee && $affected_attendee->is_host() && ( 1 === count( $this->attendee_repository->get_hosts( $event_id ) ) ) ) {
- $this->die_with_error( esc_html__( 'The event needs a host. Add a new host before stopping to attend the event.', 'gp-translation-events' ), 403 );
- }
</del><span class="cx" style="display: block; padding: 0 10px"> // The user is attending to the event, so if I don't find the attendee, I won't create it.
</span><span class="cx" style="display: block; padding: 0 10px"> if ( $affected_attendee instanceof Attendee ) {
</span><span class="cx" style="display: block; padding: 0 10px"> if ( $affected_attendee->is_host() ) {
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatsstatscalculatorphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-calculator.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-calculator.php (rev 0)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-calculator.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,339 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<?php
+
+namespace Wporg\TranslationEvents\Stats;
+
+use Exception;
+use WP_Post;
+use WP_User;
+use GP;
+use GP_Locale;
+use GP_Locales;
+use DateTimeImmutable;
+use DateTimeZone;
+
+class Stats_Row {
+ public int $created;
+ public int $reviewed;
+ public int $users;
+ public ?GP_Locale $language = null;
+
+ public function __construct( $created, $reviewed, $users, ?GP_Locale $language = null ) {
+ $this->created = $created;
+ $this->reviewed = $reviewed;
+ $this->users = $users;
+ $this->language = $language;
+ }
+}
+
+class Event_Stats {
+ /**
+ * Associative array of rows, with the locale as key.
+ *
+ * @var Stats_Row[]
+ */
+ private array $rows = array();
+
+ private Stats_Row $totals;
+
+ /**
+ * Add a stats row.
+ *
+ * @throws Exception When incorrect locale is passed.
+ */
+ public function add_row( string $locale, Stats_Row $row ) {
+ if ( ! $locale ) {
+ throw new Exception( 'locale must not be empty' );
+ }
+ $this->rows[ $locale ] = $row;
+ }
+
+ public function set_totals( Stats_Row $totals ) {
+ $this->totals = $totals;
+ }
+
+ /**
+ * Get an associative array of rows, with the locale as key.
+ *
+ * @return Stats_Row[]
+ */
+ public function rows(): array {
+ uasort(
+ $this->rows,
+ function ( $a, $b ) {
+ if ( ! $a->language && ! $b->language ) {
+ return 0;
+ }
+ if ( ! $a->language ) {
+ return -1;
+ }
+ if ( ! $b->language ) {
+ return 1;
+ }
+
+ return strcasecmp( $a->language->english_name, $b->language->english_name );
+ }
+ );
+
+ return $this->rows;
+ }
+
+ public function totals(): Stats_Row {
+ return $this->totals;
+ }
+}
+
+class Stats_Calculator {
+ /**
+ * Get stats for an event.
+ *
+ * @throws Exception When stats calculation failed.
+ */
+ public function for_event( int $event_id ): Event_Stats {
+ $stats = new Event_Stats();
+ global $wpdb, $gp_table_prefix;
+
+ // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
+ // phpcs thinks we're doing a schema change but we aren't.
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.SchemaChange
+ $rows = $wpdb->get_results(
+ $wpdb->prepare(
+ "
+ select locale,
+ sum(action = 'create') as created,
+ count(*) as total,
+ count(distinct user_id) as users
+ from {$gp_table_prefix}event_actions
+ where event_id = %d
+ group by locale with rollup
+ ",
+ array(
+ $event_id,
+ )
+ )
+ );
+ // phpcs:enable
+
+ foreach ( $rows as $index => $row ) {
+ $is_totals = null === $row->locale;
+ if ( $is_totals && array_key_last( $rows ) !== $index ) {
+ // If this is not the last row, something is wrong in the data in the database table
+ // or there's a bug in the query above.
+ throw new Exception(
+ 'Only the last row should have no locale but we found a non-last row with no locale.'
+ );
+ }
+
+ $lang = GP_Locales::by_slug( $row->locale );
+ if ( ! $lang ) {
+ $lang = null;
+ }
+
+ $stats_row = new Stats_Row(
+ $row->created,
+ $row->total - $row->created,
+ $row->users,
+ $lang
+ );
+
+ if ( ! $is_totals ) {
+ $stats->add_row( $row->locale, $stats_row );
+ } else {
+ $stats->set_totals( $stats_row );
+ }
+ }
+
+ return $stats;
+ }
+
+ /**
+ * Get contributors for an event.
+ */
+ public function get_contributors( int $event_id ): array {
+ global $wpdb, $gp_table_prefix;
+
+ // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
+ // phpcs thinks we're doing a schema change but we aren't.
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.SchemaChange
+ $rows = $wpdb->get_results(
+ $wpdb->prepare(
+ "
+ select user_id, group_concat( distinct locale ) as locales
+ from {$gp_table_prefix}event_actions
+ where event_id = %d
+ group by user_id
+ ",
+ array(
+ $event_id,
+ )
+ )
+ );
+ // phpcs:enable
+
+ $users = array();
+ foreach ( $rows as $row ) {
+ $user = new WP_User( $row->user_id );
+ $user->locales = explode( ',', $row->locales );
+ $users[] = $user;
+ }
+
+ uasort(
+ $users,
+ function ( $a, $b ) {
+ return strcasecmp( $a->display_name, $b->display_name );
+ }
+ );
+
+ return $users;
+ }
+
+ /**
+ * Get attendees without contributions for an event.
+ */
+ public function get_attendees_not_contributing( int $event_id ): array {
+ global $wpdb, $gp_table_prefix;
+
+ // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
+ $all_attendees_ids = $wpdb->get_col(
+ $wpdb->prepare(
+ "
+ select distinct user_id
+ from {$gp_table_prefix}event_attendees
+ where event_id = %d
+ ",
+ array(
+ $event_id,
+ )
+ ),
+ );
+
+ $contributing_ids = $wpdb->get_col(
+ $wpdb->prepare(
+ "
+ select distinct user_id
+ from {$gp_table_prefix}event_actions
+ where event_id = %d
+ ",
+ array(
+ $event_id,
+ )
+ )
+ );
+
+ $attendees_not_contributing_ids = array_diff( $all_attendees_ids, $contributing_ids );
+
+ $attendees_not_contributing = array();
+ foreach ( $attendees_not_contributing_ids as $user_id ) {
+ $attendees_not_contributing[] = new WP_User( $user_id );
+ }
+
+ return $attendees_not_contributing;
+ }
+
+ /**
+ * Get projects for an event.
+ */
+ public function get_projects( int $event_id ): array {
+ global $wpdb, $gp_table_prefix;
+
+ // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
+ // phpcs thinks we're doing a schema change but we aren't.
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.SchemaChange
+ $rows = $wpdb->get_results(
+ $wpdb->prepare(
+ "
+ select
+ o.project_id as project,
+ group_concat( distinct e.locale ) as locales,
+ sum(action = 'create') as created,
+ count(*) as total,
+ count(distinct user_id) as users
+ from {$gp_table_prefix}event_actions e, {$gp_table_prefix}originals o
+ where e.event_id = %d and e.original_id = o.id
+ group by o.project_id
+ ",
+ array(
+ $event_id,
+ )
+ )
+ );
+ // phpcs:enable
+
+ $projects = array();
+ foreach ( $rows as $row ) {
+ $row->project = GP::$project->get( $row->project );
+ $project_name = $row->project->name;
+ $parent_project_id = $row->project->parent_project_id;
+ while ( $parent_project_id ) {
+ $parent_project = GP::$project->get( $parent_project_id );
+ $parent_project_id = $parent_project->parent_project_id;
+ $project_name = substr( htmlspecialchars_decode( $parent_project->name ), 0, 35 ) . ' - ' . $project_name;
+ }
+ $projects[ $project_name ] = $row;
+ }
+
+ ksort( $projects );
+
+ return $projects;
+ }
+
+ /**
+ * Check if an event has stats.
+ *
+ * @param int $event_id The id of the event to check.
+ *
+ * @return bool True if the event has stats, false otherwise.
+ */
+ public function event_has_stats( int $event_id ): bool {
+ try {
+ $stats = $this->for_event( $event_id );
+ } catch ( Exception $e ) {
+ return false;
+ }
+
+ return ! empty( $stats->rows() );
+ }
+
+ /**
+ * Check if a user is a first time contributor.
+ *
+ * @param Event_Start_Date $event_start The event start date.
+ * @param int $user_id The user ID.
+ *
+ * @return bool True if the user is a first time contributor, false otherwise.
+ */
+ public function is_first_time_contributor( $event_start, $user_id ) {
+ global $wpdb, $gp_table_prefix;
+
+ // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.SchemaChange
+ $users_first_translation_date = $wpdb->get_var(
+ $wpdb->prepare(
+ "
+ select min(date_added) from {$gp_table_prefix}translations where user_id = %d
+ ",
+ array(
+ $user_id,
+ )
+ )
+ );
+
+ if ( get_userdata( $user_id ) && ! $users_first_translation_date ) {
+ return true;
+ }
+ $event_start_date_time = new DateTimeImmutable( $event_start->__toString(), new DateTimeZone( 'UTC' ) );
+ $first_translation_date = new DateTimeImmutable( $users_first_translation_date, new DateTimeZone( 'UTC' ) );
+ // A first time contributor is someone whose first translation was made not earlier than 24 hours before the event.
+ $event_start_date_time = $event_start_date_time->modify( '-1 day' );
+ return $event_start_date_time <= $first_translation_date;
+ }
+}
</ins><span class="cx" style="display: block; padding: 0 10px">Property changes on: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-calculator.php
</span><span class="cx" style="display: block; padding: 0 10px">___________________________________________________________________
</span></span></pre></div>
<a id="svneolstyle"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: svn:eol-style</h4></div>
<ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+native
</ins><span class="cx" style="display: block; padding: 0 10px">\ No newline at end of property
</span><a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatsstatsimporterphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-importer.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-importer.php (rev 0)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-importer.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,41 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<?php
+
+namespace Wporg\TranslationEvents\Stats;
+
+use Wporg\TranslationEvents\Event\Event;
+
+class Stats_Importer {
+ /**
+ * Imports the contributions a user made while a given event was active.
+ */
+ public function import_for_user_and_event( int $user_id, Event $event ): void {
+ global $wpdb, $gp_table_prefix;
+
+ // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
+ $wpdb->query(
+ $wpdb->prepare(
+ "
+ insert ignore into {$gp_table_prefix}event_actions
+ (event_id, user_id, original_id, locale, action, happened_at)
+ select %d, t.user_id, t.original_id, ts.locale, %s, t.date_added
+ from {$gp_table_prefix}translations t,
+ {$gp_table_prefix}translation_sets ts
+ where t.user_id = %d
+ and t.translation_set_id = ts.id
+ and t.status in ( 'current', 'waiting', 'changesrequested', 'fuzzy' )
+ and date_added between %s and %s
+ ",
+ array(
+ 'event_id' => $event->id(),
+ 'action' => Stats_Listener::ACTION_CREATE,
+ 'user_id' => $user_id,
+ 'date_added_after' => $event->start()->utc()->format( 'Y-m-d H:i:s' ),
+ 'date_added_before' => $event->end()->utc()->format( 'Y-m-d H:i:s' ),
+ ),
+ ),
+ );
+ // phpcs:enable
+ }
+}
</ins><span class="cx" style="display: block; padding: 0 10px">Property changes on: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-importer.php
</span><span class="cx" style="display: block; padding: 0 10px">___________________________________________________________________
</span></span></pre></div>
<a id="svneolstyle"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: svn:eol-style</h4></div>
<ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+native
</ins><span class="cx" style="display: block; padding: 0 10px">\ No newline at end of property
</span><a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatsstatslistenerphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-listener.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-listener.php (rev 0)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-listener.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,136 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<?php
+
+namespace Wporg\TranslationEvents\Stats;
+
+use DateTimeImmutable;
+use DateTimeZone;
+use Exception;
+use GP_Translation;
+use GP_Translation_Set;
+use Wporg\TranslationEvents\Attendee\Attendee_Repository;
+use Wporg\TranslationEvents\Event\Event;
+use Wporg\TranslationEvents\Event\Event_Repository_Interface;
+
+class Stats_Listener {
+ const ACTION_CREATE = 'create';
+ const ACTION_APPROVE = 'approve';
+ const ACTION_REJECT = 'reject';
+ const ACTION_REQUEST_CHANGES = 'request_changes';
+
+ private Attendee_Repository $attendee_repository;
+ private Event_Repository_Interface $event_repository;
+
+ public function __construct(
+ Event_Repository_Interface $event_repository,
+ Attendee_Repository $attendee_repository
+ ) {
+ $this->event_repository = $event_repository;
+ $this->attendee_repository = $attendee_repository;
+ }
+
+ public function start(): void {
+ add_action(
+ 'gp_translation_created',
+ function ( $translation ) {
+ $happened_at = DateTimeImmutable::createFromFormat( 'Y-m-d H:i:s', $translation->date_added, new DateTimeZone( 'UTC' ) );
+ if ( ! $translation->user_id ) {
+ return;
+ }
+ $this->handle_action( $translation, $translation->user_id, self::ACTION_CREATE, $happened_at );
+ },
+ );
+
+ add_action(
+ 'gp_translation_saved',
+ function ( $translation, $translation_before ) {
+ $user_id = $translation->user_id_last_modified;
+ $status = $translation->status;
+ $happened_at = DateTimeImmutable::createFromFormat( 'Y-m-d H:i:s', $translation->date_modified, new DateTimeZone( 'UTC' ) );
+
+ if ( $translation_before->status === $status ) {
+ // Translation hasn't changed status, so there's nothing for us to track.
+ return;
+ }
+
+ $action = null;
+ switch ( $status ) {
+ case 'current':
+ $action = self::ACTION_APPROVE;
+ break;
+ case 'rejected':
+ $action = self::ACTION_REJECT;
+ break;
+ case 'changesrequested':
+ $action = self::ACTION_REQUEST_CHANGES;
+ break;
+ }
+
+ if ( $action && $user_id ) {
+ $this->handle_action( $translation, $user_id, $action, $happened_at );
+ }
+ },
+ 10,
+ 2,
+ );
+ }
+
+ private function handle_action( GP_Translation $translation, int $user_id, string $action, DateTimeImmutable $happened_at ): void {
+ try {
+ // Get events that are active when the action happened, for which the user is registered for.
+ $active_events = $this->event_repository->get_current_events();
+ $events = $this->select_events_user_is_registered_for( $active_events->events, $user_id );
+
+ // phpcs:ignore Generic.Commenting.DocComment.MissingShort
+ /** @var GP_Translation_Set $translation_set Translation set */
+ $translation_set = ( new GP_Translation_Set() )->find_one( array( 'id' => $translation->translation_set_id ) );
+ global $wpdb, $gp_table_prefix;
+
+ foreach ( $events as $event ) {
+ // A given user can only do one action on a specific translation.
+ // So we insert ignore, which will keep only the first action.
+ // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
+ // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
+ $wpdb->query(
+ $wpdb->prepare(
+ "insert ignore into {$gp_table_prefix}event_actions (event_id, locale, user_id, original_id, action, happened_at) values (%d, %s, %d, %d, %s, %s)",
+ array(
+ // Start unique key.
+ 'event_id' => $event->id(),
+ 'locale' => $translation_set->locale,
+ 'user_id' => $user_id,
+ 'original_id' => $translation->original_id,
+ // End unique key.
+ 'action' => $action,
+ 'happened_at' => $happened_at->format( 'Y-m-d H:i:s' ),
+ ),
+ ),
+ );
+ // phpcs:enable
+ }
+ } catch ( Exception $exception ) {
+ // phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_error_log
+ error_log( $exception );
+ }
+ }
+
+ /**
+ * Filter an array of events so that it only includes events the given user is attending.
+ *
+ * @param Event[] $events Events.
+ *
+ * @return Event[]
+ */
+ // phpcs:disable Generic.CodeAnalysis.UnusedFunctionParameter.FoundAfterLastUsed
+ // phpcs:disable Generic.CodeAnalysis.UnusedFunctionParameter.Found
+ private function select_events_user_is_registered_for( array $events, int $user_id ): array {
+ $attending_event_ids = $this->attendee_repository->get_events_for_user( $user_id );
+ return array_filter(
+ $events,
+ function ( Event $event ) use ( $attending_event_ids ) {
+ return in_array( $event->id(), $attending_event_ids, true );
+ }
+ );
+ }
+ // phpcs:enable
+}
</ins><span class="cx" style="display: block; padding: 0 10px">Property changes on: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats/stats-listener.php
</span><span class="cx" style="display: block; padding: 0 10px">___________________________________________________________________
</span></span></pre></div>
<a id="svneolstyle"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: svn:eol-style</h4></div>
<ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+native
</ins><span class="cx" style="display: block; padding: 0 10px">\ No newline at end of property
</span><a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatscalculatorphp"></a>
<div class="delfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Deleted: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats-calculator.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats-calculator.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats-calculator.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -1,339 +0,0 @@
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">-<?php
-
-namespace Wporg\TranslationEvents;
-
-use Exception;
-use WP_Post;
-use WP_User;
-use GP;
-use GP_Locale;
-use GP_Locales;
-use DateTimeImmutable;
-use DateTimeZone;
-
-class Stats_Row {
- public int $created;
- public int $reviewed;
- public int $users;
- public ?GP_Locale $language = null;
-
- public function __construct( $created, $reviewed, $users, ?GP_Locale $language = null ) {
- $this->created = $created;
- $this->reviewed = $reviewed;
- $this->users = $users;
- $this->language = $language;
- }
-}
-
-class Event_Stats {
- /**
- * Associative array of rows, with the locale as key.
- *
- * @var Stats_Row[]
- */
- private array $rows = array();
-
- private Stats_Row $totals;
-
- /**
- * Add a stats row.
- *
- * @throws Exception When incorrect locale is passed.
- */
- public function add_row( string $locale, Stats_Row $row ) {
- if ( ! $locale ) {
- throw new Exception( 'locale must not be empty' );
- }
- $this->rows[ $locale ] = $row;
- }
-
- public function set_totals( Stats_Row $totals ) {
- $this->totals = $totals;
- }
-
- /**
- * Get an associative array of rows, with the locale as key.
- *
- * @return Stats_Row[]
- */
- public function rows(): array {
- uasort(
- $this->rows,
- function ( $a, $b ) {
- if ( ! $a->language && ! $b->language ) {
- return 0;
- }
- if ( ! $a->language ) {
- return -1;
- }
- if ( ! $b->language ) {
- return 1;
- }
-
- return strcasecmp( $a->language->english_name, $b->language->english_name );
- }
- );
-
- return $this->rows;
- }
-
- public function totals(): Stats_Row {
- return $this->totals;
- }
-}
-
-class Stats_Calculator {
- /**
- * Get stats for an event.
- *
- * @throws Exception When stats calculation failed.
- */
- public function for_event( int $event_id ): Event_Stats {
- $stats = new Event_Stats();
- global $wpdb, $gp_table_prefix;
-
- // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
- // phpcs thinks we're doing a schema change but we aren't.
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.SchemaChange
- $rows = $wpdb->get_results(
- $wpdb->prepare(
- "
- select locale,
- sum(action = 'create') as created,
- count(*) as total,
- count(distinct user_id) as users
- from {$gp_table_prefix}event_actions
- where event_id = %d
- group by locale with rollup
- ",
- array(
- $event_id,
- )
- )
- );
- // phpcs:enable
-
- foreach ( $rows as $index => $row ) {
- $is_totals = null === $row->locale;
- if ( $is_totals && array_key_last( $rows ) !== $index ) {
- // If this is not the last row, something is wrong in the data in the database table
- // or there's a bug in the query above.
- throw new Exception(
- 'Only the last row should have no locale but we found a non-last row with no locale.'
- );
- }
-
- $lang = GP_Locales::by_slug( $row->locale );
- if ( ! $lang ) {
- $lang = null;
- }
-
- $stats_row = new Stats_Row(
- $row->created,
- $row->total - $row->created,
- $row->users,
- $lang
- );
-
- if ( ! $is_totals ) {
- $stats->add_row( $row->locale, $stats_row );
- } else {
- $stats->set_totals( $stats_row );
- }
- }
-
- return $stats;
- }
-
- /**
- * Get contributors for an event.
- */
- public function get_contributors( int $event_id ): array {
- global $wpdb, $gp_table_prefix;
-
- // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
- // phpcs thinks we're doing a schema change but we aren't.
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.SchemaChange
- $rows = $wpdb->get_results(
- $wpdb->prepare(
- "
- select user_id, group_concat( distinct locale ) as locales
- from {$gp_table_prefix}event_actions
- where event_id = %d
- group by user_id
- ",
- array(
- $event_id,
- )
- )
- );
- // phpcs:enable
-
- $users = array();
- foreach ( $rows as $row ) {
- $user = new WP_User( $row->user_id );
- $user->locales = explode( ',', $row->locales );
- $users[] = $user;
- }
-
- uasort(
- $users,
- function ( $a, $b ) {
- return strcasecmp( $a->display_name, $b->display_name );
- }
- );
-
- return $users;
- }
-
- /**
- * Get attendees without contributions for an event.
- */
- public function get_attendees_not_contributing( int $event_id ): array {
- global $wpdb, $gp_table_prefix;
-
- // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
- $all_attendees_ids = $wpdb->get_col(
- $wpdb->prepare(
- "
- select distinct user_id
- from {$gp_table_prefix}event_attendees
- where event_id = %d
- ",
- array(
- $event_id,
- )
- ),
- );
-
- $contributing_ids = $wpdb->get_col(
- $wpdb->prepare(
- "
- select distinct user_id
- from {$gp_table_prefix}event_actions
- where event_id = %d
- ",
- array(
- $event_id,
- )
- )
- );
-
- $attendees_not_contributing_ids = array_diff( $all_attendees_ids, $contributing_ids );
-
- $attendees_not_contributing = array();
- foreach ( $attendees_not_contributing_ids as $user_id ) {
- $attendees_not_contributing[] = new WP_User( $user_id );
- }
-
- return $attendees_not_contributing;
- }
-
- /**
- * Get projects for an event.
- */
- public function get_projects( int $event_id ): array {
- global $wpdb, $gp_table_prefix;
-
- // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
- // phpcs thinks we're doing a schema change but we aren't.
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.SchemaChange
- $rows = $wpdb->get_results(
- $wpdb->prepare(
- "
- select
- o.project_id as project,
- group_concat( distinct e.locale ) as locales,
- sum(action = 'create') as created,
- count(*) as total,
- count(distinct user_id) as users
- from {$gp_table_prefix}event_actions e, {$gp_table_prefix}originals o
- where e.event_id = %d and e.original_id = o.id
- group by o.project_id
- ",
- array(
- $event_id,
- )
- )
- );
- // phpcs:enable
-
- $projects = array();
- foreach ( $rows as $row ) {
- $row->project = GP::$project->get( $row->project );
- $project_name = $row->project->name;
- $parent_project_id = $row->project->parent_project_id;
- while ( $parent_project_id ) {
- $parent_project = GP::$project->get( $parent_project_id );
- $parent_project_id = $parent_project->parent_project_id;
- $project_name = substr( htmlspecialchars_decode( $parent_project->name ), 0, 35 ) . ' - ' . $project_name;
- }
- $projects[ $project_name ] = $row;
- }
-
- ksort( $projects );
-
- return $projects;
- }
-
- /**
- * Check if an event has stats.
- *
- * @param int $event_id The id of the event to check.
- *
- * @return bool True if the event has stats, false otherwise.
- */
- public function event_has_stats( int $event_id ): bool {
- try {
- $stats = $this->for_event( $event_id );
- } catch ( Exception $e ) {
- return false;
- }
-
- return ! empty( $stats->rows() );
- }
-
- /**
- * Check if a user is a first time contributor.
- *
- * @param Event_Start_Date $event_start The event start date.
- * @param int $user_id The user ID.
- *
- * @return bool True if the user is a first time contributor, false otherwise.
- */
- public function is_first_time_contributor( $event_start, $user_id ) {
- global $wpdb, $gp_table_prefix;
-
- // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.SchemaChange
- $users_first_translation_date = $wpdb->get_var(
- $wpdb->prepare(
- "
- select min(date_added) from {$gp_table_prefix}translations where user_id = %d
- ",
- array(
- $user_id,
- )
- )
- );
-
- if ( get_userdata( $user_id ) && ! $users_first_translation_date ) {
- return true;
- }
- $event_start_date_time = new DateTimeImmutable( $event_start->__toString(), new DateTimeZone( 'UTC' ) );
- $first_translation_date = new DateTimeImmutable( $users_first_translation_date, new DateTimeZone( 'UTC' ) );
- // A first time contributor is someone whose first translation was made not earlier than 24 hours before the event.
- $event_start_date_time = $event_start_date_time->modify( '-1 day' );
- return $event_start_date_time <= $first_translation_date;
- }
-}
</del></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesstatslistenerphp"></a>
<div class="delfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Deleted: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats-listener.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats-listener.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/stats-listener.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -1,136 +0,0 @@
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">-<?php
-
-namespace Wporg\TranslationEvents;
-
-use DateTimeImmutable;
-use DateTimeZone;
-use Exception;
-use GP_Translation;
-use GP_Translation_Set;
-use Wporg\TranslationEvents\Attendee\Attendee_Repository;
-use Wporg\TranslationEvents\Event\Event;
-use Wporg\TranslationEvents\Event\Event_Repository_Interface;
-
-class Stats_Listener {
- const ACTION_CREATE = 'create';
- const ACTION_APPROVE = 'approve';
- const ACTION_REJECT = 'reject';
- const ACTION_REQUEST_CHANGES = 'request_changes';
-
- private Attendee_Repository $attendee_repository;
- private Event_Repository_Interface $event_repository;
-
- public function __construct(
- Event_Repository_Interface $event_repository,
- Attendee_Repository $attendee_repository
- ) {
- $this->event_repository = $event_repository;
- $this->attendee_repository = $attendee_repository;
- }
-
- public function start(): void {
- add_action(
- 'gp_translation_created',
- function ( $translation ) {
- $happened_at = DateTimeImmutable::createFromFormat( 'Y-m-d H:i:s', $translation->date_added, new DateTimeZone( 'UTC' ) );
- if ( ! $translation->user_id ) {
- return;
- }
- $this->handle_action( $translation, $translation->user_id, self::ACTION_CREATE, $happened_at );
- },
- );
-
- add_action(
- 'gp_translation_saved',
- function ( $translation, $translation_before ) {
- $user_id = $translation->user_id_last_modified;
- $status = $translation->status;
- $happened_at = DateTimeImmutable::createFromFormat( 'Y-m-d H:i:s', $translation->date_modified, new DateTimeZone( 'UTC' ) );
-
- if ( $translation_before->status === $status ) {
- // Translation hasn't changed status, so there's nothing for us to track.
- return;
- }
-
- $action = null;
- switch ( $status ) {
- case 'current':
- $action = self::ACTION_APPROVE;
- break;
- case 'rejected':
- $action = self::ACTION_REJECT;
- break;
- case 'changesrequested':
- $action = self::ACTION_REQUEST_CHANGES;
- break;
- }
-
- if ( $action && $user_id ) {
- $this->handle_action( $translation, $user_id, $action, $happened_at );
- }
- },
- 10,
- 2,
- );
- }
-
- private function handle_action( GP_Translation $translation, int $user_id, string $action, DateTimeImmutable $happened_at ): void {
- try {
- // Get events that are active when the action happened, for which the user is registered for.
- $active_events = $this->event_repository->get_current_events();
- $events = $this->select_events_user_is_registered_for( $active_events->events, $user_id );
-
- // phpcs:ignore Generic.Commenting.DocComment.MissingShort
- /** @var GP_Translation_Set $translation_set Translation set */
- $translation_set = ( new GP_Translation_Set() )->find_one( array( 'id' => $translation->translation_set_id ) );
- global $wpdb, $gp_table_prefix;
-
- foreach ( $events as $event ) {
- // A given user can only do one action on a specific translation.
- // So we insert ignore, which will keep only the first action.
- // phpcs:disable WordPress.DB.PreparedSQL.InterpolatedNotPrepared
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.DirectQuery
- // phpcs:disable WordPress.DB.DirectDatabaseQuery.NoCaching
- $wpdb->query(
- $wpdb->prepare(
- "insert ignore into {$gp_table_prefix}event_actions (event_id, locale, user_id, original_id, action, happened_at) values (%d, %s, %d, %d, %s, %s)",
- array(
- // Start unique key.
- 'event_id' => $event->id(),
- 'locale' => $translation_set->locale,
- 'user_id' => $user_id,
- 'original_id' => $translation->original_id,
- // End unique key.
- 'action' => $action,
- 'happened_at' => $happened_at->format( 'Y-m-d H:i:s' ),
- ),
- ),
- );
- // phpcs:enable
- }
- } catch ( Exception $exception ) {
- // phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_error_log
- error_log( $exception );
- }
- }
-
- /**
- * Filter an array of events so that it only includes events the given user is attending.
- *
- * @param Event[] $events Events.
- *
- * @return Event[]
- */
- // phpcs:disable Generic.CodeAnalysis.UnusedFunctionParameter.FoundAfterLastUsed
- // phpcs:disable Generic.CodeAnalysis.UnusedFunctionParameter.Found
- private function select_events_user_is_registered_for( array $events, int $user_id ): array {
- $attending_event_ids = $this->attendee_repository->get_events_for_user( $user_id );
- return array_filter(
- $events,
- function ( Event $event ) use ( $attending_event_ids ) {
- return in_array( $event->id(), $attending_event_ids, true );
- }
- );
- }
- // phpcs:enable
-}
</del></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventsincludesupgradephp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/upgrade.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/upgrade.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/includes/upgrade.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -5,6 +5,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> use Exception;
</span><span class="cx" style="display: block; padding: 0 10px"> use WP_Query;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Attendee\Attendee;
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use Wporg\TranslationEvents\Stats\Stats_Calculator;
</ins><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> class Upgrade {
</span><span class="cx" style="display: block; padding: 0 10px"> private const VERSION = 2;
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventstemplateseventphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/event.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/event.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/event.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -11,6 +11,8 @@
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event_End_Date;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event_Start_Date;
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use Wporg\TranslationEvents\Stats\Event_Stats;
+use Wporg\TranslationEvents\Stats\Stats_Row;
</ins><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> /** @var Attendee_Repository $attendee_repo */
</span><span class="cx" style="display: block; padding: 0 10px"> /** @var Attendee $attendee */
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -45,33 +47,25 @@
</span><span class="cx" style="display: block; padding: 0 10px"> <ul>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php foreach ( $contributors as $contributor ) : ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <li class="event-contributor" title="<?php echo esc_html( implode( ', ', $contributor->locales ) ); ?>">
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- <a href="<?php echo esc_url( get_author_posts_url( $contributor->ID ) ); ?>"><?php echo get_avatar( $contributor->ID, 48 ); ?></a>
- <a href="<?php echo esc_url( get_author_posts_url( $contributor->ID ) ); ?>"><?php echo esc_html( get_the_author_meta( 'display_name', $contributor->ID ) ); ?></a>
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ <a href="<?php echo esc_url( get_author_posts_url( $contributor->ID ) ); ?>" class="avatar"><?php echo get_avatar( $contributor->ID, 48 ); ?></a>
+ <a href="<?php echo esc_url( get_author_posts_url( $contributor->ID ) ); ?>" class="name"><?php echo esc_html( get_the_author_meta( 'display_name', $contributor->ID ) ); ?></a>
</ins><span class="cx" style="display: block; padding: 0 10px"> <?php if ( $stats_calculator->is_first_time_contributor( $event_start, $contributor->ID ) ) : ?>
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- <span class="first-time-contributor-tada"></span>
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ <span class="first-time-contributor-tada" title="<?php esc_html_e( 'New Translation Contributor', 'gp-translation-events' ); ?>"></span>
</ins><span class="cx" style="display: block; padding: 0 10px"> <?php endif; ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php
</span><span class="cx" style="display: block; padding: 0 10px"> if ( ! $event->end()->is_in_the_past() ) :
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- if ( ( $attendee instanceof Attendee && $attendee->is_host() ) || current_user_can( 'manage_options' ) ) :
- if ( $user->ID !== $contributor->ID ) :
- $_attendee = $attendee_repo->get_attendee( $event_id, $contributor->ID );
- if ( $_attendee instanceof Attendee ) :
- echo '<form class="add-remove-user-as-host" method="post" action="' . esc_url( gp_url( "/events/host/$event_id/$contributor->ID" ) ) . '">';
- if ( $_attendee->is_host() ) :
- if ( 1 === count( $attendee_repo->get_hosts( $event_id ) ) ) :
- echo '<input type="submit" class="button is-primary remove-as-host" disabled value="Remove as host"/>';
- else :
- echo '<input type="submit" class="button is-primary remove-as-host" value="Remove as host"/>';
- endif;
- else :
- echo '<input type="submit" class="button is-secondary convert-to-host" value="Make co-host"/>';
- endif;
- echo '</form>';
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ if ( ( $attendee instanceof Attendee && $attendee->is_host() ) || current_user_can( 'manage_options' ) || $user->ID === $event->author_id() ) :
+ $_attendee = $attendee_repo->get_attendee( $event_id, $contributor->ID );
+ if ( $_attendee instanceof Attendee ) :
+ echo '<form class="add-remove-user-as-host" method="post" action="' . esc_url( gp_url( "/events/host/$event_id/$contributor->ID" ) ) . '">';
+ if ( $_attendee->is_host() ) :
+ echo '<input type="submit" class="button is-primary remove-as-host" value="Remove as host"/>';
+ else :
+ echo '<input type="submit" class="button is-secondary convert-to-host" value="Make co-host"/>';
</ins><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- elseif ( ( $attendee instanceof Attendee && $attendee->is_host() ) ) :
- echo '<span class="event-you">' . esc_html__( 'You (host)', 'gp-translation-events' ) . '</span>';
- else :
- echo '<span class="event-you">' . esc_html__( 'You (event creator)', 'gp-translation-events' ) . '</span>';
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ echo '</form>';
+ else :
+ echo '<span class="event-not-attending">' . esc_html__( 'Not attending', 'gp-translation-events' ) . '</span>';
</ins><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -81,39 +75,29 @@
</span><span class="cx" style="display: block; padding: 0 10px"> </ul>
</span><span class="cx" style="display: block; padding: 0 10px"> </div>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php endif; ?>
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- <?php if ( ! empty( $attendees ) && ( ! $event->end()->is_in_the_past() || ( ( $attendee instanceof Attendee && $attendee->is_host() ) || current_user_can( 'manage_options' ) ) ) ) : ?>
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ <?php if ( ! empty( $attendees ) && ( ! $event->end()->is_in_the_past() || ( ( $attendee instanceof Attendee && $attendee->is_host() ) || current_user_can( 'manage_options' ) || $user->ID === $event->author_id() ) ) ) : ?>
</ins><span class="cx" style="display: block; padding: 0 10px"> <div class="event-attendees">
</span><span class="cx" style="display: block; padding: 0 10px"> <h2><?php esc_html_e( 'Attendees', 'gp-translation-events' ); ?></h2>
</span><span class="cx" style="display: block; padding: 0 10px"> <ul>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php foreach ( $attendees as $_user ) : ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <li class="event-attendee">
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- <a href="<?php echo esc_url( get_author_posts_url( $_user->ID ) ); ?>"><?php echo get_avatar( $_user->ID, 48 ); ?></a>
- <a href="<?php echo esc_url( get_author_posts_url( $_user->ID ) ); ?>"><?php echo esc_html( get_the_author_meta( 'display_name', $_user->ID ) ); ?></a>
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ <a href="<?php echo esc_url( get_author_posts_url( $_user->ID ) ); ?>" class="avatar"><?php echo get_avatar( $_user->ID, 48 ); ?></a>
+ <a href="<?php echo esc_url( get_author_posts_url( $_user->ID ) ); ?>" class="name"><?php echo esc_html( get_the_author_meta( 'display_name', $_user->ID ) ); ?></a>
</ins><span class="cx" style="display: block; padding: 0 10px"> <?php if ( $stats_calculator->is_first_time_contributor( $event_start, $_user->ID ) ) : ?>
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- <span class="first-time-contributor-tada"></span>
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ <span class="first-time-contributor-tada" title="<?php esc_html_e( 'New Translation Contributor', 'gp-translation-events' ); ?>"></span>
</ins><span class="cx" style="display: block; padding: 0 10px"> <?php endif; ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php
</span><span class="cx" style="display: block; padding: 0 10px"> if ( ! $event->end()->is_in_the_past() ) :
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- if ( ( $attendee instanceof Attendee && $attendee->is_host() ) || current_user_can( 'manage_options' ) ) :
- if ( $user->ID !== $_user->ID ) :
- $_attendee = $attendee_repo->get_attendee( $event_id, $_user->ID );
- if ( $_attendee instanceof Attendee ) :
- echo '<form class="add-remove-user-as-host" method="post" action="' . esc_url( gp_url( "/events/host/$event_id/$_user->ID" ) ) . '">';
- if ( $_attendee->is_host() ) :
- if ( 1 === count( $attendee_repo->get_hosts( $event_id ) ) ) :
- echo '<input type="submit" class="button is-primary remove-as-host" disabled value="Remove as host"/>';
- else :
- echo '<input type="submit" class="button is-primary remove-as-host" value="Remove as host"/>';
- endif;
- else :
- echo '<input type="submit" class="button is-secondary convert-to-host" value="Make co-host"/>';
- endif;
- echo '</form>';
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ if ( ( $attendee instanceof Attendee && $attendee->is_host() ) || current_user_can( 'manage_options' ) || $user->ID === $event->author_id() ) :
+ $_attendee = $attendee_repo->get_attendee( $event_id, $_user->ID );
+ if ( $_attendee instanceof Attendee ) :
+ echo '<form class="add-remove-user-as-host" method="post" action="' . esc_url( gp_url( "/events/host/$event_id/$_user->ID" ) ) . '">';
+ if ( $_attendee->is_host() ) :
+ echo '<input type="submit" class="button is-primary remove-as-host" value="Remove as host"/>';
+ else :
+ echo '<input type="submit" class="button is-secondary convert-to-host" value="Make co-host"/>';
</ins><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- elseif ( ( $attendee instanceof Attendee && $attendee->is_host() ) ) :
- echo '<span class="event-you">' . esc_html__( 'You (host)', 'gp-translation-events' ) . '</span>';
- else :
- echo '<span class="event-you">' . esc_html__( 'You (event creator)', 'gp-translation-events' ) . '</span>';
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ echo '</form>';
</ins><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -214,7 +198,10 @@
</span><span class="cx" style="display: block; padding: 0 10px"> ', ',
</span><span class="cx" style="display: block; padding: 0 10px"> array_map(
</span><span class="cx" style="display: block; padding: 0 10px"> function ( $contributor ) use ( $stats_calculator, $event_start ) {
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- $append_tada = $stats_calculator->is_first_time_contributor( $event_start, $contributor->ID ) ? '<span class="first-time-contributor-tada"></span>' : '';
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ $append_tada = '';
+ if ( $stats_calculator->is_first_time_contributor( $event_start, $contributor->ID ) ) {
+ $append_tada = '<span class="first-time-contributor-tada" title="' . esc_html__( 'New Translation Contributor', 'gp-translation-events' ) . '"></span>';
+ }
</ins><span class="cx" style="display: block; padding: 0 10px"> return '@' . $contributor->user_login . $append_tada;
</span><span class="cx" style="display: block; padding: 0 10px"> },
</span><span class="cx" style="display: block; padding: 0 10px"> $contributors
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -224,6 +211,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> array(
</span><span class="cx" style="display: block; padding: 0 10px"> 'span' => array(
</span><span class="cx" style="display: block; padding: 0 10px"> 'class' => array(),
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ 'title' => array(),
</ins><span class="cx" style="display: block; padding: 0 10px"> ),
</span><span class="cx" style="display: block; padding: 0 10px"> )
</span><span class="cx" style="display: block; padding: 0 10px"> );
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -257,11 +245,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> <?php else : ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <form class="event-details-attend" method="post" action="<?php echo esc_url( gp_url( "/events/attend/$event_id" ) ); ?>">
</span><span class="cx" style="display: block; padding: 0 10px"> <?php if ( $attendee instanceof Attendee ) : ?>
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- <?php if ( $attendee->is_host() && ( 1 === count( $attendee_repo->get_hosts( $event_id ) ) ) ) : ?>
- <input type="submit" class="button is-secondary attending-btn" disabled value="You're attending" />
- <?php else : ?>
- <input type="submit" class="button is-secondary attending-btn" value="You're attending" />
- <?php endif; ?>
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ <input type="submit" class="button is-secondary attending-btn" value="You're attending" />
</ins><span class="cx" style="display: block; padding: 0 10px"> <?php else : ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <input type="submit" class="button is-primary attend-btn" value="Attend Event"/>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php endif; ?>
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventstemplateseventsheaderphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/events-header.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/events-header.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/events-header.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -39,20 +39,28 @@
</span><span class="cx" style="display: block; padding: 0 10px"> <p class="event-sub-head">
</span><span class="cx" style="display: block; padding: 0 10px"> <span class="event-host">
</span><span class="cx" style="display: block; padding: 0 10px"> <?php
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- if ( 1 === count( $hosts ) ) :
- esc_html_e( 'Host:', 'gp-translation-events' );
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ if ( count( $hosts ) > 0 ) :
+ if ( 1 === count( $hosts ) ) :
+ esc_html_e( 'Host:', 'gp-translation-events' );
+ else :
+ esc_html_e( 'Hosts:', 'gp-translation-events' );
+ endif;
</ins><span class="cx" style="display: block; padding: 0 10px"> else :
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- esc_html_e( 'Hosts:', 'gp-translation-events' );
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ esc_html_e( 'Created by:', 'gp-translation-events' );
+ ?>
+ <a href="<?php echo esc_attr( get_author_posts_url( $user->ID ) ); ?>"><?php echo esc_html( get_the_author_meta( 'display_name', $user->ID ) ); ?></a>
+ <?php
</ins><span class="cx" style="display: block; padding: 0 10px"> endif;
</span><span class="cx" style="display: block; padding: 0 10px"> ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php foreach ( $hosts as $host ) : ?>
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- <?php $user = get_userdata( $host->user_id() ); ?>
- <a href="<?php echo esc_attr( get_author_posts_url( $user->ID ) ); ?>"><?php echo esc_html( get_the_author_meta( 'display_name', $user->ID ) ); ?></a>
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ <a href="<?php echo esc_attr( get_author_posts_url( $host->user_id() ) ); ?>"><?php echo esc_html( get_the_author_meta( 'display_name', $host->user_id() ) ); ?></a>
</ins><span class="cx" style="display: block; padding: 0 10px"> <?php if ( end( $hosts ) !== $host ) : ?>
</span><span class="cx" style="display: block; padding: 0 10px"> ,
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ <?php else : ?>
+ .
</ins><span class="cx" style="display: block; padding: 0 10px"> <?php endif; ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php endforeach; ?>
</span><del style="background-color: #fdd; text-decoration:none; display:block; padding: 0 10px">- .</span>
</del><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+ </span>
</ins><span class="cx" style="display: block; padding: 0 10px"> <?php $show_edit_button = ( ( $attendee instanceof Attendee && $attendee->is_host() ) || current_user_can( 'edit_post', $event->id() ) ) && $is_editable_event; ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <?php if ( $show_edit_button ) : ?>
</span><span class="cx" style="display: block; padding: 0 10px"> <a class="event-page-edit-link" href="<?php echo esc_url( gp_url( 'events/edit/' . $event->id() ) ); ?>"><span class="dashicons dashicons-edit"></span><?php esc_html_e( 'Edit event', 'gp-translation-events' ); ?></a>
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventstemplateseventsmyeventsphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/events-my-events.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/events-my-events.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/templates/events-my-events.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -6,6 +6,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> namespace Wporg\TranslationEvents;
</span><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Events_Query_Result;
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use Wporg\TranslationEvents\Stats\Stats_Calculator;
</ins><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> /** @var Events_Query_Result $events_i_created_query */
</span><span class="cx" style="display: block; padding: 0 10px"> /** @var Events_Query_Result $events_i_host_query */
</span></span></pre></div>
<a id="sitestrunkwordpressorgpublic_htmlwpcontentpluginswporggptranslationeventswporggptranslationeventsphp"></a>
<div class="modfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Modified: sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/wporg-gp-translation-events.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/wporg-gp-translation-events.php 2024-04-16 06:26:45 UTC (rev 13540)
+++ sites/trunk/wordpress.org/public_html/wp-content/plugins/wporg-gp-translation-events/wporg-gp-translation-events.php 2024-04-16 12:41:37 UTC (rev 13541)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -29,6 +29,7 @@
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event_Form_Handler;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event_Repository_Cached;
</span><span class="cx" style="display: block; padding: 0 10px"> use Wporg\TranslationEvents\Event\Event_Repository_Interface;
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+use Wporg\TranslationEvents\Stats\Stats_Listener;
</ins><span class="cx" style="display: block; padding: 0 10px">
</span><span class="cx" style="display: block; padding: 0 10px"> class Translation_Events {
</span><span class="cx" style="display: block; padding: 0 10px"> public const CPT = 'translation_event';
</span></span></pre>
</div>
</div>
</body>
</html>