@datagrok/bio 2.16.6 → 2.16.8

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/package.json CHANGED
@@ -5,7 +5,7 @@
5
5
  "name": "Aleksandr Tanas",
6
6
  "email": "atanas@datagrok.ai"
7
7
  },
8
- "version": "2.16.6",
8
+ "version": "2.16.8",
9
9
  "description": "Bioinformatics support (import/export of sequences, conversion, visualization, analysis). [See more](https://github.com/datagrok-ai/public/blob/master/packages/Bio/README.md) for details.",
10
10
  "repository": {
11
11
  "type": "git",
@@ -37,12 +37,12 @@
37
37
  ],
38
38
  "dependencies": {
39
39
  "@biowasm/aioli": "^3.1.0",
40
- "@datagrok-libraries/bio": "^5.45.4",
40
+ "@datagrok-libraries/bio": "^5.45.6",
41
41
  "@datagrok-libraries/chem-meta": "^1.2.7",
42
42
  "@datagrok-libraries/math": "^1.2.2",
43
43
  "@datagrok-libraries/ml": "^6.7.4",
44
44
  "@datagrok-libraries/tutorials": "^1.4.3",
45
- "@datagrok-libraries/utils": "^4.3.6",
45
+ "@datagrok-libraries/utils": "^4.3.7",
46
46
  "@webgpu/types": "^0.1.40",
47
47
  "ajv": "^8.12.0",
48
48
  "ajv-errors": "^3.0.0",
@@ -58,8 +58,8 @@
58
58
  "wu": "^2.1.0"
59
59
  },
