@molgenis/vip-report-template 6.1.1 → 7.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (285) hide show
  1. package/.nvmrc +1 -1
  2. package/.travis.yml +9 -11
  3. package/README.md +411 -1
  4. package/eslint.config.mjs +11 -0
  5. package/package.json +40 -35
  6. package/scripts/deploy_npm_registry.sh +5 -0
  7. package/src/App.tsx +35 -29
  8. package/src/assets/sass/main.scss +12 -4
  9. package/src/components/Allele.tsx +95 -0
  10. package/src/components/Anchor.tsx +1 -1
  11. package/src/components/Breadcrumb.tsx +8 -5
  12. package/src/components/DatasetDropdown.tsx +10 -23
  13. package/src/components/ErrorNotification.tsx +9 -0
  14. package/src/components/GenomeBrowser.tsx +40 -23
  15. package/src/components/HpoTerm.tsx +1 -1
  16. package/src/components/{record/Pager.tsx → Pager.tsx} +21 -14
  17. package/src/components/RecordsPerPage.tsx +9 -7
  18. package/src/components/RecordsTable.tsx +130 -0
  19. package/src/components/SampleTable.tsx +70 -98
  20. package/src/components/SearchBox.tsx +8 -2
  21. package/src/components/Sort.tsx +28 -25
  22. package/src/components/Table.tsx +16 -0
  23. package/src/components/Tooltip.tsx +20 -0
  24. package/src/components/VariantBreadcrumb.tsx +54 -0
  25. package/src/components/VariantConsequenceContainer.tsx +100 -0
  26. package/src/components/VariantConsequenceTable.tsx +58 -0
  27. package/src/components/VariantContainer.tsx +71 -0
  28. package/src/components/VariantFilters.tsx +27 -0
  29. package/src/components/VariantGenotypeTable.tsx +44 -0
  30. package/src/components/VariantInfoTable.tsx +24 -33
  31. package/src/components/VariantResults.tsx +103 -0
  32. package/src/components/VariantTable.tsx +62 -66
  33. package/src/components/VariantTypeSelect.tsx +34 -0
  34. package/src/components/VariantsContainer.tsx +150 -0
  35. package/src/components/VariantsContainerHeader.tsx +70 -0
  36. package/src/components/field/Field.tsx +80 -0
  37. package/src/components/field/FieldAlt.tsx +19 -0
  38. package/src/components/field/FieldChrom.tsx +6 -0
  39. package/src/components/{record/Id.tsx → field/FieldFilter.tsx} +2 -1
  40. package/src/components/field/FieldFormat.tsx +10 -0
  41. package/src/components/{record/Filter.tsx → field/FieldId.tsx} +1 -1
  42. package/src/components/field/FieldPos.tsx +6 -0
  43. package/src/components/field/FieldQual.tsx +6 -0
  44. package/src/components/field/FieldRef.tsx +8 -0
  45. package/src/components/field/composed/FieldClinVar.tsx +72 -0
  46. package/src/components/field/composed/FieldComposed.tsx +68 -0
  47. package/src/components/field/composed/FieldGene.tsx +39 -0
  48. package/src/components/field/composed/FieldGenotype.tsx +35 -0
  49. package/src/components/{record/format/GenotypeField.tsx → field/composed/FieldGenotypeSnvSv.tsx} +20 -16
  50. package/src/components/field/composed/FieldGenotypeStr.tsx +31 -0
  51. package/src/components/field/composed/FieldGnomAd.tsx +58 -0
  52. package/src/components/field/composed/FieldHpo.tsx +50 -0
  53. package/src/components/field/composed/FieldInheritanceModes.tsx +32 -0
  54. package/src/components/field/composed/FieldLocus.tsx +18 -0
  55. package/src/components/field/composed/FieldVipC.tsx +25 -0
  56. package/src/components/field/composed/FieldVipCS.tsx +15 -0
  57. package/src/components/field/composed/FieldVkgl.tsx +37 -0
  58. package/src/components/field/genotype/FieldGenotype.tsx +19 -0
  59. package/src/components/field/genotype/FieldGenotypeType.tsx +9 -0
  60. package/src/components/field/info/FieldConsequence.tsx +15 -0
  61. package/src/components/{record/info/Hgvs.tsx → field/info/FieldHgvs.tsx} +4 -6
  62. package/src/components/field/info/FieldInfo.tsx +27 -0
  63. package/src/components/{record/info/PubMed.tsx → field/info/FieldPubMed.tsx} +4 -7
  64. package/src/components/field/typed/FieldCategorical.tsx +17 -0
  65. package/src/components/{record/field/FieldValueCharacter.tsx → field/typed/FieldCharacter.tsx} +3 -2
  66. package/src/components/{record/field/FieldValueFlag.tsx → field/typed/FieldFlag.tsx} +3 -2
  67. package/src/components/{record/field/FieldValueFloat.tsx → field/typed/FieldFloat.tsx} +3 -2
  68. package/src/components/{record/field/FieldValueInteger.tsx → field/typed/FieldInteger.tsx} +3 -2
  69. package/src/components/{record/field/FieldValueString.tsx → field/typed/FieldString.tsx} +3 -2
  70. package/src/components/field/typed/FieldTyped.tsx +20 -0
  71. package/src/components/field/typed/FieldTypedItem.tsx +49 -0
  72. package/src/components/field/typed/FieldTypedMultiple.tsx +21 -0
  73. package/src/components/filter/Filter.tsx +56 -48
  74. package/src/components/filter/FilterWrapper.scss +23 -0
  75. package/src/components/filter/FilterWrapper.tsx +63 -0
  76. package/src/components/filter/composed/FilterAllelicImbalance.tsx +26 -0
  77. package/src/components/filter/composed/FilterComposed.tsx +92 -0
  78. package/src/components/filter/composed/FilterDeNovo.tsx +35 -0
  79. package/src/components/filter/composed/FilterHpo.tsx +16 -0
  80. package/src/components/filter/composed/FilterInheritance.tsx +42 -0
  81. package/src/components/filter/composed/FilterLocus.tsx +75 -0
  82. package/src/components/filter/composed/FilterVipC.tsx +16 -0
  83. package/src/components/filter/composed/FilterVipCS.tsx +16 -0
  84. package/src/components/filter/fixed/FilterAlt.tsx +20 -0
  85. package/src/components/filter/fixed/FilterChrom.tsx +22 -0
  86. package/src/components/filter/fixed/FilterFilter.tsx +20 -0
  87. package/src/components/filter/fixed/FilterFixed.tsx +96 -0
  88. package/src/components/filter/fixed/FilterId.tsx +20 -0
  89. package/src/components/filter/fixed/FilterPos.tsx +22 -0
  90. package/src/components/filter/fixed/FilterQual.tsx +21 -0
  91. package/src/components/filter/fixed/FilterRef.tsx +22 -0
  92. package/src/components/filter/typed/FilterCategorical.tsx +119 -0
  93. package/src/components/filter/typed/FilterFlag.tsx +23 -0
  94. package/src/components/filter/typed/FilterInterval.tsx +72 -0
  95. package/src/components/filter/typed/FilterString.tsx +43 -0
  96. package/src/components/filter/typed/FilterTyped.tsx +56 -0
  97. package/src/components/form/ButtonApply.tsx +11 -0
  98. package/src/components/form/ButtonDownload.tsx +11 -0
  99. package/src/components/form/ButtonReset.tsx +9 -0
  100. package/src/components/{Checkbox.tsx → form/Checkbox.tsx} +4 -9
  101. package/src/components/form/Input.tsx +19 -0
  102. package/src/components/form/Select.scss +7 -0
  103. package/src/components/form/Select.tsx +34 -0
  104. package/src/components/tree/DecisionTreeBoolMultiQuery.tsx +1 -1
  105. package/src/components/tree/DecisionTreeBoolQuery.tsx +1 -1
  106. package/src/components/tree/DecisionTreeNode.tsx +41 -39
  107. package/src/components/tree/DecisionTreeNodeBool.tsx +1 -1
  108. package/src/components/tree/DecisionTreeNodeBoolMulti.tsx +1 -1
  109. package/src/components/tree/DecisionTreeNodeCategorical.tsx +1 -1
  110. package/src/components/tree/DecisionTreeNodeExists.tsx +1 -1
  111. package/src/components/tree/DecisionTreeNodeLeaf.tsx +1 -1
  112. package/src/components/tree/DecisionTreeOutcomeNode.tsx +1 -1
  113. package/src/components/tree/DecisionTreePath.tsx +1 -1
  114. package/src/igv.d.ts +2 -1
  115. package/src/index.tsx +48 -19
  116. package/src/mocks/GRCh37/decisionTree.json +23 -22
  117. package/src/mocks/GRCh37/field_metadata.json +435 -95
  118. package/src/mocks/GRCh37/sampleTree.json +143 -0
  119. package/src/mocks/GRCh37/static.ts +63 -133
  120. package/src/mocks/GRCh37/vcf/family.vcf.blob +37 -31
  121. package/src/mocks/GRCh38/decisionTree.json +52 -33
  122. package/src/mocks/GRCh38/decisionTreeStr.json +572 -0
  123. package/src/mocks/GRCh38/fasta/chr1_149380406-149403321.fasta.gz.blob +0 -0
  124. package/src/mocks/GRCh38/field_metadata.json +435 -95
  125. package/src/mocks/GRCh38/sampleTree.json +175 -0
  126. package/src/mocks/GRCh38/static.ts +101 -42
  127. package/src/mocks/GRCh38/str.cram.blob +0 -0
  128. package/src/mocks/GRCh38/str.cram.crai.blob +0 -0
  129. package/src/mocks/GRCh38/vcf/family.vcf.blob +25 -24
  130. package/src/mocks/GRCh38/vcf/no_vep.vcf.blob +29 -28
  131. package/src/mocks/GRCh38/vcf/samples_0.vcf.blob +28 -27
  132. package/src/mocks/GRCh38/vcf/samples_1.vcf.blob +29 -28
  133. package/src/mocks/GRCh38/vcf/samples_100.vcf.blob +28 -27
  134. package/src/mocks/GRCh38/vcf/str.vcf.blob +321 -0
  135. package/src/mocks/MockApiClient.ts +341 -328
  136. package/src/mocks/config_cram.json +701 -0
  137. package/src/mocks/config_vcf.json +699 -0
  138. package/src/store/app.ts +30 -0
  139. package/src/store/index.tsx +3 -168
  140. package/src/store/variants.ts +182 -0
  141. package/src/types/config.d.ts +190 -0
  142. package/src/types/configCellComposed.d.ts +86 -0
  143. package/src/types/configCells.d.ts +129 -0
  144. package/src/types/configFilter.d.ts +80 -0
  145. package/src/types/configFilterComposed.d.ts +60 -0
  146. package/src/types/configSort.d.ts +13 -0
  147. package/src/types/filter.d.ts +17 -0
  148. package/src/types/store.d.ts +34 -0
  149. package/src/utils/api.ts +281 -0
  150. package/src/utils/config/config.ts +182 -0
  151. package/src/utils/config/configCells.ts +74 -0
  152. package/src/utils/config/configCellsComposed.ts +508 -0
  153. package/src/utils/config/configCellsField.ts +61 -0
  154. package/src/utils/config/configCellsFixed.ts +126 -0
  155. package/src/utils/config/configFilters.ts +46 -0
  156. package/src/utils/config/configFiltersComposed.ts +208 -0
  157. package/src/utils/config/configFiltersField.ts +49 -0
  158. package/src/utils/config/configFiltersFixed.ts +106 -0
  159. package/src/utils/config/configSorts.ts +44 -0
  160. package/src/utils/config/configValidator.ts +380 -0
  161. package/src/utils/config/configVip.ts +25 -0
  162. package/src/utils/csq.ts +115 -0
  163. package/src/utils/decisionTree.ts +45 -0
  164. package/src/utils/download.ts +30 -0
  165. package/src/utils/error.ts +69 -0
  166. package/src/utils/query/query.ts +55 -0
  167. package/src/utils/query/queryFilter.ts +132 -0
  168. package/src/utils/query/queryFilterComposed.ts +247 -0
  169. package/src/utils/query/queryFilterField.ts +75 -0
  170. package/src/utils/query/queryFilterFixed.ts +44 -0
  171. package/src/utils/query/querySample.ts +18 -0
  172. package/src/utils/query/queryVariantType.ts +76 -0
  173. package/src/utils/query/selector.ts +41 -0
  174. package/src/utils/{sortUtils.ts → query/sort.ts} +32 -11
  175. package/src/utils/sample.ts +19 -35
  176. package/src/utils/utils.ts +66 -2
  177. package/src/utils/variantType.ts +43 -0
  178. package/src/utils/vcf.ts +352 -0
  179. package/src/views/Help.tsx +109 -114
  180. package/src/views/Home.tsx +3 -2
  181. package/src/views/Sample.tsx +12 -7
  182. package/src/views/SampleVariant.tsx +23 -112
  183. package/src/views/SampleVariantConsequence.tsx +54 -114
  184. package/src/views/SampleVariants.tsx +33 -445
  185. package/src/views/SampleVariantsRedirect.tsx +20 -0
  186. package/src/views/Samples.tsx +7 -10
  187. package/src/views/Variant.tsx +31 -61
  188. package/src/views/VariantConsequence.tsx +42 -72
  189. package/src/views/Variants.tsx +29 -138
  190. package/src/views/VariantsRedirect.tsx +25 -0
  191. package/src/views/data/data.tsx +32 -6
  192. package/tests/store/variants.test.ts +122 -0
  193. package/tests/utils/config/config.test.ts +167 -0
  194. package/tests/utils/config/configCells.test.ts +86 -0
  195. package/tests/utils/config/configCellsComposed.test.ts +1163 -0
  196. package/tests/utils/config/configCellsField.test.ts +164 -0
  197. package/tests/utils/config/configCellsFixed.test.ts +99 -0
  198. package/tests/utils/config/configFilters.test.ts +80 -0
  199. package/tests/utils/config/configFiltersComposed.test.ts +504 -0
  200. package/tests/utils/config/configFiltersField.test.ts +140 -0
  201. package/tests/utils/config/configFiltersFixed.test.ts +81 -0
  202. package/tests/utils/config/configSorts.test.ts +55 -0
  203. package/tests/utils/config/configValidator.test.ts +56 -0
  204. package/tests/utils/config/configVip.test.ts +53 -0
  205. package/tests/utils/decisionTree.test.ts +71 -0
  206. package/tests/utils/download.test.ts +20 -0
  207. package/tests/utils/query/query.test.ts +84 -0
  208. package/tests/utils/query/queryFilter.test.ts +243 -0
  209. package/tests/utils/query/queryFilterComposed.test.ts +301 -0
  210. package/tests/utils/query/queryFilterField.test.ts +75 -0
  211. package/tests/utils/query/queryFilterFixed.test.ts +86 -0
  212. package/tests/utils/query/querySample.test.ts +45 -0
  213. package/tests/utils/query/queryVariantType.test.ts +56 -0
  214. package/{src/__tests__/sortUtils.test.ts → tests/utils/query/sort.test.ts} +3 -4
  215. package/tests/utils/sample.test.ts +259 -0
  216. package/tests/utils/utils.test.ts +120 -0
  217. package/tests/utils/variantType.test.ts +48 -0
  218. package/tests/utils/vcf.test.ts +649 -0
  219. package/tsconfig.json +6 -2
  220. package/vite.config.mts +20 -3
  221. package/.eslintignore +0 -4
  222. package/.eslintrc.js +0 -23
  223. package/src/Api.ts +0 -12
  224. package/src/__tests__/decisionTreeUtils.test.ts +0 -75
  225. package/src/__tests__/field.test.ts +0 -107
  226. package/src/__tests__/query.test.ts +0 -188
  227. package/src/__tests__/sample.test.ts +0 -184
  228. package/src/__tests__/utils.test.ts +0 -24
  229. package/src/__tests__/viewUtils.test.ts +0 -125
  230. package/src/components/ConsequenceTable.tsx +0 -45
  231. package/src/components/Error.tsx +0 -9
  232. package/src/components/FieldHeader.tsx +0 -26
  233. package/src/components/InfoCollapsablePane.tsx +0 -90
  234. package/src/components/VariantInfoNestedTable.tsx +0 -127
  235. package/src/components/VariantSampleTable.tsx +0 -58
  236. package/src/components/VariantsSampleTable.tsx +0 -183
  237. package/src/components/VariantsTable.tsx +0 -124
  238. package/src/components/filter/FilterAllelicBalance.tsx +0 -81
  239. package/src/components/filter/FilterCategorical.tsx +0 -81
  240. package/src/components/filter/FilterClinVar.tsx +0 -21
  241. package/src/components/filter/FilterGene.tsx +0 -34
  242. package/src/components/filter/FilterHpo.tsx +0 -161
  243. package/src/components/filter/FilterInheritance.tsx +0 -162
  244. package/src/components/filter/FilterIntegerGq.tsx +0 -47
  245. package/src/components/filter/FilterVI.tsx +0 -68
  246. package/src/components/filter/FilterVariantType.tsx +0 -146
  247. package/src/components/filter/Filters.tsx +0 -29
  248. package/src/components/filter/InfoFilter.tsx +0 -39
  249. package/src/components/filter/InfoFilters.tsx +0 -35
  250. package/src/components/filter/SampleFilters.tsx +0 -93
  251. package/src/components/filter/SamplesFilters.tsx +0 -33
  252. package/src/components/record/Allele.tsx +0 -38
  253. package/src/components/record/AlleleBreakend.tsx +0 -5
  254. package/src/components/record/AlleleMissing.tsx +0 -5
  255. package/src/components/record/AlleleNucs.tsx +0 -49
  256. package/src/components/record/AlleleSymbolic.tsx +0 -5
  257. package/src/components/record/Alt.tsx +0 -17
  258. package/src/components/record/Chrom.tsx +0 -5
  259. package/src/components/record/Format.tsx +0 -40
  260. package/src/components/record/Info.tsx +0 -55
  261. package/src/components/record/Pos.tsx +0 -5
  262. package/src/components/record/Qual.tsx +0 -5
  263. package/src/components/record/RecordDownload.tsx +0 -66
  264. package/src/components/record/Ref.tsx +0 -6
  265. package/src/components/record/field/Field.tsx +0 -36
  266. package/src/components/record/field/FieldMultipleValue.tsx +0 -22
  267. package/src/components/record/field/FieldSingleValue.tsx +0 -35
  268. package/src/components/record/info/ClinVar.tsx +0 -81
  269. package/src/components/record/info/Consequence.tsx +0 -18
  270. package/src/components/record/info/Gene.tsx +0 -56
  271. package/src/components/record/info/GnomAD.tsx +0 -54
  272. package/src/components/record/info/Hpo.tsx +0 -52
  273. package/src/components/record/info/InheritanceModes.tsx +0 -22
  274. package/src/components/record/info/VipC.tsx +0 -23
  275. package/src/components/record/info/Vkgl.tsx +0 -42
  276. package/src/mocks/GRCh37/vcf/no_vep.vcf.blob +0 -61
  277. package/src/mocks/GRCh37/vcf/samples_0.vcf.blob +0 -93
  278. package/src/mocks/GRCh37/vcf/samples_1.vcf.blob +0 -93
  279. package/src/mocks/GRCh37/vcf/samples_100.vcf.blob +0 -93
  280. package/src/utils/ApiUtils.ts +0 -259
  281. package/src/utils/csqUtils.ts +0 -27
  282. package/src/utils/decisionTreeUtils.ts +0 -14
  283. package/src/utils/field.ts +0 -49
  284. package/src/utils/query.ts +0 -154
  285. package/src/utils/viewUtils.ts +0 -32
