jbrowse-plugin-graphgenomeviewer 7.1.0 → 7.1.2

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 (233) hide show
  1. package/README.md +17 -8
  2. package/dist/chunks/AddTrackWorkflow-RPH4ZFSX.js +2 -0
  3. package/dist/chunks/{AddTrackWorkflow-Q6RY23LF.js.map → AddTrackWorkflow-RPH4ZFSX.js.map} +2 -2
  4. package/dist/chunks/{ChooseSamplesDialog-BNVYBGJQ.js → ChooseSamplesDialog-JRN4YLBY.js} +2 -2
  5. package/dist/chunks/{ChooseWalksDialog-EN3C6AQA.js → ChooseWalksDialog-UXLFZTZJ.js} +2 -2
  6. package/dist/chunks/GbzBaseSyntenyAdapter-LRECKL74.js +2 -0
  7. package/dist/chunks/GbzBaseSyntenyAdapter-LRECKL74.js.map +7 -0
  8. package/dist/chunks/{GraphGenomeView-Z2WZKEEO.js → GraphGenomeView-NJ5XCREB.js} +2 -2
  9. package/dist/chunks/GraphTrackSettingsDialog-47PQ6LM7.js +6 -0
  10. package/dist/chunks/GraphTrackSettingsDialog-47PQ6LM7.js.map +7 -0
  11. package/dist/chunks/{HighlightColorDialog-EYBKFSJU.js → HighlightColorDialog-UK5VDDV6.js} +2 -2
  12. package/dist/chunks/{LinearGraphDisplay-WIBVWRQE.js → LinearGraphDisplay-TXTKAACH.js} +2 -2
  13. package/dist/chunks/MinigraphBubbleAdapter-HW7XQMAI.js +2 -0
  14. package/dist/chunks/MinigraphBubbleAdapter-HW7XQMAI.js.map +7 -0
  15. package/dist/chunks/RgfaTabixAdapter-PSKYWD2X.js +3 -0
  16. package/dist/chunks/RgfaTabixAdapter-PSKYWD2X.js.map +7 -0
  17. package/dist/chunks/{TrackWarningsDialog-QT4YEXGD.js → TrackWarningsDialog-TRYBOIHX.js} +2 -2
  18. package/dist/chunks/WalkTabixSyntenyAdapter-U53JLYVU.js +2 -0
  19. package/dist/chunks/WalkTabixSyntenyAdapter-U53JLYVU.js.map +7 -0
  20. package/dist/chunks/chunk-2MCOY3YG.js +3 -0
  21. package/dist/chunks/chunk-2MCOY3YG.js.map +7 -0
  22. package/dist/chunks/{chunk-EWFJBQDV.js → chunk-5O6YRJHL.js} +2 -2
  23. package/dist/chunks/{chunk-EWFJBQDV.js.map → chunk-5O6YRJHL.js.map} +1 -1
  24. package/dist/chunks/chunk-BUY2PV7D.js +2 -0
  25. package/dist/chunks/chunk-BUY2PV7D.js.map +7 -0
  26. package/dist/chunks/chunk-DVCZ3BOC.js +2 -0
  27. package/dist/chunks/chunk-DVCZ3BOC.js.map +7 -0
  28. package/dist/chunks/{chunk-SAMJE6GH.js → chunk-EGDLEQ47.js} +3 -3
  29. package/dist/chunks/{chunk-SAMJE6GH.js.map → chunk-EGDLEQ47.js.map} +4 -4
  30. package/dist/chunks/chunk-FHZXW7IG.js +2 -0
  31. package/dist/chunks/chunk-FHZXW7IG.js.map +7 -0
  32. package/dist/chunks/{chunk-DZ4OUKQV.js → chunk-FITPB5X6.js} +2 -2
  33. package/dist/chunks/{chunk-DZ4OUKQV.js.map → chunk-FITPB5X6.js.map} +1 -1
  34. package/dist/chunks/chunk-FVK2THE4.js +2 -0
  35. package/dist/chunks/chunk-FVK2THE4.js.map +7 -0
  36. package/dist/chunks/{chunk-AHFQHYJI.js → chunk-IBWORBGY.js} +2 -2
  37. package/dist/chunks/chunk-MND7GAOG.js +2 -0
  38. package/dist/chunks/chunk-MND7GAOG.js.map +7 -0
  39. package/dist/chunks/chunk-MURN3JPK.js +2 -0
  40. package/dist/chunks/chunk-MURN3JPK.js.map +7 -0
  41. package/dist/chunks/{chunk-3Q4RBDCL.js → chunk-N6PQZSAX.js} +1 -1
  42. package/dist/chunks/{chunk-3Q4RBDCL.js.map → chunk-N6PQZSAX.js.map} +1 -1
  43. package/dist/chunks/chunk-NWJYLP6Z.js +4 -0
  44. package/dist/chunks/chunk-NWJYLP6Z.js.map +7 -0
  45. package/dist/chunks/{chunk-YJHYBDYF.js → chunk-S75W27NT.js} +2 -2
  46. package/dist/chunks/{chunk-YJHYBDYF.js.map → chunk-S75W27NT.js.map} +1 -1
  47. package/dist/chunks/{chunk-IXQK7JAW.js → chunk-T4HOC6O3.js} +1 -1
  48. package/dist/chunks/{chunk-IXQK7JAW.js.map → chunk-T4HOC6O3.js.map} +1 -1
  49. package/dist/chunks/{chunk-AU73K7LX.js → chunk-TUKJRVBS.js} +1 -1
  50. package/dist/chunks/{chunk-AU73K7LX.js.map → chunk-TUKJRVBS.js.map} +1 -1
  51. package/dist/chunks/chunk-UGCNPRKC.js +2 -0
  52. package/dist/chunks/{chunk-E3WYW7Z6.js.map → chunk-UGCNPRKC.js.map} +2 -2
  53. package/dist/chunks/{chunk-YSTMDXXX.js → chunk-VJ3SO4CH.js} +1 -1
  54. package/dist/chunks/{chunk-YSTMDXXX.js.map → chunk-VJ3SO4CH.js.map} +1 -1
  55. package/dist/chunks/{chunk-XT766CZ5.js → chunk-W6EQLQ6H.js} +1 -1
  56. package/dist/chunks/{chunk-XT766CZ5.js.map → chunk-W6EQLQ6H.js.map} +1 -1
  57. package/dist/chunks/chunk-WAMBI7OX.js +2 -0
  58. package/dist/chunks/chunk-WAMBI7OX.js.map +7 -0
  59. package/dist/chunks/chunk-WCGVUZWP.js +2 -0
  60. package/dist/chunks/chunk-WCGVUZWP.js.map +7 -0
  61. package/dist/chunks/chunk-WEGWTC52.js +2 -0
  62. package/dist/chunks/chunk-WEGWTC52.js.map +7 -0
  63. package/dist/chunks/chunk-YU7T5WOQ.js +2 -0
  64. package/dist/chunks/{chunk-6OPB7FOJ.js.map → chunk-YU7T5WOQ.js.map} +2 -2
  65. package/dist/chunks/{chunk-446RWIA3.js → chunk-ZMOMFU2B.js} +1 -1
  66. package/dist/chunks/{chunk-446RWIA3.js.map → chunk-ZMOMFU2B.js.map} +1 -1
  67. package/dist/chunks/renderSvg-KSQI5DH6.js +2 -0
  68. package/dist/chunks/renderSvg-KSQI5DH6.js.map +7 -0
  69. package/dist/jbrowse-plugin-graphgenomeviewer.esm.js +4 -4
  70. package/dist/jbrowse-plugin-graphgenomeviewer.esm.js.map +4 -4
  71. package/package.json +8 -9
  72. package/src/GbzBaseSyntenyAdapter/GbzBaseSyntenyAdapter.test.ts +12 -10
  73. package/src/GbzBaseSyntenyAdapter/GbzBaseSyntenyAdapter.ts +31 -39
  74. package/src/GbzBaseSyntenyAdapter/configSchema.ts +5 -29
  75. package/src/GetGraphHaplotypes.ts +6 -15
  76. package/src/GetGraphReads.ts +7 -14
  77. package/src/GetSubgraph.ts +11 -20
  78. package/src/GraphAddTrackWorkflow/AddTrackWorkflow.test.tsx +73 -0
  79. package/src/GraphAddTrackWorkflow/AddTrackWorkflow.tsx +1 -0
  80. package/src/GraphAddTrackWorkflow/buildTrackConfig.test.ts +3 -2
  81. package/src/GraphAddTrackWorkflow/buildTrackConfig.ts +2 -11
  82. package/src/GraphAddTrackWorkflow/graphManifest.ts +15 -3
  83. package/src/GraphGenomeView/components/BubbleHalos.tsx +5 -24
  84. package/src/GraphGenomeView/components/ElTree.tsx +6 -1
  85. package/src/GraphGenomeView/components/FacetPanels.test.tsx +65 -0
  86. package/src/GraphGenomeView/components/FacetPanels.tsx +17 -12
  87. package/src/GraphGenomeView/components/GenePins.tsx +5 -22
  88. package/src/GraphGenomeView/components/GraphCanvas.tsx +40 -234
  89. package/src/GraphGenomeView/components/GraphSettingsDialog.tsx +102 -108
  90. package/src/GraphGenomeView/components/GraphToolbar.tsx +5 -6
  91. package/src/GraphGenomeView/components/HoverLayer.tsx +3 -7
  92. package/src/GraphGenomeView/components/HoverTooltip.test.tsx +39 -0
  93. package/src/GraphGenomeView/components/HoverTooltip.tsx +122 -0
  94. package/src/GraphGenomeView/components/LabelChip.tsx +3 -5
  95. package/src/GraphGenomeView/components/LabelLayer.tsx +4 -17
  96. package/src/GraphGenomeView/components/LabelledSelect.tsx +1 -1
  97. package/src/GraphGenomeView/components/Legend.tsx +14 -23
  98. package/src/GraphGenomeView/components/PaneContextMenu.test.tsx +48 -0
  99. package/src/GraphGenomeView/components/PaneContextMenu.tsx +144 -0
  100. package/src/GraphGenomeView/components/PaneLayer.tsx +91 -0
  101. package/src/GraphGenomeView/components/PaneSvg.tsx +32 -50
  102. package/src/GraphGenomeView/components/ReferenceStripOverlay.test.tsx +48 -0
  103. package/src/GraphGenomeView/components/ReferenceStripOverlay.tsx +13 -42
  104. package/src/GraphGenomeView/components/SettingsMenu.test.tsx +29 -0
  105. package/src/GraphGenomeView/components/SettingsMenu.tsx +56 -65
  106. package/src/GraphGenomeView/components/TubeMapOverlay.tsx +15 -46
  107. package/src/GraphGenomeView/components/WalkRowsOverlay.tsx +58 -132
  108. package/src/GraphGenomeView/components/WalkStrip.tsx +17 -20
  109. package/src/GraphGenomeView/components/WalkStripLocator.tsx +8 -15
  110. package/src/GraphGenomeView/components/usePaneGestures.test.tsx +35 -0
  111. package/src/GraphGenomeView/components/usePaneGestures.ts +88 -91
  112. package/src/GraphGenomeView/genes/geneFeatures.ts +27 -45
  113. package/src/GraphGenomeView/graphLayers.ts +4 -4
  114. package/src/GraphGenomeView/host.ts +1 -1
  115. package/src/GraphGenomeView/legendSections.test.ts +23 -1
  116. package/src/GraphGenomeView/legendSections.ts +68 -74
  117. package/src/GraphGenomeView/model.test.ts +373 -39
  118. package/src/GraphGenomeView/model.ts +67 -11
  119. package/src/GraphGenomeView/pane/fitViews.ts +57 -514
  120. package/src/GraphGenomeView/pane/graphViews.ts +219 -160
  121. package/src/GraphGenomeView/pane/hostViews.ts +2 -10
  122. package/src/GraphGenomeView/pane/keepInView.ts +5 -4
  123. package/src/GraphGenomeView/pane/launchActions.ts +117 -139
  124. package/src/GraphGenomeView/pane/launchViews.ts +8 -27
  125. package/src/GraphGenomeView/pane/loadActions.ts +208 -187
  126. package/src/GraphGenomeView/pane/morph.ts +3 -9
  127. package/src/GraphGenomeView/pane/paneBase.ts +22 -11
  128. package/src/GraphGenomeView/pane/renderingActions.ts +65 -11
  129. package/src/GraphGenomeView/pane/settingActions.ts +17 -42
  130. package/src/GraphGenomeView/pane/tubeMapViews.ts +445 -0
  131. package/src/GraphGenomeView/pane/walkRowViews.ts +29 -37
  132. package/src/GraphGenomeView/renderPipeline.test.ts +1 -1
  133. package/src/GraphGenomeView/repeats/repeatFeatures.test.ts +23 -0
  134. package/src/GraphGenomeView/repeats/repeatFeatures.ts +16 -23
  135. package/src/GraphGenomeView/repeats/walkCalls.test.ts +18 -0
  136. package/src/GraphGenomeView/repeats/walkCalls.ts +46 -38
  137. package/src/GraphGenomeView/subgraphLoad.test.ts +67 -3
  138. package/src/GraphGenomeView/trackFeatures.ts +24 -0
  139. package/src/GraphGenomeView/tubeMapPanels.ts +28 -36
  140. package/src/GraphGenomeView/viewModel.ts +8 -56
  141. package/src/GraphGenomeView/walkRowGroups.ts +104 -30
  142. package/src/GraphGenomeView/walkRowSpans.test.ts +6 -0
  143. package/src/GraphGenomeView/walkRowSpans.ts +22 -31
  144. package/src/GraphGenomeView/walkRowsCut.ts +8 -17
  145. package/src/LinearGraphDisplay/LinearGraphDisplay.test.ts +173 -26
  146. package/src/LinearGraphDisplay/components/SubgraphContextSelect.test.tsx +1 -1
  147. package/src/LinearGraphDisplay/components/SubgraphContextSelect.tsx +3 -3
  148. package/src/LinearGraphDisplay/components/SubgraphHaplotypesField.test.tsx +3 -3
  149. package/src/LinearGraphDisplay/components/SubgraphHaplotypesField.tsx +7 -10
  150. package/src/LinearGraphDisplay/configSchema.ts +0 -3
  151. package/src/LinearGraphDisplay/denseWindow.ts +8 -11
  152. package/src/LinearGraphDisplay/model.ts +89 -82
  153. package/src/MinigraphBubbleAdapter/MinigraphBubbleAdapter.test.ts +21 -0
  154. package/src/MinigraphBubbleAdapter/MinigraphBubbleAdapter.ts +6 -14
  155. package/src/MinigraphBubbleAdapter/configSchema.ts +3 -9
  156. package/src/MinigraphBubbleAdapter/index.ts +1 -2
  157. package/src/RgfaTabixAdapter/RgfaTabixAdapter.test.ts +45 -1
  158. package/src/RgfaTabixAdapter/RgfaTabixAdapter.ts +111 -276
  159. package/src/RgfaTabixAdapter/configSchema.ts +15 -49
  160. package/src/RgfaTabixAdapter/index.ts +1 -2
  161. package/src/RgfaTabixAdapter/rgfaBed.ts +25 -15
  162. package/src/RgfaTabixAdapter/rgfaCut.ts +139 -0
  163. package/src/RgfaTabixAdapter/test_data/walks2_twopart.GRCh38.walks.bed.gz +0 -0
  164. package/src/RgfaTabixAdapter/test_data/walks2_twopart.GRCh38.walks.bed.gz.tbi +0 -0
  165. package/src/RgfaTabixAdapter/walkFiles.test.ts +33 -0
  166. package/src/RgfaTabixAdapter/walkReader.ts +103 -27
  167. package/src/RgfaTabixAdapter/walkRowRuns.test.ts +53 -0
  168. package/src/RgfaTabixAdapter/walkRowRuns.ts +42 -24
  169. package/src/WalkTabixSyntenyAdapter/WalkTabixSyntenyAdapter.test.ts +37 -6
  170. package/src/WalkTabixSyntenyAdapter/WalkTabixSyntenyAdapter.ts +23 -45
  171. package/src/WalkTabixSyntenyAdapter/configSchema.ts +11 -24
  172. package/src/WalkTabixSyntenyAdapter/index.ts +1 -2
  173. package/src/WalkTabixSyntenyAdapter/walkLanes.ts +35 -43
  174. package/src/adapterImplementing.ts +27 -0
  175. package/src/graphTrackDefaults/index.ts +14 -20
  176. package/src/hoverSync/lgvHover.ts +2 -4
  177. package/src/launchFromGraph/contributors.ts +1 -5
  178. package/src/launchFromGraph/graphMenuItems.ts +3 -4
  179. package/src/launchFromGraph/launchFromGraph.test.ts +0 -1
  180. package/src/launchFromGraph/launchFromGraph.ts +8 -13
  181. package/src/panSNTabix.test.ts +1 -26
  182. package/src/panSNTabix.ts +54 -51
  183. package/src/synteny/lanePairs.ts +8 -0
  184. package/src/synteny/matchFeature.ts +52 -0
  185. package/src/tabixRange.ts +13 -10
  186. package/src/version.ts +1 -1
  187. package/dist/chunks/AddTrackWorkflow-Q6RY23LF.js +0 -2
  188. package/dist/chunks/GbzBaseSyntenyAdapter-TIXR4Y3J.js +0 -2
  189. package/dist/chunks/GbzBaseSyntenyAdapter-TIXR4Y3J.js.map +0 -7
  190. package/dist/chunks/GraphTrackSettingsDialog-TAM6PMXD.js +0 -6
  191. package/dist/chunks/GraphTrackSettingsDialog-TAM6PMXD.js.map +0 -7
  192. package/dist/chunks/MinigraphBubbleAdapter-AGI2UYQR.js +0 -2
  193. package/dist/chunks/MinigraphBubbleAdapter-AGI2UYQR.js.map +0 -7
  194. package/dist/chunks/RgfaTabixAdapter-2OL5X3HF.js +0 -3
  195. package/dist/chunks/RgfaTabixAdapter-2OL5X3HF.js.map +0 -7
  196. package/dist/chunks/WalkTabixSyntenyAdapter-UKFHCFOF.js +0 -2
  197. package/dist/chunks/WalkTabixSyntenyAdapter-UKFHCFOF.js.map +0 -7
  198. package/dist/chunks/chunk-5SFGHDQA.js +0 -2
  199. package/dist/chunks/chunk-5SFGHDQA.js.map +0 -7
  200. package/dist/chunks/chunk-6OPB7FOJ.js +0 -2
  201. package/dist/chunks/chunk-AMFIBQVR.js +0 -2
  202. package/dist/chunks/chunk-AMFIBQVR.js.map +0 -7
  203. package/dist/chunks/chunk-BJMRBVG3.js +0 -2
  204. package/dist/chunks/chunk-BJMRBVG3.js.map +0 -7
  205. package/dist/chunks/chunk-E3WYW7Z6.js +0 -2
  206. package/dist/chunks/chunk-EHCF6AXH.js +0 -2
  207. package/dist/chunks/chunk-EHCF6AXH.js.map +0 -7
  208. package/dist/chunks/chunk-GOFS7BXK.js +0 -3
  209. package/dist/chunks/chunk-GOFS7BXK.js.map +0 -7
  210. package/dist/chunks/chunk-IJQTSJGT.js +0 -4
  211. package/dist/chunks/chunk-IJQTSJGT.js.map +0 -7
  212. package/dist/chunks/chunk-J6NZIAZF.js +0 -2
  213. package/dist/chunks/chunk-J6NZIAZF.js.map +0 -7
  214. package/dist/chunks/chunk-LUTMKRXY.js +0 -2
  215. package/dist/chunks/chunk-LUTMKRXY.js.map +0 -7
  216. package/dist/chunks/chunk-MHPJB22Z.js +0 -2
  217. package/dist/chunks/chunk-MHPJB22Z.js.map +0 -7
  218. package/dist/chunks/chunk-TXI43PEN.js +0 -2
  219. package/dist/chunks/chunk-TXI43PEN.js.map +0 -7
  220. package/dist/chunks/chunk-WRH2EJKX.js +0 -2
  221. package/dist/chunks/chunk-WRH2EJKX.js.map +0 -7
  222. package/dist/chunks/chunk-WX26KTZM.js +0 -2
  223. package/dist/chunks/chunk-WX26KTZM.js.map +0 -7
  224. package/dist/chunks/renderSvg-ST2GBBOC.js +0 -2
  225. package/dist/chunks/renderSvg-ST2GBBOC.js.map +0 -7
  226. package/src/GraphGenomeView/components/WalkRowContextMenu.tsx +0 -105
  227. /package/dist/chunks/{ChooseSamplesDialog-BNVYBGJQ.js.map → ChooseSamplesDialog-JRN4YLBY.js.map} +0 -0
  228. /package/dist/chunks/{ChooseWalksDialog-EN3C6AQA.js.map → ChooseWalksDialog-UXLFZTZJ.js.map} +0 -0
  229. /package/dist/chunks/{GraphGenomeView-Z2WZKEEO.js.map → GraphGenomeView-NJ5XCREB.js.map} +0 -0
  230. /package/dist/chunks/{HighlightColorDialog-EYBKFSJU.js.map → HighlightColorDialog-UK5VDDV6.js.map} +0 -0
  231. /package/dist/chunks/{LinearGraphDisplay-WIBVWRQE.js.map → LinearGraphDisplay-TXTKAACH.js.map} +0 -0
  232. /package/dist/chunks/{TrackWarningsDialog-QT4YEXGD.js.map → TrackWarningsDialog-TRYBOIHX.js.map} +0 -0
  233. /package/dist/chunks/{chunk-AHFQHYJI.js.map → chunk-IBWORBGY.js.map} +0 -0
