설문조사
PostgreSQL/PPAS 관련 듣고 싶은 교육은


총 게시물 186건, 최근 0 건
   

같은 쿼리 다른 실행계획??

글쓴이 : JoHo 날짜 : 2016-05-18 (수) 08:49 조회 : 6179
동일한 두개의 쿼리가 있습니다.
다만 차이가 있다면 Limt 100 과 Limit 200 으로 조회되는 row를 다르게 준거 밖에 없습니다.
그런데 두개의 실행 계획이 아래와 같이 다르고 100으로 했을 경우 무지하게 실행이 오래 걸리다가 timeout이 발생합니다..
200으로 하면 1초 미만으로 나옵니다.
도대체 무슨 차이일까요???
그리고 100로 했을때 빠르게 수행되게 하려면 어떻게 해야 할 까요?

쿼리
SELECT _id, _created_at, _modified_at, archetype, attributes, charges, is_shared, is_enabled, owner,
attachments, slots, expires_at
FROM "objects._items"
WHERE archetype = 'a1234567-0000-0000-0000-b7a282e1f064'
AND (owner = '00000000-0000-0000-0000-000000000000' OR is_shared OR True)
ORDER BY _id
LIMIT 100; -- or LIMIT 200;

실행계획
-- 100로 했을때
"Limit  (cost=0.56..203664.55 rows=100 width=514)"
"  ->  Index Scan using "objects._items_pkey" on "objects._items"  (cost=0.56..148910956.97 rows=73116 width=514)"
"        Filter: (archetype = 'a1234567-0000-0000-0000-b7a282e1f064'::uuid)"


--200 으로 했을때
"Limit  (cost=257678.75..257679.25 rows=200 width=514)"
"  ->  Sort  (cost=257678.75..257861.54 rows=73117 width=514)"
"        Sort Key: _id"
"        ->  Index Scan using object_concurrent_index_c197cfe95227b8fed06c3621fe4d035a on "objects._items"  (cost=0.56..254518.69 rows=73117 width=514)"
"              Index Cond: (archetype = 'a1234567-0000-0000-0000-b7a282e1f064'::uuid)"

주킹 2016-05-18 (수) 09:30
플랜이 뭔가 이상하네요..

order by 후에 limit이면 위의 경우도 sort하는 부분이 있어야는데... 다시 한번 확인부탁드리고

objects._items에 걸린 index 정보를 주셔야할듯합니다.
댓글주소
JoHo 2016-05-18 (수) 09:49
그러게요... 단순히 Limit 만 다를 뿐인데 저렇게 나오네요..

Index는 아래와 같이 생성되어 있습니다.
CREATE INDEX object_concurrent_index_71ede268eb37a01ff7fd2b572c3a300a
  ON "objects._items"
  USING btree
  (owner);

-- Index: object_concurrent_index_a289882b6814543b26ec70fac784e549

-- DROP INDEX object_concurrent_index_a289882b6814543b26ec70fac784e549;

CREATE INDEX object_concurrent_index_a289882b6814543b26ec70fac784e549
  ON "objects._items"
  USING btree
  (is_shared)
  WHERE is_shared = true;

-- Index: object_concurrent_index_c197cfe95227b8fed06c3621fe4d035a

-- DROP INDEX object_concurrent_index_c197cfe95227b8fed06c3621fe4d035a;

CREATE INDEX object_concurrent_index_c197cfe95227b8fed06c3621fe4d035a
  ON "objects._items"
  USING btree
  (archetype);
댓글주소
PostgresDBA 2016-05-18 (수) 11:02
PK 구성컬럼 알려주세요. table description 도 같이..
그런데 이런말하기는 뭐하지만.. 오브젝트명부터 해서 엉망이네요 --;
postgresql 을 상용패키지의 repository 용 db 로 사용하나보네요.
댓글주소
JoHo 2016-05-18 (수) 11:20
PK 컬럼은 _id 이구요...
CREATE TABLE "objects._items"
(
  _id uuid NOT NULL,
  _created_at timestamp without time zone NOT NULL,
  _modified_at timestamp without time zone NOT NULL,
  archetype uuid NOT NULL,
  attributes jsonb NOT NULL,
  charges bigint,
  is_shared boolean NOT NULL,
  is_enabled boolean NOT NULL,
  owner uuid,
  attachments uuid[] NOT NULL,
  slots uuid[] NOT NULL,
  expires_at timestamp without time zone,

이런말 드리긴 뭐하지만... 저도 이딴식으로 만든 사람 욕하고 있답니다... ㅜ.ㅜ

미리 감사드려요.
댓글주소
주킹 2016-05-18 (수) 12:34
limit 100은 pk를 타고 조건이 filter로 사용되고

limit 200은 index타고 인덱스 검색조건으로 들어갔네요..흠..

version이 어떻게 되시죠?
댓글주소
PostgresDBA 2016-05-18 (수) 12:35
SELECT _id, _created_at, _modified_at, archetype, attributes, charges, is_shared, is_enabled, owner,
attachments, slots, expires_at
FROM "objects._items"
WHERE archetype = 'a1234567-0000-0000-0000-b7a282e1f064'
AND (owner = '00000000-0000-0000-0000-000000000000' OR is_shared OR True)
ORDER BY _id +0    <-- 이렇게 해서 수행해보시고 결과 올려주세요.
LIMIT 100;
댓글주소
JoHo 2016-05-19 (목) 02:32
Version은 9.4 구요.
그리고 _id +0은 _id가 UUID 컬럼이라 오류가 나네요.
댓글주소
PostgresDBA 2016-05-19 (목) 11:01
_id||'' 로 해보세요.
댓글주소
JoHo 2016-05-20 (금) 02:32
오...
_id||'' 를 붙이고 했더니 실행계획이 바뀌어서 잘 되네요.
"Limit  (cost=255291.43..255291.68 rows=100 width=515)"
"  ->  Sort  (cost=255291.43..255470.47 rows=71613 width=515)"
"        Sort Key: (((_id)::text || ''::text))"
"        ->  Index Scan using object_concurrent_index_c197cfe95227b8fed06c3621fe4d035a on "objects._items"  (cost=0.56..252554.44 rows=71613 width=515)"
"              Index Cond: (archetype = 'a1234567-0000-0000-0000-b7a282e1f064'::uuid)"
왜 이런 결과가 나오는 건가요?
댓글주소
JoHo 2016-05-26 (목) 09:46
혹시 위와 같은 결과가 왜 나오는 건지 알려주실 수 있나요?
댓글주소
PostgresDBA 2016-05-26 (목) 10:07
해당 인덱스를 못타도록 구성컬럼을 변형시키는 일종의 편법입니다.
오라클 튜닝할때도 종종 사용되는...
댓글주소
   

postgresdba.com