diff --git a/src/app/components/analysis-panel/analysis-panel.component.ts b/src/app/components/analysis-panel/analysis-panel.component.ts index ec0e09a761ceeab008045ce59e8b9707c1f9b8ed..a29f32c027a7a559b72fdbc1ab5a5ffa61c0f790 100644 --- a/src/app/components/analysis-panel/analysis-panel.component.ts +++ b/src/app/components/analysis-panel/analysis-panel.component.ts @@ -203,7 +203,7 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit // @ts-ignore for (const g of Object.values(options.groups)) { // @ts-ignore - delete g.renderer + delete g.renderer; } this.drugstoneConfig.config.physicsOn = !isBig; this.networkHandler.activeNetwork.networkInternal = new vis.Network(container, this.nodeData, options); @@ -247,7 +247,8 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit if (nodeIds.length > 0) { const nodeId = nodeIds[0]; const node = this.nodeData.nodes.get(nodeId); - if (node.nodeType === 'drug' || node.drugstoneId === undefined || node.drugstoneType !== 'protein') { + if (node.drugstoneId === undefined || node.nodeType === 'drug' || node.drugstoneType !== 'protein') { + this.analysis.unmappedNodeToast(); return; } const wrapper = getWrapperFromNode(node); @@ -294,7 +295,7 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit selected, this.networkHandler.activeNetwork.getGradient(item.id), this.networkHandler.activeNetwork.nodeRenderer - ) + ); updatedNodes.push(nodeStyled); } this.nodeData.nodes.update(updatedNodes); @@ -317,8 +318,9 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit const updatedNodes = []; this.nodeData.nodes.forEach((node) => { const isSeed = this.networkHandler.activeNetwork.highlightSeeds ? this.networkHandler.activeNetwork.seedMap[node.id] : false; - if (!isSeed) - return + if (!isSeed) { + return; + } const nodeStyled = NetworkSettings.getNodeStyle( node, this.myConfig, @@ -371,8 +373,8 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit this.analysis.switchSelection('main'); this.token = null; this.tokenChange.emit(this.token); - this.legendService.remove_from_context('drug') - this.legendService.remove_from_context('drugTarget') + this.legendService.remove_from_context('drug'); + this.legendService.remove_from_context('drugTarget'); this.emitVisibleItems(false); } @@ -399,12 +401,14 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit if (normalize) { normalizeFn(this.tableProteins); - if (this.task.info.target === 'drug') - normalizeFn(this.tableDrugs) + if (this.task.info.target === 'drug') { + normalizeFn(this.tableDrugs); + } } else { unnormalizeFn(this.tableProteins); - if (this.task.info.target === 'drug') - unnormalizeFn(this.tableDrugs) + if (this.task.info.target === 'drug') { + unnormalizeFn(this.tableDrugs); + } } } @@ -434,20 +438,20 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit this.proteins = []; this.effects = []; const network = result.network; - network.nodes = [...new Set<string>(network.nodes)] + network.nodes = [...new Set<string>(network.nodes)]; const details = attributes.details || {}; - const nodeIdMap = {} + const nodeIdMap = {}; // @ts-ignore Object.entries(details).filter(e => e[1].drugstoneType === 'protein').forEach(e => { // @ts-ignore e[1].drugstoneId.forEach(id => { - nodeIdMap[id] = e[1][identifier][0] - }) - }) + nodeIdMap[id] = e[1][identifier][0]; + }); + }); for (const nodeId of network.nodes) { if (details[nodeId]) { - const nodeDetails = details[nodeId] + const nodeDetails = details[nodeId]; nodeDetails.id = nodeDetails.id ? nodeDetails.id : (typeof nodeDetails.drugstoneId === 'string' ? nodeDetails.drugstoneId : nodeDetails.drugstoneId[0]); if (nodeDetails.drugstoneId && nodeDetails.drugstoneType === 'protein') { // node is protein from database, has been mapped on init to backend protein from backend @@ -464,13 +468,13 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit } else { // node is custom input from user, could not be mapped to backend protein nodeDetails.group = nodeDetails.group ? nodeDetails.group : 'default'; - nodeDetails.label = nodeDetails.label ? nodeDetails.label : nodeDetails[identifier] + nodeDetails.label = nodeDetails.label ? nodeDetails.label : nodeDetails[identifier]; } // further analysis and the button function can be used to highlight seeds // option to use scores[node] as gradient, but sccores are very small - nodes.push(NetworkSettings.getNodeStyle(nodeDetails as Node, config, false, false, 1, this.networkHandler.activeNetwork.nodeRenderer)) + nodes.push(NetworkSettings.getNodeStyle(nodeDetails as Node, config, false, false, 1, this.networkHandler.activeNetwork.nodeRenderer)); } else { - console.log("Missing details for " + nodeId) + console.log('Missing details for ' + nodeId); } } @@ -478,10 +482,10 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit const uniqEdges = []; for (const edge of network.edges) { - const e = mapCustomEdge(edge, this.myConfig) - e.from = e.from[0] === 'p' && nodeIdMap[e.from] ? nodeIdMap[e.from] : e.from - e.to = e.to[0] === 'p' && nodeIdMap[e.to] ? nodeIdMap[e.to] : e.to - const hash = e.from + "_" + e.to; + const e = mapCustomEdge(edge, this.myConfig); + e.from = e.from[0] === 'p' && nodeIdMap[e.from] ? nodeIdMap[e.from] : e.from; + e.to = e.to[0] === 'p' && nodeIdMap[e.to] ? nodeIdMap[e.to] : e.to; + const hash = e.from + '_' + e.to; if (uniqEdges.indexOf(hash) === -1) { uniqEdges.push(hash); edges.push(e); @@ -489,7 +493,7 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit } // remove self-edges/loops if (!config.selfReferences) { - edges = edges.filter(el => el.from !== el.to) + edges = edges.filter(el => el.from !== el.to); } return { nodes, @@ -498,15 +502,17 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit } getResultNodes() { - if (this.nodeData && this.nodeData['nodes']) - return this.nodeData['nodes'].get() - return [] + if (this.nodeData && this.nodeData['nodes']) { + return this.nodeData['nodes'].get(); + } + return []; } getResultEdges() { - if (this.nodeData && this.nodeData['edges']) - return this.nodeData['edges'].get().filter(e => !e.id || !e.groupName || (typeof e.from === 'string' && typeof e.to === 'string')) - return [] + if (this.nodeData && this.nodeData['edges']) { + return this.nodeData['edges'].get().filter(e => !e.id || !e.groupName || (typeof e.from === 'string' && typeof e.to === 'string')); + } + return []; } public tableProteinSelection = (e): void => { @@ -528,7 +534,7 @@ export class AnalysisPanelComponent implements OnInit, OnChanges, AfterViewInit } this.analysis.addItems(addItems); this.analysis.removeItems(removeItems); - } + }; public toggleFullscreen() { this.fullscreen = !this.fullscreen; diff --git a/src/app/components/info-tile/info-tile.component.html b/src/app/components/info-tile/info-tile.component.html index 2fbb52888e2b2d653c75dbaa1b0f66e12269e19c..72b4caa836fdabc15d5810b2f9495b78a7d401cb 100644 --- a/src/app/components/info-tile/info-tile.component.html +++ b/src/app/components/info-tile/info-tile.component.html @@ -132,11 +132,11 @@ </a> </p> <p - *ngIf="wrapper.data.groupName" + *ngIf="drugstoneConfig.config.nodeGroups[networkHandler.activeNetwork.selectedWrapper.data[networkHandler.activeNetwork.selectedWrapper.data.group === 'selectedNode' ? '_group':'group']].groupName" [ngClass]="{ 'text-normal': drugstoneConfig.smallStyle }" > <b><span>Group:</span></b> - <span class="is-capitalized"> {{ wrapper.data.groupName }}</span> + <span class="is-capitalized"> {{drugstoneConfig.config.nodeGroups[networkHandler.activeNetwork.selectedWrapper.data[networkHandler.activeNetwork.selectedWrapper.data.group === 'selectedNode' ? '_group':'group']].groupName }}</span> </p> </div> @@ -146,7 +146,7 @@ (valueChange)=" $event ? analysis.addItems([wrapper]) : analysis.removeItems([wrapper]) " - textOn="Seed" + textOn="Selected" textOff="Off" tooltipOn="Add protein to selection." tooltipOff="Remove protein from selection." diff --git a/src/app/components/info-tile/info-tile.component.ts b/src/app/components/info-tile/info-tile.component.ts index eca0380297456eea7622f525671cb0e6917adee5..9ae830a2ce50a4f61cca0a4940350b3c6e58f9d0 100644 --- a/src/app/components/info-tile/info-tile.component.ts +++ b/src/app/components/info-tile/info-tile.component.ts @@ -2,6 +2,7 @@ import {Component, Input, OnInit} from '@angular/core'; import {DrugstoneConfigService} from 'src/app/services/drugstone-config/drugstone-config.service'; import {Wrapper} from '../../interfaces'; import {AnalysisService} from '../../services/analysis/analysis.service'; +import {NetworkHandlerService} from '../../services/network-handler/network-handler.service'; @Component({ @@ -13,7 +14,7 @@ export class InfoTileComponent implements OnInit { @Input() public wrapper: Wrapper; @Input() public expressions: any; - constructor(public drugstoneConfig: DrugstoneConfigService, public analysis: AnalysisService) { + constructor(public drugstoneConfig: DrugstoneConfigService, public analysis: AnalysisService, public networkHandler: NetworkHandlerService) { } diff --git a/src/app/components/network/network.component.ts b/src/app/components/network/network.component.ts index 331fc3bb7e632d1dd2f44f5ef3ff343e78983a4a..643a00f5351fc77c9c4233cef98762e3b9d9de75 100644 --- a/src/app/components/network/network.component.ts +++ b/src/app/components/network/network.component.ts @@ -348,15 +348,26 @@ export class NetworkComponent implements OnInit { this.nodeRenderer = null; const updatedNodes = []; // for (const item of this.proteins) { - for (const node of this.nodeData.nodes.get().filter(n => n.drugstoneType === 'protein')) { - if (node.drugstoneId === undefined) { - // nodes that are not mapped to backend remain untouched - continue; - } - // const node: Node = this.nodeData.nodes.get(item.id); - if (!node) { - continue; - } + const proteins = this.nodeData.nodes.get().filter(n => n.drugstoneId && n.drugstoneType === 'protein') + for (const node of proteins) { + const pos = this.networkInternal.getPositions([node.id]); + node.x = pos[node.id].x; + node.y = pos[node.id].y; + Object.assign( + node, + NetworkSettings.getNodeStyle( + node, + this.drugstoneConfig.config, + node.isSeed && this.networkHandler.activeNetwork.highlightSeeds, + false, + 1.0, + this.nodeRenderer + ) + ); + updatedNodes.push(node); + } + this.nodeData.nodes.update(updatedNodes); + for (const node of proteins) { const pos = this.networkInternal.getPositions([node.id]); node.x = pos[node.id].x; node.y = pos[node.id].y; @@ -370,13 +381,13 @@ export class NetworkComponent implements OnInit { 1.0, this.nodeRenderer ) - ) + ); updatedNodes.push(node); } this.nodeData.nodes.update(updatedNodes); } else { - this.selectedTissue = tissue + this.selectedTissue = tissue; const minExp = 0.3; // filter out non-proteins, e.g. drugs const proteinNodes = []; diff --git a/src/app/config.ts b/src/app/config.ts index 437a268bdf4e0c70dc37045dbaaf7ce0a0a6b612..4d792077d0b6660b8516993c7f061fe0bf25817a 100644 --- a/src/app/config.ts +++ b/src/app/config.ts @@ -1,9 +1,9 @@ -import { AlgorithmTarget, AlgorithmType, QuickAlgorithmType } from './interfaces'; +import {AlgorithmTarget, AlgorithmType, QuickAlgorithmType} from './interfaces'; // https://visjs.github.io/vis-network/docs/network/nodes.html export interface NodeGroup { groupName?: string; - groupID?:string; + groupID?: string; color?: any; shape?: 'circle' | 'triangle' | 'star' | 'square' | 'image' | 'text' | 'ellipse' | 'box' | 'diamond' | 'dot'; type?: string; @@ -32,6 +32,7 @@ export type InteractionDrugProteinDB = 'NeDRex' | 'DrugBank' | 'DrugCentral' | ' export type InteractionProteinProteinDB = 'NeDRex' | 'BioGRID' | 'IID' | 'IntAct' | 'STRING' | 'APID'; export type IndicationDrugDisorderDB = 'NeDRex' | 'CTD' | 'DrugCentral' | 'DrugBank'; export type AssociatedProteinDisorderDB = 'NeDRex' | 'DisGeNET' | 'OMIM'; +export type AdvAnalysisContentTypes = 'drug-target-search' | 'drug-search' | 'enrichment-gprofiler'; // TODO: should this be external or integrated in the backend? @@ -50,6 +51,7 @@ export interface IConfig { showItemSelector: boolean; showSimpleAnalysis: boolean; showAdvAnalysis: boolean; + showAdvAnalysisContent: Array<AdvAnalysisContentTypes>; showTasks: boolean; showSelection: boolean; showNetworkMenu: false | 'left' | 'right'; @@ -73,7 +75,7 @@ export interface IConfig { nodeGroups: { [key: string]: NodeGroup }; edgeGroups: { [key: string]: EdgeGroup }; selfReferences: boolean; - customEdges: {default: boolean, selectable: boolean}; + customEdges: { default: boolean, selectable: boolean }; interactionDrugProtein: InteractionDrugProteinDB; interactionProteinProtein: InteractionProteinProteinDB; indicationDrugDisorder: IndicationDrugDisorderDB; @@ -90,37 +92,37 @@ export interface IConfig { const defaultNodeGroup: NodeGroup = { - // this default group is used for default node group values - // and is fallback in case user does not provide any nodeGroup - groupName: 'Default Node Group', - ctxRenderer: null, - color: { - border: '#FFFF00', - background: '#FFFF00', - highlight: { - border: '#FF0000', - background: '#FF0000' - }, - }, - shape: 'triangle', - type: 'default type', - detailShowLabel: false, - font: { - color: '#000000', - size: 14, - face: 'arial', - background: undefined, - strokeWidth: 0, - strokeColor: '#ffffff', - align: 'center', - bold: false, - ital: false, - boldital: false, - mono: false, - }, - borderWidth: 1, - borderWidthSelected: 2 - }; + // this default group is used for default node group values + // and is fallback in case user does not provide any nodeGroup + groupName: 'Default Node Group', + ctxRenderer: null, + color: { + border: '#FFFF00', + background: '#FFFF00', + highlight: { + border: '#FF0000', + background: '#FF0000' + }, + }, + shape: 'triangle', + type: 'default type', + detailShowLabel: false, + font: { + color: '#000000', + size: 14, + face: 'arial', + background: undefined, + strokeWidth: 0, + strokeColor: '#ffffff', + align: 'center', + bold: false, + ital: false, + boldital: false, + mono: false, + }, + borderWidth: 1, + borderWidthSelected: 2 +}; const connectorNodeGroup: NodeGroup = JSON.parse(JSON.stringify(defaultNodeGroup)); connectorNodeGroup.groupName = 'Connector Nodes'; @@ -143,6 +145,7 @@ export const defaultConfig: IConfig = { showItemSelector: true, showSimpleAnalysis: true, showAdvAnalysis: true, + showAdvAnalysisContent: ['drug-search', 'drug-target-search', 'enrichment-gprofiler'], showSelection: true, showTasks: true, showNetworkMenu: 'right', diff --git a/src/app/interfaces.ts b/src/app/interfaces.ts index cf6f8832a480353c55b74aba5228ad8b164a68c0..68bda05b5470ad6df6c77983ced9b0647274464a 100644 --- a/src/app/interfaces.ts +++ b/src/app/interfaces.ts @@ -200,6 +200,7 @@ export interface Wrapper { color?: string; interactions?: any; group?: string; + _group?: string; groupName?: string; proteinName?: Array<string>; uniprotAc?: Array<string>; diff --git a/src/app/network-settings.ts b/src/app/network-settings.ts index 01d0b927b4fb78ce1583de2e9f11add359c1a6c3..a645b6d7adf64017104be5fbc23f37db1aa46059 100644 --- a/src/app/network-settings.ts +++ b/src/app/network-settings.ts @@ -103,36 +103,38 @@ export class NetworkSettings { // use lodash merge to not lose deep attributes, e.g. "font.size" // @ts-ignore if (node._group) + { // @ts-ignore - node.group = node._group + node.group = node._group; + } // @ts-ignore if (node._shadow) { // @ts-ignore - node.shadow = node._shadow - }else{ + node.shadow = node._shadow; + } else { if (config.nodeGroups[node.group].shadow) { - node.shadow = {enabled: config.nodeGroups[node.group].shadow} - node.shadow.color = 'rgba(0,0,0,0.5)' + node.shadow = {enabled: config.nodeGroups[node.group].shadow}; + node.shadow.color = 'rgba(0,0,0,0.5)'; } else { - node.shadow = {color: 'rgba(0,0,0,0.5)'} + node.shadow = {color: 'rgba(0,0,0,0.5)'}; } } if (isSeed) { // apply seed node style to node // @ts-ignore - node._group = node.group - node.group = 'seedNode' + node._group = node.group; + node.group = 'seedNode'; } // selection on purpose after seed style, so seed style will be combined with selection style if (isSelected) { // @ts-ignore - node._group = node.group + node._group = node.group; // apply selected node style to node - node.group = 'selectedNode' + node.group = 'selectedNode'; if (config.nodeGroups[node.group].shadow) { - node.shadow = {enabled: config.nodeGroups[node.group].shadow} - node.shadow.color = '#000000' + node.shadow = {enabled: config.nodeGroups[node.group].shadow}; + node.shadow.color = '#000000'; } else { - node.shadow = {color: '#000000'} + node.shadow = {color: '#000000'}; } } @@ -145,26 +147,26 @@ export class NetworkSettings { if (renderer !== null) { // @ts-ignore node.shape = 'custom'; - node.color = {opacity: gradient} - node.opacity = gradient + node.color = {opacity: gradient}; + node.opacity = gradient; if (isSeed) { // apply seed node style to node // @ts-ignore - node.color = config.nodeGroups[node.group].color - }else{ - delete node.color + node.color = config.nodeGroups[node.group].color; + } else { + delete node.color; } // @ts-ignore - node._shadow = node.shadow + node._shadow = node.shadow; if (config.nodeGroups[node.group].shadow) { - node.shadow = {enabled: config.nodeGroups[node.group].shadow} - node.shadow.color = 'rgba(0,0,0,0.5)' + node.shadow = {enabled: config.nodeGroups[node.group].shadow}; + node.shadow.color = 'rgba(0,0,0,0.5)'; } else { - node.shadow = {color: 'rgba(0,0,0,0.5)'} + node.shadow = {color: 'rgba(0,0,0,0.5)'}; } node.ctxRenderer = renderer; } else { - node.opacity = undefined + node.opacity = undefined; delete node.ctxRenderer; } diff --git a/src/app/pages/explorer-page/explorer-page.component.html b/src/app/pages/explorer-page/explorer-page.component.html index 9460ee255372bb9e4974e64d5b91b77e2c56d849..45d2120482c83f3f943be3c382220466e02f84c1 100644 --- a/src/app/pages/explorer-page/explorer-page.component.html +++ b/src/app/pages/explorer-page/explorer-page.component.html @@ -50,7 +50,7 @@ *ngIf="networkHandler.activeNetwork.selectedWrapper" > <span> - {{ drugstoneConfig.config.nodeGroups[networkHandler.activeNetwork.selectedWrapper.data.group].groupName }} + {{ drugstoneConfig.config.nodeGroups[networkHandler.activeNetwork.selectedWrapper.data[networkHandler.activeNetwork.selectedWrapper.data.group === 'selectedNode' ? '_group':'group']].groupName}} </span> </ng-container> </p> @@ -123,9 +123,9 @@ <p class="heading">Nodes</p> <p class="title"> {{ - networkHandler.activeNetwork.currentViewNodes != null - ? networkHandler.activeNetwork.currentViewNodes.length - : 0 + networkHandler.activeNetwork.currentViewNodes != null + ? networkHandler.activeNetwork.currentViewNodes.length + : 0 }} </p> </div> @@ -135,9 +135,9 @@ <p class="heading">Edges</p> <p class="title"> {{ - networkHandler.activeNetwork.currentViewEdges != null - ? networkHandler.activeNetwork.currentViewEdges.length - : 0 + networkHandler.activeNetwork.currentViewEdges != null + ? networkHandler.activeNetwork.currentViewEdges.length + : 0 }} </p> </div> @@ -227,7 +227,8 @@ </header> <div *ngIf="collapseAnalysis"> <div class="card-content"> - <div class="field"> + <div class="field" + *ngIf="!drugstoneConfig.config.showAdvAnalysisContent || drugstoneConfig.config.showAdvAnalysisContent.includes('drug-search')"> <div class="control" pTooltip="Find drug targets for the selected proteins." @@ -250,7 +251,7 @@ </button> </div> </div> - <div class="field"> + <div class="field" *ngIf="!drugstoneConfig.config.showAdvAnalysisContent || drugstoneConfig.config.showAdvAnalysisContent.includes('drug-target-search')"> <div class="control" pTooltip="Find drugs for the selected proteins." @@ -267,14 +268,14 @@ [disabled]="analysis.getCount() === 0" [ngClass]="{ 'text-small': drugstoneConfig.smallStyle }" > - <app-fa-solid-icon icon="capsules" classString="first-item-in-button"></app-fa-solid-icon> + <app-fa-solid-icon icon="capsules" classString="first-item-in-button"></app-fa-solid-icon> <span> {{ drugstoneConfig.config.taskDrugName }} </span> </button> </div> </div> - <div class="field"> + <div class="field" *ngIf="!drugstoneConfig.config.showAdvAnalysisContent || drugstoneConfig.config.showAdvAnalysisContent.includes('enrichment-gprofiler')"> <div class="control"> <a *ngIf="analysis.getCount() > 0" @@ -414,53 +415,53 @@ *ngIf="analysis.getCount() > 0" > <thead> - <tr> - <td>Label</td> - <td>Group</td> - <td *ngIf="drugstoneConfig.config.identifier !== 'symbol'"> - Symbol - </td> - <td *ngIf="drugstoneConfig.config.identifier !== 'uniprot'"> - Uniprot - </td> - <td>Actions</td> - </tr> + <tr> + <td>Label</td> + <td>Group</td> + <td *ngIf="drugstoneConfig.config.identifier !== 'symbol'"> + Symbol + </td> + <td *ngIf="drugstoneConfig.config.identifier !== 'uniprot'"> + Uniprot + </td> + <td>Actions</td> + </tr> </thead> <tbody> - <tr *ngFor="let p of analysis.getSelection()"> - <td> - <p class="is-capitalized">{{ p.data.label }}</p> - </td> - <td> - <p> - {{ - drugstoneConfig.config.nodeGroups[p.data['_group']][ - "groupName" - ] - }} - </p> - </td> - <td *ngIf="drugstoneConfig.config.identifier !== 'symbol'"> - <p>{{ p.data.symbol }}</p> - </td> - <td - *ngIf="drugstoneConfig.config.identifier !== 'uniprot'" - class="uniprot" - title="{{ p.data.uniprotAc }}" + <tr *ngFor="let p of analysis.getSelection()"> + <td> + <p class="is-capitalized">{{ p.data.label }}</p> + </td> + <td> + <p> + {{ + drugstoneConfig.config.nodeGroups[p.data['_group']][ + "groupName" + ] + }} + </p> + </td> + <td *ngIf="drugstoneConfig.config.identifier !== 'symbol'"> + <p>{{ p.data.symbol }}</p> + </td> + <td + *ngIf="drugstoneConfig.config.identifier !== 'uniprot'" + class="uniprot" + title="{{ p.data.uniprotAc }}" + > + <p>{{ p.data.uniprotAc }}</p> + </td> + <td> + <button + (click)="analysis.removeItems([p])" + class="button is-small is-danger is-outlined has-tooltip" + tooltipPosition="top" + pTooltip="Remove from selection." > - <p>{{ p.data.uniprotAc }}</p> - </td> - <td> - <button - (click)="analysis.removeItems([p])" - class="button is-small is-danger is-outlined has-tooltip" - tooltipPosition="top" - pTooltip="Remove from selection." - > - <app-fa-solid-icon icon="trash"></app-fa-solid-icon> - </button> - </td> - </tr> + <app-fa-solid-icon icon="trash"></app-fa-solid-icon> + </button> + </td> + </tr> </tbody> </table> <i *ngIf="analysis.getCount() === 0"> diff --git a/src/app/pages/explorer-page/explorer-page.component.ts b/src/app/pages/explorer-page/explorer-page.component.ts index 05da418ca7e63014c7d5ab11a197b4c11ab55022..2292ba0017fa364aec1794b31dc612f1d73f9990 100644 --- a/src/app/pages/explorer-page/explorer-page.component.ts +++ b/src/app/pages/explorer-page/explorer-page.component.ts @@ -309,7 +309,7 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { if (!this.drugstoneConfig.config.showSidebar) { // skip network options for selecting nodes when there are no options to use it - return + return; } this.networkHandler.activeNetwork.networkInternal.on('doubleClick', (properties) => { @@ -318,6 +318,7 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { const nodeId = nodeIds[0]; const node = this.nodeData.nodes.get(nodeId); if (node.drugstoneId === undefined || node.drugstoneType !== 'protein') { + this.analysis.unmappedNodeToast(); // skip if node is not a protein mapped to backend return; } diff --git a/src/app/services/analysis/analysis.service.ts b/src/app/services/analysis/analysis.service.ts index 54731865e1ffaab61049983cb8fb4e34cde68af7..83d5e71c48b801c208b9a14e47242503f31df03b 100644 --- a/src/app/services/analysis/analysis.service.ts +++ b/src/app/services/analysis/analysis.service.ts @@ -4,10 +4,10 @@ import {HttpClient} from '@angular/common/http'; import {environment} from '../../../environments/environment'; import {Injectable} from '@angular/core'; import {NetexControllerService} from '../netex-controller/netex-controller.service'; -import {DrugstoneConfigService} from "../drugstone-config/drugstone-config.service"; -import {NetworkHandlerService} from "../network-handler/network-handler.service"; -import { ToastService } from '../toast/toast.service'; -import { NodeGroup } from 'src/app/config'; +import {DrugstoneConfigService} from '../drugstone-config/drugstone-config.service'; +import {NetworkHandlerService} from '../network-handler/network-handler.service'; +import {ToastService} from '../toast/toast.service'; +import {NodeGroup} from 'src/app/config'; export type AlgorithmType = 'trustrank' @@ -74,11 +74,11 @@ export class AnalysisService { private tissues: Tissue[] = []; constructor( - public toast: ToastService, - private http: HttpClient, - public netex: NetexControllerService, - public drugstoneConfig: DrugstoneConfigService, - public networkHandler: NetworkHandlerService + public toast: ToastService, + private http: HttpClient, + public netex: NetexControllerService, + public drugstoneConfig: DrugstoneConfigService, + public networkHandler: NetworkHandlerService ) { const tokens = localStorage.getItem(this.tokensCookieKey); const finishedTokens = localStorage.getItem(this.tokensFinishedCookieKey); @@ -158,11 +158,11 @@ export class AnalysisService { this.networkHandler.activeNetwork.currentViewNodes.forEach((node) => { if (node.group !== group.groupID || node.drugstoneType !== 'protein') { // only consider nodes of group and proteins - return + return; } wrappers.push(getWrapperFromNode(node)); }); - this.addItems(wrappers) + this.addItems(wrappers); } public addAllToSelection() { @@ -170,11 +170,11 @@ export class AnalysisService { this.networkHandler.activeNetwork.currentViewNodes.forEach((node) => { if (node.drugstoneType !== 'protein') { // only consider proteins - return + return; } wrappers.push(getWrapperFromNode(node)); }); - this.addItems(wrappers) + this.addItems(wrappers); } // public addSeeds(nodes) { @@ -204,14 +204,14 @@ export class AnalysisService { nodes.forEach((node: Node) => { if (node.drugstoneType !== 'protein') { // only consider proteins - return + return; } const wrapper = getWrapperFromNode(node); if (!this.inSelection(wrapper)) { newSelection.push(wrapper); } }); - this.resetSelection() + this.resetSelection(); for (const wrapper of newSelection) { this.selectedItems.set(wrapper.id, wrapper); } @@ -266,9 +266,9 @@ export class AnalysisService { if (item.drugstoneType === 'protein') { seeds.push(item.id); } - }) + }); } - const target = ['connect', 'connectSelected'].includes(algorithm) ? 'drug-target' : 'drug' + const target = ['connect', 'connectSelected'].includes(algorithm) ? 'drug-target' : 'drug'; const parameters: any = { seeds: seeds, config: this.drugstoneConfig.config, @@ -296,7 +296,7 @@ export class AnalysisService { ' Once the computation finished you can view the results in the task list to the right.', type: 'success' }); - return { taskId: resp.token, algorithm: algorithm, target: target, params: parameters } + return {taskId: resp.token, algorithm: algorithm, target: target, params: parameters}; } async startAnalysis(algorithm, target: 'drug' | 'drug-target', parameters) { @@ -340,6 +340,13 @@ export class AnalysisService { }); } + unmappedNodeToast() { + this.toast.setNewToast({ + message: 'This node cannot be selected because either it could not be mapped correctly or it is not of type gene or protein.', + type: 'warning', + }); + } + public canLaunchTask(): boolean { return this.canLaunchNewTask; } @@ -348,8 +355,9 @@ export class AnalysisService { const watch = async () => { if (this.tokens.length > 0) { const newtasks = await this.getTasks(); - if (newtasks.length === 0) + if (newtasks.length === 0) { return; + } const newTaskIds = newtasks.map(t => t.token.toString()); this.tasks = newtasks.concat(this.tasks.filter(t => newTaskIds.indexOf(t.token) === -1)); if (!this.tasks) { diff --git a/src/index.html b/src/index.html index dec73108de81818de01e0d1b9bc5b810044f3bb4..5a5acd8dacf9aad1b4391023fe485520502d982b 100644 --- a/src/index.html +++ b/src/index.html @@ -95,7 +95,7 @@ <drugst-one id="netexp1" pluginId="2" groups='{"nodeGroups":{"important":{"type":"gene","color":"#ff881f","font":{"color":"#000000"},"groupName":"Seed","shape":"star"},"gene":{"type":"gene","color":"#4da300","font":{"color":"#f0f0f0"},"groupName":"Discovered target","shape":"circle"},"foundDrug":{"type":"drug","color":"#F12590","font":{"color":"#000000"},"groupName":"Drug","shape":"diamond"}},"edgeGroups":{"default":{"color":"#000000","groupName":"default edge"}}}' - config='{"identifier":"symbol","title":"ROBUST output network", "taskDrugName": "Drug Search", "showLegendNodes": true, "showLegendEdges": true, "showSidebar": "left", "showOverview": true, "legendPos": "left", "legendClass": "legend", "showQuery": true, "showItemSelector": true,"showSimpleAnalysis": false,"showAdvAnalysis": true,"showSelection": true,"showTasks": true,"showNetworkMenu": "right","showLegend": true,"showNetworkMenuButtonExpression": true, "showNetworkMenuButtonScreenshot": true,"showNetworkMenuButtonExportGraphml": true,"showNetworkMenuButtonAdjacentDrugs": true,"showNetworkMenuButtonCenter": true,"showConnectGenes": false,"networkMenuButtonAdjacentDrugsLabel": "Drugs","showNetworkMenuButtonAdjacentDisordersProteins": true,"networkMenuButtonAdjacentDisordersProteinsLabel": "Disorders (protein)","showNetworkMenuButtonAdjacentDisordersDrugs": true,"networkMenuButtonAdjacentDisordersDrugsLabel": "Disorders (drug)","showNetworkMenuButtonAnimation": true,"networkMenuButtonAnimationLabel": "Animation", "autofillEdges": false, "physicsOn": false,"useNedrexLicenced": true,"selfReferences": false, "interactionDrugProtein": "NeDRex", "indicationDrugDisorder": "NeDRex","nodeShadow": true,"edgeShadow": true, "algorithms": {"drug": ["trustrank", "closeness", "degree", "proximity"], "drug-target": ["trustrank", "multisteiner", "keypathwayminer", "degree", "closeness", "betweenness"]}, "associatedProteinDisorder": "NeDRex", "expandNetworkMenu": true}' + config='{ "identifier":"symbol","title":"ROBUST output network", "taskDrugName": "Drug Search", "showLegendNodes": true, "showLegendEdges": true, "showSidebar": "left", "showOverview": true, "legendPos": "left", "legendClass": "legend", "showQuery": true, "showItemSelector": true,"showSimpleAnalysis": false,"showAdvAnalysis": true,"showSelection": true,"showTasks": true,"showNetworkMenu": "right","showLegend": true,"showNetworkMenuButtonExpression": true, "showNetworkMenuButtonScreenshot": true,"showNetworkMenuButtonExportGraphml": true,"showNetworkMenuButtonAdjacentDrugs": true,"showNetworkMenuButtonCenter": true,"showConnectGenes": false,"networkMenuButtonAdjacentDrugsLabel": "Drugs","showNetworkMenuButtonAdjacentDisordersProteins": true,"networkMenuButtonAdjacentDisordersProteinsLabel": "Disorders (protein)","showNetworkMenuButtonAdjacentDisordersDrugs": true,"networkMenuButtonAdjacentDisordersDrugsLabel": "Disorders (drug)","showNetworkMenuButtonAnimation": true,"networkMenuButtonAnimationLabel": "Animation", "autofillEdges": false, "physicsOn": false,"useNedrexLicenced": true,"selfReferences": false, "interactionDrugProtein": "NeDRex", "indicationDrugDisorder": "NeDRex","nodeShadow": true,"edgeShadow": true, "algorithms": {"drug": ["trustrank", "closeness", "degree", "proximity"], "drug-target": ["trustrank", "multisteiner", "keypathwayminer", "degree", "closeness", "betweenness"]}, "associatedProteinDisorder": "NeDRex", "expandNetworkMenu": true}' network='{"nodes": [{"id": "UBE2I", "group": "gene"}, {"id": "EEF1A1", "group": "gene"}, {"id": "KDM5A", "group": "gene"}, {"id": "THOC2", "group": "gene"}, {"id": "XPO1", "group": "gene"}, {"id": "RPL4", "group": "gene"}, {"id": "TOP1", "group": "gene"}, {"id": "YWHAE", "group": "gene"}, {"id": "CHUK", "group": "gene"}, {"id": "HSP90AB1", "group": "gene"}, {"id": "CD6", "group": "important"}, {"id": "TYK2", "group": "important"}, {"id": "FSTL1", "group": "gene"}, {"id": "CBL", "group": "gene"}, {"id": "NR2F2", "group": "gene"}, {"id": "RUNX1T1", "group": "gene"}, {"id": "MED23", "group": "gene"}, {"id": "IFNAR1", "group": "gene"}, {"id": "LCOR", "group": "gene"}, {"id": "IL10", "group": "important"}, {"id": "NLRP3", "group": "important"}, {"id": "A2M", "group": "gene"}, {"id": "EIF4A1", "group": "gene"}, {"id": "HSPA4", "group": "gene"}, {"id": "ACTB", "group": "gene"}, {"id": "SNRPB", "group": "gene"}, {"id": "KIF1B", "group": "important"}, {"id": "HIST1H1B", "group": "gene"}, {"id": "EFNB3", "group": "gene"}, {"id": "ERP44", "group": "gene"}, {"id": "HSP90AA1", "group": "gene"}, {"id": "KIF2C", "group": "gene"}, {"id": "KCNJ10", "group": "important"}, {"id": "APOE", "group": "important"}, {"id": "RNF14", "group": "gene"}, {"id": "TM9SF1", "group": "gene"}, {"id": "TRIM28", "group": "gene"}, {"id": "RIPK2", "group": "gene"}, {"id": "IL1R1", "group": "gene"}, {"id": "IL1B", "group": "important"}, {"id": "PRDX2", "group": "gene"}, {"id": "GOPC", "group": "gene"}, {"id": "ARHGEF7", "group": "gene"}, {"id": "CASK", "group": "gene"}, {"id": "MYC", "group": "gene"}, {"id": "SNW1", "group": "gene"}, {"id": "KRT31", "group": "gene"}, {"id": "TSSC1", "group": "gene"}, {"id": "LRP2", "group": "gene"}, {"id": "VCAM1", "group": "important"}, {"id": "CRK", "group": "gene"}, {"id": "LGALS3BP", "group": "gene"}, {"id": "PCMT1", "group": "gene"}, {"id": "MLLT4", "group": "gene"}, {"id": "BRCA1", "group": "gene"}, {"id": "IL7R", "group": "important"}, {"id": "BAG1", "group": "gene"}, {"id": "RAB3B", "group": "gene"}, {"id": "MAPK1", "group": "gene"}, {"id": "CPSF7", "group": "gene"}, {"id": "STAT1", "group": "gene"}, {"id": "HLA-DPB1", "group": "important"}, {"id": "NCOR2", "group": "gene"}, {"id": "IL7", "group": "important"}, {"id": "TNFAIP3", "group": "important"}, {"id": "RNF31", "group": "gene"}, {"id": "IRF8", "group": "important"}, {"id": "PTPN11", "group": "gene"}, {"id": "CLEC16A", "group": "important"}, {"id": "BIRC3", "group": "gene"}, {"id": "DEFA1", "group": "gene"}, {"id": "POMC", "group": "important"}, {"id": "UBR4", "group": "gene"}, {"id": "SMARCA5", "group": "gene"}, {"id": "SEC24A", "group": "gene"}, {"id": "ADRB2", "group": "gene"}, {"id": "COPS2", "group": "gene"}, {"id": "TRAF3IP2", "group": "gene"}, {"id": "RBPJ", "group": "important"}, {"id": "RAB39B", "group": "gene"}, {"id": "NCOA6", "group": "gene"}, {"id": "IFNG", "group": "important"}, {"id": "SIAH1", "group": "gene"}, {"id": "CD58", "group": "important"}, {"id": "KRTAP10-8", "group": "gene"}, {"id": "WRAP73", "group": "gene"}, {"id": "FYN", "group": "gene"}, {"id": "GNAI2", "group": "gene"}, {"id": "YWHAH", "group": "gene"}, {"id": "CBLB", "group": "important"}, {"id": "IL2RA", "group": "important"}, {"id": "P2RX7", "group": "important"}, {"id": "CCND3", "group": "gene"}, {"id": "MCAM", "group": "important"}, {"id": "YBX3", "group": "gene"}, {"id": "IL1RN", "group": "important"}, {"id": "IFNB1", "group": "important"}, {"id": "FAF1", "group": "gene"}, {"id": "SPDL1", "group": "gene"}, {"id": "ELAVL1", "group": "gene"}, {"id": "IL12A", "group": "important"}, {"id": "LGALS8", "group": "gene"}, {"id": "GNAI3", "group": "gene"}, {"id": "VDR", "group": "important"}, {"id": "SNTA1", "group": "gene"}, {"id": "TNFRSF1A", "group": "important"}, {"id": "CD40", "group": "important"}, {"id": "RAP1GAP", "group": "gene"}, {"id": "PDGFRB", "group": "gene"}, {"id": "SELE", "group": "important"}, {"id": "VCL", "group": "gene"}, {"id": "IFI16", "group": "gene"}, {"id": "YWHAB", "group": "gene"}, {"id": "IL17A", "group": "important"}, {"id": "KIF11", "group": "gene"}, {"id": "GRB2", "group": "gene"}, {"id": "CNR1", "group": "important"}, {"id": "RELA", "group": "gene"}, {"id": "HSPA8", "group": "gene"}, {"id": "STAT4", "group": "important"}, {"id": "SND1", "group": "gene"}, {"id": "LRP8", "group": "gene"}, {"id": "GNAI1", "group": "gene"}, {"id": "F11R", "group": "gene"}, {"id": "HNRNPC", "group": "gene"}, {"id": "COPS5", "group": "gene"}, {"id": "ACTA2", "group": "gene"}, {"id": "FLNA", "group": "gene"}, {"id": "CSNK2A1", "group": "gene"}, {"id": "JUN", "group": "gene"}, {"id": "VDAC1", "group": "gene"}, {"id": "PSMC5", "group": "gene"}, {"id": "IL12B", "group": "gene"}, {"id": "SLAMF1", "group": "gene"}, {"id": "HLA-DRA", "group": "important"}, {"id": "APP", "group": "gene"}, {"id": "HLA-DPA1", "group": "gene"}, {"id": "BCHE", "group": "important"}, {"id": "ICAM1", "group": "important"}, {"id": "NLRC4", "group": "gene"}, {"id": "RNF41", "group": "gene"}, {"id": "COL14A1", "group": "gene"}, {"id": "YWHAG", "group": "gene"}, {"id": "MS4A1", "group": "gene"}, {"id": "SF1", "group": "gene"}, {"id": "CASP10", "group": "gene"}, {"id": "TP53", "group": "gene"}, {"id": "GC", "group": "important"}, {"id": "TRAF6", "group": "gene"}, {"id": "CASP1", "group": "important"}], "edges": [{"from": "UBE2I", "to": "KIF1B", "group": "default"}, {"from": "UBE2I", "to": "TNFRSF1A", "group": "default"}, {"from": "EEF1A1", "to": "VCAM1", "group": "default"}, {"from": "EEF1A1", "to": "KIF1B", "group": "default"}, {"from": "KDM5A", "to": "RBPJ", "group": "default"}, {"from": "KDM5A", "to": "VDR", "group": "default"}, {"from": "THOC2", "to": "VCAM1", "group": "default"}, {"from": "THOC2", "to": "KIF1B", "group": "default"}, {"from": "XPO1", "to": "RBPJ", "group": "default"}, {"from": "XPO1", "to": "VCAM1", "group": "default"}, {"from": "XPO1", "to": "RAP1GAP", "group": "default"}, {"from": "RPL4", "to": "APOE", "group": "default"}, {"from": "RPL4", "to": "ICAM1", "group": "default"}, {"from": "RPL4", "to": "VCAM1", "group": "default"}, {"from": "TOP1", "to": "NLRP3", "group": "default"}, {"from": "TOP1", "to": "IL7R", "group": "default"}, {"from": "TOP1", "to": "IRF8", "group": "default"}, {"from": "YWHAE", "to": "TNFAIP3", "group": "default"}, {"from": "YWHAE", "to": "HLA-DRA", "group": "default"}, {"from": "YWHAE", "to": "KIF1B", "group": "default"}, {"from": "CHUK", "to": "CD40", "group": "default"}, {"from": "CHUK", "to": "TNFRSF1A", "group": "default"}, {"from": "HSP90AB1", "to": "HLA-DRA", "group": "default"}, {"from": "HSP90AB1", "to": "VCAM1", "group": "default"}, {"from": "CD6", "to": "MYC", "group": "default"}, {"from": "TYK2", "to": "COPS5", "group": "default"}, {"from": "TYK2", "to": "IFNAR1", "group": "default"}, {"from": "TYK2", "to": "TRIM28", "group": "default"}, {"from": "TYK2", "to": "LGALS3BP", "group": "default"}, {"from": "TYK2", "to": "FYN", "group": "default"}, {"from": "TYK2", "to": "CBL", "group": "default"}, {"from": "TYK2", "to": "LRP8", "group": "default"}, {"from": "FSTL1", "to": "IL12A", "group": "default"}, {"from": "FSTL1", "to": "DEFA1", "group": "default"}, {"from": "CBL", "to": "IRF8", "group": "default"}, {"from": "CBL", "to": "TNFRSF1A", "group": "default"}, {"from": "NR2F2", "to": "RBPJ", "group": "default"}, {"from": "NR2F2", "to": "GC", "group": "default"}, {"from": "RUNX1T1", "to": "VDR", "group": "default"}, {"from": "RUNX1T1", "to": "RBPJ", "group": "default"}, {"from": "MED23", "to": "RBPJ", "group": "default"}, {"from": "MED23", "to": "VDR", "group": "default"}, {"from": "IFNAR1", "to": "IFNB1", "group": "default"}, {"from": "LCOR", "to": "RBPJ", "group": "default"}, {"from": "LCOR", "to": "VDR", "group": "default"}, {"from": "IL10", "to": "A2M", "group": "default"}, {"from": "NLRP3", "to": "FAF1", "group": "default"}, {"from": "NLRP3", "to": "YBX3", "group": "default"}, {"from": "NLRP3", "to": "HNRNPC", "group": "default"}, {"from": "NLRP3", "to": "SNRPB", "group": "default"}, {"from": "NLRP3", "to": "NLRC4", "group": "default"}, {"from": "NLRP3", "to": "HIST1H1B", "group": "default"}, {"from": "NLRP3", "to": "SMARCA5", "group": "default"}, {"from": "NLRP3", "to": "HSP90AA1", "group": "default"}, {"from": "A2M", "to": "IL1B", "group": "default"}, {"from": "A2M", "to": "APOE", "group": "default"}, {"from": "EIF4A1", "to": "VCAM1", "group": "default"}, {"from": "EIF4A1", "to": "KIF1B", "group": "default"}, {"from": "HSPA4", "to": "CD40", "group": "default"}, {"from": "HSPA4", "to": "KCNJ10", "group": "default"}, {"from": "ACTB", "to": "GC", "group": "default"}, {"from": "ACTB", "to": "ICAM1", "group": "default"}, {"from": "SNRPB", "to": "ICAM1", "group": "default"}, {"from": "KIF1B", "to": "YWHAH", "group": "default"}, {"from": "KIF1B", "to": "GOPC", "group": "default"}, {"from": "KIF1B", "to": "YWHAG", "group": "default"}, {"from": "KIF1B", "to": "SIAH1", "group": "default"}, {"from": "KIF1B", "to": "SEC24A", "group": "default"}, {"from": "KIF1B", "to": "BRCA1", "group": "default"}, {"from": "KIF1B", "to": "YWHAB", "group": "default"}, {"from": "KIF1B", "to": "ELAVL1", "group": "default"}, {"from": "HIST1H1B", "to": "VCAM1", "group": "default"}, {"from": "EFNB3", "to": "P2RX7", "group": "default"}, {"from": "ERP44", "to": "CD40", "group": "default"}, {"from": "ERP44", "to": "IL12B", "group": "default"}, {"from": "HSP90AA1", "to": "TNFAIP3", "group": "default"}, {"from": "HSP90AA1", "to": "HLA-DRA", "group": "default"}, {"from": "KIF2C", "to": "RBPJ", "group": "default"}, {"from": "KIF2C", "to": "TNFRSF1A", "group": "default"}, {"from": "KCNJ10", "to": "HSPA8", "group": "default"}, {"from": "KCNJ10", "to": "APP", "group": "default"}, {"from": "KCNJ10", "to": "BAG1", "group": "default"}, {"from": "KCNJ10", "to": "SNTA1", "group": "default"}, {"from": "KCNJ10", "to": "SIAH1", "group": "default"}, {"from": "KCNJ10", "to": "SEC24A", "group": "default"}, {"from": "APOE", "to": "LRP2", "group": "default"}, {"from": "APOE", "to": "ELAVL1", "group": "default"}, {"from": "APOE", "to": "HLA-DPA1", "group": "default"}, {"from": "APOE", "to": "CSNK2A1", "group": "default"}, {"from": "APOE", "to": "PCMT1", "group": "default"}, {"from": "APOE", "to": "LRP8", "group": "default"}, {"from": "APOE", "to": "PRDX2", "group": "default"}, {"from": "APOE", "to": "VDAC1", "group": "default"}, {"from": "RNF14", "to": "TNFAIP3", "group": "default"}, {"from": "RNF14", "to": "VDR", "group": "default"}, {"from": "TM9SF1", "to": "P2RX7", "group": "default"}, {"from": "TRIM28", "to": "STAT4", "group": "default"}, {"from": "TRIM28", "to": "VCAM1", "group": "default"}, {"from": "RIPK2", "to": "CASP1", "group": "default"}, {"from": "RIPK2", "to": "TNFRSF1A", "group": "default"}, {"from": "RIPK2", "to": "CD40", "group": "default"}, {"from": "IL1R1", "to": "IL1RN", "group": "default"}, {"from": "IL1R1", "to": "IL1B", "group": "default"}, {"from": "IL1B", "to": "ELAVL1", "group": "default"}, {"from": "IL1B", "to": "APP", "group": "default"}, {"from": "IL1B", "to": "CASP1", "group": "default"}, {"from": "IL1B", "to": "FYN", "group": "default"}, {"from": "PRDX2", "to": "VCAM1", "group": "default"}, {"from": "GOPC", "to": "IFNG", "group": "default"}, {"from": "ARHGEF7", "to": "CBLB", "group": "default"}, {"from": "ARHGEF7", "to": "ICAM1", "group": "default"}, {"from": "CASK", "to": "P2RX7", "group": "default"}, {"from": "MYC", "to": "VDR", "group": "default"}, {"from": "MYC", "to": "RBPJ", "group": "default"}, {"from": "SNW1", "to": "RBPJ", "group": "default"}, {"from": "SNW1", "to": "VDR", "group": "default"}, {"from": "KRT31", "to": "P2RX7", "group": "default"}, {"from": "TSSC1", "to": "CLEC16A", "group": "default"}, {"from": "LRP2", "to": "GC", "group": "default"}, {"from": "VCAM1", "to": "VCL", "group": "default"}, {"from": "VCAM1", "to": "CPSF7", "group": "default"}, {"from": "VCAM1", "to": "MLLT4", "group": "default"}, {"from": "VCAM1", "to": "UBR4", "group": "default"}, {"from": "VCAM1", "to": "SND1", "group": "default"}, {"from": "VCAM1", "to": "PCMT1", "group": "default"}, {"from": "VCAM1", "to": "VDAC1", "group": "default"}, {"from": "VCAM1", "to": "YWHAB", "group": "default"}, {"from": "VCAM1", "to": "PSMC5", "group": "default"}, {"from": "VCAM1", "to": "SF1", "group": "default"}, {"from": "CRK", "to": "STAT4", "group": "default"}, {"from": "CRK", "to": "CBLB", "group": "default"}, {"from": "LGALS3BP", "to": "SELE", "group": "default"}, {"from": "MLLT4", "to": "F11R", "group": "default"}, {"from": "MLLT4", "to": "RAP1GAP", "group": "default"}, {"from": "BRCA1", "to": "CASP1", "group": "default"}, {"from": "BRCA1", "to": "VDR", "group": "default"}, {"from": "IL7R", "to": "YBX3", "group": "default"}, {"from": "IL7R", "to": "HNRNPC", "group": "default"}, {"from": "IL7R", "to": "SF1", "group": "default"}, {"from": "BAG1", "to": "VDR", "group": "default"}, {"from": "RAB3B", "to": "IL12A", "group": "default"}, {"from": "RAB3B", "to": "SLAMF1", "group": "default"}, {"from": "MAPK1", "to": "VDR", "group": "default"}, {"from": "MAPK1", "to": "TNFRSF1A", "group": "default"}, {"from": "CPSF7", "to": "BCHE", "group": "default"}, {"from": "STAT1", "to": "VDR", "group": "default"}, {"from": "STAT1", "to": "TNFRSF1A", "group": "default"}, {"from": "HLA-DPB1", "to": "HLA-DPA1", "group": "default"}, {"from": "NCOR2", "to": "RBPJ", "group": "default"}, {"from": "NCOR2", "to": "VDR", "group": "default"}, {"from": "IL7", "to": "APP", "group": "default"}, {"from": "TNFAIP3", "to": "TNFRSF1A", "group": "default"}, {"from": "TNFAIP3", "to": "YWHAH", "group": "default"}, {"from": "TNFAIP3", "to": "YWHAG", "group": "default"}, {"from": "TNFAIP3", "to": "TP53", "group": "default"}, {"from": "TNFAIP3", "to": "KIF11", "group": "default"}, {"from": "RNF31", "to": "CD40", "group": "default"}, {"from": "RNF31", "to": "TNFRSF1A", "group": "default"}, {"from": "IRF8", "to": "COPS5", "group": "default"}, {"from": "IRF8", "to": "RELA", "group": "default"}, {"from": "IRF8", "to": "PDGFRB", "group": "default"}, {"from": "IRF8", "to": "COPS2", "group": "default"}, {"from": "IRF8", "to": "TRAF6", "group": "default"}, {"from": "PTPN11", "to": "CBLB", "group": "default"}, {"from": "PTPN11", "to": "SELE", "group": "default"}, {"from": "CLEC16A", "to": "RNF41", "group": "default"}, {"from": "CLEC16A", "to": "WRAP73", "group": "default"}, {"from": "CLEC16A", "to": "RAB39B", "group": "default"}, {"from": "BIRC3", "to": "CASP1", "group": "default"}, {"from": "BIRC3", "to": "TNFRSF1A", "group": "default"}, {"from": "DEFA1", "to": "BCHE", "group": "default"}, {"from": "POMC", "to": "APP", "group": "default"}, {"from": "POMC", "to": "UBR4", "group": "default"}, {"from": "SMARCA5", "to": "RBPJ", "group": "default"}, {"from": "ADRB2", "to": "STAT4", "group": "default"}, {"from": "ADRB2", "to": "MCAM", "group": "default"}, {"from": "COPS2", "to": "VDR", "group": "default"}, {"from": "TRAF3IP2", "to": "CD40", "group": "default"}, {"from": "TRAF3IP2", "to": "IL17A", "group": "default"}, {"from": "RBPJ", "to": "SND1", "group": "default"}, {"from": "RBPJ", "to": "APP", "group": "default"}, {"from": "NCOA6", "to": "CD40", "group": "default"}, {"from": "NCOA6", "to": "VDR", "group": "default"}, {"from": "CD58", "to": "LGALS8", "group": "default"}, {"from": "CD58", "to": "APP", "group": "default"}, {"from": "KRTAP10-8", "to": "P2RX7", "group": "default"}, {"from": "FYN", "to": "MCAM", "group": "default"}, {"from": "FYN", "to": "TNFRSF1A", "group": "default"}, {"from": "FYN", "to": "CBLB", "group": "default"}, {"from": "GNAI2", "to": "CNR1", "group": "default"}, {"from": "CBLB", "to": "PDGFRB", "group": "default"}, {"from": "CBLB", "to": "GRB2", "group": "default"}, {"from": "CBLB", "to": "TRAF6", "group": "default"}, {"from": "IL2RA", "to": "ICAM1", "group": "default"}, {"from": "IL2RA", "to": "SNTA1", "group": "default"}, {"from": "CCND3", "to": "GC", "group": "default"}, {"from": "CCND3", "to": "VDR", "group": "default"}, {"from": "MCAM", "to": "LGALS8", "group": "default"}, {"from": "YBX3", "to": "ICAM1", "group": "default"}, {"from": "IL1RN", "to": "RELA", "group": "default"}, {"from": "FAF1", "to": "CD40", "group": "default"}, {"from": "SPDL1", "to": "IL12A", "group": "default"}, {"from": "IL12A", "to": "F11R", "group": "default"}, {"from": "IL12A", "to": "COL14A1", "group": "default"}, {"from": "IL12A", "to": "IL12B", "group": "default"}, {"from": "GNAI3", "to": "CNR1", "group": "default"}, {"from": "VDR", "to": "JUN", "group": "default"}, {"from": "VDR", "to": "TP53", "group": "default"}, {"from": "VDR", "to": "PSMC5", "group": "default"}, {"from": "TNFRSF1A", "to": "HSPA8", "group": "default"}, {"from": "TNFRSF1A", "to": "TRAF6", "group": "default"}, {"from": "TNFRSF1A", "to": "GRB2", "group": "default"}, {"from": "TNFRSF1A", "to": "CASP10", "group": "default"}, {"from": "CD40", "to": "MS4A1", "group": "default"}, {"from": "RAP1GAP", "to": "CNR1", "group": "default"}, {"from": "SELE", "to": "ACTA2", "group": "default"}, {"from": "SELE", "to": "VCL", "group": "default"}, {"from": "SELE", "to": "FLNA", "group": "default"}, {"from": "IFI16", "to": "ICAM1", "group": "default"}, {"from": "IFI16", "to": "CASP1", "group": "default"}, {"from": "IL17A", "to": "TRAF6", "group": "default"}, {"from": "KIF11", "to": "CASP1", "group": "default"}, {"from": "GRB2", "to": "GC", "group": "default"}, {"from": "CNR1", "to": "GNAI1", "group": "default"}, {"from": "HSPA8", "to": "HLA-DRA", "group": "default"}, {"from": "STAT4", "to": "JUN", "group": "default"}, {"from": "ACTA2", "to": "GC", "group": "default"}, {"from": "FLNA", "to": "ICAM1", "group": "default"}, {"from": "CSNK2A1", "to": "ICAM1", "group": "default"}, {"from": "SLAMF1", "to": "BCHE", "group": "default"}, {"from": "HLA-DRA", "to": "MS4A1", "group": "default"}, {"from": "BCHE", "to": "SF1", "group": "default"}, {"from": "NLRC4", "to": "CASP1", "group": "default"}, {"from": "CASP10", "to": "CASP1", "group": "default"}]}' > </drugst-one>