@@ -26,25 +26,18 @@ import { reaction } from 'mobx'
26
26
  import { denseCovers, isNodeLimitError } from './denseWindow'
27
27
  import { cutHolds, hostCut, hostWindow } from '../GraphGenomeView/host'
28
28
  import { lenientOptionalEnum } from '../GraphGenomeView/lenientEnum'
29
- import {
30
- GraphPaneMixin,
31
- MAX_GRAPH_REGION_BP,
32
- formatSpanBp,
33
- } from '../GraphGenomeView/model'
29
+ import { GraphPane, formatSpanBp } from '../GraphGenomeView/model'
34
30
  import { FACET_KEY_PX } from '../GraphGenomeView/pane/fitViews'
31
+ import { paneBase } from '../GraphGenomeView/pane/paneBase'
35
32
  import {
36
33
  configHaplotypes,
37
34
  cutsByHaplotype,
38
- graphReferenceAssembly,
39
- offReferenceProblem,
40
35
  trackLanes,
41
36
  walkIndexed,
42
37
  } from '../graphTrackConfig'
43
38
  import { pushLaunchItem } from '../launchFromGraph/pushLaunchItem'
44
- import { trackAdapterConfig } from '../panSNAliases/trackAdapterConfig'
45
39
 
46
40
  import type { LinearGraphDisplayConfigModel } from './configSchema'
