<p>So, for the part preventing the activation, don't use:</p>

<p><code>if (Craft::$app-&gt;request-&gt;getIsSiteRequest())</code></p>

<p>Just do:</p>

<pre class="lang-twig prettyprint-override"><code>Event::on(
    Users::class,
    Users::EVENT_BEFORE_ACTIVATE_USER,
    function(Event $event){
        $formName = Craft::$app-&gt;getRequest()-&gt;post('group');
        if ($formName==='ypo' || $formName==="yp") {
           $event-&gt;isValid = false;
        }
    }
);
</code></pre>

<p>For the other part:</p>

<pre class="lang-twig prettyprint-override"><code>Event::on(
Elements::class,
Elements::EVENT_AFTER_SAVE_ELEMENT,
    function(Event $event){
        // Check it's a front end request
        if (Craft::$app-&gt;request-&gt;getIsSiteRequest()) {
            if($event-&gt;element instanceof \craft\elements\User) {
                $user = $event-&gt;element;
                if($event-&gt;isNew) {
                    $user-&gt;unverifiedEmail = $user-&gt;email;
                    Craft::$app-&gt;getElements()-&gt;saveElement($user, false);
                    $formName = Craft::$app-&gt;getRequest()-&gt;post('group');

                    if($formName==='ypo') {
                        Craft::$app-&gt;getUsers()-&gt;assignUserToGroups($user-&gt;id, [1]);
                    }
                    if($formName==='yp') {
                        Craft::$app-&gt;getUsers()-&gt;assignUserToGroups($user-&gt;id, [2]);
                        $emailSent = Craft::$app-&gt;getUsers()-&gt;sendActivationEmail($user);    
                    }
                }
            }
        }
    }
);
</code></pre>

<p>Because you don't enforce email verification in control panel/user settings, you are skipping populating the <code>unverifiedEmail</code> field for the new user which is <a href="https://github.com/craftcms/cms/blob/develop/src/controllers/UsersController.php#L1171" rel="nofollow noreferrer">done here</a> and that was part of the issue too :)</p>

CC BY-SA 4.0
2019-03-04T11:20:30.173Z
ahh the unverifiedEmail field, that did it.
Lukigi
CC BY-SA 4.0
2019-03-02T16:27:15.697Z
2019-03-02T16:27:15.697Z
Oli
<p>I have 2 front end registration forms. One for normal users and one for admins. In each form I have a hidden input with a group value like so:</p>

<pre><code>&lt;input type="hidden" name="group" value="ypo"&gt;
</code></pre>

<p>In craft I have <strong>allow public registration</strong> checked and <strong>verify user address</strong> unchecked</p>

<p>Then I have a module that does two things:
One, it assigns new registrations to the correct group based on the hidden field and that part works like a charm, but I'll still post it here just in case:</p>

<pre><code>Event::on(
        Elements::class,
        Elements::EVENT_AFTER_SAVE_ELEMENT,
        function(ElementEvent $event){
          // Check it's a front end request
          if (Craft::$app-&gt;request-&gt;getIsSiteRequest()) {
            if($event-&gt;element instanceof \craft\elements\User){
              $user = $event-&gt;element;
              if($event-&gt;isNew) {
                  $formName = Craft::$app-&gt;getRequest()-&gt;post('group');
                  if($formName==='ypo')
                  {
                    Craft::$app-&gt;getUsers()-&gt;assignUserToGroups($event-&gt;element-&gt;id, [1]);
                    logMessage('Assigning Member - id: '.$event-&gt;element-&gt;id);
                  }
                  if($formName==='yp')
                  {
                    Craft::$app-&gt;getUsers()-&gt;assignUserToGroups($event-&gt;element-&gt;id, [2]);
                    logMessage('Assigning Website User - id: '.$event-&gt;element-&gt;id);
                    $users =  Craft::$app-&gt;getUsers();
                    if($users-&gt;sendActivationEmail($user)) {
                      logMessage('Activation Email Sent');
                    }
                  }
              }
            }
          }
        }
      );
</code></pre>

<p>Two, it blocks new users from being activated like that:</p>

<pre><code>Event::on(
          Users::class,
          Users::EVENT_BEFORE_ACTIVATE_USER,
          function (UserEvent $event) {
              if (Craft::$app-&gt;request-&gt;getIsSiteRequest()) {
                // Only trigger when request comes from the specified form
                $formName = Craft::$app-&gt;getRequest()-&gt;post('group');
                if($formName==='ypo' || $formName==="yp") {
                  logMessage('Activation Withold');
                  $event-&gt;isValid = false;

                }
              }
          }
      );
</code></pre>

<p>I based this code on Brandon's answer to  [a very similar question][1] and it works, in a sense it sets the status to pending, but...</p>

<p>[1]: <a href="https://craftcms.stackexchange.com/questions/28216/how-can-i-set-new-user-accounts-to-pending-status-in-a-craft-3-module">How can I set new user accounts to pending status in a Craft 3 module?</a> but added the safeguard that the code will only be triggered when the accompanying hidden form fields are present. </p>

<p><strong>The problem</strong></p>

<p>The problem is that whenever I want to activate the account,by emailing the activation code (manually or by my script), I get an error:</p>

<p><em>Return value of craft\web\twig\variables\UserSession::getRememberedUsername() must be of the type string, null returned</em></p>

