-
Notifications
You must be signed in to change notification settings - Fork 270
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #4577 from pvannierop/sv_table_in_study_view
RFC68: Impl. structural variants table in Study View
- Loading branch information
Showing
29 changed files
with
2,846 additions
and
247 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,176 @@ | ||
var assert = require('assert'); | ||
var goToUrlAndSetLocalStorage = require('../../shared/specUtils') | ||
.goToUrlAndSetLocalStorage; | ||
var waitForStudyView = require('../../shared/specUtils').waitForStudyView; | ||
|
||
const CBIOPORTAL_URL = process.env.CBIOPORTAL_URL.replace(/\/$/, ''); | ||
// TODO remove feature flag after merge. | ||
const studyViewUrl = `${CBIOPORTAL_URL}/study/summary?id=study_es_0&featureFlags=STUDY_VIEW_STRUCT_VAR_TABLE`; | ||
const structVarTable = '//*[@data-test="structural variant pairs-table"]'; | ||
const filterCheckBox = '[data-test=labeledCheckbox]'; | ||
const structVarFilterPillTag = '[data-test=pill-tag]'; | ||
const uncheckedSvIcon = '[data-test=structVarQueryCheckboxUnchecked]'; | ||
const checkedSvIcon = '[data-test=structVarQueryCheckboxChecked]'; | ||
const structVarNameCell = '[data-test=structVarNameCell]'; | ||
const toast = '.Toastify div[role=alert]'; | ||
|
||
describe('study view structural variant table', function() { | ||
beforeEach(() => { | ||
goToUrlAndSetLocalStorage(studyViewUrl, true); | ||
waitForStudyView(); | ||
showSvPane(); | ||
}); | ||
|
||
it('adds structural variant to study view filter', () => { | ||
$(structVarTable) | ||
.$(filterCheckBox) | ||
.click(); | ||
$('[data-test=selectSamplesButton]').waitForExist(); | ||
$('[data-test=selectSamplesButton]').click(); | ||
assert($(structVarFilterPillTag).isExisting()); | ||
}); | ||
|
||
it.skip('shows all checkboxes when row is hovered', () => { | ||
$(structVarNameCell).waitForExist(); | ||
const firstSvRowCell = $$(structVarNameCell)[0]; | ||
assert.equal($$(structVarNameCell)[1].getText(), 'SND1'); | ||
assert.equal($$(structVarNameCell)[2].getText(), 'BRAF'); | ||
|
||
movePointerWithRetry(firstSvRowCell, () => | ||
$(uncheckedSvIcon).waitForDisplayed() | ||
); | ||
assert.equal($$(uncheckedSvIcon).length, 3); | ||
}); | ||
|
||
it.skip('shows only checked checkboxes when row is not hovered', () => { | ||
$(structVarNameCell).waitForExist(); | ||
const gene1Cell = $$(structVarNameCell)[1]; | ||
movePointerWithRetry(gene1Cell, () => | ||
$(uncheckedSvIcon).waitForDisplayed() | ||
); | ||
assert.equal($$(uncheckedSvIcon).length, 3); | ||
|
||
gene1Cell.waitForClickable(); | ||
gene1Cell.click(); | ||
|
||
// hover somewhere else: | ||
movePointerWithRetry($('span=Gene 2'), $(checkedSvIcon).waitForExist()); | ||
|
||
assert.equal($$(uncheckedSvIcon).length, 0); | ||
assert.equal($$(checkedSvIcon).length, 1); | ||
}); | ||
|
||
it.skip('adds gene1::gene2 to Results View query', () => { | ||
$(structVarNameCell).waitForExist(); | ||
const firstSvRowCell = $$(structVarNameCell)[0]; | ||
|
||
movePointerWithRetry(firstSvRowCell, () => { | ||
$$(uncheckedSvIcon)[0].waitForClickable(); | ||
}); | ||
const gene1And2Checkbox = $$(uncheckedSvIcon)[0]; | ||
gene1And2Checkbox.click(); | ||
$(toast).waitForDisplayed(); | ||
clearToast(); | ||
|
||
const resultsViewQueryBox = openResultViewQueryBox(); | ||
assert.equal('SND1: FUSION::BRAF;', resultsViewQueryBox.getValue()); | ||
}); | ||
|
||
it.skip('adds gene1::* to Results View query', () => { | ||
$(structVarNameCell).waitForExist(); | ||
const gene1Cell = $$(structVarNameCell)[1]; | ||
movePointerWithRetry(gene1Cell, () => | ||
$(uncheckedSvIcon).waitForDisplayed() | ||
); | ||
gene1Cell.waitForClickable(); | ||
gene1Cell.click(); | ||
$(toast).waitForDisplayed(); | ||
clearToast(); | ||
|
||
const resultsViewQueryBox = openResultViewQueryBox(); | ||
assert.equal('SND1: FUSION::;', resultsViewQueryBox.getValue()); | ||
}); | ||
|
||
it.skip('adds *::gene2 to Results View query', () => { | ||
$(structVarNameCell).waitForExist(); | ||
const gene2Cell = $$(structVarNameCell)[2]; | ||
movePointerWithRetry(gene2Cell, () => | ||
$(uncheckedSvIcon).waitForDisplayed() | ||
); | ||
gene2Cell.waitForClickable(); | ||
gene2Cell.click(); | ||
$(toast).waitForDisplayed(); | ||
clearToast(); | ||
|
||
const resultsViewQueryBox = openResultViewQueryBox(); | ||
assert.equal('BRAF: ::FUSION;', resultsViewQueryBox.getValue()); | ||
}); | ||
}); | ||
|
||
function showSvPane() { | ||
const $chartsBtn = $('[data-test=add-charts-button]'); | ||
$chartsBtn.waitForExist(); | ||
$chartsBtn.waitForClickable(); | ||
$chartsBtn.click(); | ||
const $chartsGenomicTab = $('.tabAnchor_Genomic'); | ||
$chartsGenomicTab.waitForExist(); | ||
$chartsGenomicTab.waitForClickable(); | ||
$chartsGenomicTab.click(); | ||
const $svChartCheckbox = $( | ||
'[data-test="add-chart-option-structural-variants"]' | ||
).$('[data-test="labeledCheckbox"]'); | ||
$svChartCheckbox.waitForExist(); | ||
$svChartCheckbox.waitForClickable(); | ||
if (!$svChartCheckbox.isSelected()) { | ||
$svChartCheckbox.click(); | ||
} | ||
$chartsBtn.click(); | ||
waitForStudyView(); | ||
} | ||
|
||
function openResultViewQueryBox() { | ||
const resultsViewQueryBox = $('[data-test=geneSet]'); | ||
resultsViewQueryBox.waitForClickable(); | ||
resultsViewQueryBox.click(); | ||
return resultsViewQueryBox; | ||
} | ||
|
||
function clearToast() { | ||
const toastify = $('.Toastify button'); | ||
toastify.waitForClickable(); | ||
toastify.click(); | ||
browser.pause(100); | ||
} | ||
|
||
function movePointerTo(element) { | ||
element.waitForDisplayed(); | ||
element.scrollIntoView(); | ||
const x = element.getLocation('x'); | ||
const y = element.getLocation('y'); | ||
browser.performActions([ | ||
{ | ||
type: 'pointer', | ||
parameters: { pointerType: 'mouse' }, | ||
actions: [ | ||
{ type: 'pointerMove', duration: 0, x, y }, | ||
{ type: 'pointerMove', duration: 0, x, y }, | ||
], | ||
}, | ||
]); | ||
} | ||
|
||
/** | ||
* When scrolling to the new location, some tooltips might pop up and interfere. | ||
* A retry solves this problem: the second time the pointer is already near/at the desired location | ||
*/ | ||
function movePointerWithRetry(element, isOk) { | ||
movePointerTo(element); | ||
try { | ||
if (isOk()) { | ||
return; | ||
} | ||
} catch (e) { | ||
// retry | ||
movePointerTo(element); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -30,17 +30,17 @@ | |
"buildBootstrap": "sass --style :compressed src/globalStyles/bootstrap-entry.scss src/globalStyles/prefixed-bootstrap.min.css", | ||
"heroku-postbuild": "yarn run build && yarn add [email protected] -g", | ||
"updateAPI": "yarn run fetchAPI && yarn run buildAPI && yarn run updateOncoKbAPI && yarn run updateGenomeNexusAPI", | ||
"fetchAPILocal": "export CBIOPORTAL_URL=http://localhost:8090 && curl -L -k ${CBIOPORTAL_URL}/api/api-docs | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/cbioportal-ts-api-client/src/generated/CBioPortalAPI-docs.json && curl -L -k ${CBIOPORTAL_URL}/api/api-docs?group=internal | json | grep -v host | grep -v basePath | grep -v termsOfService > packages/cbioportal-ts-api-client/src/generated/CBioPortalAPIInternal-docs.json", | ||
"fetchAPI": "./scripts/env_vars.sh && eval \"$(./scripts/env_vars.sh)\" && curl -L -k ${CBIOPORTAL_URL}/api/api-docs | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/cbioportal-ts-api-client/src/generated/CBioPortalAPI-docs.json && curl -L -k ${CBIOPORTAL_URL}/api/api-docs?group=internal | json | grep -v host | grep -v basePath | grep -v termsOfService > packages/cbioportal-ts-api-client/src/generated/CBioPortalAPIInternal-docs.json", | ||
"fetchAPILocal": "export CBIOPORTAL_URL=http://localhost:8090 && curl -s -L -k ${CBIOPORTAL_URL}/api/api-docs | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/cbioportal-ts-api-client/src/generated/CBioPortalAPI-docs.json && curl -s -L -k ${CBIOPORTAL_URL}/api/api-docs?group=internal | json | grep -v host | grep -v basePath | grep -v termsOfService > packages/cbioportal-ts-api-client/src/generated/CBioPortalAPIInternal-docs.json", | ||
"fetchAPI": "./scripts/env_vars.sh && eval \"$(./scripts/env_vars.sh)\" && curl -s -L -k ${CBIOPORTAL_URL}/api/api-docs | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/cbioportal-ts-api-client/src/generated/CBioPortalAPI-docs.json && curl -s -L -k ${CBIOPORTAL_URL}/api/api-docs?group=internal | json | grep -v host | grep -v basePath | grep -v termsOfService > packages/cbioportal-ts-api-client/src/generated/CBioPortalAPIInternal-docs.json", | ||
"buildAPI": "node scripts/generate-api.js packages/cbioportal-ts-api-client/src/generated CBioPortalAPI CBioPortalAPIInternal", | ||
"updateOncoKbAPI": "yarn run fetchOncoKbAPI && yarn run buildOncoKbAPI", | ||
"fetchOncoKbAPI": "curl -k https://www.oncokb.org/api/v1/v2/api-docs?group=Public%20APIs | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/oncokb-ts-api-client/src/generated/OncoKbAPI-docs.json", | ||
"fetchOncoKbAPI": "curl -s -k https://www.oncokb.org/api/v1/v2/api-docs?group=Public%20APIs | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/oncokb-ts-api-client/src/generated/OncoKbAPI-docs.json", | ||
"buildOncoKbAPI": "node scripts/generate-api.js packages/oncokb-ts-api-client/src/generated OncoKbAPI", | ||
"updateG2SAPI": "yarn run fetchG2SAPI && yarn run buildG2SAPI", | ||
"fetchG2SAPI": "curl -k http://g2s.genomenexus.org/v2/api-docs?group=api > packages/genome-nexus-ts-api-client/src/generated/Genome2StructureAPI-docs.json", | ||
"fetchG2SAPI": "curl -s -k http://g2s.genomenexus.org/v2/api-docs?group=api > packages/genome-nexus-ts-api-client/src/generated/Genome2StructureAPI-docs.json", | ||
"buildG2SAPI": "node scripts/generate-api.js packages/genome-nexus-ts-api-client/src/generated Genome2StructureAPI", | ||
"updateGenomeNexusAPI": "yarn run fetchGenomeNexusAPI && yarn run buildGenomeNexusAPI", | ||
"fetchGenomeNexusAPI": "./scripts/env_vars.sh && eval \"$(./scripts/env_vars.sh)\" && curl -k ${GENOME_NEXUS_URL}/v2/api-docs | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/genome-nexus-ts-api-client/src/generated/GenomeNexusAPI-docs.json && curl -k ${GENOME_NEXUS_URL}/v2/api-docs?group=internal | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/genome-nexus-ts-api-client/src/generated/GenomeNexusAPIInternal-docs.json", | ||
"fetchGenomeNexusAPI": "./scripts/env_vars.sh && eval \"$(./scripts/env_vars.sh)\" && curl -s -k ${GENOME_NEXUS_URL}/v2/api-docs | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/genome-nexus-ts-api-client/src/generated/GenomeNexusAPI-docs.json && curl -s -k ${GENOME_NEXUS_URL}/v2/api-docs?group=internal | json | grep -v basePath | grep -v termsOfService | grep -v host > packages/genome-nexus-ts-api-client/src/generated/GenomeNexusAPIInternal-docs.json", | ||
"buildGenomeNexusAPI": "node scripts/generate-api.js packages/genome-nexus-ts-api-client/src/generated GenomeNexusAPI GenomeNexusAPIInternal", | ||
"updateHotspotGenes": "./scripts/get_hotspot_genes.sh > src/shared/static-data/hotspotGenes.json", | ||
"compileOqlParser": "cd src/shared/lib/oql && pegjs oql-parser.pegjs", | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,163 @@ | ||
import { assert } from 'chai'; | ||
import * as React from 'react'; | ||
import { | ||
STRUCTVARAnyGeneStr, | ||
STRUCTVARNullGeneStr, | ||
STUCTVARDownstreamFusionStr, | ||
STUCTVARUpstreamFusionStr, | ||
} from 'shared/lib/oql/oqlfilter'; | ||
import { SingleGeneQuery } from 'shared/lib/oql/oql-parser'; | ||
import { | ||
oqlQueryToStructVarGenePair, | ||
StructVarGenePair, | ||
} from 'pages/studyView/StructVarUtils'; | ||
|
||
describe('StructVarUtils', () => { | ||
describe('oqlQueryToStructVarGenePair', () => { | ||
it.each([ | ||
[{ gene: 'A', alterations: [] }, []], | ||
[ | ||
{ | ||
gene: 'A', | ||
alterations: [ | ||
{ | ||
gene: undefined, | ||
alteration_type: STUCTVARDownstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
], | ||
}, | ||
[], | ||
], | ||
[ | ||
{ | ||
gene: 'A', | ||
alterations: [ | ||
{ | ||
gene: 'B', | ||
alteration_type: STUCTVARDownstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
], | ||
}, | ||
[{ gene1HugoSymbolOrOql: 'A', gene2HugoSymbolOrOql: 'B' }], | ||
], | ||
[ | ||
{ | ||
gene: 'A', | ||
alterations: [ | ||
{ | ||
gene: STRUCTVARAnyGeneStr, | ||
alteration_type: STUCTVARDownstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
], | ||
}, | ||
[ | ||
{ | ||
gene1HugoSymbolOrOql: 'A', | ||
gene2HugoSymbolOrOql: STRUCTVARAnyGeneStr, | ||
}, | ||
], | ||
], | ||
[ | ||
{ | ||
gene: 'A', | ||
alterations: [ | ||
{ | ||
gene: STRUCTVARNullGeneStr, | ||
alteration_type: STUCTVARDownstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
], | ||
}, | ||
[ | ||
{ | ||
gene1HugoSymbolOrOql: 'A', | ||
gene2HugoSymbolOrOql: STRUCTVARNullGeneStr, | ||
}, | ||
], | ||
], | ||
[ | ||
{ | ||
gene: 'A', | ||
alterations: [ | ||
{ | ||
gene: 'B', | ||
alteration_type: STUCTVARUpstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
], | ||
}, | ||
[{ gene1HugoSymbolOrOql: 'B', gene2HugoSymbolOrOql: 'A' }], | ||
], | ||
[ | ||
{ | ||
gene: 'A', | ||
alterations: [ | ||
{ | ||
gene: STRUCTVARAnyGeneStr, | ||
alteration_type: STUCTVARUpstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
], | ||
}, | ||
[ | ||
{ | ||
gene1HugoSymbolOrOql: STRUCTVARAnyGeneStr, | ||
gene2HugoSymbolOrOql: 'A', | ||
}, | ||
], | ||
], | ||
[ | ||
{ | ||
gene: 'A', | ||
alterations: [ | ||
{ | ||
gene: STRUCTVARNullGeneStr, | ||
alteration_type: STUCTVARUpstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
], | ||
}, | ||
[ | ||
{ | ||
gene1HugoSymbolOrOql: STRUCTVARNullGeneStr, | ||
gene2HugoSymbolOrOql: 'A', | ||
}, | ||
], | ||
], | ||
[ | ||
{ | ||
gene: 'A', | ||
alterations: [ | ||
{ | ||
gene: 'B', | ||
alteration_type: STUCTVARDownstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
{ | ||
gene: 'C', | ||
alteration_type: STUCTVARDownstreamFusionStr, | ||
modifiers: [], | ||
}, | ||
], | ||
}, | ||
[ | ||
{ gene1HugoSymbolOrOql: 'A', gene2HugoSymbolOrOql: 'B' }, | ||
{ gene1HugoSymbolOrOql: 'A', gene2HugoSymbolOrOql: 'C' }, | ||
], | ||
], | ||
])( | ||
'converts %p into %p', | ||
(singleGeneQuery, expected: StructVarGenePair[]) => { | ||
assert.deepEqual( | ||
oqlQueryToStructVarGenePair( | ||
singleGeneQuery as SingleGeneQuery | ||
), | ||
expected | ||
); | ||
} | ||
); | ||
}); | ||
}); |
Oops, something went wrong.