47
- import type { DenseWindow } from './denseWindow'
48
41
  import type { SubgraphRegion, SubgraphTier } from '../GetSubgraph'
49
42
  import type { GraphLayers } from '../GraphGenomeView/graphLayers'
50
43
  import type { HostWindow } from '../GraphGenomeView/host'
@@ -53,11 +46,27 @@ import type { LaunchGraphGenomeViewArgs } from '../LaunchGraphGenomeView'
53
46
  import type { LayoutModeValue } from '@jbrowse/bandage-core/layoutModes'
54
47
  import type { MenuItem } from '@jbrowse/core/ui'
55
48
  import type { ExportSvgDisplayOptions } from '@jbrowse/display-kit/types'
56
- import type { Instance } from '@jbrowse/mobx-state-tree'
49
+ import type { Instance, SnapshotOut } from '@jbrowse/mobx-state-tree'
57
50
  import type { DisplayStatusPhase } from '@jbrowse/render-core/displayPhase'
58
51
 
59
52
  type GraphViewSpec = Omit<LaunchGraphGenomeViewArgs, 'session'>
60
53
 
54
+ // the pane's viewport, which a new graph view fits to its drawing
55
+ const VIEWPORT_PROPS = new Set(['scale', 'translateX', 'translateY'])
56
+
57
+ type PaneSettings = Omit<
58
+ SnapshotOut<typeof paneBase>,
59
+ 'scale' | 'translateX' | 'translateY'
60
+ >
61
+
62
+ function paneSettings(pane: Instance<typeof paneBase>) {
63
+ return Object.fromEntries(
64
+ Object.keys(paneBase.properties)
65
+ .filter(key => !VIEWPORT_PROPS.has(key))
66
+ .map(key => [key, pane[key as keyof typeof pane]]),
67
+ ) as PaneSettings
68
+ }
69
+
61
70
  // A variant under this many of the linear view's pixels folds into the
