Grant CREATE TABLE permission to MySQL User - mysql

I have a database that is shared between some users, and I want to manage their permissions on this.
I want to give permission for creating a new table, and accessing (select, insert, update, delete) to that table of course, to a user that doesn't have full permission on the database (only he has SELECT access to some tables).
So, I executed this query:
GRANT CREATE ON eh1 TO user1
Then, when I logged in with that user and tried to create a new table, I got this error:
1142 - CREATE command denied to user 'user1'#'localhost' for table 'folan'
What is the problem here? How can I do that?
UPDATE
The problem solved partially by changing the command to this:
GRANT CREATE ON eh1.* TO user1
Now there is another problem, that the user1 cannot select or insert into the newly created table. The reason is understandable, but is there a way to solve this?
Thanks

use as per below-
GRANT CREATE ON eh1.* TO user1#'%' IDENTIFIED BY 'user1_password';
Note: '%' will provide access from all ips, so we should provide rights to specific ip instead of all ips, so change '%' with any ip like '191.161.3.1'
If user need select/insert/update/delete/create rights then syntax will be -
GRANT SELECT, INSERT, UPDATE, DELETE, CREATE ON eh1.* TO user1#'%' IDENTIFIED BY 'user1_password';
Update as per user requirement:
GRANT CREATE ON eh1.* TO user1#'%' IDENTIFIED BY 'user1_password';
GRANT SELECT, INSERT, UPDATE ON eh1.table1 TO user1#'%';
GRANT SELECT, INSERT, UPDATE ON eh1.table2 TO user1#'%';

Following this, correct syntax is
GRANT CREATE ON eh1.* TO user1
With eh1 a database.
If you don't use ".*", your database is considered a table.

Related

Mysql won't let me create user with GRANT

I have made a database called hospitals but when I try and grant my user privileges to the database I get an error back.
My code:
input:
CREATE USER 'axel'#'%' IDENTIFIED BY '123'
output:
Query OK, 0 rows affected (0.19 sec)
input:
grant all on hospitals.* to 'axel'#'localhost';
output:
You are not allowed to create a user with GRANT
How do I fix this? I have tried different things but nothing seems to work and I keep getting the same error message.
The user 'axel'#'%' is not the same user as 'axel'#'localhost'.
You created the former with CREATE USER, then you try to use grant for the latter user, but that user doesn't exist.
MySQL used to allow you to create a user implicitly by granting privileges, but they disabled that specifically for cases like yours. The problem being that since you didn't realize these are different users, your GRANT would have inadvertently created 'axel'#'localhost' as a new user with no password. This was considered a security risk.

Mysql override permission for a single table

I've a Mysql DB with more than 250 tables, i need to block delete permissions for a single user on a single one of them.
we've already tried with grant but there's permission for delete for this DB, so the grant query for the single table doesn't take effect, i still can delete rows from this table. I did:
GRANT SELECT, INSERT, UPDATE ON db.table TO 'user'#'host';
the global permission:
GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, ALTER ON `db`.* TO 'user'#'host'
Is there a way to override permissions for a single table or we've to delete the global permissions and set permissions for the user in each table?
Maybe some way to set global permission for all (*) except one so the second grant will take effect?
Also tried #kiks73 post:
REVOKE DELETE ON db.table FROM 'user'#'host';
Getting:
ERROR 1147 (42000): There is no such grant defined for user 'user' on host 'host' on table 'table'
But there's the global permission set for this user, including delete permissions for this table.
thanks
I think that you need to use the REVOKE statement, because you have to remove a previously granted permission:
REVOKE DELETE ON db.table FROM 'user'#'host';
UPDATE
Referring to this Super User Q&A, if there is no specific grant to revoke on that table for that user, you should try to remove the GRANT ALL ON db.* and assign a grant to all to every single user on every single table, except the specific user on the specific table, that will be granted only for insert and update.
If you have 250 tables, you could create a script combining this SQL to get the list of user created tables:
SELECT * from information_schema.tables
WHERE table_schema not in ('information_schema', 'mysql', 'performance_schema')
and users:
SELECT User FROM mysql.user;
to create a SQL string with the grant you need.

How to set table level privileges in MySQL

I am trying to revoke select privilege from a particular table from a MySQL DB.
Database level restriction is working but table level is not.
When I write "show grants"
This is what I get :
| GRANT USAGE ON *.* TO 'rachit'#'localhost' IDENTIFIED BY PASSWORD '*2470C0C06DEE42FD1618BB99005ADCA2EC9D1E19' |
| GRANT ALL PRIVILEGES ON `test123`.* TO 'rachit'#'localhost' |
| GRANT INSERT, UPDATE, DELETE ON `test123`.`names123` TO 'rachit'#'localhost'
As you can see above I want to
revoke select privilege from rachit user on 'names123' table of 'test123' database, but SELECT is working.
I have attached a screenshot below for better understanding.
https://ibb.co/GRtjXX7
If you GRANT ALL ON test123.* TO 'rachit'#'localhost' you cannot remove one table by running REVOKE ALL ON test123.* TO 'rachit'#'localhost'.
some DBMS systems specifically DENY option for specifically denying access to specific table but this is not the case for mysql.
you may consider to write script and give access to each table one by one
Discussion:
If it wasn't specifically GRANTed, it can't be REVOKEd. This is an unfortunate side effect of the not-so-user-friendly Grant/Revoke syntax and implementation.
You can use a SELECT against information_schema.TABLES to automate the discovery of all the other tables. And have the SELECT build the desired GRANTs.
Possible workaround:
Another approach to your particular problem is to move that one table to a different database. Then GRANT different permissions to that db.

