小编Ric*_*mes的帖子

备份/恢复用户/密码/权限

我正在从一台服务器移动到另一台服务器,我想从我的 MySQL 服务器备份所有数据库 + 用户/权限/密码。我发现使用 备份数据库mysqldump,但我不知道如何备份所有用户和给定的权限。有没有办法实现这一点,还是我必须在新服务器上重新设置?

mysql migration installation

20
推荐指数
1
解决办法
7万
查看次数

如何在 MySQL Workbench 的所有表中搜索特定列名?

在 MySQL Workbench 中,是否可以在所有表​​中搜索特定列名?

(在右上角的字段中编写要查找的字符串没有任何作用)。

谢谢你。

mysql mysql-workbench

19
推荐指数
3
解决办法
6万
查看次数

具有多个变体/属性的产品的架构设计?

我正在使用 MySQL。这个想法类似于 shopify 具有不同的概念,因此用户将添加具有多种类型的变体和属性的产品。

从我所做的所有研究来看,这对我来说似乎是最有可能的解决方案,我只是想知道以下模式是否有任何问题以及有哪些优点/缺点?

谢谢

Table: products
------------------------------
| ID | ProductName           |
|----------------------------| 
| 1  | Leather Wallet Case   |
| 2  | Jeans                 |
| 3  | Power Bank            |



Table: products_variants
-------------------------------
| ID | ProductId | ParentId | Variant  | VariantName | SKU  | StockTotal | WholeSalePrice | BuyPrice | OnSale | OnSalePrice |
|---------------------------------------------------------------------------------------------------------------------------|
| 1  | 1         | null     | model    | iPhone5     | SKU  | 10         | 3              | 10       | null …
Run Code Online (Sandbox Code Playgroud)

mysql schema database-design eav

18
推荐指数
2
解决办法
5万
查看次数

MySQL 索引维护

我对如何在 MySQL 中维护索引以防止碎片化并以某种方式优化某些查询的执行进行了大量研究。

我熟悉计算表可用的最大空间与数据和索引使用的空间之间的比率的公式。

但是,我的主要问题仍未得到解答。也许这是因为我熟悉SQL Server中的索引维护,并且我倾向于认为在MySQL中它应该在某种程度上相似。

在 SQL Server 中,您可以有多个索引,并且每个索引都可以具有不同级别的碎片。然后,您可以选择一个并在该特定索引中执行“重组”或“重建”操作,而不会影响其余部分。

据我所知,没有这样的“表碎片”,并且 SQL Server 不提供任何工具来修复“表碎片”。它提供的是检查索引碎片的工具(理解为索引使用的页面数量与该页面的完整度和连续性之间的比率),以及内部和外部碎片。

所有这些都很容易理解,至少对我来说是这样。

现在,轮到在 MySQL 中维护索引时,只存在“表碎片”的概念,如上所述。

MySQL 中的一个表可以有多个索引,但是当我用那个著名的公式检查“碎片率”时,我没有看到每个索引的碎片,而是整个表。

当我想优化 MySQL 中的索引时,我不会选择要操作的特定索引(如在 SQL Server 中)。相反,我在整个表中执行“优化”操作,这可能会影响所有索引。

当在 MySQL 中优化表时,数据 + 索引使用的空间与整体空间之间的比率减少,这表明硬盘驱动器中进行了某种物理重组,这转化为物理空间的减少。但是,索引碎片不仅与物理空间有关,还与由于插入和更新而随时间发生变化的树结构有关。

最后,我在 InnoDB/MySQL 中得到了一张表。该表有 300 万条记录、105 列和 55 个索引。它是 1.5GB,不包括索引,即 2.1GB。

该表每天都会被访问数千次以进行更新、插入(我们实际上并没有删除记录)。

该表已创建多年,我确信没有人在维护任何索引。

我期待在那里找到一个巨大的碎片,但是当我按照规定执行碎片计算时

free_space / (data_length + index_length)
Run Code Online (Sandbox Code Playgroud)

事实证明,我只有 0.2% 的碎片。恕我直言,这是非常不现实的。

所以最大的问题是:

  1. 如何检查 MySQL 中特定索引的碎片,而不是整个表
  2. OPTIMIZE TABLE 是否真的像在 SQL Server 中一样修复了索引的内部/外部碎片?
  3. 当我在 MySQL 中优化一个表时,它是否真的重建了表上的所有索引?
  4. 认为减少索引的物理空间(而不重建树本身)实际上可以转化为更好的性能是否现实?