62
71
  // reference before layout, so the drawing gains detail as the view zooms in.
63
72
  // It is the width `gfa-to-tabix build` gives a backbone node at the zoom a
@@ -89,7 +98,7 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
89
98
  'LinearGraphDisplay',
90
99
  BaseDisplay,
91
100
  TrackHeightMixin(),
92
- GraphPaneMixin(),
101
+ GraphPane,
93
102
  types.model({
94
103
  type: types.literal('LinearGraphDisplay'),
95
104
  configuration: ConfigurationReference(configSchema),
@@ -102,35 +111,20 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
102
111
  // whether that cut came from the track's coarse pair
103
112
  // (RgfaTabixAdapter), on which no bp cap applies
104
113
  coarseCut: types.optional(types.boolean, false),
105
- // The bp ceiling on a fine cut, a proxy for node count that only
106
- // holds at fine granularity; `maxGraphNodes` counts what came back.
107
- maxRegionBp: types.optional(types.number, MAX_GRAPH_REGION_BP),
108
- // How far the cut follows links past the region's own segments. At
109
- // 0 a detour that leaves the backbone before the window and rejoins
110
- // after it arrives as a fragment, since its interior is indexed only
111
- // under its own sequence, so one bubble draws as two unrelated
112
- // insertions. A hop follows alleles only, so it never walks the
113
- // backbone out of the window.
114
- subgraphContext: types.optional(types.number, 1),
115
- // the haplotypes a GBZ or walk-indexed cut is for; unset is the
116
- // config's defaultHaplotypes, else the lanes the track names
117
- subgraphHaplotypes: types.maybe(types.frozen<string[]>()),
118
114
  }),
