@datagrok/bio 1.10.2 → 1.11.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.
- package/README.md +1 -1
- package/detectors.js +45 -20
- package/dist/package-test.js +600 -323
- package/dist/package.js +404 -264
- package/package.json +5 -4
- package/src/package-test.ts +1 -0
- package/src/package.ts +73 -30
- package/src/tests/WebLogo-positions-test.ts +10 -9
- package/src/tests/checkInputColumn-tests.ts +72 -0
- package/src/tests/convert-test.ts +6 -3
- package/src/tests/detectors-test.ts +3 -3
- package/src/tests/renderers-test.ts +56 -22
- package/src/tests/sequence-space-utils.ts +8 -3
- package/src/tests/splitters-test.ts +15 -0
- package/src/tests/test-sequnces-generators.ts +16 -21
- package/src/utils/cell-renderer.ts +18 -17
- package/src/utils/constants.ts +3 -5
- package/src/utils/convert.ts +5 -2
- package/src/utils/multiple-sequence-alignment.ts +5 -4
- package/src/utils/sequence-activity-cliffs.ts +120 -8
- package/src/utils/sequence-space.ts +1 -1
- package/src/utils/utils.ts +3 -2
- package/test-Bio-f1ac5a5eade4-a0f7e8c0.html +261 -0
- package/src/utils/split-to-monomers.ts +0 -8
- package/test-Bio-eb4783c07294-0aa1538b.html +0 -355
|
@@ -2,18 +2,19 @@ import * as C from './constants';
|
|
|
2
2
|
import * as DG from 'datagrok-api/dg';
|
|
3
3
|
import {AminoacidsPalettes} from '@datagrok-libraries/bio/src/aminoacids';
|
|
4
4
|
import {NucleotidesPalettes} from '@datagrok-libraries/bio/src/nucleotides';
|
|
5
|
-
import {
|
|
5
|
+
import {UnknownSeqPalettes} from '@datagrok-libraries/bio/src/unknown';
|
|
6
6
|
import {SplitterFunc, WebLogo} from '@datagrok-libraries/bio/src/viewers/web-logo';
|
|
7
7
|
import {SeqPalette} from '@datagrok-libraries/bio/src/seq-palettes';
|
|
8
8
|
import * as ui from 'datagrok-api/ui';
|
|
9
9
|
import {printLeftOrCentered, DrawStyle} from '@datagrok-libraries/bio/src/utils/cell-renderer';
|
|
10
|
+
import {UnitsHandler} from '@datagrok-libraries/bio/src/utils/units-handler';
|
|
10
11
|
|
|
11
12
|
const undefinedColor = 'rgb(100,100,100)';
|
|
12
13
|
const monomerToShortFunction: (amino: string, maxLengthOfMonomer: number) => string = WebLogo.monomerToShort;
|
|
13
14
|
const gapRenderer = 5;
|
|
14
15
|
|
|
15
16
|
|
|
16
|
-
function
|
|
17
|
+
function getPaletteByType(paletteType: string): SeqPalette {
|
|
17
18
|
switch (paletteType) {
|
|
18
19
|
case 'PT':
|
|
19
20
|
return AminoacidsPalettes.GrokGroups;
|
|
@@ -29,6 +30,10 @@ function getPalleteByType(paletteType: string): SeqPalette {
|
|
|
29
30
|
}
|
|
30
31
|
}
|
|
31
32
|
|
|
33
|
+
function getUpdatedWidth(grid: DG.Grid | null, g: CanvasRenderingContext2D, x: number, w: number): number {
|
|
34
|
+
return grid ? Math.min(grid.canvas.width - x, w) : g.canvas.width - x;
|
|
35
|
+
}
|
|
36
|
+
|
|
32
37
|
export function processSequence(subParts: string[]): [string[], boolean] {
|
|
33
38
|
const simplified = !subParts.some((amino, index) =>
|
|
34
39
|
amino.length > 1 &&
|
|
@@ -57,13 +62,12 @@ export class MacromoleculeSequenceCellRenderer extends DG.GridCellRenderer {
|
|
|
57
62
|
get defaultWidth(): number { return 230; }
|
|
58
63
|
|
|
59
64
|
onMouseMove(gridCell: DG.GridCell, e: MouseEvent): void {
|
|
60
|
-
if (gridCell.cell.column.getTag(
|
|
65
|
+
if (gridCell.cell.column.getTag(UnitsHandler.TAGS.aligned) !== 'SEQ.MSA') {
|
|
61
66
|
return;
|
|
62
67
|
}
|
|
63
68
|
const maxLengthWordsSum = gridCell.cell.column.temp['bio-sum-maxLengthWords'];
|
|
64
69
|
const maxIndex = gridCell.cell.column.temp['bio-maxIndex'];
|
|
65
|
-
|
|
66
|
-
const argsX = e.layerX - gridCell.gridColumn.left + (gridCell.gridColumn.left - gridCell.bounds.x);
|
|
70
|
+
const argsX = e.offsetX - gridCell.gridColumn.left + (gridCell.gridColumn.left - gridCell.bounds.x);
|
|
67
71
|
let left = 0;
|
|
68
72
|
let right = maxIndex;
|
|
69
73
|
let found = false;
|
|
@@ -108,23 +112,22 @@ export class MacromoleculeSequenceCellRenderer extends DG.GridCellRenderer {
|
|
|
108
112
|
g: CanvasRenderingContext2D, x: number, y: number, w: number, h: number, gridCell: DG.GridCell,
|
|
109
113
|
cellStyle: DG.GridCellStyle
|
|
110
114
|
): void {
|
|
111
|
-
const grid = gridCell.gridRow !== -1 ? gridCell.grid :
|
|
115
|
+
const grid = gridCell.gridRow !== -1 ? gridCell.grid : null;
|
|
112
116
|
const cell = gridCell.cell;
|
|
113
|
-
const
|
|
117
|
+
const paletteType = gridCell.cell.column.getTag(C.TAGS.ALPHABET);
|
|
114
118
|
const minDistanceRenderer = 50;
|
|
115
|
-
w =
|
|
119
|
+
w = getUpdatedWidth(grid, g, x, w);
|
|
116
120
|
g.save();
|
|
117
121
|
g.beginPath();
|
|
118
122
|
g.rect(x, y, w, h);
|
|
119
123
|
g.clip();
|
|
120
124
|
g.font = '12px monospace';
|
|
121
125
|
g.textBaseline = 'top';
|
|
122
|
-
const s: string = cell.value ?? '';
|
|
123
126
|
|
|
124
127
|
//TODO: can this be replaced/merged with splitSequence?
|
|
125
128
|
const units = gridCell.cell.column.getTag(DG.TAGS.UNITS);
|
|
126
129
|
|
|
127
|
-
const palette =
|
|
130
|
+
const palette = getPaletteByType(paletteType);
|
|
128
131
|
|
|
129
132
|
const separator = gridCell.cell.column.getTag('separator') ?? '';
|
|
130
133
|
const splitLimit = gridCell.bounds.width / 5;
|
|
@@ -183,10 +186,8 @@ export class MacromoleculeSequenceCellRenderer extends DG.GridCellRenderer {
|
|
|
183
186
|
g.fillStyle = undefinedColor;
|
|
184
187
|
let last = index === subParts.length - 1;
|
|
185
188
|
x1 = printLeftOrCentered(x1, y, w, h, g, monomerToShortFunction(amino, maxLengthOfMonomer), color, 0, true, 1.0, separator, last, drawStyle, maxLengthWords, index, gridCell);
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
}
|
|
189
|
-
return true;
|
|
189
|
+
return x1 - minDistanceRenderer - gridCell.gridColumn.left + (gridCell.gridColumn.left - gridCell.bounds.x) <= gridCell.bounds.width;
|
|
190
|
+
|
|
190
191
|
});
|
|
191
192
|
|
|
192
193
|
g.restore();
|
|
@@ -225,7 +226,7 @@ export class MonomerCellRenderer extends DG.GridCellRenderer {
|
|
|
225
226
|
g.font = `12px monospace`;
|
|
226
227
|
g.textBaseline = 'top';
|
|
227
228
|
|
|
228
|
-
const palette =
|
|
229
|
+
const palette = getPaletteByType(gridCell.tableColumn!.tags[C.TAGS.ALPHABET]);
|
|
229
230
|
const s: string = gridCell.cell.value ? gridCell.cell.value : '-';
|
|
230
231
|
const color = palette.get(s);
|
|
231
232
|
|
|
@@ -261,7 +262,7 @@ export class MacromoleculeDifferenceCellRenderer extends DG.GridCellRenderer {
|
|
|
261
262
|
const grid = gridCell.grid;
|
|
262
263
|
const cell = gridCell.cell;
|
|
263
264
|
|
|
264
|
-
w =
|
|
265
|
+
w = getUpdatedWidth(grid, g, w, x);
|
|
265
266
|
g.save();
|
|
266
267
|
g.beginPath();
|
|
267
268
|
g.rect(x, y, w, h);
|
|
@@ -285,7 +286,7 @@ export class MacromoleculeDifferenceCellRenderer extends DG.GridCellRenderer {
|
|
|
285
286
|
|
|
286
287
|
let palette: SeqPalette = UnknownSeqPalettes.Color;
|
|
287
288
|
if (units != 'HELM')
|
|
288
|
-
palette =
|
|
289
|
+
palette = getPaletteByType(units.substring(units.length - 2));
|
|
289
290
|
|
|
290
291
|
const vShift = 7;
|
|
291
292
|
for (let i = 0; i < subParts1.length; i++) {
|
package/src/utils/constants.ts
CHANGED
|
@@ -9,17 +9,13 @@ export enum COLUMNS_NAMES {
|
|
|
9
9
|
MEAN_DIFFERENCE = 'Mean difference',
|
|
10
10
|
}
|
|
11
11
|
|
|
12
|
-
export enum CATEGORIES {
|
|
13
|
-
OTHER = 'Other',
|
|
14
|
-
ALL = 'All',
|
|
15
|
-
}
|
|
16
|
-
|
|
17
12
|
export enum TAGS {
|
|
18
13
|
AAR = 'AAR',
|
|
19
14
|
POSITION = 'Pos',
|
|
20
15
|
SEPARATOR = 'separator',
|
|
21
16
|
SELECTION = 'selection',
|
|
22
17
|
ALPHABET = 'alphabet',
|
|
18
|
+
ALIGNED = 'aligned',
|
|
23
19
|
}
|
|
24
20
|
|
|
25
21
|
export enum SEM_TYPES {
|
|
@@ -30,6 +26,8 @@ export enum SEM_TYPES {
|
|
|
30
26
|
MACROMOLECULE = 'Macromolecule',
|
|
31
27
|
}
|
|
32
28
|
|
|
29
|
+
export const MSA = 'MSA';
|
|
30
|
+
|
|
33
31
|
export const STATS = 'stats';
|
|
34
32
|
|
|
35
33
|
export const EMBEDDING_STATUS = 'embeddingStatus';
|
package/src/utils/convert.ts
CHANGED
|
@@ -5,7 +5,7 @@ import $ from 'cash-dom';
|
|
|
5
5
|
|
|
6
6
|
import {Subscription} from 'rxjs';
|
|
7
7
|
import {NotationConverter} from '@datagrok-libraries/bio/src/utils/notation-converter';
|
|
8
|
-
import {NOTATION} from '@datagrok-libraries/bio/src/utils/units-handler';
|
|
8
|
+
import {NOTATION, UnitsHandler} from '@datagrok-libraries/bio/src/utils/units-handler';
|
|
9
9
|
|
|
10
10
|
|
|
11
11
|
let convertDialog: DG.Dialog | null = null;
|
|
@@ -42,7 +42,7 @@ export function convert(col: DG.Column): void {
|
|
|
42
42
|
// set correct visibility on init
|
|
43
43
|
toggleSeparator();
|
|
44
44
|
|
|
45
|
-
targetNotationInput.onChanged(
|
|
45
|
+
targetNotationInput.onChanged(() => {
|
|
46
46
|
toggleSeparator();
|
|
47
47
|
});
|
|
48
48
|
|
|
@@ -85,6 +85,9 @@ export async function convertDo(
|
|
|
85
85
|
const converter = new NotationConverter(srcCol);
|
|
86
86
|
const newColumn = converter.convert(targetNotation, separator);
|
|
87
87
|
srcCol.dataFrame.columns.add(newColumn);
|
|
88
|
+
|
|
89
|
+
// call to calculate 'cell.renderer' tag
|
|
88
90
|
await grok.data.detectSemanticTypes(srcCol.dataFrame);
|
|
91
|
+
|
|
89
92
|
return newColumn;
|
|
90
93
|
}
|
|
@@ -9,6 +9,7 @@ import {FastaFileHandler} from '@datagrok-libraries/bio/src/utils/fasta-handler'
|
|
|
9
9
|
import Aioli from '@biowasm/aioli';
|
|
10
10
|
|
|
11
11
|
import {AlignedSequenceEncoder} from '@datagrok-libraries/bio/src/sequence-encoder';
|
|
12
|
+
import {UnitsHandler} from '@datagrok-libraries/bio/src/utils/units-handler';
|
|
12
13
|
|
|
13
14
|
/**
|
|
14
15
|
* Converts array of sequences into simple fasta string.
|
|
@@ -58,14 +59,14 @@ export async function runKalign(srcCol: DG.Column, isAligned = false, unUsedName
|
|
|
58
59
|
// units
|
|
59
60
|
const srcUnits = srcCol.getTag(DG.TAGS.UNITS);
|
|
60
61
|
//aligned
|
|
61
|
-
const srcAligned = srcCol.getTag(
|
|
62
|
+
const srcAligned = srcCol.getTag(UnitsHandler.TAGS.aligned);
|
|
62
63
|
const tgtAligned = srcAligned + '.MSA';
|
|
63
64
|
//alphabet
|
|
64
|
-
const srcAlphabet = srcCol.getTag(
|
|
65
|
+
const srcAlphabet = srcCol.getTag(UnitsHandler.TAGS.alphabet);
|
|
65
66
|
|
|
66
67
|
tgtCol.setTag(DG.TAGS.UNITS, srcUnits);
|
|
67
|
-
tgtCol.setTag(
|
|
68
|
-
tgtCol.setTag(
|
|
68
|
+
tgtCol.setTag(UnitsHandler.TAGS.aligned, tgtAligned);
|
|
69
|
+
tgtCol.setTag(UnitsHandler.TAGS.alphabet, srcAlphabet);
|
|
69
70
|
tgtCol.semType = DG.SEMTYPE.MACROMOLECULE;
|
|
70
71
|
return tgtCol;
|
|
71
72
|
}
|
|
@@ -3,18 +3,130 @@ import * as DG from 'datagrok-api/dg';
|
|
|
3
3
|
import * as ui from 'datagrok-api/ui';
|
|
4
4
|
import {getSimilarityFromDistance} from '@datagrok-libraries/utils/src/similarity-metrics';
|
|
5
5
|
import {AvailableMetrics} from '@datagrok-libraries/ml/src/typed-metrics';
|
|
6
|
+
import * as grok from 'datagrok-api/grok';
|
|
6
7
|
|
|
7
|
-
export async function
|
|
8
|
+
export async function getDistances(col: DG.Column, seq: string): Promise<Array<number>> {
|
|
8
9
|
const stringArray = col.toList();
|
|
9
|
-
const distances = new Array(stringArray.length).fill(0
|
|
10
|
+
const distances = new Array(stringArray.length).fill(0);
|
|
10
11
|
for (let i = 0; i < stringArray.length; ++i)
|
|
11
|
-
distances[i] = stringArray[i] ?
|
|
12
|
-
return
|
|
12
|
+
distances[i] = stringArray[i] ? AvailableMetrics['String']['Levenshtein'](stringArray[i], seq) : null;
|
|
13
|
+
return distances;
|
|
13
14
|
}
|
|
14
15
|
|
|
15
|
-
export function
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
16
|
+
export async function getSimilaritiesMarix(dim: number, seqCol: DG.Column, df: DG.DataFrame, colName: string, simArr: DG.Column[])
|
|
17
|
+
: Promise<DG.Column[]> {
|
|
18
|
+
|
|
19
|
+
function arrayMin(arr: number[]) {
|
|
20
|
+
return arr.reduce(function (p, v) {
|
|
21
|
+
return (p < v ? p : v);
|
|
22
|
+
});
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
function arrayMax(arr: number[]) {
|
|
26
|
+
return arr.reduce(function (p, v) {
|
|
27
|
+
return (p > v ? p : v);
|
|
28
|
+
});
|
|
29
|
+
}
|
|
30
|
+
const distances = new Array(simArr.length).fill(null);
|
|
31
|
+
let min = Infinity;
|
|
32
|
+
let max = -Infinity;
|
|
33
|
+
for (let i = 0; i != dim - 1; ++i) {
|
|
34
|
+
const seq = seqCol.get(i);
|
|
35
|
+
df.rows.removeAt(0, 1, false);
|
|
36
|
+
distances[i] = (await getDistances(df.col(colName)!, seq))!;
|
|
37
|
+
const newMin = arrayMin(distances[i]);
|
|
38
|
+
const newMax = arrayMax(distances[i]);
|
|
39
|
+
if (newMin < min)
|
|
40
|
+
min = newMin;
|
|
41
|
+
if (newMax > max)
|
|
42
|
+
max = newMax;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
for (let i = 0; i < distances.length; i++) {
|
|
46
|
+
for (let j = 0; j < distances[i].length; j++) {
|
|
47
|
+
distances[i][j] = getSimilarityFromDistance((distances[i][j] - min)/(max - min));
|
|
48
|
+
}
|
|
49
|
+
simArr[i] = DG.Column.fromList(DG.COLUMN_TYPE.FLOAT, 'distances', distances[i]);
|
|
50
|
+
}
|
|
51
|
+
return simArr;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
export function createTooltipElement(params: ITooltipAndPanelParams): HTMLDivElement {
|
|
55
|
+
const tooltipElement = ui.divH([]);
|
|
56
|
+
const columnNames = ui.divV([
|
|
57
|
+
ui.divText(params.seqCol.name),
|
|
58
|
+
ui.divText(params.activityCol.name),
|
|
59
|
+
]);
|
|
60
|
+
columnNames.style.fontWeight = 'bold';
|
|
61
|
+
columnNames.style.display = 'flex';
|
|
62
|
+
columnNames.style.justifyContent = 'space-between';
|
|
63
|
+
tooltipElement.append(columnNames);
|
|
64
|
+
params.line.mols.forEach((molIdx: number, idx: number) => {
|
|
65
|
+
const activity = ui.divText(params.activityCol.get(molIdx).toFixed(2));
|
|
66
|
+
activity.style.display = 'flex';
|
|
67
|
+
activity.style.justifyContent = 'left';
|
|
68
|
+
activity.style.paddingLeft = '30px';
|
|
69
|
+
tooltipElement.append(ui.divV([
|
|
70
|
+
ui.divText(params.seqCol.get(molIdx)),
|
|
71
|
+
activity,
|
|
72
|
+
]));
|
|
19
73
|
});
|
|
74
|
+
return tooltipElement;
|
|
20
75
|
}
|
|
76
|
+
|
|
77
|
+
function moleculeInfo(df: DG.DataFrame, idx: number, seqColName: string): HTMLElement {
|
|
78
|
+
let dict: {[key: string]: string} = {};
|
|
79
|
+
for (let col of df.columns) {
|
|
80
|
+
if(col.name !== seqColName) {
|
|
81
|
+
dict[col.name] = df.get(col.name, idx);
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
return ui.tableFromMap(dict);
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
|
|
88
|
+
export function createPropPanelElement(params: ITooltipAndPanelParams): HTMLDivElement {
|
|
89
|
+
const propPanel = ui.divV([]);
|
|
90
|
+
const columnNames = ui.divH([
|
|
91
|
+
ui.divText(params.seqCol.name),
|
|
92
|
+
ui.divText(params.activityCol.name),
|
|
93
|
+
]);
|
|
94
|
+
columnNames.style.fontWeight = 'bold';
|
|
95
|
+
columnNames.style.justifyContent = 'space-between';
|
|
96
|
+
propPanel.append(columnNames);
|
|
97
|
+
const hosts: HTMLDivElement[] = [];
|
|
98
|
+
params.line.mols.forEach((molIdx: number, hostIdx: number) => {
|
|
99
|
+
const activity = ui.divText(params.activityCol.get(molIdx).toFixed(2));
|
|
100
|
+
activity.style.paddingLeft = '15px';
|
|
101
|
+
activity.style.paddingLeft = '10px';
|
|
102
|
+
const molHost = ui.divText(params.seqCol.get(molIdx));
|
|
103
|
+
if (params.df.currentRowIdx === molIdx) {
|
|
104
|
+
molHost.style.border = 'solid 1px lightgrey';
|
|
105
|
+
}
|
|
106
|
+
//@ts-ignore
|
|
107
|
+
ui.tooltip.bind(molHost, () => moleculeInfo(params.df, molIdx, params.seqCol.name));
|
|
108
|
+
molHost.onclick = () => {
|
|
109
|
+
const obj = grok.shell.o;
|
|
110
|
+
molHost.style.border = 'solid 1px lightgrey';
|
|
111
|
+
params.df.currentRowIdx = molIdx;
|
|
112
|
+
hosts.forEach((h, i) => {
|
|
113
|
+
if (i !== hostIdx) {
|
|
114
|
+
h.style.border = '';
|
|
115
|
+
}
|
|
116
|
+
})
|
|
117
|
+
setTimeout(() => {
|
|
118
|
+
grok.shell.o = obj
|
|
119
|
+
}, 1000);
|
|
120
|
+
};
|
|
121
|
+
propPanel.append(ui.divH([
|
|
122
|
+
molHost,
|
|
123
|
+
activity,
|
|
124
|
+
]));
|
|
125
|
+
hosts.push(molHost);
|
|
126
|
+
});
|
|
127
|
+
propPanel.append(ui.divH([
|
|
128
|
+
ui.divText(`Cliff: `, {style: {fontWeight: 'bold', paddingRight: '5px'}}),
|
|
129
|
+
ui.divText(params.sali!.toFixed(2))
|
|
130
|
+
]));
|
|
131
|
+
return propPanel;
|
|
132
|
+
}
|
|
@@ -16,7 +16,7 @@ export async function sequenceSpace(spaceParams: ISequenceSpaceParams): Promise<
|
|
|
16
16
|
// code deprecated since seqCol is encoded
|
|
17
17
|
/* let preparedData: any;
|
|
18
18
|
if (!(spaceParams.seqCol!.tags[DG.TAGS.UNITS] === 'HELM')) {
|
|
19
|
-
const sep = spaceParams.seqCol.getTag(
|
|
19
|
+
const sep = spaceParams.seqCol.getTag(UnitsHandler.TAGS.separator);
|
|
20
20
|
const sepFinal = sep ? sep === '.' ? '\\\.' : sep : '-';
|
|
21
21
|
const regex = new RegExp(sepFinal, 'g');
|
|
22
22
|
if (Object.keys(AvailableMetrics['String']).includes(spaceParams.similarityMetric))
|
package/src/utils/utils.ts
CHANGED
|
@@ -5,6 +5,7 @@ import {
|
|
|
5
5
|
CAP_GROUP_NAME, CAP_GROUP_SMILES, jsonSdfMonomerLibDict, MONOMER_ENCODE_MAX, MONOMER_ENCODE_MIN, MONOMER_SYMBOL,
|
|
6
6
|
RGROUP_ALTER_ID, RGROUP_FIELD, RGROUP_LABEL, SDF_MONOMER_NAME
|
|
7
7
|
} from '../const';
|
|
8
|
+
import {UnitsHandler} from '@datagrok-libraries/bio/src/utils/units-handler';
|
|
8
9
|
|
|
9
10
|
export const HELM_CORE_LIB_FILENAME = '/samples/HELMCoreLibrary.json';
|
|
10
11
|
export const HELM_CORE_LIB_MONOMER_SYMBOL = 'symbol';
|
|
@@ -16,7 +17,7 @@ export function encodeMonomers(col: DG.Column): DG.Column | null {
|
|
|
16
17
|
let encodeSymbol = MONOMER_ENCODE_MIN;
|
|
17
18
|
const monomerSymbolDict: { [key: string]: number } = {};
|
|
18
19
|
const units = col.tags[DG.TAGS.UNITS];
|
|
19
|
-
const sep = col.getTag(
|
|
20
|
+
const sep = col.getTag(UnitsHandler.TAGS.separator);
|
|
20
21
|
const splitterFunc: SplitterFunc = WebLogo.getSplitter(units, sep);
|
|
21
22
|
const encodedStringArray = [];
|
|
22
23
|
for (let i = 0; i < col.length; ++i) {
|
|
@@ -25,7 +26,7 @@ export function encodeMonomers(col: DG.Column): DG.Column | null {
|
|
|
25
26
|
monomers.forEach((m) => {
|
|
26
27
|
if (!monomerSymbolDict[m]) {
|
|
27
28
|
if (encodeSymbol > MONOMER_ENCODE_MAX) {
|
|
28
|
-
grok.shell.error(`Not
|
|
29
|
+
grok.shell.error(`Not enough symbols to encode monomers`);
|
|
29
30
|
return null;
|
|
30
31
|
}
|
|
31
32
|
monomerSymbolDict[m] = encodeSymbol;
|
|
@@ -0,0 +1,261 @@
|
|
|
1
|
+
<html><head><meta charset="utf-8"/><title>Bio Test Report. Datagrok version datagrok/datagrok:latest SHA=f1ac5a5eade4. Commit a0f7e8c0.</title><style type="text/css">html,
|
|
2
|
+
body {
|
|
3
|
+
font-family: Arial, Helvetica, sans-serif;
|
|
4
|
+
font-size: 1rem;
|
|
5
|
+
margin: 0;
|
|
6
|
+
padding: 0;
|
|
7
|
+
color: #333;
|
|
8
|
+
}
|
|
9
|
+
body {
|
|
10
|
+
padding: 2rem 1rem;
|
|
11
|
+
font-size: 0.85rem;
|
|
12
|
+
}
|
|
13
|
+
#jesthtml-content {
|
|
14
|
+
margin: 0 auto;
|
|
15
|
+
max-width: 70rem;
|
|
16
|
+
}
|
|
17
|
+
header {
|
|
18
|
+
display: flex;
|
|
19
|
+
align-items: center;
|
|
20
|
+
}
|
|
21
|
+
#title {
|
|
22
|
+
margin: 0;
|
|
23
|
+
flex-grow: 1;
|
|
24
|
+
}
|
|
25
|
+
#logo {
|
|
26
|
+
height: 4rem;
|
|
27
|
+
}
|
|
28
|
+
#timestamp {
|
|
29
|
+
color: #777;
|
|
30
|
+
margin-top: 0.5rem;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/** SUMMARY */
|
|
34
|
+
#summary {
|
|
35
|
+
color: #333;
|
|
36
|
+
margin: 2rem 0;
|
|
37
|
+
display: flex;
|
|
38
|
+
font-family: monospace;
|
|
39
|
+
font-size: 1rem;
|
|
40
|
+
}
|
|
41
|
+
#summary > div {
|
|
42
|
+
margin-right: 2rem;
|
|
43
|
+
background: #eee;
|
|
44
|
+
padding: 1rem;
|
|
45
|
+
min-width: 15rem;
|
|
46
|
+
}
|
|
47
|
+
#summary > div:last-child {
|
|
48
|
+
margin-right: 0;
|
|
49
|
+
}
|
|
50
|
+
@media only screen and (max-width: 720px) {
|
|
51
|
+
#summary {
|
|
52
|
+
flex-direction: column;
|
|
53
|
+
}
|
|
54
|
+
#summary > div {
|
|
55
|
+
margin-right: 0;
|
|
56
|
+
margin-top: 2rem;
|
|
57
|
+
}
|
|
58
|
+
#summary > div:first-child {
|
|
59
|
+
margin-top: 0;
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
.summary-total {
|
|
64
|
+
font-weight: bold;
|
|
65
|
+
margin-bottom: 0.5rem;
|
|
66
|
+
}
|
|
67
|
+
.summary-passed {
|
|
68
|
+
color: #4f8a10;
|
|
69
|
+
border-left: 0.4rem solid #4f8a10;
|
|
70
|
+
padding-left: 0.5rem;
|
|
71
|
+
}
|
|
72
|
+
.summary-failed,
|
|
73
|
+
.summary-obsolete-snapshots {
|
|
74
|
+
color: #d8000c;
|
|
75
|
+
border-left: 0.4rem solid #d8000c;
|
|
76
|
+
padding-left: 0.5rem;
|
|
77
|
+
}
|
|
78
|
+
.summary-pending {
|
|
79
|
+
color: #9f6000;
|
|
80
|
+
border-left: 0.4rem solid #9f6000;
|
|
81
|
+
padding-left: 0.5rem;
|
|
82
|
+
}
|
|
83
|
+
.summary-empty {
|
|
84
|
+
color: #999;
|
|
85
|
+
border-left: 0.4rem solid #999;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
.test-result {
|
|
89
|
+
padding: 1rem;
|
|
90
|
+
margin-bottom: 0.25rem;
|
|
91
|
+
}
|
|
92
|
+
.test-result:last-child {
|
|
93
|
+
border: 0;
|
|
94
|
+
}
|
|
95
|
+
.test-result.passed {
|
|
96
|
+
background-color: #dff2bf;
|
|
97
|
+
color: #4f8a10;
|
|
98
|
+
}
|
|
99
|
+
.test-result.failed {
|
|
100
|
+
background-color: #ffbaba;
|
|
101
|
+
color: #d8000c;
|
|
102
|
+
}
|
|
103
|
+
.test-result.pending {
|
|
104
|
+
background-color: #ffdf61;
|
|
105
|
+
color: #9f6000;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
.test-info {
|
|
109
|
+
display: flex;
|
|
110
|
+
justify-content: space-between;
|
|
111
|
+
}
|
|
112
|
+
.test-suitename {
|
|
113
|
+
width: 20%;
|
|
114
|
+
text-align: left;
|
|
115
|
+
font-weight: bold;
|
|
116
|
+
word-break: break-word;
|
|
117
|
+
}
|
|
118
|
+
.test-title {
|
|
119
|
+
width: 40%;
|
|
120
|
+
text-align: left;
|
|
121
|
+
font-style: italic;
|
|
122
|
+
}
|
|
123
|
+
.test-status {
|
|
124
|
+
width: 20%;
|
|
125
|
+
text-align: right;
|
|
126
|
+
}
|
|
127
|
+
.test-duration {
|
|
128
|
+
width: 10%;
|
|
129
|
+
text-align: right;
|
|
130
|
+
font-size: 0.75rem;
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
.failureMessages {
|
|
134
|
+
padding: 0 1rem;
|
|
135
|
+
margin-top: 1rem;
|
|
136
|
+
border-top: 1px dashed #d8000c;
|
|
137
|
+
}
|
|
138
|
+
.failureMessages.suiteFailure {
|
|
139
|
+
border-top: none;
|
|
140
|
+
}
|
|
141
|
+
.failureMsg {
|
|
142
|
+
white-space: pre-wrap;
|
|
143
|
+
white-space: -moz-pre-wrap;
|
|
144
|
+
white-space: -pre-wrap;
|
|
145
|
+
white-space: -o-pre-wrap;
|
|
146
|
+
word-wrap: break-word;
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
.suite-container {
|
|
150
|
+
margin-bottom: 2rem;
|
|
151
|
+
}
|
|
152
|
+
.suite-info {
|
|
153
|
+
padding: 1rem;
|
|
154
|
+
background-color: #eee;
|
|
155
|
+
color: #777;
|
|
156
|
+
display: flex;
|
|
157
|
+
align-items: center;
|
|
158
|
+
margin-bottom: 0.25rem;
|
|
159
|
+
}
|
|
160
|
+
.suite-info .suite-path {
|
|
161
|
+
word-break: break-all;
|
|
162
|
+
flex-grow: 1;
|
|
163
|
+
font-family: monospace;
|
|
164
|
+
font-size: 1rem;
|
|
165
|
+
}
|
|
166
|
+
.suite-info .suite-time {
|
|
167
|
+
margin-left: 0.5rem;
|
|
168
|
+
padding: 0.2rem 0.3rem;
|
|
169
|
+
font-size: 0.75rem;
|
|
170
|
+
}
|
|
171
|
+
.suite-info .suite-time.warn {
|
|
172
|
+
background-color: #d8000c;
|
|
173
|
+
color: #fff;
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
/* CONSOLE LOGS */
|
|
177
|
+
.suite-consolelog {
|
|
178
|
+
margin-bottom: 0.25rem;
|
|
179
|
+
padding: 1rem;
|
|
180
|
+
background-color: #efefef;
|
|
181
|
+
}
|
|
182
|
+
.suite-consolelog-header {
|
|
183
|
+
font-weight: bold;
|
|
184
|
+
}
|
|
185
|
+
.suite-consolelog-item {
|
|
186
|
+
padding: 0.5rem;
|
|
187
|
+
}
|
|
188
|
+
.suite-consolelog-item pre {
|
|
189
|
+
margin: 0.5rem 0;
|
|
190
|
+
white-space: pre-wrap;
|
|
191
|
+
white-space: -moz-pre-wrap;
|
|
192
|
+
white-space: -pre-wrap;
|
|
193
|
+
white-space: -o-pre-wrap;
|
|
194
|
+
word-wrap: break-word;
|
|
195
|
+
}
|
|
196
|
+
.suite-consolelog-item-origin {
|
|
197
|
+
color: #777;
|
|
198
|
+
font-weight: bold;
|
|
199
|
+
}
|
|
200
|
+
.suite-consolelog-item-message {
|
|
201
|
+
color: #000;
|
|
202
|
+
font-size: 1rem;
|
|
203
|
+
padding: 0 0.5rem;
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
/* OBSOLETE SNAPSHOTS */
|
|
207
|
+
.suite-obsolete-snapshots {
|
|
208
|
+
margin-bottom: 0.25rem;
|
|
209
|
+
padding: 1rem;
|
|
210
|
+
background-color: #ffbaba;
|
|
211
|
+
color: #d8000c;
|
|
212
|
+
}
|
|
213
|
+
.suite-obsolete-snapshots-header {
|
|
214
|
+
font-weight: bold;
|
|
215
|
+
}
|
|
216
|
+
.suite-obsolete-snapshots-item {
|
|
217
|
+
padding: 0.5rem;
|
|
218
|
+
}
|
|
219
|
+
.suite-obsolete-snapshots-item pre {
|
|
220
|
+
margin: 0.5rem 0;
|
|
221
|
+
white-space: pre-wrap;
|
|
222
|
+
white-space: -moz-pre-wrap;
|
|
223
|
+
white-space: -pre-wrap;
|
|
224
|
+
white-space: -o-pre-wrap;
|
|
225
|
+
word-wrap: break-word;
|
|
226
|
+
}
|
|
227
|
+
.suite-obsolete-snapshots-item-message {
|
|
228
|
+
color: #000;
|
|
229
|
+
font-size: 1rem;
|
|
230
|
+
padding: 0 0.5rem;
|
|
231
|
+
}
|
|
232
|
+
</style></head><body><div id="jesthtml-content"><header><h1 id="title">Bio Test Report. Datagrok version datagrok/datagrok:latest SHA=f1ac5a5eade4. Commit a0f7e8c0.</h1></header><div id="metadata-container"><div id="timestamp">Started: 2022-09-08 10:03:50</div><div id="summary"><div id="suite-summary"><div class="summary-total">Suites (1)</div><div class="summary-passed summary-empty">0 passed</div><div class="summary-failed">1 failed</div><div class="summary-pending summary-empty">0 pending</div></div><div id="test-summary"><div class="summary-total">Tests (1)</div><div class="summary-passed summary-empty">0 passed</div><div class="summary-failed">1 failed</div><div class="summary-pending summary-empty">0 pending</div></div></div></div><div id="suite-1" class="suite-container"><div class="suite-info"><div class="suite-path">/home/runner/work/public/public/packages/Bio/src/__jest__/remote.test.ts</div><div class="suite-time warn">10.76s</div></div><div class="suite-tests"><div class="test-result failed"><div class="test-info"><div class="test-suitename"> </div><div class="test-title">TEST</div><div class="test-status">failed</div><div class="test-duration">0s</div></div><div class="failureMessages"> <pre class="failureMsg">Error: Unknown server alias. Please add it to /home/runner/.grok/config.yaml
|
|
233
|
+
at getDevKey (/home/runner/work/public/public/packages/Bio/src/__jest__/test-node.ts:48:13)
|
|
234
|
+
at Object.<anonymous> (/home/runner/work/public/public/packages/Bio/src/__jest__/test-node.ts:57:15)
|
|
235
|
+
at Generator.next (<anonymous>)
|
|
236
|
+
at /home/runner/work/public/public/packages/Bio/src/__jest__/test-node.ts:31:71
|
|
237
|
+
at new Promise (<anonymous>)
|
|
238
|
+
at Object.<anonymous>.__awaiter (/home/runner/work/public/public/packages/Bio/src/__jest__/test-node.ts:27:12)
|
|
239
|
+
at Object.getBrowserPage (/home/runner/work/public/public/packages/Bio/src/__jest__/test-node.ts:94:12)
|
|
240
|
+
at /home/runner/work/public/public/packages/Bio/src/__jest__/remote.test.ts:13:27
|
|
241
|
+
at Generator.next (<anonymous>)
|
|
242
|
+
at /home/runner/work/public/public/packages/Bio/src/__jest__/remote.test.ts:34:71
|
|
243
|
+
at new Promise (<anonymous>)
|
|
244
|
+
at Object.<anonymous>.__awaiter (/home/runner/work/public/public/packages/Bio/src/__jest__/remote.test.ts:30:12)
|
|
245
|
+
at /home/runner/work/public/public/packages/Bio/src/__jest__/remote.test.ts:12:22
|
|
246
|
+
at Promise.then.completed (/home/runner/work/public/public/packages/Bio/node_modules/jest-circus/build/utils.js:391:28)
|
|
247
|
+
at new Promise (<anonymous>)
|
|
248
|
+
at callAsyncCircusFn (/home/runner/work/public/public/packages/Bio/node_modules/jest-circus/build/utils.js:316:10)
|
|
249
|
+
at _callCircusHook (/home/runner/work/public/public/packages/Bio/node_modules/jest-circus/build/run.js:181:40)
|
|
250
|
+
at _runTestsForDescribeBlock (/home/runner/work/public/public/packages/Bio/node_modules/jest-circus/build/run.js:47:7)
|
|
251
|
+
at run (/home/runner/work/public/public/packages/Bio/node_modules/jest-circus/build/run.js:25:3)
|
|
252
|
+
at runAndTransformResultsToJestFormat (/home/runner/work/public/public/packages/Bio/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapterInit.js:170:21)
|
|
253
|
+
at jestAdapter (/home/runner/work/public/public/packages/Bio/node_modules/jest-circus/build/legacy-code-todo-rewrite/jestAdapter.js:82:19)
|
|
254
|
+
at runTestInternal (/home/runner/work/public/public/packages/Bio/node_modules/jest-runner/build/runTest.js:389:16)
|
|
255
|
+
at runTest (/home/runner/work/public/public/packages/Bio/node_modules/jest-runner/build/runTest.js:475:34)
|
|
256
|
+
at TestRunner.runTests (/home/runner/work/public/public/packages/Bio/node_modules/jest-runner/build/index.js:101:12)
|
|
257
|
+
at TestScheduler.scheduleTests (/home/runner/work/public/public/packages/Bio/node_modules/@jest/core/build/TestScheduler.js:333:13)
|
|
258
|
+
at runJest (/home/runner/work/public/public/packages/Bio/node_modules/@jest/core/build/runJest.js:404:19)
|
|
259
|
+
at _run10000 (/home/runner/work/public/public/packages/Bio/node_modules/@jest/core/build/cli/index.js:320:7)
|
|
260
|
+
at runCLI (/home/runner/work/public/public/packages/Bio/node_modules/@jest/core/build/cli/index.js:173:3)
|
|
261
|
+
at Object.run (/home/runner/work/public/public/packages/Bio/node_modules/jest-cli/build/cli/index.js:155:37)</pre></div></div></div></div></div></body></html>
|