mysql fragmentation index-maintenance

12
推荐指数
2
解决办法
1万
查看次数

身份栏重新播种:什么时候需要?

在大学的最后一节课(我是学生)中,讲师要求我们开发一个数据库(如果重要的话,MySQL 服务器)和使用该数据库作为数据源的小型客户端应用程序。

要求之一是标识列(即每个表中的 PK)必须是连续的,因为这是一个很好的做法(按照讲师的话)。也就是说,当表行被删除时,它的 PK 必须在后续插入中重用。我对 RDBMS、PK 和身份列有一般的了解。据我了解,该标识列只是一种让 DB 在插入行时自动生成 PK 的方法,仅此而已。并且标识列值不得以任何方式与行属性相关(只要它不是自然键)。

这个要求(严格顺序标识列)对我来说是可疑的。我试图问讲师如果身份不是顺序的(由删除引起的差距)有什么问题,但得到了非常抽象的答案,比如“这对用户来说很方便,对维护数据库的数据库管理员很有用”。没有具体的例子。“方便用户”的说法听起来很傻,因为它在业务领域没有任何意义。

因此,我很好奇这些原因是否真实?我只能想到一种需要重新设置身份列的情况——当身份空间耗尽时。但是当标识列类型选择不正确时,这是更多的设计问题,说简单int而不是bigintuniqueidentifier当表包含十亿行。假设,一个标识列是一个聚集索引:标识列中的间隙会影响索引性能吗?也许我不知道在每次删除后自动标识列重新播种的其他现实原因?

提前致谢!

mysql auto-increment identity

12
推荐指数
3
解决办法
1430
查看次数

为什么这个查询会导致死锁?

我在下面提供了原始 MySQL 查询以及我以编程方式执行此操作的代码。如果同时执行两个请求会导致以下错误模式:

