I need a sql query count list of how many users have more than one role (by role and by role combination) eg:
admin, author: 50
admin, author, annoymouse user, authenticated user: 20
members, authenticated user: 100
etc
Thank you
MySQL query is:
mysql> SELECT ur.rid, r.name, count(*) as TOT from users_roles ur INNER JOIN role r ON r.rid = ur.rid group by ur.rid ;
+-----+---------------+-----+
| rid | name | TOT |
+-----+---------------+-----+
| 3 | administrator | 2 |
| 4 | tst | 1 |
+-----+---------------+-----+
2 rows in set (0,00 sec)
As alternative option, you have the Views Module. Create a new view, type: user. Enable and play with aggregation on the Role field
Related
I have 10 roles and i want to get table which contains the details for each role provided
by the below command
SHOW GRANTS OF ROLE ROLENAME_1;
this gives output
CREATED_ON | DELETED_ON | ROLE | GRANTED_TO | GRANTEE_NAME | GRANTED_BY
2022-09-02 06:19:36.661 -0700 | | ROLENAME_1 | USER | XXXXXXX | SYSTEM_PROD
2022-09-02 06:19:50.169 -0700 | | ROLENAME_1 | USER | YYYYYY | SYSTEM_PROD
2022-08-01 06:39:01.130 -0700 | | ROLENAME_1 | USER | ZZZZZZ | SYSTEM_PROD
2022-09-02 06:19:50.055 -0700 | | ROLENAME_1 | USER | LLLLLL | SYSTEM_PROD
now I want to get for each role the above output but in one table
something like i run the below
SHOW GRANTS OF ROLE ROLENAME_1;
SHOW GRANTS OF ROLE ROLENAME_2;
SHOW GRANTS OF ROLE ROLENAME_3;
SHOW GRANTS OF ROLE ROLENAME_4;
SHOW GRANTS OF ROLE ROLENAME_5;
SHOW GRANTS OF ROLE ROLENAME_6;
SHOW GRANTS OF ROLE ROLENAME_7;
SHOW GRANTS OF ROLE ROLENAME_8;
SHOW GRANTS OF ROLE ROLENAME_9;
SHOW GRANTS OF ROLE ROLENAME_10;
and get their output in one table.
HOw can i do this in snowflake
You could run all these SHOW commands and the UNION the results together using RESULT_SCAN e.g.
select * from table(result_scan(last_query_id()))
union
select * from table(result_scan(last_query_id(-1)))
union
select * from table(result_scan(last_query_id(-2)))
union
…
However, it would be easier to just query the GRANTS_TO_ROLES view
I have a table which has records of sessions a players have played in a group music play. (music instruments)
so if a user joins a session, and leaves, there is one row created. If they join even the same session 2x, then two rows are created.
Table: music_sessions_user_history
| Column | Type | Default|
| --- | --- | ---|---
| id | character varying(64) | uuid_generate_v4()|
| user_id | user_id | |
| created_at | timestamp without time zone | now()|
| session_removed_at | timestamp without time zone | |
| max_concurrent_connections | integer |
| music_session_id|character varying(64)|
This table is basically the amount of time a user was in a given session. So you can think of it as a timerange or tsrange in PG. The max_concurrent_connections which is a count of the number of users who were in the session at once.
so the query at it's heart needs to find overlapping time ranges for different users in the same session; and to then count them up as a pair that played together.
The query needs to do this: It tries to report each user that played in a music session with others - and who those users were
So for example, if a userA played with userB, and that's the only data in the database, then two rows would be returned like:
| User | Other users in the session |
| --- | --- |
|userA | [userB] |
|userB | [userA] |
But if userA played with both userB and UserC, then three rows would be like:
| User | Other users in the session |
| --- | --- |
|userA | [userB, userC]|
|userB | [userA, userC]|
|userC | [userA, userB]|
Any help of constructing this query is much appreciated.
update:
I am able to get overlapping records using this query.
select m1.user_id, m1.created_at, m1.session_removed_at, m1.max_concurrent_connections, m1.music_session_id
from music_sessions_user_history m1
where exists (select 1
from music_sessions_user_history m2
where tsrange(m2.created_at, m2.session_removed_at, '[]') && tsrange(m1.created_at, m1.session_removed_at, '[]')
and m2.music_session_id = m1.music_session_id
and m2.id <> m1.id);
Need to find a way to convert these results in to pairs.
create a cursor and for each fetched record determine which other records intersect using a between time of start and end time.
append the intersecting results into a temporary table
select the results of the temporary table
The scenario is that I have an access table that contains rows of data for users access, and it also contains an Access Level which has either a 1 or a 2. The 1 denotes 'User' and 2 for 'Admin'. The problem is though that a user can contain both of those values (Access source coming from a variety of other systems that feed into this table).
Therefore, my problem is, how do I write a query that will return a list of users and their access level, where it ONLY shows the max value that the user has for a given Department?
Username | Department | AccessLevel
---------------------------------------------
John Smith | IT | 1
John Smith | IT | 2
John Smith | Security | 2
Sally Harris | Security | 1
Craig Larry | IT | 1
As you can see the table contains two records from John Smith, with the second having a higher access level.
The results I would like would be
John Smith | IT | 2
John Smith | Security | 2
Sally Harris | Security | 1
Craig Larry | IT | 1
This is what I have tried:
Select DISTINCT(Username), Department, MAX(AccessLevel )
From departmentaccess
Group By Username, Department, AccessLevel
The results I get back are exactly as what is in the table. I believe this query I am trying returns the Max record for rows that are entirely duplicate.
What can I do to improve this to get only my expected results?
You should remove group by AccessLevel
Select Username, Department, MAX(AccessLevel )
From departmentaccess
Group By Username, Department
You are on the right track, but you should be aggregating only by username and department:
SELECT Username, Department, MAX(AccessLevel)
FROM departmentaccess
GROUP BY Username, Department;
A more general query which would work if there were more columns in the table which did not appear in the GROUP BY clause would be:
SELECT TOP 1 WITH TIES Username, Department, AccessLevel, other_column
FROM departmentaccess
ORDER BY ROW_NUMBER() OVER (PARTITION BY Username, Department ORDER BY AccessLevel DESC);
I have the following SQL Server db with one table so far.
----------------
|Users |
----------------
| UserId PK |
| |
| Other fields |
----------------
I need to add few more tables to it which is not a problem but this is the goal:
---------------- ---------------- ---------------- ----------------
|Users | |Roles | | Teams | | Groups |
---------------- ---------------- ---------------- ----------------
| UserId PK | | RoleId PK | | TeamId PK | | GroupId PK |
| | | | | | | |
| Other fields | | Other fields | | Other fields | | Other fields |
---------------- ---------------- ---------------- ----------------
What I need to achieve is the following:
I have X amount of users
User1
User2
UserX
I have 3 roles only for all users to use in all teams and groups
Admin
Member
Visitor
One user can create X amount of teams
Team1
Team2
TeamX
One user can create X amount of groups
Group1
Group2
GroupX
Groups and Teams can have users assigned to them with different roles (Admin, Member, Visitor)
One user can belong to one or many team or groups
One user can belong to one or many roles
I have some hard time understanding the relation between those tables.
Here is what I managed to achieve based on the answer from #Robertas Valeika.
You need 3 more tables.
UsersRoles
UsersRolesGroups
UsersRolesTeams.
Relationships:
UsersRoles - UsersRolesGroups,
Groups - UsersRolesGroups
UsersRoles - UsersRolesTeams,
Teams - UsersRolesTeams
Users - UsersRoles,
Roles - UsersRoles.
And add FK to users in groups and teams tables to identify creator of group and team.
I'm working on project that run on CakePHP 2 framework. In this application I have:
models:
Wallnote, User, Group
relationships:
Group HABTM User
Wallnote HABTM User
Wallnote HABTM Group
tables:
wallnotes
- id
- user_id (owner id)
- ...
users_wallnotes
- user_id
- wallnote_id
groups_wallnotes
- group_id
- wallnote_id
groups_users
- group_id
- user_id
I'm using the relationships "Wallnote HABTM User" and "Wallnote HABTM Group" as a filter i.e. user_id/group_id(6) wallnote_id(10) mean, that wallnote with id 10 will be visible for user with id 6, respectively for all users in group with id 6.
I would like to find all wallnotes matching these conditions:
logged user is an owner of this wallnote OR
wallnote was shared with logged user -> record in table users_wallnotes OR
wallnote was shared with some group and logged user is member of this group
It is possible to do this using find() function?
Thanks for answer.
You have two roles: group and user.
it's very difficult to handle it with User and Group separately...
I think the standard way is you have unique role for each user and group, for handling this you must have this tables:
wallnotes
- id
- user_id (owner id)
- ...
roles
- id
- user_id
- group_id
(each rows in this table have group_id or user_id , no both of them)
roles_wallnotes
- id
- role_id
- wallnote_id
when you create a user(or group) you must create a role for it. So all groups and users, now have unique id.
for example you have 2 groups(with 1,2 ids) and 4 users(with 1,2,3,4 ids), then:
users :
|id|name |
---|------
1 | user1
2 | user2
3 | user3
4 | user4
groups :
|id|name |
---|------
1 | group1
2 | group2
roles :
|id| user_id | group_id |
---|---------|----------|
1 | 1 | null |
2 | 2 | null |
3 | 3 | null |
4 | 4 | null |
5 | null | 1 |
6 | null | 2 |
now you must have this relations:
Role hasOne Group
Role hasOne User
Wallnote HABTM Role
with this solution you can easily use find function for retrieve your data you need...