【问题标题】:PostgreSQL slow query over rankedPostgreSQL 慢查询超过排名
【发布时间】:2021-10-01 09:50:04
【问题描述】:

我有一个查询运行速度非常慢(900 毫秒,有时甚至 3-4 秒) 由于表很大,查询非常简单且缓慢,但对于慢速服务器则不然。我在 Aurora RDS 无服务器上运行。我在问有没有更好的方法。我只想用他的最新值加入两个表之间。我使用 created_at 排名排序

SELECT t1.* From (select msv.*, rank() OVER ( PARTITION BY machine_setting_id ORDER BY msv.created_at DESC )
                  as ranked from machine_setting_values msv inner join tasks t on t.id = msv.task_id inner join machine_settings ms
                  on ms.id = msv.machine_setting_id where t.work_order_id = 777 ) t1 where t1.ranked = 1

这是对查询的解释。有什么帮助可以做得更好吗?我做错了什么?

DDL + 索引

//machine settings table
CREATE TABLE IF NOT EXISTS public.machine_settings
(
    id bigint NOT NULL,
    key character varying(255) COLLATE pg_catalog."default" NOT NULL,
    name character varying(255) COLLATE pg_catalog."default",
    type character varying(255) COLLATE pg_catalog."default",
    unit character varying(255) COLLATE pg_catalog."default",
    machine_id bigint,
    position_in_list integer,
    impact character varying(1024) COLLATE pg_catalog."default",
    offline boolean NOT NULL DEFAULT false,
    parameter_type integer NOT NULL DEFAULT 0,
    owner_uuid uuid,
    CONSTRAINT machine_settings_pkey PRIMARY KEY (id),
    CONSTRAINT machine_id_to_key_constraint UNIQUE (machine_id, key),
    CONSTRAINT fkgwgt4t00xcqaqp5yp54ojvjqn FOREIGN KEY (machine_id)
        REFERENCES public.machines (id) MATCH SIMPLE
        ON UPDATE NO ACTION
        ON DELETE NO ACTION
)
CREATE INDEX machine_settings_key_idx
    ON public.machine_settings USING btree
    (key COLLATE pg_catalog."default" ASC NULLS LAST)
    TABLESPACE pg_default;
CREATE INDEX owner_id_machine_settings_index
    ON public.machine_settings USING btree
    (owner_uuid ASC NULLS LAST)
    TABLESPACE pg_default;

//Tasks table 
CREATE TABLE IF NOT EXISTS public.tasks
(
    id bigint NOT NULL,
    item_uuid uuid NOT NULL,
    type integer NOT NULL,
    created_at timestamp with time zone,
    updated_at timestamp with time zone,
    status integer NOT NULL DEFAULT 0,
    work_order_id bigint,
    owner_uuid uuid,
    CONSTRAINT tasks_pkey PRIMARY KEY (id),
    CONSTRAINT uk_hlgan0jf8stp23qon7hfq3fbr UNIQUE (item_uuid)
)
CREATE INDEX owner_id_tasks_index
    ON public.tasks USING btree
    (owner_uuid ASC NULLS LAST)
    TABLESPACE pg_default;
CREATE INDEX tasks_item_uuid_idx
    ON public.tasks USING btree
    (item_uuid ASC NULLS LAST)
    TABLESPACE pg_default;

CREATE INDEX tasks_time_range_idx
    ON public.tasks USING btree
    (created_at ASC NULLS LAST, updated_at DESC NULLS FIRST)
    TABLESPACE pg_default;

//machine settings values table
CREATE TABLE IF NOT EXISTS public.machine_setting_values
(
    id bigint NOT NULL,
    value character varying(255) COLLATE pg_catalog."default",
    machine_setting_id bigint,
    centerline_value character varying(255) COLLATE pg_catalog."default",
    feedback_id bigint,
    created_at timestamp with time zone NOT NULL DEFAULT now(),
    status integer,
    task_id bigint,
    min_value character varying(255) COLLATE pg_catalog."default",
    max_value character varying(255) COLLATE pg_catalog."default",
    owner_uuid uuid,
    CONSTRAINT machine_setting_values_pkey PRIMARY KEY (id),
    CONSTRAINT fk3w46u5qq6vkgd1hji8aey1usk FOREIGN KEY (machine_setting_id)
        REFERENCES public.machine_settings (id) MATCH SIMPLE
        ON UPDATE NO ACTION
        ON DELETE NO ACTION,
    CONSTRAINT machine_setting_values_feedback_id_fkey FOREIGN KEY (feedback_id)
        REFERENCES public.feedbacks (id) MATCH SIMPLE
        ON UPDATE NO ACTION
        ON DELETE NO ACTION
)
CREATE INDEX owner_id_machine_setting_values_index
    ON public.machine_setting_values USING btree
    (owner_uuid ASC NULLS LAST)
    TABLESPACE pg_default;

【问题讨论】:

  • Edit 问题并为所有涉及的表及其上的所有索引添加 DDL。
  • 显示EXPLAIN (ANALYZE, BUFFERS)的输出,而不仅仅是EXPLAIN
  • 感谢@stickybit 的提示
  • 谢谢@jjanes 的额外解释。

标签: sql postgresql performance


【解决方案1】:

索引on machine_setting_values (task_id) 可能是您最好的选择。这样你就不需要完全扫描 machine_settigs_values 来获取匹配的行,你可以使用嵌套循环。但是如果不试一试,就无法确定它是否会起作用(尤其是因为估计值相差甚远,预测为 1043 与实际为 57)。

但如果您还没有这样做,您应该在执行任何其他操作之前对所有涉及的表进行 VACUUM ANALYZE。

【讨论】:

  • 再次感谢@jjanes 我将进行真空分析并尝试索引。我会让你知道结果
  • 有了索引,我的性能得到了很大的提升。祝你周日愉快!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-28
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多