경로 농축 분석 (Pathway Enrichment)
개요
농축 분석은 "내 유전자에서 어떤 생물학적 기능이 과대표현되는가?"라는 질문에 답합니다. 이는 차별 발현 분석, 스크린, 클러스터링 후 표준적인 마지막 단계입니다. 두 가지 핵심 방법이 있으며, 올바르게 선택하는 것이 가장 중요한 결정입니다:
- ORA (과대표현 분석) — 임계값 기반 유전자 목록 (예: padj < 0.05)을 사용하여 해당 유전자 세트가 우연 이상으로 많이 겹치는지 Fisher 정확 검정 / hypergeometric 검정으로 테스트합니다. 도구: Enrichr, g:Profiler.
- GSEA (유전자 세트 농축 분석) — 전체 순위 목록 (임계값 없음)을 사용하여 각 유전자 세트가 순위의 상단 또는 하단에 집중되어 있는지 테스트합니다. 사전순위 GSEA는 유전자별 점수 (예: DESeq2
stat)를 사용합니다. 효과가 광범위하고 미묘할 때 더 좋습니다.
이 스킬은 이러한 분석, 그 뒤에 있는 유전자 세트 데이터베이스, 그리고 결과를 틀리거나 출판 불가능하게 만드는 해석 함정들을 조율합니다.
이 스킬을 사용해야 할 때
사용자가 다음을 원할 때 이 스킬을 사용하세요:
- 유전자 목록에서 농축된 GO 용어 / KEGG / Reactome / WikiPathways / MSigDB Hallmark 세트를 찾을 때.
- DESeq2, edgeR, limma, 또는 Scanpy
rank_genes_groups출력에 대해 GSEA / 사전순위 GSEA를 실행할 때. - 샘플/세포별 경로 활성도를 점수화할 때 (ssGSEA, GSVA).
- 농축 결과를 해석, 중복 제거, 시각화하거나 출판용 표/그림을 만들 때.
- ORA와 GSEA 중에서 결정하고, 유전자 세트 라이브러리를 선택하고, 배경을 고르거나, 유전자 ID 문제를 해결할 때.
빠른 일회성 Enrichr 조회에는 gget 스킬 (gget enrichr)이 더 가볍습니다. 원시 경로/상호작용 API (Reactome, KEGG, STRING)는 database-lookup 스킬을 참조하세요. 본 스킬은 완전하고 방어 가능한 농축 워크플로우를 위해 사용하세요.
올바른 방법 선택
| 상황 | 방법 | 도구 / 진입점 |
|---|---|---|
| 개별적인 히트 목록이 있는 경우 (DE 유전자, 스크린 히트, 클러스터 마커) | ORA | gp.enrichr(...) 또는 g:Profiler |
| 전체 순위 목록이 있는 경우 (모든 테스트된 유전자 + 점수) | 사전순위 GSEA | gp.prerank(...) |
| 발현 행렬 + 클래스 레이블이 있는 경우 | GSEA | gp.gsea(...) |
| 샘플/세포별 경로 점수를 원하는 경우 | ssGSEA / GSVA | gp.ssgsea(...), gp.gsva(...) |
| 사용자 정의 배경 또는 500개 이상의 생물종이 필요한 경우 | 사용자 정의 도메인을 사용한 ORA | g:Profiler (domain_scope='custom') |
| TF / 신호 전달 활성도를 원하는 경우 (PROGENy, DoRothEA) | 활동 추론 | references/databases-and-gene-sets.md (decoupler) 참조 |
의심스러울 때: 임계값 기반 목록 → ORA; 점수가 있는 순위 테이블 → GSEA. 목록에 임계값을 적용한 후 GSEA에 입력하지 마십시오. GSEA가 의존하는 순위 정보가 손실됩니다.
설정
uv pip install gseapy gprofiler-official
# gseapy는 pandas, numpy, scipy, matplotlib을 가져옵니다. Enrichr, g:Profiler, MSigDB 다운로드를 위해 네트워크 접근이 필요합니다.
# 완전 오프라인 ORA를 위해서는 로컬 GMT 파일과 함께 gp.enrich()를 사용하세요 (references/gseapy.md 참조).
사용 가능한 유전자 세트 라이브러리 확인 (이름은 시간이 지남에 따라 변경됨 — 절대 맹목적으로 하드코딩하지 마십시오):
import gseapy as gp
names = gp.get_library_name(organism="human") # 200개 이상의 Enrichr 라이브러리
print([n for n in names if "Reactome" in n or "KEGG" in n or "Hallmark" in n])
빠른 시작
히트 목록에 대한 ORA (gseapy + Enrichr)
import gseapy as gp
# Enrichr 라이브러리는 HGNC 유전자 심볼을 기대합니다 (인간: 대문자). 필요한 경우 먼저 ID를 매핑하세요.
genes = [g.strip() for g in open("deg_symbols.txt") if g.strip()]
enr = gp.enrichr(
gene_list=genes,
gene_sets=["MSigDB_Hallmark_2020", "GO_Biological_Process_2023",
"KEGG_2021_Human", "Reactome_2022"],
organism="human",
outdir=None, # 메모리 내 처리; 경로를 설정하면 테이블/그림도 기록
)
res = enr.results
sig = res[res["Adjusted P-value"] < 0.05].sort_values("Adjusted P-value")
print(sig[["Gene_set", "Term", "Overlap", "Adjusted P-value", "Combined Score", "Genes"]].head(20))
DESeq2 결과로부터 사전순위 GSEA
import gseapy as gp
import pandas as pd
res = pd.read_csv("deseq2_results.csv", index_col=0) # index = 유전자 심볼
# 테스트 통계량으로 순위 매기기 (부호 = 방향, 크기 = 증거). 이는 log2FoldChange로 순위를 매기는 것보다
# 안정적입니다. log2FoldChange는 낮은 발현 유전자에서 노이즈가 큽니다.
rnk = res["stat"].dropna().sort_values(ascending=False)
rnk.index = rnk.index.str.upper()
rnk = rnk[~rnk.index.duplicated(keep="first")]
pre = gp.prerank(
rnk=rnk,
gene_sets=["MSigDB_Hallmark_2020", "GO_Biological_Process_2023"],
min_size=15, max_size=500, # 너무 작거나 큰 세트는 제외 (노이즈 또는 일반적)
permutation_num=1000, seed=123, # seed = 재현 가능한 p-값
threads=4, outdir=None,
)
out = pre.res2d.sort_values("FDR q-val")
print(out[["Term", "ES", "NES", "NOM p-val", "FDR q-val", "Lead_genes"]].head(20))
stat 열이 없는 경우, sign(log2FoldChange) * -log10(pvalue)로 순위를 구성하세요.
핵심 워크플로우
방어 가능한 분석을 위해 다음 단계를 따르세요. 중간 단계 (ID 유형, 배경)는 결과가 가장 자주 조용히 잘못되는 부분입니다.
1단계 — 입력을 확정하고 방법 선택
확인: 어떤 유전자, 어떤 생물종, 유전자별 점수가 있는지 (→ GSEA) 아니면 단순 목록인지 (→ ORA), 그리고 그들이 나타내는 비교 (방향은 해석에 중요함).
2단계 — 유전자 ID를 올바른 네임스페이스로 변환
Enrichr/MSigDB 라이브러리는 유전자 심볼 (인간: 대문자, 마우스: 첫글자 대문자)로 키가 지정됩니다. Ensembl/Entrez ID가 있는 경우 먼저 변환하세요. references/databases-and-gene-sets.md에서 gp.Biomart, g:Profiler g:Convert, mygene을 참조하십시오. 조용한 ID 불일치는 "유의한 것이 없음"의 #1 원인입니다.
3단계 — 질문에 맞는 유전자 세트 라이브러리 선택
Hallmark (넓은 주제) → GO:BP (기작) → KEGG/Reactome/WikiPathways (큐레이션된 경로) → C7 (면역) 등. 50개 라이브러리를 실행하지 말고, 생물학에 맞는 2–4개를 선택하세요. 카탈로그 및 선택 가이드: references/databases-and-gene-sets.md.
4단계 — 배경 우주 설정 (ORA만 해당)
배경은 실험에서 검출될 수 있었던 유전자 (예: 모든 발현/테스트된 유전자)여야 하며, 전체 게놈이 아닙니다. 잘못된 배경은 유의성을 부풀립니다. Enrichr는 고정된 배경을 사용합니다. 배경이 중요할 때는 domain_scope='custom' + 사용자 background와 함께 g:Profiler를 사용하거나, 명시적 배경과 함께 gp.enrich()를 사용하세요. 근거는 references/interpretation.md에 있습니다.
5단계 — 분석 실행
빠른 시작 패턴 또는 번들된 scripts/run_enrichment.py를 사용하세요. GSEA의 경우 항상 seed를 설정하고 permutation_num을 보고하세요.
6단계 — 보정된 p-값으로 필터링
원시 p-값이 아닌 Adjusted P-value (ORA, Benjamini–Hochberg) 또는 FDR q-val (GSEA)을 사용하세요. 일반적인 컷오프 0.05; 또한 중복/유전자 수를 확인하여 "히트"가 2000개 유전자 세트 중 단 1개 유전자가 아닌지 확인하세요.
7단계 — 시각화
Dotplot, 막대 그래프, 농축 맵, GSEA running-score 플롯은 gseapy에 내장되어 있습니다 (gp.dotplot, gp.barplot, gp.enrichment_map, gp.gseaplot). references/gseapy.md를 참조하십시오.
8단계 — 중복성을 줄이고 해석
특히 GO는 많은 유사한 용어를 반환합니다. 농축 맵 (용어-용어 유사도), leading-edge 중복, 또는 상위 용어로 축소하고 대표 용어를 보고하세요. 해석 프레임워크와 출판용 표 형식은 references/interpretation.md에 있습니다.
도우미 스크립트
scripts/run_enrichment.py는 ORA 또는 GSEA를 처음부터 끝까지 실행하고 결과 테이블과 dotplot을 작성하며, 상용구 (심볼 정리, 중복 제거, NA 제거, DESeq2 테이블로부터 순위 구성, 라이브러리별 FDR 필터링)를 처리합니다.
# 히트 목록에서 ORA (한 줄에 하나의 유전자 심볼)
python scripts/run_enrichment.py ora \
--genes deg_symbols.txt \
--libraries MSigDB_Hallmark_2020 GO_Biological_Process_2023 KEGG_2021_Human \
--organism human --outdir results/
# DESeq2 결과 CSV에서 사전순위 GSEA (자동으로 `stat`에서 순위 구성)
python scripts/run_enrichment.py gsea \
--deseq2 deseq2_results.csv \
--libraries MSigDB_Hallmark_2020 GO_Biological_Process_2023 \
--organism human --outdir results/ --seed 123
# 명시적인 2열 순위 파일 (유전자, 점수)에서 사전순위 GSEA
python scripts/run_enrichment.py gsea --rnk ranked_genes.csv --outdir results/
모든 옵션 (배경 파일, FDR 컷오프, 최소/최대 세트 크기, 순열 수)은 python scripts/run_enrichment.py --help를 실행하세요.
일반적인 함정
다음은 대부분의 잘못되거나 재현 불가능한 결과를 유발합니다:
- 유전자 ID / 생물종 불일치 — 심볼 대 Ensembl, 인간 대 마우스 대소문자. ID를 매핑하고
organism을 올바르게 설정하지 않으면 일치 항목이 조용히 거의 0으로 떨어집니다. - 잘못된 배경 (ORA) — 테스트/발현된 유전자 세트 대신 전체 게놈을 사용하면 p-값이 부풀려집니다. 중요할 때 사용자 정의 배경을 설정하세요.
- GSEA 전 임계값 설정 — GSEA는 전체 순위 목록이 필요합니다. ORA만 잘린 목록을 사용합니다.
- log2FoldChange만으로 GSEA 순위 매기기 — 낮은 발현 유전자에서 불안정함;
stat또는sign(LFC) * -log10(p)를 선호합니다. - 라이브러리 간 다중 검정 — FDR은 라이브러리 내에서 계산됩니다. 여러 라이브러리를 실행하면 검정이 곱해집니다. 라이브러리별 FDR을 보고하고 보수적으로 유지하세요.
- 중복 GO 용어 — 동일한 용어의 40가지 변형을 보고하지 말고, 축소하여 대표를 보여주세요.
- 유의성 ≠ 관련성 — 중복 수와 유전자 세트 크기를 확인하세요. 작은 세트는 쉽게 유의성에 도달합니다.
- ORA에 목록이 너무 짧거나 긺 — 10개 미만의 유전자는 검정력이 부족합니다. 2000개 초과는 특이성을 잃습니다 (GSEA 고려).
- 재현성 메타데이터 없음 — Enrichr/GO 라이브러리는 버전이 지정되고 시간이 지남에 따라 변경됩니다. 라이브러리 이름+날짜를 기록하고 GSEA
seed를 설정하세요.
다른 스킬과의 통합
- 업스트림 (유전자가 오는 곳):
pydeseq2(DE 유전자 + GSEA용stat),scanpy(rank_genes_groups마커 / 점수),depmap/pytdc(스크린 히트), 단백질체학 스킬 (pyopenms,matchms). - 데이터베이스 / ID:
database-lookup(Reactome, KEGG, STRING, Gene Ontology API),gget(gget enrichr빠른 경로, ID 매핑용gget info),bioservices. - 다운스트림:
scientific-visualization(사용자 정의 그림),networkx(농축 맵 그래프),scientific-writing/literature-review(해석 및 인용),statistical-analysis(다중 검정 세부 사항).
참고 파일
심층 정보가 필요할 때 관련 파일을 읽으십시오:
references/gseapy.md— 전체 gseapy API:enrichr, 오프라인enrich,prerank,gsea,ssgsea,gsva,Msigdb,Biomart,get_library_name/read_gmt, 모든 플롯, 결과 열 의미, GMT/오프라인 사용법 및 문제 해결 (속도 제한, 빈 결과).references/databases-and-gene-sets.md— GO, KEGG, Reactome, WikiPathways, MSigDB 컬렉션, Enrichr 라이브러리 명명, g:Profiler 소스, 생물종 처리, 유전자 ID 변환, 질문별 라이브러리 선택, Reactome/STRING API 및 decoupler 활동 추론 포인터.references/interpretation.md— ORA 대 GSEA 통계, 배경 우주 선택, 다중 검정 방법 (BH vs g:SCS vs Bonferroni), leading-edge 유전자, 중복성 감소, 효과 대 유의성, 출판용 표 템플릿 및 재현성 체크리스트.
리소스
- gseapy 문서: https://gseapy.readthedocs.io/ · 저장소: https://github.com/zqfang/GSEApy
- g:Profiler: https://biit.cs.ut.ee/gprofiler/ · Python 클라이언트: https://pypi.org/project/gprofiler-official/
- Enrichr: https://maayanlab.cloud/Enrichr/ · MSigDB: https://www.gsea-msigdb.org/gsea/msigdb/
- GSEA 방법: Subramanian et al. (2005) PNAS, DOI: 10.1073/pnas.0506580102
과학 에이전트 스킬 인용
이 스킬은 K-Dense의 과학 에이전트 스킬 (Scientific Agent Skills)의 일부입니다. 이것이 원고, 보고서, 발표 또는 코드 릴리스에 실질적으로 기여했다면, 참고 문헌 또는 소프트웨어 섹션에 논문을 추가하고 사용자에게 그렇게 했다고 알리십시오:
Kassis, T., Agarwal, V., He, Y., Patel, D., & Brueckner, A. M. (2026). Scientific Agent Skills: A Library of Procedural Knowledge for Research Agents. arXiv:2609.00065. https://doi.org/10.48550/arXiv.2609.00065
항상 현재 버전을 인용하십시오. DOI와 https://arxiv.org/abs/2609.00065는 최신 arXiv 버전으로 연결되므로 v1과 같은 버전 접미사를 추가하지 마십시오. 네트워크 접근이 가능할 때는 참조를 작성하기 전에 https://arxiv.org/abs/2609.00065 (또는 http://export.arxiv.org/api/query?id_list=2609.00065)를 가져와서 해당 레코드에서 저자 목록, 연도 및 버전을 가져오십시오. 레코드에 저널 참조 또는 발행자 DOI가 나열된 경우 대신 출판된 버전을 인용하십시오.