SQLSTATE[40001]:序列化失败:1213 尝试获取锁时发现死锁;请尝试重新启动交易(SQL: update user_chats set updated_at = 2018-06-29 10:07:13 where id = 1

如果我执行相同的查询但没有事务块,它将在许多并发调用中正常工作而不会出错。为什么 ?(交易获得锁,对吗?)

有没有办法在不锁定整个表的情况下解决这个问题?(想尽量避免表级锁)

我知道使用 InnoDB 在 MySql 中插入/更新/删除表需要锁定,但仍然不明白为什么会在这里发生死锁以及如何以最有效的方式解决它。

    START TRANSACTION;

    insert into `user_chat_messages` (`user_chat_id`, `from_user_id`, `content`)
        values (1, 2, 'dfasfdfk);
    update `user_chats`
        set `updated_at` = '2018-06-28 08:33:14' where `id` = 1;

    COMMIT;
Run Code Online (Sandbox Code Playgroud)

以上是原始查询,但我在 PHP Laravel Query Builder 中执行如下:

    /**
     * @param UserChatMessageEntity $message
     * @return int
     * @throws \Exception
     */
    public function insertChatMessage(UserChatMessageEntity $message) : int
    {
        $this->db->beginTransaction();
        try
        {
            $id = $this->db->table('user_chat_messages')->insertGetId([ …
Run Code Online (Sandbox Code Playgroud)

mysql deadlock transaction

8
推荐指数
1
解决办法
1万
查看次数

为什么查询优化器会选择这种糟糕的执行计划?

我们有一个包含超过 1TB 数据的 mariadb 表(故事),定期运行一个查询来获取最近添加的行以在其他地方建立索引。

innodb_version: 5.6.36-82.1
version       : 10.1.26-MariaDB-0+deb9u1
Run Code Online (Sandbox Code Playgroud)

当查询优化器决定使用二级索引进行范围遍历(以 1000 为单位)时,查询工作正常

explain extended     SELECT  stories.item_guid
    FROM  `stories`
    WHERE  (updated_at >= '2018-09-21 15:00:00')
      AND  (updated_at <= '2018-09-22 05:30:00')
    ORDER BY  `stories`.`id` ASC
    LIMIT  1000;

+------+-------------+---------+-------+-----------------------------+-----------------------------+---------+------+--------+----------+---------------------------------------+
| id   | select_type | table   | type  | possible_keys               | key                         | key_len | ref  | rows   | filtered | Extra                                 |
+------+-------------+---------+-------+-----------------------------+-----------------------------+---------+------+--------+----------+---------------------------------------+
|    1 | SIMPLE      | stories | range | index_stories_on_updated_at | index_stories_on_updated_at | 5       | NULL | 192912 |   100.00 …
Run Code Online (Sandbox Code Playgroud)

innodb mariadb execution-plan

7
推荐指数
1
解决办法
944
查看次数

MySQL Processlist 中的统计信息

我有一个busy MySQL Server查询

SELECT  sys_sess_state, index_state, timeout_lvl, last_queued_dt,
        last_polled_wait_dt, create_id, create_dt, modify_id,
        modify_dt
    FROM  PQR_AM_SYSTEM_SESSION
    WHERE  (pqr_sess_id=592885621) FOR UPDATE  
Run Code Online (Sandbox Code Playgroud)

哪里pqr_sess_idPrimary Key在表中。

当我独立执行查询时,它正在完成,0.00 secs,但我多次观察到挂起的查询是带有状态统计信息的进程列表。

可能是什么问题,我在慢日志中发现此查询的计数超过 10K 次。

mysql> show full processlist;
+------+-----------------+---------------------+-----------+---------+------+-----------------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Id   | User            | Host                | db        | Command | Time | State                       | Info                                                                                                                                                                                                                                                                                                         |
+------+-----------------+---------------------+-----------+---------+------+-----------------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| 2899 | root            | 192.168.9.217:49340 | abdulrony | Query   |   58 | statistics                  | SELECT sys_sess_state, index_state, timeout_lvl, last_queued_dt, last_polled_wait_dt, …
Run Code Online (Sandbox Code Playgroud)

mysql performance transaction mysql-5.1 query-performance

6
推荐指数
1
解决办法
2万
查看次数

根据先进先出 (FIFO) 计算数量

我正在尝试根据 FIFO 获取数量结果,下面有 2 个表:

表购买:

| PO    | Date         | Quantity | Item | 
|-------|--------------|----------|------|
| PO001 | 01-Jan-2016  | 3        | AO21 |  
| PO002 | 10-Jan-2016  | 7        | AO21 |  
| PO003 | 01-Feb-2016  | 3        | AO21 |  
Run Code Online (Sandbox Code Playgroud)

表库存:

| SO    | Date        | Quantity | Item |
|-------|-------------|----------|------|
| SO001 | 02-Jan-2016 | 2        | AO21 |
| SO002 | 11-Feb-2016 | 8        | AO21 |
| SO003 | 12-Feb-2016 | 6        | AO23 …
Run Code Online (Sandbox Code Playgroud)

mysql running-totals

6
推荐指数
1
解决办法
6099
查看次数

将值传递给嵌套子查询

我有以下查询(为简洁起见已删除),其目的是创建w8用于对结果进行排序的值:

SELECT elements.id, [ ... ],
(SELECT 
    COALESCE(craft_w8_a.weight, 0) + COALESCE(SUM(craft_w8_b.weight), 0) 
    FROM `craft_w8` `craft_w8_a`
    LEFT JOIN `craft_w8` `craft_w8_b` 
        ON craft_w8_b.elementId
        IN ( SELECT targetId FROM `craft_relations`
                WHERE fieldId IN (15, 16)
                  AND sourceId = elements.id)
    WHERE craft_w8_a.elementId = elements.id
) as w8
FROM `craft_elements` `elements`
[ ... ]
GROUP BY `elements`.`id`
ORDER BY `w8` DESC, `name` ASC LIMIT 100
Run Code Online (Sandbox Code Playgroud)

我遇到的问题是第二个嵌套子查询(左连接中的那个)无法elements.id从初始选择中找到该列。

从我发现在 SQL 中搜索只传递一级深度的值,我一直无法找到合适的解决方法。

是否可以强制 SQL 传递比一级更深的值?或者有没有办法修改查询以不使用另一个子查询,但仍然得到相同的结果?

对不起,如果我做任何愚蠢的事情或遗漏了任何明显的东西,SQL 不是我的强项!

mysql subquery

6
推荐指数
1
解决办法
3万
查看次数