select rows has numeric length more than x - mysql

I have these values in a database under field name : username and table name : users
... | username | ...
--------------------------
| a651378 |
| b3789 |
| c3125621903 |
| d32168 |
| e789532 |
| f41589964312 |
For example how to select username where it has a number length greater than 6 digits
As the above values the query should return
... | username | ...
--------------------------
| c3125621903 |
| f41589964312 |

Try this:
SELECT * FROM users WHERE CHAR_LENGTH(username) > 7
CHAR_LENGTH function

Assuming that you do not know how long the character portions are, you can use regular expressions:
select u.*
from users u
where u.username regexp '^.*[0-9]{7}.*$';
Actually, this can be simplified to:
select u.*
from users u
where u.username regexp '[0-9]{7}';
When using regular expressions, I just like to be careful. LIKE patterns match the whole string (from the beginning to the end). REGEXP patterns match within a string.

Related

mysql query showing wrong result

I have a database table look like this
+======+===========+============+
| ID | user Name |user surname|
+======+===========+============+
| 100 | name | surname |
| 101 | name | surname |
| 102 | name | surname |
+===============================+
When i run this query which should show me no rows because there is no row with 101foo2 value :
SELECT * FROM tableName WHERE ID = '101foo2'
I am getting a result with same ID without the foo2 word
+======+===========+============+
| ID | user Name |user surname|
+======+===========+============+
| 101 | name | surname |
+===============================+
how it is showing the row with ID 101 if my query is ID = '101foo2'
You are mixing types. ID is an integer (or number). You are comparing it to a string. So, MySQL needs to decide what type to use for the comparison. What types gets used? Well, a string? No. A number. The string is converted to a number, using the leading digits. So, it becomes 101 and matches.
You should really only compare numbers to numbers, and strings to strings. You could try to write the code as:
SELECT * FROM tableName WHERE ID = 101foo2
However, you would get an error. Another possibility is to force the conversion to a string:
SELECT * FROM tableName WHERE CAST(ID as CHAR) = '101foo2'

Why this sql is correct? (sql injection)

