We launched new forums in March 2019—join us there. In a hurry for help with your website? Get Help Now!
    • 10152
    • 156 Posts
    Hey, I got a "simple" question about how to retrieve users with attributes from the modx_user_attributes table.

    This is a failed attempt to get users with photos in their profile, should it not be ok ?
            $c = $modx->newQuery('modUser');   
            $c->innerJoin ('modUserAttributes','UserAttributes');      //  tried leftJoin too
            $c->innerJoin ('modUserGroupMember','UserGroupMembers');     
            $c->innerJoin ('modUserGroup','UserGroup','UserGroupMembers.user_group = UserGroup.id');
            $c->leftJoin  ('modUserGroupRole','UserGroupRole','UserGroupMembers.role = UserGroupRole.id');
             
            $c->where(array(
                'active' => '1',
                'UserAttributes.photo:!=' => '',
                'UserGroupMembers.user_group' => '2',                        
            ));
            
            $c->select('
                `modUser`.*,
                `UserGroup`.`id` AS `usergroup`,
                `UserGroup`.`name` AS `usergroup_name`,
                `UserGroupRole`.`name` AS `role`,
                `UserGroupRole`.`name` AS `role_name`
            ');
    
      • 28215
      • 4,149 Posts
      Try this:

      $c = $modx->newQuery('modUser');
      $c->innerJoin ('modUserProfile','Profile'); 
      $c->innerJoin ('modUserGroupMember','UserGroupMembers');
      $c->innerJoin ('modUserGroup','UserGroup','`UserGroupMembers`.`user_group` = `UserGroup`.`id`');
      $c->leftJoin  ('modUserGroupRole','UserGroupRole','`UserGroupMembers`.`role` = `UserGroupRole`.`id`');
      $c->where(array(
          'active' => true,
          'Profile.photo:!=' => '',
          'UserGroupMembers.user_group' => '2',
      ));
      $c->select('
          `modUser`.*,
          `UserGroup`.`id` AS `usergroup`,
          `UserGroup`.`name` AS `usergroup_name`,
          `UserGroupRole`.`name` AS `role`,
          `UserGroupRole`.`name` AS `role_name`
      ');
      $users = $modx->getCollection('modUser',$c);
      


      Note that it’s ’modUserProfile’, with an alias of ’Profile’.
        shaun mccormick | bigcommerce mgr of software engineering, former modx co-architect | github | splittingred.com
        • 10152
        • 156 Posts
        Thank you very much Splittingred !
          • 10152
          • 156 Posts
          Sorry for reviving the post, is there a special syntax for extended json values in a where ?
          $c->where(array(
              'Profile.photo:!=' => '',
              'Profile.extended.availability:>=' => time (), //this line is the problem
              'UserGroupMembers.user_group' => '2',                        
          ));
          
            • 22303 MODX Staff
            • 10,725 Posts
            Quote from: French at Jul 14, 2010, 06:21 PM

            Sorry for reviving the post, is there a special syntax for extended json values in a where ?
            $c->where(array(
                'Profile.photo:!=' => '',
                'Profile.extended.availability:>=' => time (), //this line is the problem
                'UserGroupMembers.user_group' => '2',                        
            ));
            

            These are stored as raw JSON in a text field. You’ll have to use a LIKE expression OR a boolean full-text expression for extended attribute searches, but your particular situation won’t work here because you cannot use MySQL comparison operators (i.e. greater than or equal to) in these expressions. You could do a partial match though for any user with an availability specified or fetch all records and use PHP to filter your results on the extended attributes.
            <?php
            // assuming rest of criteria specified first...
            $c->where(array(
                'Profile.photo:!=' => '',
                'Profile.extended:LIKE' => '%"availability":%', //get any profile with an availability specified
                'UserGroupMembers.user_group' => '2',                        
            ));
            $results = array();
            $collection = $modx->getCollectionGraph('modUser', '{"Profile":{}}', $c);
            foreach ($collection as $object) {
                $extended = $object->get('extended');
                if ($extended && isset($extended['availability']) && $extended['availability'] >= time()) {
                    $results[] = $object;
                }
            }
            unset($collection);
            // now use your filtered user objects contained in $results
            ?>
              • 10152
              • 156 Posts
              Thank you for the full explanations.

              Maybe these extended profile attributes can be moved to the user parameters, allowing to skip the php filter.
                • 22303 MODX Staff
                • 10,725 Posts
                I think filtering the results in PHP is your best bet (maybe cache the results?). Otherwise, I would consider creating an external table class to store your custom attributes so you can properly index and organize it for your specific storage, search and sorting requirements.