Cannot create NVARCHAR column in MariaDb/Mysql - mysql

I'm using MariaDb server (Ver 15.1 Distrib 10.2.7-MariaDB).
When I execute
CREATE TABLE `my_table` (
`id` INT NOT NULL,
`name` NVARCHAR(64) NULL,
PRIMARY KEY (`id`)
);
Describe output:
MariaDB [db]> describe my_table;
+-------+-------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-------+-------------+------+-----+---------+-------+
| id | int(11) | NO | PRI | NULL | |
| name | varchar(64) | YES | | NULL | |
+-------+-------------+------+-----+---------+-------+
2 rows in set (0.00 sec)
Why there is no error, and "name" column datatype is varchar (not nvarchar)?
db schema details:
Default collation: utf8_general_ci
Default characterset: utf8

NVARCHAR is a synonym for VARCHAR in MySQL/MariaDB. But you need to add the CHARACTER SET utf8mb4 to be sure that you get full UTF-8 support.
What you show as the default for that database is only the subset, called 'utf8'. It will not handle Emoji or some of Chinese.

Related

Why MYSQL Query dose not using the table's composite index? [duplicate]

This question already has answers here:
MySQL varchar index length
(2 answers)
Closed 1 year ago.
Note:
First I want to mention that I read all other related questions and answers.
Question:
I had created 2 indexes for the table I have but whenever I use my queries it's not using the index. even when forced to use the index it's not using it.
The table has 1.5M rows and it will be increased, and the query is taking 35+ seconds.
Query 1
explain analyze
SELECT sum(cid_user_usd_earned)
FROM `bbtv_adv_records`
WHERE (user_id =2
and `cid_assign_month` = '2020-08-01'
And `content_type` = 'UGC'
);
explain analyze
SELECT sum(cid_user_usd_earned)
FROM `bbtv_adv_records`
USE INDEX (bbtv_adv_records_user_id_cid_assign_month_content_type_index)
WHERE (user_id =2
and `cid_assign_month` = '2020-08-01'
And `content_type` = 'UGC'
);
Query 2
explain analyze
SELECT *
FROM `bbtv_adv_records`
WHERE (user_id =2
and `cid_assign_month` = '2020-08-01'
);
Query 3
explain analyze
SELECT sum(cid_user_usd_earned),channel_id
FROM `bbtv_adv_records`
WHERE (user_id =2
and `cid_assign_month` = '2020-08-01'
Group by `channel_id`
);
Table
CREATE TABLE `bbtv_adv_records` (
`id` bigint UNSIGNED NOT NULL,
`content_type` varchar(400) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
....
`channel_id` varchar(400) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
...
`cid_assign_month` date NOT NULL,
`cid_process_state` enum('process','done','fail') CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci NOT NULL,
`user_id` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
--
-- Indexes for table `bbtv_adv_records`
--
ALTER TABLE `bbtv_adv_records`
ADD PRIMARY KEY (`id`),
ADD KEY `bbtv_adv_records_user_id_cid_assign_month_index
` (`user_id`,`cid_assign_month`),
ADD KEY `bbtv_adv_records_user_id_cid_assign_month_content_type_index`
(`user_id`,`cid_assign_month`,`content_type`);
--
-- AUTO_INCREMENT for table `bbtv_adv_records`
--
ALTER TABLE `bbtv_adv_records`
MODIFY `id` bigint UNSIGNED NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=1543191;
COMMIT;
mysql> show index from bbtv_adv_records
+------------------+------------+--------------------------------------------------------------+--------------+------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
| Table | Non_unique | Key_name | Seq_in_index | Column_name | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment | Index_comment | Visible | Expression |
+------------------+------------+--------------------------------------------------------------+--------------+------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
| bbtv_adv_records | 0 | PRIMARY | 1 | id | A | 1456578 | NULL | NULL | | BTREE | | | YES | NULL |
| bbtv_adv_records | 1 | bbtv_adv_records_user_id_cid_assign_month_index | 1 | user_id | A | 8 | NULL | NULL | YES | BTREE | | | YES | NULL |
| bbtv_adv_records | 1 | bbtv_adv_records_user_id_cid_assign_month_index | 2 | cid_assign_month | A | 47 | NULL | NULL | | BTREE | | | YES | NULL |
| bbtv_adv_records | 1 | bbtv_adv_records_user_id_cid_assign_month_content_type_index | 1 | user_id | A | 8 | NULL | NULL | YES | BTREE | | | YES | NULL |
| bbtv_adv_records | 1 | bbtv_adv_records_user_id_cid_assign_month_content_type_index | 2 | cid_assign_month | A | 49 | NULL | NULL | | BTREE | | | YES | NULL |
| bbtv_adv_records | 1 | bbtv_adv_records_user_id_cid_assign_month_content_type_index | 3 | content_type | A | 58 | NULL | NULL | YES | BTREE | | | YES | NULL |
+------------------+------------+--------------------------------------------------------------+--------------+------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
6 rows in set (0.01 sec)
note the best result I have 10 seconds when creating only the cid_assign_month index alone, but all my queries have the cid_assign_month with the user_id always.
could you show the result of "show index from bbtv_adv_records ".
The mysql query optimizer is a cost based optimiser.
It try to find out the best execution plan.
If the cost of ALL( full table scan) is less then REF_OR_NULL (using secondary index fetch data), It will use full table scan where time complexity is O(n) .
for example, there are the commonest cost matrix
the IO cost of Reading 1 block page is 1.
the CPU cost of comparing 1 record is 0.2.
the query 1:
SELECT sum(cid_user_usd_earned) FROM bbtv_adv_records WHERE (user_id =2 and cid_assign_month = '2020-08-01' And content_type = 'UGC');
because the column cid_user_usd_earned is not in secondary index bbtv_adv_records_user_id_cid_assign_month_content_type_index, mysql will return to the primary index to get cid_user_usd_earned, after using binary search in secondary index.
Solved
It looks that MySQL indexing will not work with varchar(400) or any large length.
change from
`content_type` varchar(400) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
`channel_id` varchar(400) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
`user_id` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
to
`content_type` varchar(30) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
`channel_id` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL,
`user_id` bigint UNSIGNED DEFAULT NULL,
now the Query show indexing and faster from 34s to 8s
mysql> explain analyze SELECT sum(cid_user_usd_earned) FROM `bbtv_adv_records` WHERE (user_id =2 and `cid_assign_month` = '2020-08-01' And `content_type` = 'UGC');
+-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| EXPLAIN |
+-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| -> Aggregate: sum(bbtv_adv_records.cid_user_usd_earned) (actual time=8247.975..8247.981 rows=1 loops=1)
-> Index lookup on bbtv_adv_records using bbtv_adv_records_user_id_cid_assign_month_content_type_index (user_id=2, cid_assign_month=DATE'2020-08-01', content_type='UGC') (cost=116370.56 rows=496622) (actual time=0.373..6175.144 rows=259373 loops=1)
|
+-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
1 row in set (8.25 sec)

Is there any other way to speed up my MySQL query speed?

I initially selected part of the stock_hfq table, and then filtered it with ts_code.
I used the intermediate table stock_hfq_temp to filter the stock_hfq data. The data queried out is about 2M rows. It takes 2min 1s without exists, and 1min 5s with exists.However, adding the time to write the temporary table stock_hfq_temp and the time to create the index ts_code of the temporary table, the total time difference is only 4s.
Is there any other way to speed up my query speed?
ts_code is unique in the stock_hfq_temp table.
The relevant sentences and results are as follows:
select * from stock_hfq t where t.trade_date>'20110302';
Wall time: 2min 12s
select ts_code from stock_hfq_temp b
Wall time: 8 ms
select * from stock_hfq t where t.trade_date>'20110302' and exists (select 1 from stock_hfq_temp b where b.ts_code=t.ts_code);
Wall time: 1min 5s
The analysis of the database is as follows:
mysql> select count(1) from stock_hfq;
+----------+
| count(1) |
+----------+
| 11546271 |
+----------+
1 row in set (3 min 31.64 sec)
mysql> select count(1) from (select distinct ts_code from stock_hfq b) t;
+----------+
| count(1) |
+----------+
| 4480 |
+----------+
1 row in set (1.26 sec)
mysql> select count(1) from stock_hfq_temp;
+----------+
| count(1) |
+----------+
| 1502 |
+----------+
1 row in set (0.18 sec)
Both tables are indexed.
mysql> show index from stock_hfq;
+-----------+------------+------------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
| Table | Non_unique | Key_name | Seq_in_index | Column_name | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment | Index_comment | Visible | Expression |
+-----------+------------+------------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
| stock_hfq | 1 | ts_code | 1 | ts_code | A | 16782 | NULL | NULL | YES | BTREE | | | YES | NULL |
| stock_hfq | 1 | trade_date | 1 | trade_date | A | 94773 | NULL | NULL | YES | BTREE | | | YES | NULL |
+-----------+------------+------------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
2 rows in set (0.00 sec)
mysql> show index from stock_hfq_temp;
+----------------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
| Table | Non_unique | Key_name | Seq_in_index | Column_name | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment | Index_comment | Visible | Expression |
+----------------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
| stock_hfq_temp | 1 | ts_code | 1 | ts_code | A | 1502 | NULL | NULL | YES | BTREE | | | YES | NULL |
+----------------+------------+----------+--------------+-------------+-----------+-------------+----------+--------+------+------------+---------+---------------+---------+------------+
1 row in set (0.00 sec)
explain:
mysql> explain select * from stock_hfq t where exists (select 1 from stock_hfq_temp b where b.ts_code =t.ts_code);
+----+-------------+-------+------------+-------+---------------+---------+---------+----------------------+------+----------+-------------------------------------+
| id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra |
+----+-------------+-------+------------+-------+---------------+---------+---------+----------------------+------+----------+-------------------------------------+
| 1 | SIMPLE | b | NULL | index | ts_code | ts_code | 83 | NULL | 1502 | 100.00 | Using where; Using index; LooseScan |
| 1 | SIMPLE | t | NULL | ref | ts_code | ts_code | 83 | quant_test.b.ts_code | 681 | 100.00 | NULL |
+----+-------------+-------+------------+-------+---------------+---------+---------+----------------------+------+----------+-------------------------------------+
2 rows in set, 2 warnings (0.00 sec)
mysql> show warnings;
+-------+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Level | Code | Message |
+-------+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Note | 1276 | Field or reference 'quant_test.t.ts_code' of SELECT #2 was resolved in SELECT #1 |
| Note | 1003 | /* select#1 */ select `quant_test`.`t`.`ts_code` AS `ts_code`,`quant_test`.`t`.`trade_date` AS `trade_date`,`quant_test`.`t`.`open` AS `open`,`quant_test`.`t`.`high` AS `high`,`quant_test`.`t`.`low` AS `low`,`quant_test`.`t`.`close` AS `close`,`quant_test`.`t`.`pre_close` AS `pre_close`,`quant_test`.`t`.`change` AS `change`,`quant_test`.`t`.`pct_chg` AS `pct_chg`,`quant_test`.`t`.`vol` AS `vol`,`quant_test`.`t`.`amount` AS `amount`,`quant_test`.`t`.`adj_factor` AS `adj_factor` from `quant_test`.`stock_hfq` `t` semi join (`quant_test`.`stock_hfq_temp` `b`) where (`quant_test`.`t`.`ts_code` = `quant_test`.`b`.`ts_code`) |
+-------+------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
2 rows in set (0.00 sec)
CREATE TABLE statements for all relevant tables :
/*
Navicat Premium Data Transfer
Source Server : localhost_3306
Source Server Type : MySQL
Source Server Version : 80021
Source Host : localhost:3306
Source Schema : quant_test
Target Server Type : MySQL
Target Server Version : 80021
File Encoding : 65001
Date: 12/06/2021 13:55:28
*/
SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;
-- ----------------------------
-- Table structure for stock_hfq
-- ----------------------------
DROP TABLE IF EXISTS `stock_hfq`;
CREATE TABLE `stock_hfq` (
`ts_code` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci DEFAULT NULL,
`trade_date` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci DEFAULT NULL,
`open` double DEFAULT NULL,
`high` double DEFAULT NULL,
`low` double DEFAULT NULL,
`close` double DEFAULT NULL,
`pre_close` double DEFAULT NULL,
`change` double DEFAULT NULL,
`pct_chg` double DEFAULT NULL,
`vol` double DEFAULT NULL,
`amount` double DEFAULT NULL,
`adj_factor` double DEFAULT NULL,
INDEX `ts_code`(`ts_code`) USING BTREE,
INDEX `trade_date`(`trade_date`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;
SET FOREIGN_KEY_CHECKS = 1;
/*
Navicat Premium Data Transfer
Source Server : localhost_3306
Source Server Type : MySQL
Source Server Version : 80021
Source Host : localhost:3306
Source Schema : quant_test
Target Server Type : MySQL
Target Server Version : 80021
File Encoding : 65001
Date: 12/06/2021 13:55:38
*/
SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;
-- ----------------------------
-- Table structure for stock_hfq_temp
-- ----------------------------
DROP TABLE IF EXISTS `stock_hfq_temp`;
CREATE TABLE `stock_hfq_temp` (
`ts_code` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci DEFAULT NULL,
`name` text CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci,
`trade_date` text CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci,
`amount` double DEFAULT NULL,
`vol` double DEFAULT NULL,
`close` double DEFAULT NULL,
`h1` double DEFAULT NULL,
`mid` double DEFAULT NULL,
`l1` double DEFAULT NULL,
INDEX `ts_code`(`ts_code`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;
SET FOREIGN_KEY_CHECKS = 1;

MariaDB / pymysql: Data shows up in columns as hex values (0x5761746572 instead of "Water")

I'm trying to create a local Docker image that represents a development version of my production database. I've started a MariaDB container with the same version as production (10.1) and loaded a schema based on a mysqldump of production.
However when I start inserting data, I get weird hex values in every column.
The production data looks like:
select * from projects where p_project = 'Water';
+-----------+----------------+------------+----------+-------------+---------+----------+----------+---------+--------------------+
| p_project | p_timestamp | p_wikipage | p_parent | p_shortname | p_count | p_qcount | p_icount | p_scope | p_upload_timestamp |
+-----------+----------------+------------+----------+-------------+---------+----------+----------+---------+--------------------+
| Water | 20200305045828 | NULL | NULL | NULL | 841 | 644 | 554 | 0 | 20190813001026 |
+-----------+----------------+------------+----------+-------------+---------+----------+----------+---------+--------------------+
While the dev database looks like:
select * from projects where p_project = 'Water';
+----------------------+--------------------------------+------------------------+--------------------+--------------------------+---------+----------+----------+---------+----------------------------------------+
| p_project | p_timestamp | p_wikipage | p_parent | p_shortname | p_count | p_qcount | p_icount | p_scope | p_upload_timestamp |
+----------------------+--------------------------------+------------------------+--------------------+--------------------------+---------+----------+----------+---------+----------------------------------------+
| 0x5761746572 | 0x3230323030333035303532333538 | 0x | 0x | 0x | NULL | NULL | NULL | 0 | 0x |
+----------------------+--------------------------------+------------------------+--------------------+--------------------------+---------+----------+----------+---------+----------------------------------------+
The production database is defined as so:
show create database enwp10;
enwp10 | CREATE DATABASE `enwp10` /*!40100 DEFAULT CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci */ |
And dev is:
show create database enwp10_dev;
| enwp10_dev | CREATE DATABASE `enwp10_dev` /*!40100 DEFAULT CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci */ |
Here's the table definition:
show create table projects;
----------------------------------------------------------------------+
| projects | CREATE TABLE `projects` (
`p_project` varbinary(63) NOT NULL,
`p_timestamp` binary(14) NOT NULL,
`p_wikipage` varbinary(255) DEFAULT NULL,
`p_parent` varbinary(63) DEFAULT NULL,
`p_shortname` varbinary(255) DEFAULT NULL,
`p_count` int(10) unsigned DEFAULT '0',
`p_qcount` int(10) unsigned DEFAULT '0',
`p_icount` int(10) unsigned DEFAULT '0',
`p_scope` int(10) unsigned NOT NULL DEFAULT '0',
`p_upload_timestamp` binary(14) DEFAULT NULL,
PRIMARY KEY (`p_project`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |
+----------
The interesting part is that the select works in both cases, so maybe it's my mysql client display settings that are off?
My kwargs to my pymysql connect call include:
'charset': None,
'use_unicode': False,
Which has always worked perfectly fine in production. Additionally, I have set my global server charset to 'utf8mb4' and server collation to 'utf8mb4_unicode_ci' for the development database.
All of the tables in the development database are defined with CHARSET=latin1, but that's also true for the production tables.
Any ideas what is going on here? Thanks!
The problem was that I was using the mysql client binary that was installed by mysql, and the protocol must be slightly different with this old (10.1) version of MariaDB. See comment on question.
The solution was to install MariaDB for MacOS, at the proper version, and use /usr/local/mariadb/server/bin/mariadb to connect to my docker database.

Non ASCII colum name in mysql

Can I use UTF-8 names in column name on data base? Like example here:
$zapytaj = mysql_query("SELECT * FROM users WHERE `użytkownicy` = '$nazwaużytkownika' ");
This give me error:
Unknown column 'użytkownicy' in 'where clause'
Can someone explain why this is not working?
mysql> SHOW VARIABLES LIKE 'character%';
+--------------------------+-------------
| Variable_name | Value
+--------------------------+-------------
| character_set_client | utf8mb4
| character_set_connection | utf8mb4
| character_set_database | utf8mb4
| character_set_filesystem | binary
| character_set_results | utf8mb4
| character_set_server | latin1
| character_set_system | utf8
mysql> SELECT COLUMN_NAME, HEX(COLUMN_NAME)
FROM information_schema.columns WHERE table_name = "so31349641";
+--------------+--------------------------+
| COLUMN_NAME | HEX(COLUMN_NAME) |
+--------------+--------------------------+
| id | 6964 |
| użytkownicy | 75C5BC79746B6F776E696379 | -- Note the C5BC for ż
| hasło | 686173C5826F | -- and the C582 for ł
+--------------+--------------------------+
If I delete `` from użytkownicy I see this error:
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '�ytkownicy = 'xxx'' at line 1
Maybe PHP file are don't have UTF8 coding? How to check this file in PHPStorm?
!SOLUTION!
If You have this error just change mysql to PDO that should fix Your problem.
To answer your stated question, column names are utf8:
mysql> SHOW CREATE TABLE information_schema.columns\G
*************************** 1. row ***************************
Table: COLUMNS
Create Table: CREATE TEMPORARY TABLE `COLUMNS` (
`TABLE_CATALOG` varchar(512) NOT NULL DEFAULT '',
`TABLE_SCHEMA` varchar(64) NOT NULL DEFAULT '',
`TABLE_NAME` varchar(64) NOT NULL DEFAULT '',
`COLUMN_NAME` varchar(64) NOT NULL DEFAULT '', -- NOTE --
`ORDINAL_POSITION` bigint(21) unsigned NOT NULL DEFAULT '0',
`COLUMN_DEFAULT` longtext,
`IS_NULLABLE` varchar(3) NOT NULL DEFAULT '',
`DATA_TYPE` varchar(64) NOT NULL DEFAULT '',
`CHARACTER_MAXIMUM_LENGTH` bigint(21) unsigned DEFAULT NULL,
`CHARACTER_OCTET_LENGTH` bigint(21) unsigned DEFAULT NULL,
`NUMERIC_PRECISION` bigint(21) unsigned DEFAULT NULL,
`NUMERIC_SCALE` bigint(21) unsigned DEFAULT NULL,
`DATETIME_PRECISION` bigint(21) unsigned DEFAULT NULL,
`CHARACTER_SET_NAME` varchar(32) DEFAULT NULL,
`COLLATION_NAME` varchar(32) DEFAULT NULL,
`COLUMN_TYPE` longtext NOT NULL,
`COLUMN_KEY` varchar(3) NOT NULL DEFAULT '',
`EXTRA` varchar(30) NOT NULL DEFAULT '',
`PRIVILEGES` varchar(80) NOT NULL DEFAULT '',
`COLUMN_COMMENT` varchar(1024) NOT NULL DEFAULT ''
) ENGINE=MyISAM DEFAULT CHARSET=utf8
To get to the root of the implied question ("Why does the query fail"), let's see
SHOW VARIABLES LIKE 'character%';
Edit
Well, something un-obvious going on. This works for me:
mysql> create table so31349641 (
id int(11) NOT NULL AUTO_INCREMENT,
użytkownicy varchar(24) NOT NULL,
hasło varchar(24) NOT NULL, PRIMARY KEY (id)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
mysql> INSERT INTO so31349641 VALUES (1, 'a', 'b');
mysql> SELECT * FROM so31349641 WHERE użytkownicy = 'a';
+----+--------------+--------+
| id | użytkownicy | hasło |
+----+--------------+--------+
| 1 | a | b |
+----+--------------+--------+
This seems ordinary:
mysql> SHOW VARIABLES LIKE 'character%';
+--------------------------+-------------
| Variable_name | Value
+--------------------------+-------------
| character_set_client | utf8
| character_set_connection | utf8
| character_set_database | latin1
| character_set_filesystem | binary
| character_set_results | utf8
| character_set_server | latin1
| character_set_system | utf8
Looking in the IS:
mysql> SELECT COLUMN_NAME, HEX(COLUMN_NAME)
FROM information_schema.columns WHERE table_name = "so31349641";
+--------------+--------------------------+
| COLUMN_NAME | HEX(COLUMN_NAME) |
+--------------+--------------------------+
| id | 6964 |
| użytkownicy | 75C5BC79746B6F776E696379 | -- Note the C5BC
| hasło | 686173C5826F | -- and the C582 for ł
+--------------+--------------------------+
That is as I would expect it.
My char% values are different than yours, but I think we are both "OK" for this situation.
Try a SELECT on the information_schema similar to what I did.
Next, what is your client? PHP? Something else? Perhaps the encoding is incorrect in the client.
(Rather than trying to use HTML tags in a Comment, Edit your original question with the added info.)
It looks like UTF-8 in SQL is not default, but tables/databases can be changed to be so.
Some potentially helpful links:
The mySQL documentation on charsets:
https://dev.mysql.com/doc/refman/5.0/en/charset.html
A SO question on determining the charset:
determining the character set of a table / database?
On changing the charset: http://makandracards.com/makandra/2529-show-and-change-mysql-default-character-set
Hope this helps.

Discover collation of a MySQL column

I previously created a MySQL table and now I want to find out what collation some of the fields are using. What SQL or MySQL commands can I use to discover this?
You could use SHOW FULL COLUMNS FROM tablename which returns a column Collation, for example for a table 'accounts' with a special collation on the column 'name'
mysql> SHOW FULL COLUMNS FROM accounts;
+----------+--------------+-------------------+------+-----+---------+----------+
| Field | Type | Collation | Null | Key | Default | Extra |
+----------+--------------+-------------------+------+-----+---------+----------|
| id | int(11) | NULL | NO | PRI | NULL | auto_inc |
| name | varchar(255) | utf8_bin | YES | | NULL | |
| email | varchar(255) | latin1_swedish_ci | YES | | NULL | |
...
Or you could use SHOW CREATE TABLE tablename which will result in a statement like
mysql> SHOW CREATE TABLE accounts;
CREATE TABLE `accounts` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin DEFAULT NULL,
`email` varchar(255) DEFAULT NULL,
...
If you want the collation for just that specific column (for possible use with a subquery)...
SELECT COLLATION_NAME
FROM information_schema.columns
WHERE TABLE_SCHEMA = 'tableschemaname'
AND TABLE_NAME = 'tablename'
AND COLUMN_NAME = 'fieldname';
SHOW CREATE TABLE [tablename] will show you the collation of each column as well as the default collation.