<p>You can modify the query to select only the title (since you don't need anything else) and sort the results by title in descending order:</p>
<pre class="lang-php prettyprint-override"><code>$history = $user-&gt;history-&gt;orderBy('title DESC')-&gt;select('title')-&gt;column();
</code></pre>
<p>This will give you an array of years (assuming the titles only include the year and nothing else) in descending order. Then you can simplify the logic to increase the loyalty count for every consecutive year that's included in the array, starting from the current one. For example:</p>
<pre class="lang-php prettyprint-override"><code>$loyalty = 0;
$year = (int) date('Y');
while (in_array($year, $history)) {
    $loyalty++;
    $year--;
}
</code></pre>

CC BY-SA 4.0
2023-05-09T12:22:07.437Z
Wow, that's so simple! Thank you!
supazu
CC BY-SA 4.0
2023-05-09T09:44:58.607Z
2023-05-09T12:29:18.697Z
2023-05-09T12:29:18.697Z
MoritzLost
<p>I'm trying to calculate a 'loyalty' score on Users. I have an Entries field <code>history</code>, with Entries like 2023, 2022, 2021 etc.</p>
<p>I want to calculate the number of consecutive years, going backward from the current year. So for example, a user with 2023, 2022, 2021 would have a loyalty score of 3. A user with 2022 and 2021 would have a loyalty score of 0 because they don't have a 2023 Membership. Should they buy one, they would immediately have 3 years of loyalty.</p>
<p>One additional problem is that these entries might not be in order in the field. They might be in order like 2019, 2022, 2020, 2023, 2021.</p>
<p>I <a href="https://craftcms.stackexchange.com/questions/40011/count-consecutive-years-in-tag-array-in-a-module">previously had this working with tags</a>, but with 4.4 and 5 coming soon I want to Entrify everything.</p>
<p>Here's my attempt based on that, but my loyalty value is only ever 0 or 1. I guess the <code>previousYear</code> part isn't working. Does anyone have ideas on fixing this or a better way to do it?</p>
<pre><code>$currentYear = date('Y');
$previousYear = null;
$history = $user-&gt;history-&gt;all();
$loyalty = 0;
foreach ($history as $item) {
    $year = $item-&gt;title;
    if ($year === $currentYear) {
        $loyalty++;
        $previousYear = $year - 1;
    } elseif ($previousYear !== null &amp;&amp; $year === $previousYear) {
        $loyalty++;
        $previousYear = $year - 1;
    }
}
$user-&gt;setFieldValue('loyalty', $loyalty);
</code></pre>

<modules>
Calculating loyalty from consecutive entries on a user
# Calculating loyalty from consecutive entries on a user

(Asked by: username_0 on 2023-05-09)

I'm trying to calculate a 'loyalty' score on Users. I have an Entries field history, with Entries like 2023, 2022, 2021 etc.
I want to calculate the number of consecutive years, going backward from the current year. So for example, a user with 2023, 2022, 2021 would have a loyalty score of 3. A user with 2022 and 2021 would have a loyalty score of 0 because they don't have a 2023 Membership. Should they buy one, they would immediately have 3 years of loyalty.
One additional problem is that these entries might not be in order in the field. They might be in order like 2019, 2022, 2020, 2023, 2021.
I previously had this working with tags, but with 4.4 and 5 coming soon I want to Entrify everything.
Here's my attempt based on that, but my loyalty value is only ever 0 or 1. I guess the previousYear part isn't working. Does anyone have ideas on fixing this or a better way to do it?
$currentYear = date('Y');
$previousYear = null;
$history = $user->history->all();
$loyalty = 0;
foreach ($history as $item) {
    $year = $item->title;
    if ($year === $currentYear) {
        $loyalty++;
        $previousYear = $year - 1;
    } elseif ($previousYear !== null && $year === $previousYear) {
        $loyalty++;
        $previousYear = $year - 1;
    }
}
$user->setFieldValue('loyalty', $loyalty);

**Tags:** modules

---

## 1 answers

### Answer by username_1 on 2023-05-09. Score: 2 | Accepted answer

You can modify the query to select only the title (since you don't need anything else) and sort the results by title in descending order:
$history = $user->history->orderBy('title DESC')->select('title')->column();

This will give you an array of years (assuming the titles only include the year and nothing else) in descending order. Then you can simplify the logic to increase the loyalty count for every consecutive year that's included in the array, starting from the current one. For example:
$loyalty = 0;
$year = (int) date('Y');
while (in_array($year, $history)) {
    $loyalty++;
    $year--;
}

> **Comments:**
> **username_0**: Wow, that's so simple! Thank you!  

---