<p><em>EDIT: error was due to having 'autoLoginAfterAccountActivation' => true in settings. Switching that off got rid of the error, but the activation still doesn't work.</em></p>

<p>What's even more weird is when I use the activation code from the admin panel, I'm then redirected to set your new password page instead of activation.</p>

<p>My log doesn't show that my script has been triggered, so it shouldn't prevent activation from link or email. Any help would be appreciated.</p>

<hr>

<p>I did a lot of testing, If I remove EVENT_BEFORE_ACTIVATE_USER code and register a user, and then put it back in and send email, activation works. This means that setting craft\events\UserEvent::$isValid to false is permanent and can no longer be activated. Any idea why?</p>

<plugin-development><craft3><users><modules><usermodel>
How to pragmatically set registered user status to pending and then manually send activation email
# How to pragmatically set registered user status to pending and then manually send activation email

(Asked by: username_0 on 2019-03-01)

I have 2 front end registration forms. One for normal users and one for admins. In each form I have a hidden input with a group value like so:


In craft I have allow public registration checked and verify user address unchecked
Then I have a module that does two things:
One, it assigns new registrations to the correct group based on the hidden field and that part works like a charm, but I'll still post it here just in case:
Event::on(
        Elements::class,
        Elements::EVENT_AFTER_SAVE_ELEMENT,
        function(ElementEvent $event){
          // Check it's a front end request
          if (Craft::$app->request->getIsSiteRequest()) {
            if($event->element instanceof \craft\elements\User){
              $user = $event->element;
              if($event->isNew) {
                  $formName = Craft::$app->getRequest()->post('group');
                  if($formName==='ypo')
                  {
                    Craft::$app->getUsers()->assignUserToGroups($event->element->id, [1]);
                    logMessage('Assigning Member - id: '.$event->element->id);
                  }
                  if($formName==='yp')
                  {
                    Craft::$app->getUsers()->assignUserToGroups($event->element->id, [2]);
                    logMessage('Assigning Website User - id: '.$event->element->id);
                    $users =  Craft::$app->getUsers();
                    if($users->sendActivationEmail($user)) {
                      logMessage('Activation Email Sent');
                    }
                  }
              }
            }
          }
        }
      );

Two, it blocks new users from being activated like that:
Event::on(
          Users::class,
          Users::EVENT_BEFORE_ACTIVATE_USER,
          function (UserEvent $event) {
              if (Craft::$app->request->getIsSiteRequest()) {
                // Only trigger when request comes from the specified form
                $formName = Craft::$app->getRequest()->post('group');
                if($formName==='ypo' || $formName==="yp") {
                  logMessage('Activation Withold');
                  $event->isValid = false;

                }
              }
          }
      );

I based this code on Brandon's answer to  [a very similar question][1] and it works, in a sense it sets the status to pending, but...
[1]: How can I set new user accounts to pending status in a Craft 3 module? but added the safeguard that the code will only be triggered when the accompanying hidden form fields are present. 
The problem
The problem is that whenever I want to activate the account,by emailing the activation code (manually or by my script), I get an error:
Return value of craft\web\twig\variables\UserSession::getRememberedUsername() must be of the type string, null returned
EDIT: error was due to having 'autoLoginAfterAccountActivation' => true in settings. Switching that off got rid of the error, but the activation still doesn't work.
What's even more weird is when I use the activation code from the admin panel, I'm then redirected to set your new password page instead of activation.
My log doesn't show that my script has been triggered, so it shouldn't prevent activation from link or email. Any help would be appreciated.

I did a lot of testing, If I remove EVENT_BEFORE_ACTIVATE_USER code and register a user, and then put it back in and send email, activation works. This means that setting craft\events\UserEvent::$isValid to false is permanent and can no longer be activated. Any idea why?

**Tags:** plugin-development, craft3, users, modules, usermodel

---

## 1 answers

### Answer by username_1 on 2019-03-02. Score: 1 | Accepted answer

So, for the part preventing the activation, don't use:
if (Craft::$app->request->getIsSiteRequest())
Just do:
Event::on(
    Users::class,
    Users::EVENT_BEFORE_ACTIVATE_USER,
    function(Event $event){
        $formName = Craft::$app->getRequest()->post('group');
        if ($formName==='ypo' || $formName==="yp") {
           $event->isValid = false;
        }
    }
);

For the other part:
Event::on(
Elements::class,
Elements::EVENT_AFTER_SAVE_ELEMENT,
    function(Event $event){
        // Check it's a front end request
        if (Craft::$app->request->getIsSiteRequest()) {
            if($event->element instanceof \craft\elements\User) {
                $user = $event->element;
                if($event->isNew) {
                    $user->unverifiedEmail = $user->email;
                    Craft::$app->getElements()->saveElement($user, false);
                    $formName = Craft::$app->getRequest()->post('group');

                    if($formName==='ypo') {
                        Craft::$app->getUsers()->assignUserToGroups($user->id, [1]);
                    }
                    if($formName==='yp') {
                        Craft::$app->getUsers()->assignUserToGroups($user->id, [2]);
                        $emailSent = Craft::$app->getUsers()->sendActivationEmail($user);    
                    }
                }
            }
        }
    }
);

Because you don't enforce email verification in control panel/user settings, you are skipping populating the unverifiedEmail field for the new user which is done here and that was part of the issue too :)

> **Comments:**
> **username_0**: ahh the unverifiedEmail field, that did it.  

---