60
60
  "devDependencies": {
61
- "@datagrok-libraries/helm-web-editor": "^1.1.12",
62
- "@datagrok-libraries/js-draw-lite": "^0.0.9",
61
+ "@datagrok-libraries/helm-web-editor": "^1.1.13",
62
+ "@datagrok-libraries/js-draw-lite": "^0.0.10",
63
63
  "@datagrok/chem": "^1.12.3",
64
64
  "@datagrok/dendrogram": "^1.2.33",
65
65
  "@datagrok/helm": "^2.5.3",
package/src/package.ts CHANGED
@@ -1139,7 +1139,6 @@ export async function sdfToJsonLib(table: DG.DataFrame) {
1139
1139
  //input: string seq { semType: Macromolecule }
1140
1140
  //input: bool nonlinear
1141
1141
  //output: string molfile { semType: Molecule }
1142
- //meta.role: converter
1143
1142
  export async function seq2atomic(seq: string, nonlinear: boolean): Promise<string | undefined> {
1144
1143
  if (!(seq.trim())) return '';
1145
1144
  try {
@@ -81,8 +81,8 @@ category('SeqHandler: getHelm', () => {
81
81
  await grok.data.detectSemanticTypes(df);
82
82
 
83
83
  const sh = seqHelper.getSeqHandler(seqCol);
84
- const resMValue = await sh.getValue(0);
85
- const resHelm = resMValue.helm;
84
+ const resSeqValue = await sh.getValue(0);
85
+ const resHelm = resSeqValue.helm;
86
86
  expect(resHelm, tgtHelm);
87
87
  }
88
88
  });
@@ -114,7 +114,8 @@ rut2-rty-her2---wert-rut12-rty-her2---wert
114
114
  PEPTIDE1{meI.hHis.Aca.N.T.dE.Thr_PO3H2.Aca.D-Tyr_Et.Thr_PO3H2.Aca.D-Tyr_Et}$$$$
115
115
  PEPTIDE1{meI.hHis.Aca.Cys_SEt.T.dK.Thr_PO3H2.Aca.dK.Thr_PO3H2.Aca}$$$$
116
116
  PEPTIDE1{Lys_Boc.hHis.Aca.Cys_SEt.T.dK.Thr_PO3H2.Aca.dK.Thr_PO3H2.Aca}$$$$
117
- PEPTIDE1{meI.hHis.Aca.Cys_SEt.T.dK.Thr_PO3H2.T.dK.Thr_PO3H2}$$$$`
117
+ PEPTIDE1{meI.hHis.Aca.Cys_SEt.T.dK.Thr_PO3H2.T.dK.Thr_PO3H2}$$$$,
118
+ PEPTIDE1{meI.hHis.Aca.Cys_SEt.T.dK.Thr_PO3H2.T.dK}|PEPTIDE2{Thr_PO3H2}$$$$`,
118
119
  },
119
120
  tgt: {
120
121
  notation: NOTATION.HELM,
@@ -123,6 +124,7 @@ PEPTIDE1{meI.hHis.Aca.Cys_SEt.T.dK.Thr_PO3H2.T.dK.Thr_PO3H2}$$$$`
123
124
  ['meI', 'hHis', 'Aca', 'Cys_SEt', 'T', 'dK', 'Thr_PO3H2', 'Aca', 'dK', 'Thr_PO3H2', 'Aca'],
124
125
  ['Lys_Boc', 'hHis', 'Aca', 'Cys_SEt', 'T', 'dK', 'Thr_PO3H2', 'Aca', 'dK', 'Thr_PO3H2', 'Aca'],
125
126
  ['meI', 'hHis', 'Aca', 'Cys_SEt', 'T', 'dK', 'Thr_PO3H2', 'T', 'dK', 'Thr_PO3H2'],
127
+ ['meI', 'hHis', 'Aca', 'Cys_SEt', 'T', 'dK', 'Thr_PO3H2', 'T', 'dK', 'Thr_PO3H2'],
126
128
  ]
127
129
  }
128
130
  }
@@ -81,8 +81,7 @@ export class MacromoleculeSequenceCellRenderer extends DG.GridCellRenderer {
81
81
 
82
82
  override onMouseMove(gridCell: DG.GridCell, e: MouseEvent): void {
83
83
  const [gridCol, tableCol, temp] = getGridCellColTemp<string, MonomerPlacer>(gridCell);
84
- const back = temp.rendererBack;
85
- back.onMouseMove(gridCell, e);
84
+ temp.rendererBack?.onMouseMove(gridCell, e);
86
85
  }
87
86
 
88
87
  override onMouseLeave(gridCell: DG.GridCell, e: MouseEvent) {
@@ -99,7 +98,6 @@ export class MacromoleculeSequenceCellRenderer extends DG.GridCellRenderer {
99
98
  * @param {number} h height of the cell.
100
99
  * @param {DG.GridCell} gridCell Grid cell.
101
100
  * @param {DG.GridCellStyle} _cellStyle Cell style.
102
- * @memberof AlignedSequenceCellRenderer
103
101
  */
104
102
  render(
105
103
  g: CanvasRenderingContext2D, x: number, y: number, w: number, h: number, gridCell: DG.GridCell,
@@ -132,7 +132,7 @@ class LibraryControlsManager {
132
132
 
133
133
  private _createControlsForm(): HTMLElement {
134
134
  const libraryControls = this.createLibraryControls();
135
- const inputsForm = ui.form(libraryControls);
135
+ const inputsForm = ui.form(libraryControls, undefined, false);
136
136
  $(inputsForm).addClass('monomer-lib-controls-form');
137
137
 
138
138
  return inputsForm;
@@ -868,6 +868,7 @@ class MonomerForm implements INewMonomerForm {
868
868
  await grok.dapi.files.writeAsText(LIB_PATH + libName, JSON.stringify(libJSON));
869
869
  await (await MonomerLibManager.getInstance()).loadLibraries(true);
870
870
  await this.refreshTable(monomer.symbol);
871
+ this._molChanged = false; // reset the flag
871
872
  grok.shell.info(`Monomer ${monomer.symbol} was successfully saved in library ${libName}`);
872
873
  } catch (e) {
873
874
  grok.shell.error('Error saving monomer');
@@ -14,7 +14,7 @@ import {GAP_SYMBOL, GapOriginals} from '@datagrok-libraries/bio/src/utils/macrom
14
14
  import {CellRendererBackBase, GridCellRendererTemp} from '@datagrok-libraries/bio/src/utils/cell-renderer-back-base';
15
15
  import {HelmTypes} from '@datagrok-libraries/bio/src/helm/consts';
16
16
  import {HelmType} from '@datagrok-libraries/bio/src/helm/types';
17
- import {ISeqHandler, ConvertFunc, JoinerFunc, SeqTemps, MacromoleculeValueBase} from '@datagrok-libraries/bio/src/utils/macromolecule/seq-handler';
17
+ import {ConvertFunc, ISeqHandler, JoinerFunc, SeqTemps, SeqValueBase} from '@datagrok-libraries/bio/src/utils/macromolecule/seq-handler';
18
18
 
19
19
  import {SeqHelper} from './seq-helper';
20
20
 
@@ -28,7 +28,7 @@ export class SeqHandler implements ISeqHandler {
28
28
  protected readonly _units: string; // units, of the form fasta, separator
29
29
  protected readonly _notation: NOTATION; // current notation (without :SEQ:NT, etc.)
30
30
  protected readonly _defaultGapOriginal: string;
31
- protected readonly notationProvider: INotationProvider | null = null;
31
+ protected readonly notationProvider!: INotationProvider;
32
32
 
33
33
  private _splitter: SplitterFunc | null = null;
34
34
 
@@ -38,15 +38,25 @@ export class SeqHandler implements ISeqHandler {
38
38
  if (col.type !== DG.TYPE.STRING)
39
39
  throw new Error(`Unexpected column type '${col.type}', must be '${DG.TYPE.STRING}'.`);
40
40
  this._column = col;
41
- const units = this._column.meta.units;
42
- if (units !== null && units !== undefined)
43
- this._units = units;
44
- else
41
+ const units: string | null = this._column.meta.units;
42
+ if (!units)
45
43
  throw new Error('Units are not specified in column');
44
+ this._units = units!;
45
+
46
46
  this._notation = this.getNotation();
47
- this._defaultGapOriginal = (this.isFasta()) ? GapOriginals[NOTATION.FASTA] :
48
- (this.isHelm()) ? GapOriginals[NOTATION.HELM] :
49
- GapOriginals[NOTATION.SEPARATOR];
47
+ if (this.isCustom()) {
48
+ // this.column.temp[SeqTemps.notationProvider] must be set at detector stage
49
+ this.notationProvider = this.column.temp[SeqTemps.notationProvider] ?? null;
50
+ }
51
+
52
+ const defaultGapOriginal = this.isFasta() ? GapOriginals[NOTATION.FASTA] :
53
+ this.isSeparator() ? GapOriginals[NOTATION.SEPARATOR] :
54
+ this.isHelm() ? GapOriginals[NOTATION.HELM] :
55
+ this.isCustom() ? this.notationProvider.defaultGapOriginal :
56
+ undefined;
57
+ if (defaultGapOriginal == undefined)
58
+ throw new Error(`Unexpected defaultGapOriginal for notation '${this.notation}'`);
59
+ this._defaultGapOriginal = defaultGapOriginal;
50
60
 
51
61
  if (!this.column.tags.has(TAGS.aligned) || !this.column.tags.has(TAGS.alphabet) ||
52
62
  (!this.column.tags.has(TAGS.alphabetIsMultichar) && !this.isHelm() && this.alphabet === ALPHABET.UN)
@@ -60,6 +70,8 @@ export class SeqHandler implements ISeqHandler {
60
70
  this.seqHelper.setUnitsToSeparatorColumn(this, separator);
61
71
  } else if (this.isHelm())
62
72
  this.seqHelper.setUnitsToHelmColumn(this);
73
+ else if (this.isCustom())
74
+ this.notationProvider!.setUnits(this);
63
75
  else
64
76
  throw new Error(`Unexpected units '${this.column.meta.units}'.`);
65
77
  }
@@ -82,10 +94,6 @@ export class SeqHandler implements ISeqHandler {
82
94
  }
83
95
  }
84
96
 
85
- if (this.column.meta.units === NOTATION.CUSTOM) {
86
- // this.column.temp[SeqTemps.notationProvider] must be set at detector stage
87
- this.notationProvider = this.column.temp[SeqTemps.notationProvider] ?? null;
88
- }
89
97
  this.columnVersion = this.column.version;
90
98
  }
91
99
 
@@ -241,16 +249,23 @@ export class SeqHandler implements ISeqHandler {
241
249
  }
242
250
 
243
251
  /** Any Macromolecule can be represented on Helm format. The reverse is not always possible. */
244
- public async getValue(rowIdx: number, options?: any): Promise<MacromoleculeValueBase> {
252
+ public getValue(rowIdx: number, options?: any): SeqValueBase {
245
253
  const seq: string = this.column.get(rowIdx);
246
254
  let resHelm: string;
247
- if (this.notationProvider)
248
- resHelm = await this.notationProvider.getHelm(seq, options);
249
- else {
250
- resHelm = this.convertToHelm(seq);
251
- }
252
- const resMValue = new MacromoleculeValueBase(resHelm, this, rowIdx);
253
- return resMValue;
255
+ const resSeqValue = new SeqValueBase(rowIdx, this);
256
+ return resSeqValue;
257
+ }
258
+
259
+ public getHelm(rowIdx: number): string {
260
+ let resHelm: string;
261
+ const seq = this.column.get(rowIdx);
262
+ if (this.notation === NOTATION.HELM)
263
+ resHelm = seq;
264
+ else if (this.notation === NOTATION.CUSTOM)
265
+ resHelm = this.notationProvider!.getHelm(seq, {});
266
+ else
267
+ resHelm = this.getConverter(NOTATION.HELM)(seq);
268
+ return resHelm;
254
269
  }
255
270
 
256
271
  private _stats: SeqColStats | null = null;
@@ -306,6 +321,8 @@ export class SeqHandler implements ISeqHandler {
306
321
 
307
322
  public isHelm(): boolean { return this.notation === NOTATION.HELM; }
308
323
 
324
+ public isCustom(): boolean { return this.notation === NOTATION.CUSTOM; }
325
+
309
326
  public isRna(): boolean { return this.alphabet === ALPHABET.RNA; }
310
327
 
311
328
  public isDna(): boolean { return this.alphabet === ALPHABET.DNA; }
@@ -452,6 +469,12 @@ export class SeqHandler implements ISeqHandler {
452
469
  return newColumn;
453
470
  }
454
471
 
472
+ get splitter(): SplitterFunc {
473
+ if (this._splitter === null)
474
+ this._splitter = this.getSplitter();
475
+ return this._splitter;
476
+ }
477
+
455
478
  /** Gets function to split seq value to monomers */
456
479
  protected getSplitter(limit?: number): SplitterFunc {
457
480
  let splitter: SplitterFunc | null = null;
@@ -543,12 +566,6 @@ export class SeqHandler implements ISeqHandler {
543
566
 
544
567
  // -- Notation Converter --
545
568
 
546
- protected get splitter(): SplitterFunc {
547
- if (this._splitter === null)
548
- this._splitter = this.getSplitter();
549
- return this._splitter;
550
- }
551
-
552
569
  public toFasta(targetNotation: NOTATION): boolean { return targetNotation === NOTATION.FASTA; }
553
570
 
554
571
  public toSeparator(targetNotation: NOTATION): boolean { return targetNotation === NOTATION.SEPARATOR; }