@@ -1,124 +0,0 @@
1
- import { Metadata, Record } from "@molgenis/vip-report-vcf/src/Vcf";
2
- import { Component, createMemo, For } from "solid-js";
3
- import { Ref } from "./record/Ref";
4
- import { Chrom } from "./record/Chrom";
5
- import { Pos } from "./record/Pos";
6
- import { Id } from "./record/Id";
7
- import { Alt } from "./record/Alt";
8
- import { Qual } from "./record/Qual";
9
- import { Filter } from "./record/Filter";
10
- import { Info } from "./record/Info";
11
- import { FieldMetadata } from "@molgenis/vip-report-vcf/src/MetadataParser";
12
- import { HtsFileMetadata, Item } from "@molgenis/vip-report-api/src/Api";
13
- import { FieldHeader } from "./FieldHeader";
14
- import { InfoCollapsablePane } from "./InfoCollapsablePane";
15
-
16
- const computeRowspan = (recordsMetadata: Metadata) =>
17
- Object.values(recordsMetadata.info).find((field) => field.nested) !== undefined ? 2 : 1;
18
- // '+1' for the column with the collapse button
19
- const computeColspan = (field: FieldMetadata) => (field.nested ? field.nested.items.length + 1 : undefined);
20
-
21
- export const VariantsTable: Component<{
22
- records: Item<Record>[];
23
- recordsMetadata: Metadata;
24
- htsFileMeta: HtsFileMetadata;
25
- }> = (props) => {
26
- const infoFields = () => Object.values(props.recordsMetadata.info);
27
- const infoFieldsNested = () => infoFields().filter((infoField) => infoField.nested);
28
-
29
- const rowspan = createMemo(() => computeRowspan(props.recordsMetadata));
30
-
31
- return (
32
- <div style={{ display: "grid" }}>
33
- {/* workaround for https://github.com/jgthms/bulma/issues/2572#issuecomment-523099776 */}
34
- <div class="table-container">
35
- <table class="table is-narrow">
36
- <thead>
37
- <tr>
38
- <th rowspan={rowspan()}>CHROM</th>
39
- <th rowspan={rowspan()}>POS</th>
40
- <th rowspan={rowspan()}>ID</th>
41
- <th rowspan={rowspan()}>REF</th>
42
- <th rowspan={rowspan()}>ALT</th>
43
- <th rowspan={rowspan()}>QUAL</th>
44
- <th rowspan={rowspan()}>FILTER</th>
45
- <For each={infoFields()}>
46
- {(infoField) => (
47
- <FieldHeader
48
- field={infoField}
49
- rowspan={infoField.nested ? undefined : rowspan()}
50
- colspan={computeColspan(infoField)}
51
- />
52
- )}
53
- </For>
54
- </tr>
55
- {rowspan() && rowspan() > 1 && (
56
- <tr>
57
- <For each={infoFieldsNested()}>
58
- {(infoField) => (
59
- <>
60
- {infoField.number.count !== 1 && <th />}
61
- <For each={infoField.nested?.items}>
62
- {(nestedInfoField) => <FieldHeader field={nestedInfoField} />}
63
- </For>
64
- </>
65
- )}
66
- </For>
67
- </tr>
68
- )}
69
- </thead>
70
- <tbody>
71
- <For each={props.records}>
72
- {(record) => (
73
- <tr>
74
- <td>
75
- <Chrom value={record.data.c} />
76
- </td>
77
- <td>
78
- <a href={`/variants/${record.id}`}>
79
- <Pos value={record.data.p} />
80
- </a>
81
- </td>
82
- <td>
83
- <Id value={record.data.i} />
84
- </td>
85
- <td>
86
- <Ref value={record.data.r} isAbbreviate={true} />
87
- </td>
88
- <td>
89
- <Alt value={record.data.a} isAbbreviate={true} />
90
- </td>
91
- <td>
92
- <Qual value={record.data.q} />
93
- </td>
94
- <td>
95
- <Filter value={record.data.f} />
96
- </td>
97
- <For each={infoFields()}>
98
- {(infoField) =>
99
- infoField.nested ? (
100
- <InfoCollapsablePane
101
- fields={infoField.nested.items}
102
- record={record}
103
- htsFileMeta={props.htsFileMeta}
104
- />
105
- ) : (
106
- <td>
107
- <Info
108
- info={{ value: record.data.n[infoField.id], record: record }}
109
- infoMeta={infoField}
110
- context={props.htsFileMeta}
111
- />
112
- </td>
113
- )
114
- }
115
- </For>
116
- </tr>
117
- )}
118
- </For>
119
- </tbody>
120
- </table>
121
- </div>
122
- </div>
123
- );
124
- };
@@ -1,81 +0,0 @@
1
- import { Component } from "solid-js";
2
- import { ComposedQuery, Item, Query, Sample, Selector } from "@molgenis/vip-report-api/src/Api";
3
- import { Checkbox, CheckboxEvent } from "../Checkbox";
4
- import { FilterChangeEvent, FilterClearEvent } from "./Filters";
5
- import { selector, selectorKey } from "../../utils/query";
6
- import { FieldMetadata } from "@molgenis/vip-report-vcf/src/MetadataParser";
7
-
8
- export function getAllelicBalanceQuery(sampleIndex: number): ComposedQuery {
9
- const hetQuery: ComposedQuery = {
10
- operator: "and",
11
- args: [
12
- { selector: ["s", sampleIndex, "GT", "t"], operator: "==", args: "het" },
13
- {
14
- operator: "and",
15
- args: [
16
- { selector: ["s", sampleIndex, "VIAB"], operator: ">=", args: 0.2 },
17
- { selector: ["s", sampleIndex, "VIAB"], operator: "<=", args: 0.8 },
18
- ],
19
- },
20
- ],
21
- };
22
- const homQuery: ComposedQuery = {
23
- operator: "and",
24
- args: [
25
- {
26
- operator: "or",
27
- args: [
28
- { selector: ["s", sampleIndex, "GT", "t"], operator: "==", args: "hom_a" },
29
- { selector: ["s", sampleIndex, "GT", "t"], operator: "==", args: "hom_r" },
30
- ],
31
- },
32
- {
33
- operator: "or",
34
- args: [
35
- { selector: ["s", sampleIndex, "VIAB"], operator: "<", args: 0.02 },
36
- { selector: ["s", sampleIndex, "VIAB"], operator: ">", args: 0.98 },
37
- ],
38
- },
39
- ],
40
- };
41
- const otherGtQuery: ComposedQuery = {
42
- operator: "or",
43
- args: [
44
- { selector: ["s", sampleIndex, "GT", "t"], operator: "==", args: "miss" },
45
- { selector: ["s", sampleIndex, "GT", "t"], operator: "==", args: "part" },
46
- { selector: ["s", sampleIndex, "VIAB"], operator: "==", args: null },
47
- { selector: ["s", sampleIndex, "VIAB"], operator: "==", args: undefined },
48
- ],
49
- };
50
- const combinedQuery: ComposedQuery = { operator: "or", args: [hetQuery, homQuery, otherGtQuery] };
51
-
52
- return combinedQuery;
53
- }
54
-
55
- export const FilterAllelicBalance: Component<{
56
- field: FieldMetadata;
57
- sample?: Item<Sample>;
58
- query?: Query;
59
- onChange: (event: FilterChangeEvent) => void;
60
- onClear: (event: FilterClearEvent) => void;
61
- }> = (props) => {
62
- const onFilterChange = (event: CheckboxEvent) => {
63
- const fieldSelector: Selector = ["s", (props.sample as Item<Sample>).data.index, ...selector(props.field)];
64
- if (event.checked) {
65
- props.onChange({
66
- query: getAllelicBalanceQuery((props.sample?.data as Sample).index),
67
- key: selectorKey(fieldSelector),
68
- });
69
- } else props.onClear({ key: selectorKey(fieldSelector) });
70
- };
71
- return (
72
- <div class="control">
73
- <Checkbox
74
- desc="Filter variants with allelic imbalance; For hetrozygote calls: AB < 0.2 or AB > 0.8 and for homozygote calls: AB > 0.02 are considered allelic imbalance"
75
- label="No allelic imbalance"
76
- checked={props.query && props.query.args !== undefined}
77
- onChange={onFilterChange}
78
- />
79
- </div>
80
- );
81
- };
@@ -1,81 +0,0 @@
1
- import { Component, For } from "solid-js";
2
- import { Checkbox, CheckboxEvent } from "../Checkbox";
3
- import { FilterProps } from "./Filter";
4
- import { selector, selectorKey } from "../../utils/query";
5
-
6
- export type CheckboxGroup = {
7
- [key: string]: boolean;
8
- };
9
-
10
- export type CategoryLabels = {
11
- [key: string]: string;
12
- };
13
-
14
- export const FilterCategorical: Component<
15
- FilterProps & {
16
- labels?: CategoryLabels;
17
- }
18
- > = (props) => {
19
- const group: CheckboxGroup = {};
20
- const label = () => (props.field.label !== undefined ? props.field.label : props.field.id);
21
- if (props.query !== undefined) {
22
- (props.query?.args as string[]).forEach((key) => {
23
- group[key] = true;
24
- });
25
- }
26
-
27
- const nullValue = "__null";
28
-
29
- // enable null category for any_has_any case if someone asks for it (requires query to be composed)
30
- const includeNullCategory = () => !props.field.required && props.field.number.count === 1;
31
-
32
- const onChange = (event: CheckboxEvent) => {
33
- group[event.value !== undefined ? event.value : nullValue] = event.checked;
34
- const values = Object.keys(group)
35
- .filter((key) => group[key])
36
- .map((key) => (key !== nullValue ? key : null));
37
- if (values.length > 0) {
38
- props.onChange({
39
- key: selectorKey(selector(props.field)),
40
- query: {
41
- selector: selector(props.field),
42
- operator: props.field.number.count === 1 ? "has_any" : "any_has_any",
43
- args: values,
44
- },
45
- });
46
- } else {
47
- props.onClear({ key: selectorKey(selector(props.field)) });
48
- }
49
- };
50
-
51
- return (
52
- <>
53
- <p class="has-text-weight-semibold">
54
- {props.field.description ? <abbr title={props.field.description}>{label()}</abbr> : <span>{label()}</span>}
55
- </p>
56
-
57
- <div class="field">
58
- <For each={props.field.categories}>
59
- {(category) => (
60
- <div class="control">
61
- <Checkbox
62
- value={category}
63
- label={props.labels ? props.labels[category] : category}
64
- checked={props.query && (props.query.args as (string | null)[]).includes(category)}
65
- onChange={onChange}
66
- />
67
- </div>
68
- )}
69
- </For>
70
- {includeNullCategory() && (
71
- <Checkbox
72
- value={nullValue}
73
- label="No value"
74
- checked={props.query && (props.query.args as (string | null)[]).includes(null)}
75
- onChange={onChange}
76
- />
77
- )}
78
- </div>
79
- </>
80
- );
81
- };
@@ -1,21 +0,0 @@
1
- import { Component } from "solid-js";
2
- import { FilterProps } from "./Filter";
3
- import { FilterCategorical } from "./FilterCategorical";
4
-
5
- export const FilterClinVar: Component<FilterProps> = (props) => {
6
- return (
7
- <FilterCategorical
8
- field={props.field}
9
- labels={{
10
- Benign: "B",
11
- Likely_benign: "LB",
12
- Uncertain_significance: "VUS",
13
- Likely_pathogenic: "LP",
14
- Pathogenic: "P",
15
- Conflicting_interpretations_of_pathogenicity: "Conflict",
16
- }}
17
- onChange={props.onChange}
18
- onClear={props.onClear}
19
- />
20
- );
21
- };
@@ -1,34 +0,0 @@
1
- import { Component } from "solid-js";
2
- import { FilterProps } from "./Filter";
3
- import { Checkbox, CheckboxEvent } from "../Checkbox";
4
- import { selector, selectorKey } from "../../utils/query";
5
-
6
- export const FilterGene: Component<FilterProps> = (props) => {
7
- const onFilterChange = (event: CheckboxEvent) => {
8
- const fieldSelector = selector(props.field);
9
- if (event.checked) {
10
- props.onChange({
11
- key: selectorKey(fieldSelector),
12
- query: {
13
- selector: fieldSelector,
14
- operator: "any_has_any",
15
- args: ["1"],
16
- },
17
- });
18
- } else props.onClear({ key: selectorKey(fieldSelector) });
19
- };
20
-
21
- return (
22
- <>
23
- <p class="has-text-weight-semibold">{<span>Various</span>}</p>
24
- <div class="field">
25
- <Checkbox
26
- desc="Gene is associated with incomplete penetrance"
27
- label="Inc. Penetrance"
28
- checked={props.query && props.query.args !== undefined}
29
- onChange={onFilterChange}
30
- />
31
- </div>
32
- </>
33
- );
34
- };
@@ -1,161 +0,0 @@
1
- import { Component, For, Show } from "solid-js";
2
- import { Checkbox, CheckboxEvent } from "../Checkbox";
3
- import { FilterProps } from "./Filter";
4
- import { infoSelector, selector, selectorKey } from "../../utils/query";
5
- import { FieldMetadata } from "@molgenis/vip-report-vcf/src/MetadataParser";
6
- import { Query, QueryClause } from "@molgenis/vip-report-api/src/Api";
7
-
8
- export type CheckboxGroup = {
9
- [key: string]: boolean;
10
- };
11
-
12
- export type CategoryLabels = {
13
- [key: string]: string;
14
- };
15
-
16
- export const FilterHpo: Component<
17
- FilterProps & {
18
- labels?: CategoryLabels;
19
- }
20
- > = (props) => {
21
- const group: CheckboxGroup = {};
22
- const hpoSelector = selector(props.field);
23
- const csqMeta = props.field.parent;
24
- const label = () => (props.field.label !== undefined ? props.field.label : props.field.id);
25
- let gadoHcChecked = false;
26
- let gadoLcChecked = false;
27
- let hpoValues: (string | null)[] = [];
28
-
29
- let gadoMeta: FieldMetadata | null = null;
30
- csqMeta?.nested?.items.forEach((meta) => {
31
- if (meta.id === "GADO_PD") {
32
- gadoMeta = meta;
33
- }
34
- });
35
-
36
- if (props.query !== undefined) {
37
- (props.query.args as Query[]).forEach((childQuery) => {
38
- if (selectorKey((childQuery as QueryClause).selector) === selectorKey(infoSelector(props.field))) {
39
- (childQuery.args as string[]).forEach((key) => {
40
- group[key] = true;
41
- hpoValues.push(key);
42
- });
43
- } else if (
44
- gadoMeta &&
45
- selectorKey((childQuery as QueryClause).selector) === selectorKey(infoSelector(gadoMeta))
46
- ) {
47
- if ((childQuery.args as string[]).indexOf("LC") !== -1) {
48
- group["gado_lc"] = true;
49
- gadoLcChecked = true;
50
- }
51
- if ((childQuery.args as string[]).indexOf("HC") !== -1) {
52
- group["gado_hc"] = true;
53
- gadoHcChecked = true;
54
- }
55
- }
56
- });
57
- }
58
-
59
- const nullValue = "__null";
60
-
61
- let gadoLcQuery: Query;
62
- let gadoHcQuery: Query;
63
- if (gadoMeta !== null) {
64
- gadoLcQuery = {
65
- selector: selector(gadoMeta),
66
- operator: "has_any",
67
- args: ["LC"],
68
- };
69
-
70
- gadoHcQuery = {
71
- selector: selector(gadoMeta),
72
- operator: "has_any",
73
- args: ["HC"],
74
- };
75
- }
76
- const onChange = (event: CheckboxEvent) => {
77
- const queries: Query[] = [];
78
- group[event.value !== undefined ? event.value : nullValue] = event.checked;
79
- const values = Object.keys(group)
80
- .filter((key) => group[key])
81
- .map((key) => (key !== nullValue ? key : null));
82
- if (values.length > 0) {
83
- if (gadoMeta !== null) {
84
- if (values.includes("gado_lc")) {
85
- queries.push(gadoLcQuery);
86
- gadoLcChecked = true;
87
- } else {
88
- gadoHcChecked = false;
89
- }
90
- if (values.includes("gado_hc")) {
91
- queries.push(gadoHcQuery);
92
- gadoHcChecked = true;
93
- } else {
94
- gadoHcChecked = false;
95
- }
96
- }
97
- hpoValues = values.filter((key) => key !== "gado_lc" && key !== "gado_hc");
98
- if (hpoValues.length > 0) {
99
- const hpoQuery: Query = {
100
- selector: hpoSelector,
101
- operator: "any_has_any",
102
- args: hpoValues,
103
- };
104
- queries.push(hpoQuery);
105
- } else if (gadoMeta !== null) {
106
- props.onClear({ key: selectorKey(hpoSelector) });
107
- }
108
-
109
- props.onChange({
110
- key: selectorKey(hpoSelector),
111
- query: {
112
- operator: "or",
113
- args: queries,
114
- },
115
- });
116
- } else {
117
- props.onClear({ key: selectorKey(hpoSelector) });
118
- }
119
- };
120
- return (
121
- <>
122
- <p class="has-text-weight-semibold">
123
- {props.field.description ? <abbr title={props.field.description}>{label()}</abbr> : <span>{label()}</span>}
124
- </p>
125
- <div class="field">
126
- <For each={props.field.categories}>
127
- {(category) => (
128
- <div class="control">
129
- <Checkbox
130
- value={category}
131
- label={props.labels ? props.labels[category] : category}
132
- checked={hpoValues && hpoValues.includes(category)}
133
- onChange={onChange}
134
- />
135
- </div>
136
- )}
137
- </For>
138
- <Show when={gadoMeta !== null}>
139
- <div class="control">
140
- <Checkbox
141
- value="gado_hc"
142
- label="GADO high"
143
- desc="Gene predicted to have a relation with phenotypes of the proband (phenotypes of other samples are ignored!) with high confidence (Z-Score above 5)."
144
- checked={gadoHcChecked}
145
- onChange={onChange}
146
- />
147
- </div>
148
- <div class="control">
149
- <Checkbox
150
- value="gado_lc"
151
- label="GADO low"
152
- desc="Gene predicted to have a relation with phenotypes of the proband (phenotypes of other samples are ignored!) with low confidence (Z-Score above 3 but below 5)."
153
- checked={gadoLcChecked}
154
- onChange={onChange}
155
- />
156
- </div>
157
- </Show>
158
- </div>
159
- </>
160
- );
161
- };
@@ -1,162 +0,0 @@
1
- import { Component } from "solid-js";
2
- import { Checkbox, CheckboxEvent } from "../Checkbox";
3
- import { selector, selectorKey } from "../../utils/query";
4
- import { Item, Query, QueryClause, Sample, Selector } from "@molgenis/vip-report-api/src/Api";
5
- import { FieldMetadata } from "@molgenis/vip-report-vcf/src/MetadataParser";
6
- import { FilterChangeEvent, FilterClearEvent } from "./Filters";
7
-
8
- export type FilterInheritanceProps = {
9
- vimField: FieldMetadata;
10
- vidField: FieldMetadata;
11
- query?: Query;
12
- onChange: (event: FilterChangeEvent) => void;
13
- onClear: (event: FilterClearEvent) => void;
14
- sample: Item<Sample>;
15
- key: string;
16
- };
17
- export const FilterInheritance: Component<FilterInheritanceProps> = (props) => {
18
- const VIM_TRUE = "VIM_true";
19
- const VIM_MISSING = "VIM_missing";
20
- const VID = "VID_true";
21
- const VID_MISSING = "VID_missing";
22
-
23
- let isVimMissingChecked = false;
24
- let isVimTrueChecked = false;
25
- let isVidTrueChecked = false;
26
- let isVidMissingChecked = false;
27
-
28
- const vimFieldSelector: Selector = ["s", props.sample.data.index, ...selector(props.vimField)];
29
- const vidFieldSelector: Selector = ["s", props.sample.data.index, ...selector(props.vidField)];
30
-
31
- if (props.query !== undefined) {
32
- (props.query?.args as QueryClause[]).forEach((query) => {
33
- const selectorKeyValue = selectorKey(query.selector);
34
- if (selectorKeyValue === selectorKey(vimFieldSelector) && query.args === 1) {
35
- isVimTrueChecked = true;
36
- } else if (
37
- selectorKeyValue === selectorKey(vimFieldSelector) &&
38
- (query.args === null || query.args === undefined)
39
- ) {
40
- isVimMissingChecked = true;
41
- } else if (selectorKeyValue === selectorKey(vidFieldSelector) && query.args === 1) {
42
- isVidTrueChecked = true;
43
- } else if (
44
- selectorKeyValue === selectorKey(vidFieldSelector) &&
45
- (query.args === null || query.args === undefined)
46
- ) {
47
- isVidMissingChecked = true;
48
- }
49
- });
50
- }
51
- const onFilterChange = (event: CheckboxEvent) => {
52
- const queries: QueryClause[] = [];
53
- if ((event.value === VIM_TRUE && event.checked) || (isVimTrueChecked && event.value !== VIM_TRUE)) {
54
- queries.push({
55
- selector: vimFieldSelector,
56
- operator: "==",
57
- args: 1,
58
- });
59
- isVimTrueChecked = true;
60
- } else if (isVimTrueChecked && event.value === VIM_TRUE && !event.checked) {
61
- isVimTrueChecked = false;
62
- }
63
-
64
- if ((event.value === VIM_MISSING && event.checked) || (isVimMissingChecked && event.value !== VIM_MISSING)) {
65
- queries.push(
66
- {
67
- selector: vimFieldSelector,
68
- operator: "==",
69
- args: null,
70
- },
71
- {
72
- selector: vimFieldSelector,
73
- operator: "==",
74
- args: undefined,
75
- },
76
- );
77
- isVimMissingChecked = true;
78
- } else if (isVimMissingChecked && event.value === VIM_MISSING && !event.checked) {
79
- isVimMissingChecked = false;
80
- }
81
- if ((event.value === VID && event.checked) || (isVidTrueChecked && event.value !== VID)) {
82
- queries.push({
83
- selector: vidFieldSelector,
84
- operator: "==",
85
- args: 1,
86
- });
87
- isVidTrueChecked = true;
88
- } else if ((event.value === VID_MISSING && event.checked) || (isVidMissingChecked && event.value !== VID_MISSING)) {
89
- queries.push(
90
- {
91
- selector: vidFieldSelector,
92
- operator: "==",
93
- args: null,
94
- },
95
- {
96
- selector: vidFieldSelector,
97
- operator: "==",
98
- args: undefined,
99
- },
100
- );
101
- isVimMissingChecked = true;
102
- } else if (isVidTrueChecked && event.value === VID && !event.checked) {
103
- isVidTrueChecked = false;
104
- }
105
- if (queries.length > 0) {
106
- props.onChange({
107
- key: props.key,
108
- query: {
109
- operator: "or",
110
- args: queries,
111
- },
112
- });
113
- } else {
114
- props.onClear({ key: props.key });
115
- }
116
- };
117
-
118
- return (
119
- <>
120
- <div class="control">
121
- <Checkbox
122
- value={VIM_TRUE}
123
- label="Match"
124
- desc="Genotypes, affected statuses and known gene inheritance patterns match (can include de novo variants)."
125
- checked={isVimTrueChecked}
126
- onChange={onFilterChange}
127
- />
128
- </div>
129
- <div class="control">
130
- <Checkbox
131
- value={VIM_MISSING}
132
- label="Match: Potential"
133
- desc="Genotypes, affected statuses match but gene inheritance pattern is unknown (can include de novo variants)."
134
- checked={isVimMissingChecked}
135
- onChange={onFilterChange}
136
- />
137
- </div>
138
- <div class="control">
139
- <Checkbox
140
- value={VID}
141
- label="De novo"
142
- desc="On autosomes:
143
- - Available parents do not have the variant, or genotype is missing.
144
- On the X chromosome:
145
- - Female proband: same as autosomes.
146
- - Male proband: Mother does not have the variant, or mother genotype missing."
147
- checked={isVidTrueChecked}
148
- onChange={onFilterChange}
149
- />
150
- </div>
151
- <div class="control">
152
- <Checkbox
153
- value={VID_MISSING}
154
- label="De novo: Potential"
155
- desc="Variant could be denovo but some genotype data of the sample or parents is missing."
156
- checked={isVidTrueChecked}
157
- onChange={onFilterChange}
158
- />
159
- </div>
160
- </>
161
- );
162
- };