What does it mean?
SELECT * from users where password = ''*'';
if I check this in mysql workbench I get only one line, although I have lot of users in table.
What exactly does this select?
Interesting question. Let's see what ''*'' does.
mysql> select ''*'';
+-------+
| ''*'' |
+-------+
| 0 |
+-------+
Let's create some users:
mysql> select * from users;
+------+-------+
| id | name |
+------+-------+
| 1 | joe |
| 2 | moe |
| 3 | shmoe |
| 4 | 4four |
+------+-------+
And test our query:
mysql> select * from users where name = ''*'';
+------+-------+
| id | name |
+------+-------+
| 1 | joe |
| 2 | moe |
| 3 | shmoe |
+------+-------+
Interestingly enough, user 4 was not selected! But let's try this way:
mysql> select * from users where name = 4;
+------+-------+
| id | name |
+------+-------+
| 4 | 4four |
+------+-------+
So, what can we deduct from this?
''*'' somehow means 0 (I am not that fluent in mysql string operators, so let's take it as a fact);
MySQL, apparently, does type conversions in this case. So if you query a varchar column against an integer, it tries to convert those strings to ints and see if it's a match;
You have only one row whose password begins with 0 or non-digit.
You can always use an expression in SQL. Like SELECT 5-4 AS one and get 1. So you can tell that here is an expression.
MySQL is a loosely typed language, so it can multiply strings. Casting them to numbers. And get you zero as a result of '' * ''
When comparing a string with a number, MySQL casts both to a number. So 0 = 'name' condition will get you true
The ''*'' is a multiplication: its two arguments (empty strings) are converted to numericals (i.e. 0) and the result is 0. Then the left side of the equation is also converted to a number, which will sometimes be zero (when the password cannot be evaluated to a non-zero number), sometimes not.
It is a bit obscure, and you could ask yourself whether this was intended in your case or an accidental behaviour, while the actual intention was to test for '*'. A user with bad intentions might have entered '*' as a password hoping you were not protected against SQL injection in order to get into the system without a valid password.

How to SELECT values if id available in column(Comma separated values) using mysql?

How to SELECT values if id available in column(Comma separated values) using MySQL?
Here I need to get all values when the given id=17 available in group_id column.
Table:
+------------+---------------+
| user_id | group_id |
+------------+---------------+
| 1 | 1,2,3 |
| 3 | 12,23,17 |
| 5 | 17,26 |
+------------+---------------+
I try:
SELECT * FROM `group` WHERE units_id IN('17'); //No result
Expecting result:
+------------+---------------+
| user_id | group_id |
+------------+---------------+
| 3 | 12,23,17 |
| 5 | 17,26 |
+------------+---------------+
You can use FIND_IN_SET
SELECT * FROM `group` WHERE FIND_IN_SET(17,group_id);
Note: It's highly discouraged to store comma separated values in column. A must read:
Is storing a delimited list in a database column really that bad?
Yes
Also you shouldn't use MySQL reserved words as your identifer's name. Be careful to enclose by backtick while using.
Try this one.
You can use find_in_set :
SELECT * FROM `user` WHERE find_in_set('17',group_id) ORDER BY user_id;
RESULT:
+------------+---------------+
| user_id | group_id |
+------------+---------------+
| 3 | 12,23,17 |
| 5 | 17,26 |
+------------+---------------+
REF: MySQL query finding values in a comma separated string
You can use ´find_in_set`
SELECT * FROM `group` WHERE find_in_set('17',units_id );
IN checks if a column contains values from a comma separated list
It is very bad db design if you store values as csv.
For more infoemartion see mysql documentation

How to select records where two fields are unique

I have a table that looks something like this:
+-------------+----------+---------------+------------+
| Contract_ID | Name | Username | Password |
+-------------+----------+---------------+------------+
| 12345671 | Facebook | john.doe | password |
| 12345672 | Google | john.doe | password |
| 12345673 | Apple | martha.malone | doodlebear |
| 12345674 | Samsung | jimmy47 | parkour445 |
| 12345675 | HTC | rick.grimes | simpsons33 |
+-------------+----------+---------------+------------+
I'd like to select only records where there is a one to one ratio between username/password combination and contract id. In this case, that would mean I'd like to select the 3rd, 4th and 5th records in this table.
I've tried different combinations of the DISTINCT keyword but that doesn't seem to be the correct route to go. Is there a query that can return this information?
As a sort of bonus question: is there a query that can produce the opposite results (ie. only records where there is greater than 1 to 1 ratio between contract ids and username/password combination)?
You should use the GROUP BY clause together with the HAVING clause, for example:
SELECT Username, Password FROM Table
GROUP BY Username, Password
HAVING COUNT(*) = 1
The opposite is:
SELECT Username, Password FROM Table
GROUP BY Username, Password
HAVING COUNT(*) > 1
Group by (Name, Password) doesn't work?
Very naughty way of doing it,not good at all, but it works:
select distinct
least(col1, col2) as value1
, greatest(col1, col2) as value2
from yourtable

Check if a string contains numbers

How do I check if a string in a MySQL field contains a number then delete them?
Example table:
tbl_tags
-------------
| id | tag |
-------------
| 1 | hello |
| 2 | hello2 |
| 3 | 2hello |
| 4 | hel3lo |
-------------
The only way I can think of is to do each number individually and use LIKE '%1%' OR LIKE '%2%' etc. But there must be an easier way?
Check out the MySQL Regex methods. Something like the following should work.
SELECT * FROM table WHERE tag REGEXP '[0-9]'
SELECT *
FROM clients
WHERE name REGEXP '^[[:digit:]]+$'
ORDER BY `clients`.`country_id` DESC
LIMIT 0 , 30
this is the answer if you're looking for strings with only digits