MySQL: Explicit Hostname Vs Hostname with wildcard

Does MySQL treat an explicit hostname the same as a hostname with a wild card? For example, I have created a user via the following:
CREATE USER IF NOT EXISTS 'iga'#'ip-10-11-2-150.aws.example.hostname' IDENTIFIED BY 'SOMEPASSWORD';
Now, I want to grant the user permissions. Could I do it like the following, where the wildcard resolves any user from an ip-10-11-2-anything address?
GRANT INSERT, UPDATE, DELETE, SELECT ON iga.* TO 'iga'#'ip-10-11-2-%';
Or, do I have to explicitly put the same hostname as the user is created with, like the following:
GRANT INSERT, UPDATE, DELETE, SELECT ON iga.* TO 'iga'#'ip-10-11-2-150.aws.example.hostname';
Those are two distinct users. If we run this statement:
GRANT SELECT ON iga.* TO 'iga'#'ip-10-11-%'
Then MySQL will attempt to create a new user
'iga'#'ip-10-11-%'
This user is separate and distinct from the user created with the CREATE USER statement:
'iga'#'ip-10-11-2-150.aws.example.hostname'
which does not get the SELECT privilege. To give privileges to that user, We would need to give the full name that user in a GRANT statement:
GRANT SELECT ON iga.* TO 'iga'#'ip-10-11-2-150.aws.example.hostname'
When a session connects to MySQL, it matches one row in the mysql.user table; it will find an exact match if it exists, otherwise, it may find a wildcard match. But once it matches a user, that's the only user it matches. The session gets only the privileges associated with the one user, not privileges granted to other users that would also be wildcard matches.

“Error (1142): SHOW command denied to user…” when trying to restrict access to columns

I ran the following query to create a user with restrictions on what columns they can view/edit in a certain table. The table has foreign keys to other tables that I haven't given any access to. I want the user to be able to edit the columns under INSERT and just have read-only access to the columns under SELECT.
CREATE USER 'user'#'hostname';
GRANT SELECT (`Status`,`Number`,`Location`), INSERT (`Name`,`Address`,`Email Address`,_
`Home Number`,`Work Number`,`Mobile Number`,`Date Available`) ON `project1`.`table1`_
TO 'user'#'hostname' IDENTIFIED BY 'password';
The query runs and creates the user. I am getting users to use HeidiSQL to edit data in this table. When I login as the user, the only table visible is table1, as expected, however when I click on the table I get the error:
/* SQL Error (1142): SHOW command denied to user 'user'#'<IP address different to hostname IP address>' for table 'table1' */
and cannot see any data at all under 'Data'
The following question was asked on Stack Overflow, however none of the suggested solutions worked for me:
'SHOW command denied to user' when setting up user permissions
If I run the query
SHOW GRANTS FOR CURRENT_USER;
I get:
GRANT USAGE ON *.* TO 'user'#'%' IDENTIFIED BY PASSWORD '*<password different to one set originally>'
GRANT SELECT (Status,Number,Location), INSERT (Name,Address,Email Address,Home Number,Work Number,Mobile Number,Date Available) ON `project1`.`table1` TO 'user'#'%'
I get a view of the columns in the table if I run (but still can't view any data):
SHOW COLUMNS FROM table1;
Does anyone know why this user is not getting a view of the data in table1?
I managed to find a solution.
I needed to first of all 'GRANT SHOW VIEW' to the user so they could view the data in the table.
Next, I changed my query so that I granted the SELECT permission to ALL the columns, and granted the UPDATE permission to all the columns EXCEPT the colulms I wanted to leave as Read-Only to the user.
The following is the query I ran, which worked successfully:
CREATE USER 'user'#'localhost';
GRANT SHOW VIEW ON `project1`.`table1` TO 'user'#'localhost' IDENTIFIED BY 'password';
GRANT SELECT (`Status`,`Number`,`Location`,`Name`,`Address`,`Email Address`,`Home Number`,_
`Work Number`,`Mobile Number`,`Date Available`), UPDATE (`Name`,`Address`,`Email Address`,_
`Home Number`,`Work Number`,`Mobile Number`,`Date Available`) ON `project1`.`table1` TO _
'user'#'localhost' IDENTIFIED BY 'password';