119
115
  )
120
116
  .volatile(() => ({
121
117
  recuts: 0,
122
118
  // the host window the settle clock last woke on
123
119
  settledWindow: undefined as HostWindow | undefined,
124
- dense: undefined as DenseWindow | undefined,
120
+ // where a cut came back over its node limit (denseCovers)
121
+ dense: undefined as SubgraphRegion | undefined,
125
122
  // the haplotypes a walk-indexed graph's header names, once read
126
123
  haplotypeNames: undefined as string[] | undefined,
127
124
  // the fold the latest cut asked for
128
125
  cutFoldBp: 0,
129
126
  }))
130
127
  .views(self => ({
131
- get adapterConfig() {
132
- return trackAdapterConfig(self, self.parentTrack.configuration)
133
- },
134
128
  get grammar(): GraphGrammar {
135
129
  return {
136
130
  layoutMode: getConf(self, 'layoutMode'),
@@ -152,17 +146,18 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
152
146
  get canRetryLoad() {
153
147
  return self.cutRegion !== undefined
154
148
  },
155
- get cutHaplotypes() {
149
+ // the config's defaultHaplotypes, else the lanes the track names
150
+ get trackHaplotypes() {
151
+ const adapter = self.sourceAdapter
152
+ const track = self.sourceTrack
156
153
  return (
157
- self.subgraphHaplotypes ??
158
- configHaplotypes(this.adapterConfig) ??
159
- trackLanes(self.parentTrack.configuration)
154
+ (adapter && configHaplotypes(adapter)) ?? (track && trackLanes(track))
160
155
  )
161
156
  },
162
157
  // the linear view's zoom past which the track's coarse pair is cut, or
163
158
  // undefined for a track with none
164
159
  get coarseAboveBpPerPx() {
165
- return coarseHandover(self.adapterConfig.coarse)
160
+ return coarseHandover(self.sourceAdapter?.coarse)
166
161
  },
167
162
  }))
168
163
  .views(self => ({
@@ -175,13 +170,13 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
175
170
  },
176
171
  // Whether a zoom has moved far enough from the one the drawing was
177
172
  // folded for that folding again would show or hide more. A graph with
178
- // walks is never folded.
173
+ // walks is never folded, and a fold rounded to 0 bp counts as 1 bp.
179
174
  foldDrifted(bpPerPx: number) {
180
175
  const want = FOLD_PX * bpPerPx
181
176
  const had = self.cutFoldBp
182
177
  return (
183
178
  !self.graph?.paths?.length &&
184
- (want >= 2 * had ||
179
+ (want >= 2 * Math.max(had, 1) ||
185
180
  (self.foldedBelowBp !== undefined && want <= had / 2))
186
181
  )
187
182
  },
@@ -267,15 +262,16 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
267
262
  setConf(self, slot as keyof GraphGrammar, value)
268
263
  }
269
264
  },
270
- // The setters describe the next cut; the caller re-cuts.
265
+ // The setters describe the next cut, which recut makes
271
266
  setSubgraphContext(hops: number) {
272
267
  self.subgraphContext = hops
268
+ self.dense = undefined
273
269
  },
274
270
  setSubgraphHaplotypes(haplotypes: string[] | undefined) {
275
271
  self.subgraphHaplotypes = haplotypes
276
272
  self.dense = undefined
277
273
  },
278
- setDense(window: DenseWindow | undefined) {
274
+ setDense(window: SubgraphRegion | undefined) {
279
275
  self.dense = window
280
276
  },
281
277
  setHaplotypeNames(names: string[] | undefined) {
@@ -288,13 +284,11 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
288
284
  // a fine one does, since a tier is the same graph folded.
289
285
  cut() {
290
286
  const region = self.cutRegion
291
- if (!region) {
287
+ const adapterConfig = self.sourceAdapter
288
+ if (!region || !adapterConfig) {
292
289
  return
293
290
  }
294
- const problem = offReferenceProblem(
295
- graphReferenceAssembly(self.parentTrack.configuration),
296
- region.assemblyName,
297
- )
291
+ const problem = self.offReference(region)
298
292
  if (problem) {
299
293
  self.clearGraph()
300
294
  self.setError(new Error(problem))
@@ -305,17 +299,9 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
305
299
  FOLD_PX * (self.settledWindow?.bpPerPx ?? self.host?.bpPerPx ?? 0),
306
300
  )
307
301
  return self.cutSubgraph(
308
- self.adapterConfig,
302
+ adapterConfig,
309
303
  region,
310
- {
311
- hops: self.subgraphContext,
312
- haplotypes: self.cutHaplotypes,
313
- tier: coarse ? 'coarse' : undefined,
314
- ...(self.chosenLayoutMode === 'walkrows' ? { walkRows: true } : {}),
315
- ...(layoutModeByValue(self.chosenLayoutMode).wholeWalks
316
- ? { snarls: 'overlapping' as const }
317
- : {}),
318
- },
304
+ { ...self.cutOptions, tier: coarse ? 'coarse' : undefined },
319
305
  self.cutFoldBp,
320
306
  )
321
307
  },
@@ -353,10 +339,16 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
353
339
  ) {
354
340
  return false
355
341
  }
356
- // The error is the latest cut's, since a cut clears it as it
357
- // starts and an outrun cut sets nothing
358
- void Promise.resolve(self.recutAt(seen)).then(() => {
359
- if (isAlive(self) && isNodeLimitError(self.error)) {
342
+ // An outrun cut resolves without touching the error, so the error
343
+ // is this cut's only while no later one has started
344
+ const cut = self.recutAt(seen)
345
+ const recut = self.recuts
346
+ void Promise.resolve(cut).then(() => {
347
+ if (
348
+ isAlive(self) &&
349
+ self.recuts === recut &&
350
+ isNodeLimitError(self.error)
351
+ ) {
360
352
  this.refuseDenseCut(seen)
361
353
  }
362
354
  })
@@ -369,16 +361,23 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
369
361
  self.cutRegion = undefined
370
362
  this.settleOn(self.settledWindow ?? seen)
371
363
  },
372
- relayoutFrom(fromMode: LayoutModeValue) {
373
- const from = layoutModeByValue(fromMode)
374
- const to = layoutModeByValue(self.chosenLayoutMode)
364
+ // Cut the region again with the current options, or the window on
365
+ // screen where a refused cut left no region
366
+ recut() {
367
+ if (self.cutRegion) {
368
+ void self.cut()
369
+ } else if (self.settledWindow) {
370
+ this.settleOn(self.settledWindow)
371
+ }
372
+ },
373
+ relayoutFrom(from: LayoutModeValue) {
375
374
  const seen = self.host ? hostWindow(self.host) : undefined
376
375
  if (
377
376
  seen &&
378
377
  !self.regionTooLarge &&
379
- (to.cutMargins !== from.cutMargins ||
380
- to.wholeWalks !== from.wholeWalks ||
381
- (from.value === 'walkrows') !== (to.value === 'walkrows'))
378
+ (self.cutChangedFrom(from) ||
379
+ layoutModeByValue(from).cutMargins !==
380
+ layoutModeByValue(self.chosenLayoutMode).cutMargins)
382
381
  ) {
383
382
  return self.recutAt(seen)
384
383
  }
@@ -396,18 +395,23 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
396
395
  }))
397
396
  .actions(self => ({
398
397
  // A failed read leaves the picker taking typed names
399
- async fetchHaplotypeNames(adapterConfig: Record<string, unknown>) {
398
+ async fetchHaplotypeNames(
399
+ adapterConfig: Record<string, unknown>,
400
+ signal?: AbortSignal,
401
+ ) {
400
402
  try {
401
403
  const names = await getSession(self).rpcManager.call(
402
404
  getRpcSessionId(self),
403
405
  'GetGraphHaplotypes',
404
- { adapterConfig },
406
+ { adapterConfig, signal },
405
407
  )
406
- if (isAlive(self) && self.adapterConfig === adapterConfig) {
408
+ if (isAlive(self) && self.sourceAdapter === adapterConfig) {
407
409
  self.setHaplotypeNames(names)
408
410
  }
409
411
  } catch (e) {
410
- console.warn('[LinearGraphDisplay] no haplotype names', e)
412
+ if (!signal?.aborted) {
413
+ console.warn('[LinearGraphDisplay] no haplotype names', e)
414
+ }
411
415
  }
412
416
  },
413
417
  }))
@@ -456,15 +460,24 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
456
460
  if (self.cutRegion && !self.graph) {
457
461
  void self.cut()
458
462
  }
463
+ let namesRead: AbortController | undefined
464
+ addDisposer(self, () => {
465
+ namesRead?.abort()
466
+ })
459
467
  addDisposer(
460
468
  self,
461
469
  reaction(
462
- () =>
463
- walkIndexed(self.adapterConfig) ? self.adapterConfig : undefined,
470
+ () => {
471
+ const adapter = self.sourceAdapter
472
+ return adapter && walkIndexed(adapter) ? adapter : undefined
473
+ },
464
474
  adapterConfig => {
475
+ namesRead?.abort()
476
+ namesRead = undefined
465
477
  self.setHaplotypeNames(undefined)
466
478
  if (adapterConfig) {
467
- void self.fetchHaplotypeNames(adapterConfig)
479
+ namesRead = new AbortController()
480
+ void self.fetchHaplotypeNames(adapterConfig, namesRead.signal)
468
481
  }
469
482
  },
470
483
  { fireImmediately: true, name: 'GraphHaplotypeNames' },
@@ -579,6 +592,7 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
579
592
  const start = Math.floor(seen.start)
580
593
  const end = Math.ceil(seen.end)
581
594
  return {
595
+ ...paneSettings(self),
582
596
  loadedTrackId: trackId,
583
597
  loadedRegion: {
584
598
  refName: seen.refName,
@@ -586,19 +600,10 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
586
600
  start,
587
601
  end,
588
602
  },
589
- subgraphContext: self.subgraphContext,
590
603
  subgraphHaplotypes: self.cutHaplotypes,
591
604
  maxRegionBp: Math.max(self.maxRegionBp, end - start),
592
605
  ...self.grammar,
593
606
  layoutMode: self.chosenLayoutMode,
594
- referencePath: self.referencePath,
595
- geneTrackId: self.geneTrackId,
596
- walkLayers: self.walkLayers,
597
- layoutEngine: self.layoutEngine,
598
- layoutQuality: self.layoutQuality,
599
- bubbleSpread: self.bubbleSpread,
600
- linearLayout: self.linearLayout,
601
- maxGraphNodes: self.maxGraphNodes,
602
607
  connectedViewId: self.host?.id,
603
608
  } satisfies GraphViewSpec
604
609
  },
@@ -616,16 +621,18 @@ export function stateModelFactory(configSchema: LinearGraphDisplayConfigModel) {
616
621
  // graph, the config's default set or the assemblies the track names,
617
622
  // or a list chosen in Graph settings
618
623
  cutMenuItems(): MenuItem[] {
619
- if (!cutsByHaplotype(self.adapterConfig)) {
624
+ const adapter = self.sourceAdapter
625
+ const track = self.sourceTrack
626
+ if (!adapter || !track || !cutsByHaplotype(adapter)) {
620
627
  return []
621
628
  }
622
- const defaults = configHaplotypes(self.adapterConfig)
623
- const lanes = trackLanes(self.parentTrack.configuration)
629
+ const defaults = configHaplotypes(adapter)
630
+ const lanes = trackLanes(track)
624
631
  const names = self.haplotypeNames
625
632
  const chosen = self.subgraphHaplotypes
626
633
  const recut = (haplotypes: string[] | undefined) => {
627
634
  self.setSubgraphHaplotypes(haplotypes)
628
- void self.cut()
635
+ self.recut()
629
636
  }
630
637
  return [
631
638
  { type: 'subHeader', label: 'Load' },
@@ -4,11 +4,13 @@ import {
4
4
  bubbleLabel,
5
5
  parseBubbleLine,
6
6
  } from '@jbrowse/bandage-core/bubbles/bubbleLine'
7
+ import PluginManager from '@jbrowse/core/PluginManager'
7
8
  import { firstValueFrom } from 'rxjs'
8
9
  import { toArray } from 'rxjs/operators'
9
10
 
10
11
  import Adapter from './MinigraphBubbleAdapter.ts'
11
12
  import configSchema from './configSchema.ts'
13
+ import MinigraphBubbleAdapterF from './index.ts'
12
14
 
13
15
  // Unmodified `gfatools bubble` output cut to chr6:32.4-32.7 Mb, so the column
14
16
  // order here is the real one. Its stable names are bare (`chr6`) rather than
@@ -36,6 +38,12 @@ const mhc = {
36
38
  end: 32420000,
37
39
  }
38
40
 
41
+ test("the byte gate measures a region from the bubble file's index", async () => {
42
+ const adapter = makeAdapter()
43
+ expect(await adapter.getRegionByteSize([mhc])).toBeGreaterThan(0)
44
+ expect(await adapter.getRegionByteSize([{ ...mhc, refName: 'chr7' }])).toBe(0)
45
+ })
46
+
39
47
  test('getRefNames lists the sequences the bubbles sit on', async () => {
40
48
  expect(await makeAdapter().getRefNames()).toEqual(['chr6'])
41
49
  })
@@ -155,3 +163,16 @@ test('reports assembly-facing contigs for a PanSN-named file', async () => {
155
163
  const adapter = makeAdapter()
156
164
  expect(await adapter.getRefNames({ assemblyName: 'hg38' })).toEqual(['chr6'])
157
165
  })
166
+
167
+ test("the adapter type expands the uri shorthand with the schema's preprocessor", () => {
168
+ const pluginManager = new PluginManager()
169
+ MinigraphBubbleAdapterF(pluginManager)
170
+ pluginManager.createPluggableElements()
171
+ const { normalizeSnapshot } = pluginManager.getAdapterType(
172
+ 'MinigraphBubbleAdapter',
173
+ )
174
+ expect(normalizeSnapshot?.({ uri: 'bb.bed.gz' })).toMatchObject({
175
+ bubblesLocation: { uri: 'bb.bed.gz' },
176
+ index: { location: { uri: 'bb.bed.gz.tbi' } },
177
+ })
178
+ })
@@ -11,36 +11,28 @@ import { PanSNRefNames, openTabixSlot } from '../panSNTabix.ts'
11
11
  import { getLines } from '../tabixRange.ts'
12
12
 
13
13
  import type { MinigraphBubbleAdapterConfig } from './configSchema.ts'
14
- import type PluginManager from '@jbrowse/core/PluginManager'
15
14
  import type { BaseOptions } from '@jbrowse/core/data_adapters/BaseAdapter'
16
- import type { getSubAdapterType } from '@jbrowse/core/data_adapters/dataAdapterCache'
17
15
  import type { Feature } from '@jbrowse/core/util'
18
16
  import type { Region } from '@jbrowse/core/util/types'
19
17
 
20
18
  export default class MinigraphBubbleAdapter extends BaseFeatureDataAdapter<MinigraphBubbleAdapterConfig> {
21
19
  public static capabilities = ['getFeatures', 'getRefNames']
22
20
 
23
- private readonly bubbles
21
+ private readonly bubbles = openTabixSlot(this, ['bubblesLocation'], ['index'])
24
22
  // `gfatools bubble` names each row after the graph's stable sequence, so a
25
23
  // Minigraph-Cactus graph produces PanSN rows (`GRCh38#0#chr6`) where a plain
26
24
  // minigraph graph produces bare ones (`chr6`). Same resolution the segment
27
25
  // adapter does, through the same `assemblyNameToPanSN` slot.
28
- private readonly refNames
29
-
30
- public constructor(
31
- config: MinigraphBubbleAdapterConfig,
32
- getSubAdapter?: getSubAdapterType,
33
- pluginManager?: PluginManager,
34
- ) {
35
- super(config, getSubAdapter, pluginManager)
36
- this.bubbles = openTabixSlot(this, ['bubblesLocation'], ['index'])
37
- this.refNames = new PanSNRefNames(this.bubbles, this)
38
- }
26
+ private readonly refNames = new PanSNRefNames(this.bubbles, this)
39
27
 
40
28
  async getRefNames(opts: BaseOptions = {}) {
41
29
  return this.refNames.assemblyRefNames(opts)
42
30
  }
43
31
 
32
+ async getRegionByteSize(regions: Region[], opts: BaseOptions = {}) {
33
+ return this.refNames.regionBytes(regions, opts)
34
+ }
35
+
44
36
  public async hasDataForRefName() {
45
37
  return true
46
38
  }
@@ -1,6 +1,6 @@
1
1
  import { ConfigurationSchema } from '@jbrowse/core/configuration'
2
2
 
3
- import { tabixIndexSchema, tbiBeside } from '../panSNTabix.ts'
3
+ import { fileLocationSlot, tabixIndexSchema, tbiBeside } from '../panSNTabix.ts'
4
4
 
5
5
  import type { Instance } from '@jbrowse/mobx-state-tree'
6
6
 
@@ -25,7 +25,7 @@ import type { Instance } from '@jbrowse/mobx-state-tree'
25
25
  * ```
26
26
  */
27
27
 
28
- export function normalizeSnapshot(snap: Record<string, unknown>) {
28
+ function normalizeSnapshot(snap: Record<string, unknown>) {
29
29
  const { uri, baseUri, csi } = snap
30
30
  return typeof uri === 'string'
31
31
  ? {
@@ -42,13 +42,7 @@ const MinigraphBubbleAdapter = ConfigurationSchema(
42
42
  /**
43
43
  * #slot
44
44
  */
45
- bubblesLocation: {
46
- type: 'fileLocation',
47
- defaultValue: {
48
- uri: '/path/to/graph.bb.bed.gz',
49
- locationType: 'UriLocation',
50
- },
51
- },
45
+ bubblesLocation: fileLocationSlot('/path/to/graph.bb.bed.gz'),
52
46
  /**
53
47
  * #slot
54
48
  */
@@ -1,6 +1,6 @@
1
1
  import AdapterType from '@jbrowse/core/pluggableElementTypes/AdapterType'
2
2
 
3
- import configSchema, { normalizeSnapshot } from './configSchema.ts'
3
+ import configSchema from './configSchema.ts'
4
4
 
5
5
  import type PluginManager from '@jbrowse/core/PluginManager'
6
6
 
@@ -10,7 +10,6 @@ export default function MinigraphBubbleAdapterF(pluginManager: PluginManager) {
10
10
  new AdapterType({
11
11
  name: 'MinigraphBubbleAdapter',
12
12
  displayName: 'Minigraph bubble BED adapter',
13
- normalizeSnapshot,
14
13
  configSchema,
15
14
  adapterMetadata: {
16
15
  category: 'Graph adapters',
@@ -1,14 +1,19 @@
1
- import { readFileSync } from 'node:fs'
1
+ import { execFileSync } from 'node:child_process'
2
+ import { mkdtempSync, readFileSync } from 'node:fs'
3
+ import { tmpdir } from 'node:os'
4
+ import { join } from 'node:path'
2
5
  import { gunzipSync } from 'node:zlib'
3
6
 
4
7
  import { TabixIndexedFile } from '@gmod/tabix'
5
8
  import { parseGFA } from '@jbrowse/bandage-core/gfa-core/index'
9
+ import PluginManager from '@jbrowse/core/PluginManager'
6
10
  import { readConfObject } from '@jbrowse/core/configuration'
7
11
  import { firstValueFrom } from 'rxjs'
8
12
  import { toArray } from 'rxjs/operators'
9
13
 
10
14
  import Adapter from './RgfaTabixAdapter.ts'
11
15
  import configSchema from './configSchema.ts'
16
+ import RgfaTabixAdapterF from './index.ts'
12
17
  import { linkKey, parseLinkLine } from './rgfaBed.ts'
13
18
 
14
19
  import type { WalkCut } from './walkRowRuns.ts'
@@ -79,6 +84,16 @@ test('getFeatures returns the segments on a stable sequence', async () => {
79
84
  ])
80
85
  })
81
86
 
87
+ test("the byte gate measures a region from the segment file's index", async () => {
88
+ const bytes = vi.spyOn(TabixIndexedFile.prototype, 'bytesForRegions')
89
+ const size = await makeAdapter().getRegionByteSize([k12])
90
+ expect(size).toBeGreaterThan(0)
91
+ expect(bytes.mock.calls.map(call => call[0])).toEqual([
92
+ [{ refName: 'K12#1#chr', start: k12.start, end: k12.end }],
93
+ ])
94
+ bytes.mockRestore()
95
+ })
96
+
82
97
  test('getFeatures resolves a PanSN name given unqualified', async () => {
83
98
  const qualified = await firstValueFrom(
84
99
  makeAdapter()
@@ -119,6 +134,24 @@ test('getSubgraph reaches off-reference neighbours', async () => {
119
134
  )
120
135
  })
121
136
 
137
+ // node runs the script with type stripping, which refuses a parameter property
138
+ // or an enum anywhere among the cut's imports
139
+ test('scripts/dump-subgraph.ts writes the cut getSubgraph makes', async () => {
140
+ const out = join(mkdtempSync(join(tmpdir(), 'dump-subgraph-')), 'cut.gfa')
141
+ const window = { ...k12, start: 1_000_000, end: 1_100_000 }
142
+ execFileSync(process.execPath, [
143
+ require.resolve('../../scripts/dump-subgraph.ts'),
144
+ prefix,
145
+ 'K12',
146
+ 'chr',
147
+ String(window.start),
148
+ String(window.end),
149
+ out,
150
+ ])
151
+ const cut = gfaText(await makeAdapter().getSubgraph(window, { hops: 1 }))
152
+ expect(readFileSync(out, 'utf8')).toBe(`${cut}\n`)
153
+ })
154
+
122
155
  test('getSubgraph is byte-identical across calls', async () => {
123
156
  const adapter = makeAdapter()
124
157
  expect(await adapter.getSubgraph(k12)).toBe(await adapter.getSubgraph(k12))
@@ -407,6 +440,17 @@ test("getSubgraph with tier: 'coarse' cuts the coarse pair", async () => {
407
440
  expect(bubbles.every(n => fineIds.has(n.id))).toBe(true)
408
441
  })
409
442
 
443
+ test("the adapter type expands the uri shorthand with the schema's preprocessor", () => {
444
+ const pluginManager = new PluginManager()
445
+ RgfaTabixAdapterF(pluginManager)
446
+ pluginManager.createPluggableElements()
447
+ const { normalizeSnapshot } = pluginManager.getAdapterType('RgfaTabixAdapter')
448
+ expect(normalizeSnapshot?.({ uri: 'hprc', walksUri: 'w' })).toMatchObject({
449
+ segmentsLocation: { uri: 'hprc.segs.bed.gz' },
450
+ walksLocation: { uri: 'w.walks.bed.gz' },
451
+ })
452
+ })
453
+
410
454
  test('the coarse uri shorthand resolves a pair against the adapter baseUri', () => {
411
455
  const config = configSchema.create({
412
456
  uri: 'hprc',