diff --git a/browser/src/VariantList/mergeExomeAndGenomeData.spec.ts b/browser/src/VariantList/mergeExomeAndGenomeData.spec.ts index 5bb03ae12..e93c09361 100644 --- a/browser/src/VariantList/mergeExomeAndGenomeData.spec.ts +++ b/browser/src/VariantList/mergeExomeAndGenomeData.spec.ts @@ -163,7 +163,10 @@ describe('mergeExomeAndGenomeData', () => { ac_hom: 3, an: 4, af: 5, - faf95: undefined, + faf95: { + popmax: null, + popmax_population: null, + }, filters: ['RF'], populations: exomeGeneticAncestryGroupObjects, }, @@ -178,9 +181,8 @@ describe('mergeExomeAndGenomeData', () => { ac_hemi: 2, ac_hom: 3, an: 4, - af: 5, - allele_freq: 5, - faf95: undefined, + af: 0.25, + allele_freq: 0.25, filters: ['RF'], populations: exomeGeneticAncestryGroupObjects, }, @@ -201,9 +203,12 @@ describe('mergeExomeAndGenomeData', () => { ac: 2, ac_hemi: 3, ac_hom: 4, + faf95: { + popmax: null, + popmax_population: null, + }, an: 5, af: 6, - faf95: undefined, filters: ['AC0'], populations: genomeGeneticAncestryGroupObjects, }, @@ -218,9 +223,8 @@ describe('mergeExomeAndGenomeData', () => { ac_hemi: 3, ac_hom: 4, an: 5, - af: 6, - allele_freq: 6, - faf95: undefined, + af: 0.4, + allele_freq: 0.4, filters: ['AC0'], populations: genomeGeneticAncestryGroupObjects, }, @@ -249,8 +253,11 @@ describe('mergeExomeAndGenomeData', () => { ac: 1, ac_hemi: 2, ac_hom: 3, + faf95: { + popmax: null, + popmax_population: null, + }, an: 4, - faf95: undefined, filters: ['RF'], populations: exomeGeneticAncestryGroupObjects, }, @@ -258,8 +265,11 @@ describe('mergeExomeAndGenomeData', () => { ac: 2, ac_hemi: 3, ac_hom: 4, + faf95: { + popmax: null, + popmax_population: null, + }, an: 6, - faf95: undefined, filters: ['AC0'], populations: genomeGeneticAncestryGroupObjects, }, @@ -306,9 +316,12 @@ describe('mergeExomeAndGenomeData', () => { ac: 1, ac_hemi: 2, ac_hom: 3, + faf95: { + popmax: null, + popmax_population: null, + }, an: 4, af: 5, - faf95: undefined, filters: ['RF'], populations: exomeGeneticAncestryGroupObjects, }, @@ -316,9 +329,14 @@ describe('mergeExomeAndGenomeData', () => { ac: 10, hemizygote_count: 20, homozygote_count: 30, + fafmax: { + faf95_max: null, + faf95_max_gen_anc: null, + faf99_max: null, + faf99_max_gen_anc: null, + }, an: 40, - faf95: undefined, - filters: ['RF'], + filters: ['discrepant_frequencies'], populations: jointGeneticAncestryGroupObjects, }, }) @@ -329,12 +347,12 @@ describe('mergeExomeAndGenomeData', () => { { ...testExomeAndJointVariant, ac: 10, - hemizygote_count: 20, - homozygote_count: 30, + ac_hemi: 20, + ac_hom: 30, an: 40, + af: 0.25, allele_freq: 0.25, - faf95: undefined, - filters: ['RF'], + filters: ['RF', 'discrepant_frequencies'], populations: jointGeneticAncestryGroupObjects, }, ] @@ -359,9 +377,12 @@ describe('mergeExomeAndGenomeData', () => { ac: 1, ac_hemi: 2, ac_hom: 3, + faf95: { + popmax: null, + popmax_population: null, + }, an: 4, af: 5, - faf95: undefined, filters: ['RF'], populations: genomeGeneticAncestryGroupObjects, }, @@ -369,9 +390,14 @@ describe('mergeExomeAndGenomeData', () => { ac: 10, hemizygote_count: 20, homozygote_count: 30, + fafmax: { + faf95_max: null, + faf95_max_gen_anc: null, + faf99_max: null, + faf99_max_gen_anc: null, + }, an: 40, - faf95: undefined, - filters: ['RF'], + filters: ['discrepant_frequencies'], populations: jointGeneticAncestryGroupObjects, }, }) @@ -382,12 +408,12 @@ describe('mergeExomeAndGenomeData', () => { { ...testGenomeAndJointVariant, ac: 10, - hemizygote_count: 20, - homozygote_count: 30, + ac_hemi: 20, + ac_hom: 30, an: 40, + af: 0.25, allele_freq: 0.25, - faf95: undefined, - filters: ['RF'], + filters: ['RF', 'discrepant_frequencies'], populations: jointGeneticAncestryGroupObjects, }, ] @@ -421,7 +447,10 @@ describe('mergeExomeAndGenomeData', () => { ac_hom: 3, an: 4, af: 5, - faf95: undefined, + faf95: { + popmax: null, + popmax_population: null, + }, filters: ['RF'], populations: exomeGeneticAncestryGroupObjects, }, @@ -431,7 +460,10 @@ describe('mergeExomeAndGenomeData', () => { ac_hom: 5, an: 6, af: 5, - faf95: undefined, + faf95: { + popmax: null, + popmax_population: null, + }, filters: ['AC0'], populations: genomeGeneticAncestryGroupObjects, }, @@ -440,7 +472,12 @@ describe('mergeExomeAndGenomeData', () => { hemizygote_count: 20, homozygote_count: 30, an: 40, - faf95: undefined, + fafmax: { + faf95_max: null, + faf95_max_gen_anc: null, + faf99_max: null, + faf99_max_gen_anc: null, + }, filters: ['discrepant_frequencies'], populations: jointGeneticAncestryGroupObjects, }, @@ -458,12 +495,7 @@ describe('mergeExomeAndGenomeData', () => { af: 0.25, allele_freq: 0.25, filters: ['RF', 'AC0', 'discrepant_frequencies'], - populations: [ - { ac: 9, ac_hemi: 11, ac_hom: 13, an: 90, id: 'afr' }, - { ac: 18, ac_hemi: 20, ac_hom: 22, an: 180, id: 'remaining' }, - { ac: 36, ac_hemi: 38, ac_hom: 40, an: 360, id: 'eur' }, - { ac: 64, ac_hemi: 65, ac_hom: 66, an: 640, id: 'mid' }, - ], + populations: jointGeneticAncestryGroupObjects, }, ] diff --git a/browser/src/VariantList/mergeExomeAndGenomeData.ts b/browser/src/VariantList/mergeExomeAndGenomeData.ts index b793c9c40..9790777c3 100644 --- a/browser/src/VariantList/mergeExomeAndGenomeData.ts +++ b/browser/src/VariantList/mergeExomeAndGenomeData.ts @@ -1,4 +1,6 @@ -import { Population, SequencingType } from '../VariantPage/VariantPage' +import { Filter } from '../QCFilter' +import { Population, SequencingType, Variant } from '../VariantPage/VariantPage' +import { omit } from 'lodash' // safe math on possibly null values const add = (n1: any, n2: any) => (n1 || 0) + (n2 || 0) @@ -43,73 +45,84 @@ export const mergeExomeAndGenomePopulationData = ( return Object.values(populations) } -export const mergeExomeAndGenomeData = (variants: any) => - variants.map((variant: any) => { +type MergedVariant = Variant & { + ac: number + an: number + af: number + allele_freq: number + ac_hemi: number + ac_hom: number + filters: Filter[] + populations: Population[] +} + +export const mergeExomeAndGenomeData = (variants: Variant[]): MergedVariant[] => { + const mergedVariants = variants.map((variant: Variant) => { const { exome, genome, joint } = variant - if (!exome) { - if (!joint) { - return { - ...variant, - ...variant.genome, - allele_freq: variant.genome.af, // hack for variant track which expects allele_freq field - } - } + + if (joint) { + const exomeFilters = exome ? exome.filters : [] + const genomeFilters = genome ? genome.filters : [] + const jointFilters = exomeFilters.concat(genomeFilters, joint.filters) + return { ...variant, - ...variant.joint, - filters: variant.genome.filters, - allele_freq: variant.joint.ac / variant.joint.an, + ac: joint.ac, + an: joint.an, + af: joint.ac / joint.an, + allele_freq: joint.ac / joint.an, + ac_hemi: joint.hemizygote_count, + ac_hom: joint.homozygote_count, + filters: jointFilters, + populations: joint.populations, } } - if (!genome) { - if (!joint) { - return { - ...variant, - ...variant.exome, - allele_freq: variant.exome.af, // hack for variant track which expects allele_freq field - } - } - return { - ...variant, - ...variant.joint, - filters: variant.exome.filters, - allele_freq: variant.joint.ac / variant.joint.an, // hack for variant track which expects allele_freq field - } + + const emptySequencingType = { + ac: 0, + ac_hemi: 0, + ac_hom: 0, + faf95: { + popmax: null, + popmax_population: null, + }, + an: 0, + af: 5, + filters: [] as Filter[], + populations: [] as Population[], } - const jointAC = variant.joint ? variant.joint.ac : add(exome.ac, genome.ac) - const jointAN = variant.joint ? variant.joint.an : add(exome.an, genome.an) - const jointAF = jointAC ? jointAC / jointAN : 0 + const exomeOrNone = exome || emptySequencingType + const genomeOrNone = genome || emptySequencingType - const jointHemizygoteCount = variant.joint - ? variant.joint.hemizygote_count - : add(exome.ac_hemi, genome.ac_hemi) - const jointHomozygoteCount = variant.joint - ? variant.joint.homozygote_count - : add(exome.ac_hom, genome.ac_hom) + const combinedAC = add(exomeOrNone.ac, genomeOrNone.ac) + const combinedAN = add(exomeOrNone.an, genomeOrNone.an) + const combinedAF = combinedAC ? combinedAC / combinedAN : 0 + const combinedHemizygoteCount = add(exomeOrNone.ac_hemi, genomeOrNone.ac_hemi) + const combinedHomozygoteCount = add(exomeOrNone.ac_hom, genomeOrNone.ac_hom) - const exomeAndGenomeFilters = exome.filters.concat(genome.filters) - const jointFilters = variant.joint - ? exomeAndGenomeFilters.concat(variant.joint.filters) - : exomeAndGenomeFilters + const exomeFilters: Filter[] = exomeOrNone.filters + const genomeFilters: Filter[] = genomeOrNone.filters + const combinedFilters = exomeFilters.concat(genomeFilters) - const jointPopulations = variant.join - ? variant.joint.populations - : mergeExomeAndGenomePopulationData(exome!, genome!) + const combinedPopulations = mergeExomeAndGenomePopulationData( + exomeOrNone as SequencingType, + genomeOrNone as SequencingType + ) - const jointVariantData = { + return { ...variant, - ac: jointAC, - an: jointAN, - af: jointAF, - allele_freq: jointAF, // hack for variant track which expects allele_freq field - ac_hemi: jointHemizygoteCount, - ac_hom: jointHomozygoteCount, - filters: jointFilters, - populations: jointPopulations, + ac: combinedAC, + an: combinedAN, + af: combinedAF, + allele_freq: combinedAF, + ac_hemi: combinedHemizygoteCount, + ac_hom: combinedHomozygoteCount, + filters: combinedFilters, + populations: combinedPopulations, } - - return jointVariantData }) + return mergedVariants +} export default mergeExomeAndGenomeData diff --git a/browser/src/VariantPage/VariantPage.tsx b/browser/src/VariantPage/VariantPage.tsx index 542629185..d239f52a2 100644 --- a/browser/src/VariantPage/VariantPage.tsx +++ b/browser/src/VariantPage/VariantPage.tsx @@ -182,8 +182,8 @@ export type VariantQualityMetrics = { } export type Faf95 = { - popmax: number - popmax_population: string + popmax: number | null + popmax_population: string | null } type BaseSequencingType = { @@ -191,7 +191,6 @@ type BaseSequencingType = { an: number homozygote_count: number hemizygote_count: number - faf95: Faf95 filters: Filter[] populations: Population[] age_distribution: AgeDistribution | null @@ -203,9 +202,16 @@ export type SequencingType = BaseSequencingType & { ac_hom: number ac_hemi: number af?: number + faf95: Faf95 } export type JointSequencingType = BaseSequencingType & { + fafmax: { + faf95_max: number | null + faf95_max_gen_anc: PopulationId | null + faf99_max: number | null + faf99_max_gen_anc: PopulationId | null + } freq_comparison_stats: { contingency_table_test: { p_value: number