@malloydata/malloy 0.0.70-dev230810160240 → 0.0.70

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.
@@ -24,6 +24,35 @@
24
24
  Object.defineProperty(exports, "__esModule", { value: true });
25
25
  const test_translator_1 = require("./test-translator");
26
26
  require("./parse-expects");
27
+ const jest_diff_1 = require("jest-diff");
28
+ expect.extend({
29
+ matchesAnnotation(result, shouldBe) {
30
+ function stripAt(a) {
31
+ const clean = {};
32
+ if (a.inherits) {
33
+ clean.inherits = stripAt(a.inherits);
34
+ }
35
+ if (a.blockNotes) {
36
+ clean.blockNotes = a.blockNotes.map(bn => bn.text);
37
+ }
38
+ if (a.notes) {
39
+ clean.notes = a.notes.map(n => n.text);
40
+ }
41
+ return clean;
42
+ }
43
+ const got = stripAt(result);
44
+ if (!this.equals(got, shouldBe)) {
45
+ return {
46
+ pass: false,
47
+ message: () => (0, jest_diff_1.diff)(shouldBe, got, { expand: true }) || '',
48
+ };
49
+ }
50
+ return {
51
+ pass: true,
52
+ message: () => '',
53
+ };
54
+ },
55
+ });
27
56
  const defaultTags = {
28
57
  blockNotes: ['# blockNote\n'],
29
58
  notes: ['# note\n', '# b4-is\n', '# after-is\n'],
@@ -58,12 +87,12 @@ describe('document annotation', () => {
58
87
  const note_a = m.getSourceDef('note_a');
59
88
  expect(note_a).toBeDefined();
60
89
  if (note_a) {
61
- expect(note_a.annotation).toEqual(defaultTags);
90
+ expect(note_a.annotation).matchesAnnotation(defaultTags);
62
91
  }
63
92
  const note_b = m.getSourceDef('note_b');
64
93
  expect(note_b).toBeDefined();
65
94
  if (note_b) {
66
- expect(note_b.annotation).toEqual({
95
+ expect(note_b.annotation).matchesAnnotation({
67
96
  blockNotes: defaultTags.blockNotes,
68
97
  notes: ['# note1\n'],
69
98
  });
@@ -79,7 +108,7 @@ describe('document annotation', () => {
79
108
  const note_a = m.getSourceDef('note_a');
80
109
  expect(note_a).toBeDefined();
81
110
  if (note_a) {
82
- expect(note_a.annotation).toEqual({
111
+ expect(note_a.annotation).matchesAnnotation({
83
112
  blockNotes: ['# note1\n', '# note1.1\n'],
84
113
  });
85
114
  }
@@ -95,7 +124,7 @@ describe('document annotation', () => {
95
124
  const note_a = m.getSourceDef('note_a');
96
125
  expect(note_a).toBeDefined();
97
126
  if (note_a) {
98
- expect(note_a.annotation).toEqual({
127
+ expect(note_a.annotation).matchesAnnotation({
99
128
  inherits: { blockNotes: ['# note0\n'] },
100
129
  blockNotes: ['# note1\n'],
101
130
  });
@@ -116,7 +145,7 @@ describe('document annotation', () => {
116
145
  const note_a = m.getQuery('note_a');
117
146
  expect(note_a).toBeDefined();
118
147
  if (note_a) {
119
- expect(note_a.annotation).toEqual(defaultTags);
148
+ expect(note_a.annotation).matchesAnnotation(defaultTags);
120
149
  }
121
150
  });
122
151
  test('anonymous query annotation points', () => {
@@ -130,7 +159,7 @@ describe('document annotation', () => {
130
159
  const note_a = m.getQuery(0);
131
160
  expect(note_a).toBeDefined();
132
161
  if (note_a) {
133
- expect(note_a.annotation).toEqual({
162
+ expect(note_a.annotation).matchesAnnotation({
134
163
  blockNotes: ['# note1\n'],
135
164
  notes: ['# note2\n'],
136
165
  });
@@ -147,7 +176,7 @@ describe('document annotation', () => {
147
176
  const note_a = m.getQuery(0);
148
177
  expect(note_a).toBeDefined();
149
178
  if (note_a) {
150
- expect(note_a.annotation).toEqual({
179
+ expect(note_a.annotation).matchesAnnotation({
151
180
  blockNotes: ['# note1\n'],
152
181
  notes: ['# note2\n'],
153
182
  });
@@ -163,7 +192,7 @@ describe('document annotation', () => {
163
192
  const note_a = m.getQuery('note_a');
164
193
  expect(note_a).toBeDefined();
165
194
  if (note_a) {
166
- expect(note_a.annotation).toEqual({
195
+ expect(note_a.annotation).matchesAnnotation({
167
196
  blockNotes: ['# note1\n', '# note2\n'],
168
197
  });
169
198
  }
@@ -181,7 +210,7 @@ describe('document annotation', () => {
181
210
  const note_a = m.getQuery('note_a');
182
211
  expect(note_a).toBeDefined();
183
212
  if (note_a) {
184
- expect(note_a.annotation).toEqual({
213
+ expect(note_a.annotation).matchesAnnotation({
185
214
  inherits: { blockNotes: ['# noteb0\n'], notes: ['# noteb1\n'] },
186
215
  blockNotes: ['# note1\n'],
187
216
  });
@@ -195,7 +224,7 @@ describe('document annotation', () => {
195
224
  expect(m).toTranslate();
196
225
  const note_a = m.getQuery(0);
197
226
  expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toBeDefined();
198
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual({ inherits: defaultTags });
227
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation({ inherits: defaultTags });
199
228
  });
200
229
  test('model annotations', () => {
201
230
  var _a;
@@ -207,14 +236,26 @@ describe('document annotation', () => {
207
236
  const model = (_a = m.translate()) === null || _a === void 0 ? void 0 : _a.translated;
208
237
  expect(model).toBeDefined();
209
238
  const notes = model === null || model === void 0 ? void 0 : model.modelDef.annotation;
210
- expect(notes).toEqual({ notes: ['## model1\n', '## model2\n'] });
239
+ expect(notes).matchesAnnotation({ notes: ['## model1\n', '## model2\n'] });
211
240
  });
212
241
  test('ignores objectless object annotations', () => {
213
242
  const m = new test_translator_1.TestTranslator(`
214
243
  # note1
215
244
  ## model1
216
245
  `);
246
+ expect(m).translationToFailWith('Object annotation not connected to any object');
247
+ });
248
+ test('errors reported from compiler flags', () => {
249
+ expect(`
250
+ ##! missingCloseQuote="...
251
+ `).translationToFailWith(/no viable alternative at input/);
252
+ });
253
+ test('checking compiler flags', () => {
254
+ const m = (0, test_translator_1.model) `
255
+ ##! flagThis
256
+ `;
217
257
  expect(m).toTranslate();
258
+ expect(m.translator.compilerFlags.has('flagThis')).toBeTruthy();
218
259
  });
219
260
  });
220
261
  describe('source definition annotations', () => {
@@ -226,7 +267,7 @@ describe('source definition annotations', () => {
226
267
  if (na) {
227
268
  const note_a = (0, test_translator_1.getFieldDef)(na, 'note_a');
228
269
  expect(note_a).toBeDefined();
229
- expect(note_a.annotation).toEqual(defaultTags);
270
+ expect(note_a.annotation).matchesAnnotation(defaultTags);
230
271
  }
231
272
  });
232
273
  test('refined turtle inherits annotation', () => {
@@ -242,7 +283,7 @@ describe('source definition annotations', () => {
242
283
  if (na) {
243
284
  const note_a = (0, test_translator_1.getFieldDef)(na, 'new_note_a');
244
285
  expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toBeDefined();
245
- expect(note_a.annotation).toEqual({ inherits: defaultTags });
286
+ expect(note_a.annotation).matchesAnnotation({ inherits: defaultTags });
246
287
  }
247
288
  });
248
289
  test('dimension block annotation', () => {
@@ -263,7 +304,7 @@ describe('source definition annotations', () => {
263
304
  expect(na).toBeDefined();
264
305
  if (na) {
265
306
  const note_a = (0, test_translator_1.getFieldDef)(na, 'note_a');
266
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
307
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
267
308
  }
268
309
  });
269
310
  test('measure block annotation', () => {
@@ -284,7 +325,7 @@ describe('source definition annotations', () => {
284
325
  expect(na).toBeDefined();
285
326
  if (na) {
286
327
  const note_a = (0, test_translator_1.getFieldDef)(na, 'note_a');
287
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
328
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
288
329
  }
289
330
  });
290
331
  test('join_one-with block annotation', () => {
@@ -305,7 +346,7 @@ describe('source definition annotations', () => {
305
346
  expect(na).toBeDefined();
306
347
  if (na) {
307
348
  const note_a = (0, test_translator_1.getFieldDef)(na, 'note_a');
308
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
349
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
309
350
  }
310
351
  });
311
352
  test('join_many-on block annotation', () => {
@@ -326,7 +367,7 @@ describe('source definition annotations', () => {
326
367
  expect(na).toBeDefined();
327
368
  if (na) {
328
369
  const note_a = (0, test_translator_1.getFieldDef)(na, 'note_a');
329
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
370
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
330
371
  }
331
372
  });
332
373
  test('ignores model annotation', () => {
@@ -335,18 +376,17 @@ describe('source definition annotations', () => {
335
376
  ## model1
336
377
  }
337
378
  `);
338
- expect(m).toTranslate();
379
+ expect(m).translationToFailWith('Model annotations not allowed at this scope');
339
380
  });
340
381
  });
341
382
  describe('query operation annotations', () => {
342
383
  test('ignores model annotation', () => {
343
- const m = new test_translator_1.TestTranslator(`
384
+ expect(`
344
385
  query: a -> {
345
386
  ## model1
346
387
  project: *
347
388
  }
348
- `);
349
- expect(m).toTranslate();
389
+ `).translationToFailWith('Model annotations not allowed at this scope');
350
390
  });
351
391
  test('project new definition annotation', () => {
352
392
  const m = new test_translator_1.TestTranslator(`
@@ -366,7 +406,7 @@ describe('query operation annotations', () => {
366
406
  expect(foundYou).toBeDefined();
367
407
  if (foundYou) {
368
408
  const note_a = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_a');
369
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
409
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
370
410
  }
371
411
  });
372
412
  test('project ref inherits annotation', () => {
@@ -392,7 +432,7 @@ describe('query operation annotations', () => {
392
432
  expect(foundYou).toBeDefined();
393
433
  if (foundYou) {
394
434
  const note_a = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_a');
395
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual({
435
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation({
396
436
  inherits: defaultTags,
397
437
  blockNotes: ['# note1\n'],
398
438
  notes: ['# note2\n'],
@@ -417,7 +457,7 @@ describe('query operation annotations', () => {
417
457
  expect(foundYou).toBeDefined();
418
458
  if (foundYou) {
419
459
  const note_a = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_a');
420
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
460
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
421
461
  }
422
462
  });
423
463
  test('caculate def', () => {
@@ -439,7 +479,7 @@ describe('query operation annotations', () => {
439
479
  expect(foundYou).toBeDefined();
440
480
  if (foundYou) {
441
481
  const note_a = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_a');
442
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
482
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
443
483
  }
444
484
  });
445
485
  test('group_by ref inherits', () => {
@@ -466,7 +506,7 @@ describe('query operation annotations', () => {
466
506
  expect(foundYou).toBeDefined();
467
507
  if (foundYou) {
468
508
  const note_a = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_a');
469
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual({
509
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation({
470
510
  blockNotes: ['# note1\n'],
471
511
  inherits: defaultTags,
472
512
  notes: ['# note2\n'],
@@ -491,7 +531,7 @@ describe('query operation annotations', () => {
491
531
  expect(foundYou).toBeDefined();
492
532
  if (foundYou) {
493
533
  const note_a = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_a');
494
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
534
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
495
535
  }
496
536
  });
497
537
  test('aggregate ref inherits', () => {
@@ -518,7 +558,7 @@ describe('query operation annotations', () => {
518
558
  expect(foundYou).toBeDefined();
519
559
  if (foundYou) {
520
560
  const note_a = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_a');
521
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual({
561
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation({
522
562
  blockNotes: ['# note1\n'],
523
563
  inherits: defaultTags,
524
564
  notes: ['# note2\n'],
@@ -543,7 +583,7 @@ describe('query operation annotations', () => {
543
583
  expect(foundYou).toBeDefined();
544
584
  if (foundYou) {
545
585
  const note_a = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_a');
546
- expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).toEqual(defaultTags);
586
+ expect(note_a === null || note_a === void 0 ? void 0 : note_a.annotation).matchesAnnotation(defaultTags);
547
587
  }
548
588
  });
549
589
  test('nest from existing inherits annotation', () => {
@@ -558,7 +598,7 @@ describe('query operation annotations', () => {
558
598
  expect(foundYou).toBeDefined();
559
599
  if (foundYou) {
560
600
  const note_b = (0, test_translator_1.getFieldDef)(foundYou.pipeline[0], 'note_b');
561
- expect(note_b === null || note_b === void 0 ? void 0 : note_b.annotation).toEqual({ inherits: defaultTags });
601
+ expect(note_b === null || note_b === void 0 ? void 0 : note_b.annotation).matchesAnnotation({ inherits: defaultTags });
562
602
  }
563
603
  });
564
604
  });
package/dist/malloy.d.ts CHANGED
@@ -4,7 +4,7 @@ import { DocumentCompletion as DocumentCompletionDefinition, DocumentHighlight a
4
4
  import { DocumentHelpContext } from './lang/parse-tree-walkers/document-help-context-walker';
5
5
  import { CompiledQuery, DocumentReference, FieldBooleanDef, FieldDateDef, FieldJSONDef, FieldNumberDef, FieldStringDef, FieldTimestampDef, FieldTypeDef, FilterExpression, Query as InternalQuery, ModelDef, DocumentPosition as ModelDocumentPosition, NamedQuery, QueryData, QueryDataRow, QueryResult, SQLBlock, SQLBlockStructDef, SearchIndexResult, SearchValueMapResult, StructDef, TurtleDef, FieldUnsupportedDef, QueryRunStats, ImportLocation } from './model';
6
6
  import { Connection, InfoConnection, LookupConnection, ModelString, ModelURL, QueryString, QueryURL, URLReader } from './runtime_types';
7
- import { Taggable, Tags } from './tags';
7
+ import { TagParse, TagParseSpec, Taggable, Tags } from './tags';
8
8
  export interface Loggable {
9
9
  debug: (message?: any, ...optionalParams: any[]) => void;
10
10
  info: (message?: any, ...optionalParams: any[]) => void;
@@ -153,6 +153,8 @@ export declare class Model implements Taggable {
153
153
  readonly problems: LogMessage[];
154
154
  constructor(modelDef: ModelDef, queryList: InternalQuery[], sqlBlocks: SQLBlockStructDef[], problems: LogMessage[], referenceAt?: (location: ModelDocumentPosition) => DocumentReference | undefined, importAt?: (location: ModelDocumentPosition) => ImportLocation | undefined);
155
155
  getTags(): Tags;
156
+ tagParse(spec?: TagParseSpec): TagParse;
157
+ getTaglines(prefix?: RegExp): string[];
156
158
  /**
157
159
  * Retrieve a document reference for the token at the given position within
158
160
  * the document that produced this model.
@@ -228,6 +230,8 @@ export declare class PreparedQuery implements Taggable {
228
230
  name?: string;
229
231
  constructor(query: InternalQuery, model: ModelDef, name?: string);
230
232
  getTags(): Tags;
233
+ tagParse(spec?: TagParseSpec): TagParse;
234
+ getTaglines(prefix?: RegExp): string[];
231
235
  /**
232
236
  * Generate the SQL for this query.
233
237
  *
@@ -411,6 +415,8 @@ export declare class PreparedResult implements Taggable {
411
415
  protected modelDef: ModelDef;
412
416
  constructor(query: CompiledQuery, modelDef: ModelDef);
413
417
  getTags(): Tags;
418
+ tagParse(spec?: TagParseSpec): TagParse;
419
+ getTaglines(prefix?: RegExp): string[];
414
420
  /**
415
421
  * @return The name of the connection this query should be run against.
416
422
  */
@@ -563,6 +569,8 @@ export declare class AtomicField extends Entity implements Taggable {
563
569
  constructor(fieldTypeDef: FieldTypeDef, parent: Explore, source?: AtomicField);
564
570
  get type(): AtomicFieldType;
565
571
  getTags(): Tags;
572
+ tagParse(spec?: TagParseSpec): TagParse;
573
+ getTaglines(prefix?: RegExp): string[];
566
574
  isIntrinsic(): boolean;
567
575
  isQueryField(): this is QueryField;
568
576
  isExploreField(): this is ExploreField;
@@ -642,6 +650,8 @@ export declare class QueryField extends Query implements Taggable {
642
650
  protected parent: Explore;
643
651
  constructor(turtleDef: TurtleDef, parent: Explore, source?: Query);
644
652
  getTags(): Tags;
653
+ tagParse(spec?: TagParseSpec): TagParse;
654
+ getTaglines(prefix?: RegExp): string[];
645
655
  isQueryField(): this is QueryField;
646
656
  isExploreField(): this is ExploreField;
647
657
  isAtomicField(): this is AtomicField;
@@ -660,6 +670,8 @@ export declare class ExploreField extends Explore implements Taggable {
660
670
  constructor(structDef: StructDef, parentExplore: Explore, source?: Explore);
661
671
  get joinRelationship(): JoinRelationship;
662
672
  getTags(): Tags;
673
+ tagParse(spec?: TagParseSpec): TagParse;
674
+ getTaglines(prefix?: RegExp): string[];
663
675
  isQueryField(): this is QueryField;
664
676
  isExploreField(): this is ExploreField;
665
677
  isAtomicField(): this is AtomicField;
package/dist/malloy.js CHANGED
@@ -329,6 +329,12 @@ class Model {
329
329
  getTags() {
330
330
  return new tags_1.Tags(this.modelDef.annotation);
331
331
  }
332
+ tagParse(spec) {
333
+ return tags_1.Tag.annotationToTag(this.modelDef.annotation, spec);
334
+ }
335
+ getTaglines(prefix) {
336
+ return tags_1.Tag.annotationToTaglines(this.modelDef.annotation, prefix);
337
+ }
332
338
  /**
333
339
  * Retrieve a document reference for the token at the given position within
334
340
  * the document that produced this model.
@@ -462,6 +468,13 @@ class PreparedQuery {
462
468
  getTags() {
463
469
  return new tags_1.Tags(this._query.annotation);
464
470
  }
471
+ tagParse(spec) {
472
+ // mtoy todo spec.scopes ||= [Model.getTag(somehow.find.modelDef)] ;
473
+ return tags_1.Tag.annotationToTag(this._query.annotation, spec);
474
+ }
475
+ getTaglines(prefix) {
476
+ return tags_1.Tag.annotationToTaglines(this._query.annotation, prefix);
477
+ }
465
478
  /**
466
479
  * Generate the SQL for this query.
467
480
  *
@@ -705,6 +718,13 @@ class PreparedResult {
705
718
  getTags() {
706
719
  return new tags_1.Tags(this.inner.annotation);
707
720
  }
721
+ tagParse(spec) {
722
+ // mtoy todo spec.scopes ||= [Model.getTag(somehow.find.modelDef)] ;
723
+ return tags_1.Tag.annotationToTag(this.inner.annotation, spec);
724
+ }
725
+ getTaglines(prefix) {
726
+ return tags_1.Tag.annotationToTaglines(this.inner.annotation, prefix);
727
+ }
708
728
  /**
709
729
  * @return The name of the connection this query should be run against.
710
730
  */
@@ -1134,6 +1154,13 @@ class AtomicField extends Entity {
1134
1154
  getTags() {
1135
1155
  return new tags_1.Tags(this.fieldTypeDef.annotation);
1136
1156
  }
1157
+ tagParse(spec) {
1158
+ // mtoy todo spec.scopes ||= [Model.getTag(somehow.find.modelDef)] ;
1159
+ return tags_1.Tag.annotationToTag(this.fieldTypeDef.annotation, spec);
1160
+ }
1161
+ getTaglines(prefix) {
1162
+ return tags_1.Tag.annotationToTaglines(this.fieldTypeDef.annotation, prefix);
1163
+ }
1137
1164
  isIntrinsic() {
1138
1165
  return (0, model_1.FieldIsIntrinsic)(this.fieldTypeDef);
1139
1166
  }
@@ -1336,6 +1363,13 @@ class QueryField extends Query {
1336
1363
  getTags() {
1337
1364
  return new tags_1.Tags(this.turtleDef.annotation);
1338
1365
  }
1366
+ tagParse(spec) {
1367
+ // mtoy todo spec.scopes ||= [Model.getTag(somehow.find.modelDef)] ;
1368
+ return tags_1.Tag.annotationToTag(this.turtleDef.annotation, spec);
1369
+ }
1370
+ getTaglines(prefix) {
1371
+ return tags_1.Tag.annotationToTaglines(this.turtleDef.annotation, prefix);
1372
+ }
1339
1373
  isQueryField() {
1340
1374
  return true;
1341
1375
  }
@@ -1389,6 +1423,13 @@ class ExploreField extends Explore {
1389
1423
  getTags() {
1390
1424
  return new tags_1.Tags(this._structDef.annotation);
1391
1425
  }
1426
+ tagParse(spec) {
1427
+ // mtoy todo spec.scopes ||= [Model.getTag(somehow.find.modelDef)] ;
1428
+ return tags_1.Tag.annotationToTag(this._structDef.annotation, spec);
1429
+ }
1430
+ getTaglines(prefix) {
1431
+ return tags_1.Tag.annotationToTaglines(this._structDef.annotation, prefix);
1432
+ }
1392
1433
  isQueryField() {
1393
1434
  return false;
1394
1435
  }
@@ -581,10 +581,14 @@ export interface ModelDef {
581
581
  export declare type NamedStructDefs = Record<string, StructDef>;
582
582
  export declare type NamedModelObjects = Record<string, NamedModelObject>;
583
583
  /** Malloy source annotations attached to objects */
584
+ export interface Note {
585
+ text: string;
586
+ at: DocumentLocation;
587
+ }
584
588
  export interface Annotation {
585
589
  inherits?: Annotation;
586
- blockNotes?: string[];
587
- notes?: string[];
590
+ blockNotes?: Note[];
591
+ notes?: Note[];
588
592
  }
589
593
  export declare type QueryScalar = string | boolean | number | Date | Buffer | null;
590
594
  /** One value in one column of returned data. */
package/dist/tags.d.ts CHANGED
@@ -1,4 +1,67 @@
1
+ import { LogMessage } from './lang';
1
2
  import { Annotation } from './model';
3
+ export declare type TagDict = Record<string, TagInterface>;
4
+ declare type TagValue = string | TagInterface[];
5
+ interface TagInterface {
6
+ eq?: TagValue;
7
+ properties?: TagDict;
8
+ }
9
+ export interface TagParse {
10
+ tag: Tag;
11
+ log: LogMessage[];
12
+ }
13
+ export interface TagParseSpec {
14
+ prefix?: RegExp;
15
+ extending?: Tag;
16
+ scopes?: Tag[];
17
+ }
18
+ export interface Taggable {
19
+ getTags: () => Tags;
20
+ tagParse: (spec?: TagParseSpec) => TagParse;
21
+ getTaglines: (prefix?: RegExp) => string[];
22
+ }
23
+ /**
24
+ * Class for interacting with the parsed output of an annotation
25
+ * containing the Malloy tag language. Used by the parser to
26
+ * generate parsed data, and as an API to that data.
27
+ * ```
28
+ * tag.text(p?) => string value of tag.p or ''
29
+ * tag.array(p?) => Tag[] value of tag.p or []
30
+ * tag.numeric(p?) => numeric value of tag.p or NaN
31
+ * tag.dict => Record<string, Tag> of tag properties
32
+ * tag.tag(p) => Tag value of tag.p
33
+ * ```
34
+ */
35
+ export declare class Tag implements TagInterface {
36
+ eq?: TagValue;
37
+ properties?: TagDict;
38
+ static tagFrom(from?: TagInterface): Tag;
39
+ static ids: Map<Tag, number>;
40
+ static nextTagId: number;
41
+ static id(t: Tag): number;
42
+ peek(): string;
43
+ /**
44
+ * Parse a line of Malloy tag language into a Tag which can be queried
45
+ * @param source -- The source line to be parsed. If the string starts with #, then it skips
46
+ * all characters up to the first space.
47
+ * @param extending A tag which this line will be extending
48
+ * @param importing Outer "scopes" for $() references
49
+ * @returns Something shaped like { tag: Tag , log: ParseErrors[] }
50
+ */
51
+ static fromTagline(str: string, extending: Tag | undefined, ...importing: Tag[]): TagParse;
52
+ static annotationToTaglines(annote: Annotation | undefined, prefix?: RegExp): string[];
53
+ static annotationToTag(annote: Annotation | undefined, spec?: TagParseSpec): TagParse;
54
+ constructor(from?: TagInterface);
55
+ private find;
56
+ tag(...at: string[]): Tag | undefined;
57
+ has(...at: string[]): boolean;
58
+ text(...at: string[]): string;
59
+ numeric(...at: string[]): number;
60
+ get dict(): Record<string, Tag>;
61
+ array(...at: string[]): Tag[];
62
+ getProperties(): TagDict;
63
+ clone(): Tag;
64
+ }
2
65
  export declare type MalloyTagProperties = Record<string, string | boolean>;
3
66
  interface PropertyTag {
4
67
  properties: MalloyTagProperties;
@@ -6,9 +69,6 @@ interface PropertyTag {
6
69
  export interface MalloyTags extends PropertyTag {
7
70
  docStrings: string[];
8
71
  }
9
- export interface Taggable {
10
- getTags: () => Tags;
11
- }
12
72
  /**
13
73
  * Collection of useful functions for handing tag data ...
14
74
  */