pinstripe 0.22.0 → 0.23.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (143) hide show
  1. package/README.md +10 -0
  2. package/cli.js +46 -0
  3. package/lib/class.js +64 -0
  4. package/lib/client.js +20 -0
  5. package/lib/command.js +39 -0
  6. package/lib/commands/_file_importer.js +1 -0
  7. package/lib/commands/drop_database.js +6 -0
  8. package/lib/commands/generate_command.js +39 -0
  9. package/lib/commands/generate_component.js +37 -0
  10. package/lib/commands/generate_migration.js +55 -0
  11. package/lib/commands/generate_model.js +43 -0
  12. package/lib/commands/generate_project.js +133 -0
  13. package/lib/commands/generate_service.js +32 -0
  14. package/lib/commands/generate_static_site.js +74 -0
  15. package/lib/commands/generate_view.js +44 -0
  16. package/lib/commands/init_database.js +9 -0
  17. package/lib/commands/list_commands.js +15 -0
  18. package/lib/commands/list_components.js +16 -0
  19. package/lib/commands/list_migrations.js +15 -0
  20. package/lib/commands/list_models.js +15 -0
  21. package/lib/commands/list_services.js +15 -0
  22. package/lib/commands/list_views.js +16 -0
  23. package/lib/commands/migrate_database.js +6 -0
  24. package/lib/commands/purge_old_sessions.js +12 -0
  25. package/lib/commands/reset_database.js +9 -0
  26. package/lib/commands/seed_database.js +6 -0
  27. package/lib/commands/show_config.js +6 -0
  28. package/lib/commands/start_repl.js +6 -0
  29. package/lib/commands/start_server.js +9 -0
  30. package/lib/component.js +56 -24
  31. package/lib/component_event.js +28 -0
  32. package/lib/components/_file_importer.js +1 -0
  33. package/lib/components/{anchor.js → a.js} +2 -3
  34. package/lib/components/body.js +2 -4
  35. package/lib/components/document.js +2 -4
  36. package/lib/components/form.js +2 -4
  37. package/lib/components/{frame.js → pinstripe_frame.js} +2 -4
  38. package/lib/components/{markdown_editor.js → pinstripe_markdown_editor.js} +4 -4
  39. package/lib/components/{overlay.js → pinstripe_overlay.js} +2 -4
  40. package/lib/components/{progress_bar.js → pinstripe_progress_bar.js} +2 -4
  41. package/lib/components/pinstripe_silo.js +2 -0
  42. package/lib/constants.js +26 -0
  43. package/lib/context.js +40 -0
  44. package/lib/database/client.js +211 -0
  45. package/lib/database/column_reference.js +13 -0
  46. package/lib/database/constants.js +87 -0
  47. package/lib/database/index.js +7 -0
  48. package/lib/database/migration.js +30 -0
  49. package/lib/database/migrator.js +28 -0
  50. package/lib/database/row.js +392 -0
  51. package/lib/database/singleton.js +12 -0
  52. package/lib/database/table.js +516 -0
  53. package/lib/database/table_reference.js +33 -0
  54. package/lib/database/union.js +128 -0
  55. package/lib/database.js +139 -0
  56. package/lib/defer.js +35 -0
  57. package/lib/defer.test.js +37 -0
  58. package/lib/escape_html.js +2 -0
  59. package/lib/extensions/_file_importer.js +2 -0
  60. package/lib/extensions/multi-app/index.js +4 -0
  61. package/lib/extensions/multi-app/views/_file_importer.js +2 -0
  62. package/lib/extensions/multi-app/views/apps/default.js +6 -0
  63. package/lib/extensions/multi-app/views/apps/guard.js +7 -0
  64. package/lib/extensions/multi-app/views/guard.js +21 -0
  65. package/lib/extensions/multi-tenant/database/row.js +27 -0
  66. package/lib/extensions/multi-tenant/database/table.js +30 -0
  67. package/lib/extensions/multi-tenant/database.js +8 -0
  68. package/lib/extensions/multi-tenant/index.js +4 -0
  69. package/lib/extensions/multi-tenant/migrations/1627976174_create_tenant_table_and_add_tenant_id_to_existing_tables.js +20 -0
  70. package/lib/extensions/multi-tenant/migrations/_file_importer.js +2 -0
  71. package/lib/extensions/multi-tenant/services/_file_importer.js +2 -0
  72. package/lib/extensions/multi-tenant/services/database.js +32 -0
  73. package/lib/html.js +72 -0
  74. package/lib/import_all.js +94 -0
  75. package/lib/index.js +10 -2
  76. package/lib/inflector.js +173 -0
  77. package/lib/model.js +110 -0
  78. package/lib/project.js +71 -0
  79. package/lib/registry.js +133 -0
  80. package/lib/service_consumer.js +16 -0
  81. package/lib/service_factory.js +20 -0
  82. package/lib/services/_file_importer.js +1 -0
  83. package/lib/services/args.js +9 -0
  84. package/lib/services/bot.js +69 -0
  85. package/lib/services/cli_utils.js +77 -0
  86. package/lib/services/client_builder.js +68 -0
  87. package/lib/services/config.js +63 -0
  88. package/lib/services/cookies.js +19 -0
  89. package/lib/services/create_model.js +8 -0
  90. package/lib/services/database.js +14 -0
  91. package/lib/services/defer.js +8 -0
  92. package/lib/services/fetch.js +116 -0
  93. package/lib/services/format_date.js +8 -0
  94. package/lib/services/fs_builder.js +132 -0
  95. package/lib/services/inflector.js +8 -0
  96. package/lib/services/initial_params.js +13 -0
  97. package/lib/services/params.js +13 -0
  98. package/lib/services/parse_html.js +8 -0
  99. package/lib/services/project.js +8 -0
  100. package/lib/services/render_form.js +161 -0
  101. package/lib/services/render_html.js +8 -0
  102. package/lib/services/render_markdown.js +43 -0
  103. package/lib/services/render_view.js +8 -0
  104. package/lib/services/repl.js +54 -0
  105. package/lib/services/run_command.js +8 -0
  106. package/lib/services/run_in_new_workspace.js +11 -0
  107. package/lib/services/send_mail.js +46 -0
  108. package/lib/services/server.js +90 -0
  109. package/lib/services/view_names.js +8 -0
  110. package/lib/singleton.js +13 -0
  111. package/lib/string_reader.js +22 -0
  112. package/lib/trapify.js +32 -0
  113. package/lib/unescape_html.js +2 -0
  114. package/lib/unescape_html.test.js +9 -0
  115. package/lib/util.js +3 -0
  116. package/lib/validation_error.js +7 -0
  117. package/lib/view.js +46 -0
  118. package/lib/view_file_importers/ejs.js +82 -0
  119. package/lib/view_file_importers/md.js +42 -0
  120. package/lib/views/_file_importer.js +1 -0
  121. package/lib/views/assets/javascripts/all.js.js +7 -0
  122. package/lib/views/assets/javascripts/all.js.map.js +7 -0
  123. package/lib/views/assets/stylesheets/all.css.js +28 -0
  124. package/lib/views/assets/stylesheets/components/button.css +43 -0
  125. package/lib/views/assets/stylesheets/components/card.css +29 -0
  126. package/lib/views/assets/stylesheets/components/form.css +4 -0
  127. package/lib/views/assets/stylesheets/components/frame.css +3 -0
  128. package/lib/views/assets/stylesheets/components/input.css +40 -0
  129. package/lib/views/assets/stylesheets/components/label.css +9 -0
  130. package/lib/views/assets/stylesheets/components/modal.css +62 -0
  131. package/lib/views/assets/stylesheets/components/overlay.css +11 -0
  132. package/lib/views/assets/stylesheets/components/pagination.css +60 -0
  133. package/lib/views/assets/stylesheets/components/progress_bar.css +20 -0
  134. package/lib/views/assets/stylesheets/components/textarea.css +10 -0
  135. package/lib/views/assets/stylesheets/global.css +120 -0
  136. package/lib/views/assets/stylesheets/reset.css +74 -0
  137. package/lib/views/assets/stylesheets/vars.css +25 -0
  138. package/lib/virtual_node.js +171 -0
  139. package/lib/virtual_node.test.js +28 -0
  140. package/lib/workspace.js +21 -0
  141. package/package.json +28 -5
  142. package/lib/components/index.js +0 -9
  143. package/lib/event_wrapper.js +0 -26
@@ -0,0 +1,16 @@
1
+
2
+ import chalk from 'chalk';
3
+ import { Component } from 'pinstripe';
4
+
5
+ export default {
6
+ run(){
7
+ console.log('');
8
+ console.log('The following components are available:');
9
+ console.log('');
10
+ Component.names.forEach(componentName => {
11
+ console.log(` * ${chalk.green(componentName)}`);
12
+ });
13
+ console.log('');
14
+ }
15
+ };
16
+
@@ -0,0 +1,15 @@
1
+
2
+ import chalk from 'chalk';
3
+ import { Migration } from 'pinstripe/database';
4
+
5
+ export default {
6
+ run(){
7
+ console.log('');
8
+ console.log('The following migrations are available:');
9
+ console.log('');
10
+ Migration.names.forEach(migrationName => {
11
+ console.log(` * ${chalk.green(migrationName)}`);
12
+ });
13
+ console.log('');
14
+ }
15
+ };
@@ -0,0 +1,15 @@
1
+
2
+ import chalk from 'chalk';
3
+ import { Row } from 'pinstripe/database';
4
+
5
+ export default {
6
+ run(){
7
+ console.log('');
8
+ console.log('The following models are available:');
9
+ console.log('');
10
+ Row.names.forEach(modelName => {
11
+ console.log(` * ${chalk.green(modelName)}`);
12
+ });
13
+ console.log('');
14
+ }
15
+ };
@@ -0,0 +1,15 @@
1
+
2
+ import chalk from 'chalk';
3
+ import { ServiceFactory } from 'pinstripe';
4
+
5
+ export default {
6
+ run(){
7
+ console.log('');
8
+ console.log('The following views are available:');
9
+ console.log('');
10
+ ServiceFactory.names.forEach(serviceFactoryName => {
11
+ console.log(` * ${chalk.green(serviceFactoryName)}`);
12
+ });
13
+ console.log('');
14
+ }
15
+ };
@@ -0,0 +1,16 @@
1
+
2
+ import chalk from 'chalk';
3
+ import { View } from 'pinstripe';
4
+
5
+ export default {
6
+ run(){
7
+ console.log('');
8
+ console.log('The following views are available:');
9
+ console.log('');
10
+ View.names.forEach(viewName => {
11
+ console.log(` * ${chalk.green(viewName)}`);
12
+ });
13
+ console.log('');
14
+ }
15
+ };
16
+
@@ -0,0 +1,6 @@
1
+
2
+ export default {
3
+ async run(){
4
+ await this.database.migrate();
5
+ }
6
+ };
@@ -0,0 +1,12 @@
1
+
2
+ export default {
3
+ meta(){
4
+ this.schedule('*/5 * * * *');
5
+ },
6
+
7
+ minutesUntilExpiry: 30,
8
+
9
+ async run(){
10
+ // await this.database.withoutMultiTenancy.sessions.lastAccessedAtLt(Date.now() - (1000 * 60 * this.minutesUntilExpiry)).delete();
11
+ }
12
+ };
@@ -0,0 +1,9 @@
1
+
2
+ import { Command } from 'pinstripe';
3
+
4
+ export default {
5
+ async run(){
6
+ await this.runCommand('drop-database');
7
+ await this.runCommand('init-database');
8
+ }
9
+ };
@@ -0,0 +1,6 @@
1
+
2
+ export default {
3
+ run(){
4
+ // do nothing
5
+ }
6
+ };
@@ -0,0 +1,6 @@
1
+
2
+ export default {
3
+ async run(){
4
+ console.log(JSON.stringify(await this.config, null, 2));
5
+ }
6
+ };
@@ -0,0 +1,6 @@
1
+
2
+ export default {
3
+ async run(){
4
+ await this.repl.start()
5
+ }
6
+ };
@@ -0,0 +1,9 @@
1
+
2
+ export default {
3
+ run(){
4
+ this.server.start();
5
+
6
+ //TODO: be able to pass a --without-bot option
7
+ this.bot.start();
8
+ }
9
+ };
package/lib/component.js CHANGED
@@ -1,12 +1,20 @@
1
1
 
2
- import { Class, TEXT_ONLY_TAGS, Inflector, VirtualNode, Registry } from "haberdash";
2
+ import { fileURLToPath } from 'url'; // pinstripe-if-client: const fileURLToPath = undefined;
3
3
 
4
- import { EventWrapper } from './event_wrapper.js';
4
+ import { Class } from './class.js';
5
+ import { TEXT_ONLY_TAGS } from './constants.js';
6
+ import { Inflector } from './inflector.js';
7
+ import { VirtualNode } from './virtual_node.js';
8
+ import { Registry } from './registry.js';
9
+ import { ComponentEvent } from './component_event.js';
10
+ import { Client } from './client.js'; // pinstripe-if-client: const Client = undefined;
5
11
 
6
12
  export const Component = Class.extend().include({
7
13
  meta(){
8
14
  this.include(Registry);
9
15
 
16
+ const { importFile } = this;
17
+
10
18
  this.assignProps({
11
19
  instanceFor(node){
12
20
  if(!node._component){
@@ -22,6 +30,22 @@ export const Component = Class.extend().include({
22
30
 
23
31
  normalizeName(name){
24
32
  return Inflector.instance.dasherize(name);
33
+ },
34
+
35
+ async importFile(params){
36
+ const { filePath, relativeFilePathWithoutExtension } = params;
37
+ if((await import(filePath)).default){
38
+ Client.instance.addModule(`
39
+ import { Component } from ${JSON.stringify(fileURLToPath(`${import.meta.url}/../index.js`))};
40
+ import include from ${JSON.stringify(filePath)};
41
+ Component.register(${JSON.stringify(relativeFilePathWithoutExtension)}, include);
42
+ `);
43
+ } else {
44
+ Client.instance.addModule(`
45
+ import ${JSON.stringify(filePath)};
46
+ `);
47
+ }
48
+ return importFile.call(this, params);
25
49
  }
26
50
  });
27
51
  },
@@ -103,7 +127,9 @@ export const Component = Class.extend().include({
103
127
  },
104
128
 
105
129
  get realParent(){
106
- return this.node.parentNode ? this.constructor.instanceFor(this.node.parentNode) : null;
130
+ if(this.node.parentNode) return this.constructor.instanceFor(this.node.parentNode);
131
+ if(this.node.host instanceof Element) return this.constructor.instanceFor(this.node.host);
132
+ return null;
107
133
  },
108
134
 
109
135
  get parent(){
@@ -277,7 +303,7 @@ export const Component = Class.extend().include({
277
303
  const selector = args.pop()
278
304
 
279
305
  const wrapperFn = (event, ...args) => {
280
- const eventWrapper = EventWrapper.instanceFor(event)
306
+ const eventWrapper = ComponentEvent.instanceFor(event)
281
307
  if(selector){
282
308
  if(eventWrapper.target.is(selector)){
283
309
  return fn.call(eventWrapper.target, eventWrapper, ...args);
@@ -464,6 +490,9 @@ const matchesSelector = (() => {
464
490
  })();
465
491
 
466
492
  function cleanChildren(){
493
+ if(this.node.shadowRoot){
494
+ this.shadow.children.forEach(child => clean.call(child));
495
+ }
467
496
  this.children.forEach(child => clean.call(child));
468
497
  }
469
498
 
@@ -494,6 +523,9 @@ function clearTimers(){
494
523
  }
495
524
 
496
525
  function initChildren(){
526
+ if(this.node.shadowRoot){
527
+ this.shadow.children.forEach(child => initChildren.call(child));
528
+ }
497
529
  this.children.forEach(child => initChildren.call(child));
498
530
  }
499
531
 
@@ -516,13 +548,19 @@ function createVirtualNode(html){
516
548
  }
517
549
 
518
550
  function patch(attributes, virtualChildren){
519
- const isEmptyFrame = this.is('.frame') && virtualChildren.length == 0;
551
+ const isFrame = this.type == 'pinstripe-frame' || this.attributes['data-component'] == 'pinstripe-frame';
552
+ const isEmptyFrame = isFrame && virtualChildren.length == 0;
520
553
  if(isEmptyFrame && attributes['data-load-on-init'] === undefined){
521
554
  attributes['data-load-on-init'] = 'true';
522
555
  }
523
556
  patchAttributes.call(this, attributes);
524
557
  if(isEmptyFrame) return;
525
- patchChildren.call(this, virtualChildren);
558
+ if(this.is('pinstripe-silo, [data-component="pinstripe-silo"]')){
559
+ patchChildren.call(this.shadow, virtualChildren);
560
+ patchChildren.call(this, []);
561
+ } else {
562
+ patchChildren.call(this, virtualChildren);
563
+ }
526
564
  }
527
565
 
528
566
  function patchAttributes(attributes){
@@ -601,10 +639,17 @@ function insert(virtualNode, referenceChild, returnComponent = true){
601
639
  insert.call(new Component(node, true), child, null, false);
602
640
  })
603
641
 
604
- this.node.insertBefore(
605
- node,
606
- referenceChild && referenceChild.node
607
- );
642
+ if(this.is('pinstripe-silo, [data-component="pinstripe-silo"]')){
643
+ this.shadow.node.insertBefore(
644
+ node,
645
+ referenceChild && referenceChild.node
646
+ );
647
+ } else {
648
+ this.node.insertBefore(
649
+ node,
650
+ referenceChild && referenceChild.node
651
+ );
652
+ }
608
653
 
609
654
  if(returnComponent){
610
655
  return Component.instanceFor(node);
@@ -632,17 +677,4 @@ function normalizeVirtualNode(){
632
677
  }
633
678
  }
634
679
 
635
- EventWrapper.Component = Component;
636
-
637
- [
638
- ['#document', 'pinstripe-document'],
639
- ['a', 'pinstripe-anchor'],
640
- ['body', 'pinstripe-body'],
641
- ['form', 'pinstripe-form']
642
- ].forEach(([name, include]) => {
643
- Component.register(name, {
644
- meta(){
645
- this.include(include);
646
- }
647
- })
648
- });
680
+ ComponentEvent.Component = Component;
@@ -0,0 +1,28 @@
1
+
2
+ import { Class } from './class.js';
3
+ import { trapify } from './trapify.js';
4
+
5
+ export const ComponentEvent = Class.extend().include({
6
+ meta(){
7
+ this.assignProps({
8
+ instanceFor(event){
9
+ if(!event._componentEvent){
10
+ event._componentEvent = ComponentEvent.new(event);
11
+ }
12
+ return event._componentEvent;
13
+ }
14
+ });
15
+ },
16
+
17
+ initialize(event){
18
+ this.event = event;
19
+ return trapify(this);
20
+ },
21
+
22
+ __get(target, name){
23
+ const out = target.event[name];
24
+ if(out instanceof Node) return ComponentEvent.Component.instanceFor(out);
25
+ if(typeof out == 'function') return (...args) => out.call(target.event, ...args);
26
+ return out;
27
+ }
28
+ });
@@ -0,0 +1 @@
1
+ export { Component as default } from 'pinstripe';
@@ -1,8 +1,7 @@
1
1
 
2
- import { Component } from "../component.js";
3
2
  import { loadFrame, removeFrame } from "./helpers.js";
4
3
 
5
- Component.register('pinstripe-anchor', {
4
+ export default {
6
5
  initialize(...args){
7
6
  this.constructor.parent.prototype.initialize.call(this, ...args);
8
7
 
@@ -19,4 +18,4 @@ Component.register('pinstripe-anchor', {
19
18
 
20
19
  if(this.is('input, textarea')) this.on('keyup', (event) => this.trigger('click'));
21
20
  }
22
- });
21
+ };
@@ -1,7 +1,5 @@
1
1
 
2
- import { Component } from "../component.js";
3
-
4
- Component.register('pinstripe-body', {
2
+ export default {
5
3
  initialize(...args){
6
4
  this.constructor.parent.prototype.initialize.call(this, ...args);
7
5
 
@@ -32,4 +30,4 @@ Component.register('pinstripe-body', {
32
30
  unclip(){
33
31
  this.shadow.find('.styles').patch('');
34
32
  }
35
- });
33
+ };
@@ -1,7 +1,5 @@
1
1
 
2
- import { Component } from "../component.js";
3
-
4
- Component.register('pinstripe-document', {
2
+ export default {
5
3
  meta(){
6
4
  this.include('pinstripe-frame');
7
5
  },
@@ -48,4 +46,4 @@ Component.register('pinstripe-document', {
48
46
  }, headers)
49
47
  }, otherOptions));
50
48
  }
51
- });
49
+ };
@@ -1,9 +1,7 @@
1
1
 
2
- import { Component } from "../component.js";
3
-
4
2
  import { loadFrame } from "./helpers.js";
5
3
 
6
- Component.register('pinstripe-form', {
4
+ export default {
7
5
  initialize(...args){
8
6
  this.constructor.parent.prototype.initialize.call(this, ...args);
9
7
 
@@ -24,4 +22,4 @@ Component.register('pinstripe-form', {
24
22
  get hasUnsavedChanges(){
25
23
  return this.data.hasUnsavedChanges || JSON.stringify(this.values) != this._initialHash;
26
24
  }
27
- });
25
+ };
@@ -1,7 +1,5 @@
1
1
 
2
- import { Component } from "../component.js";
3
-
4
- Component.register('pinstripe-frame', {
2
+ export default {
5
3
  initialize(...args){
6
4
  this.constructor.parent.prototype.initialize.call(this, ...args);
7
5
 
@@ -46,4 +44,4 @@ Component.register('pinstripe-frame', {
46
44
 
47
45
  return this.patch(await response.text());
48
46
  }
49
- });
47
+ };
@@ -1,7 +1,7 @@
1
1
 
2
2
  import { Component } from '../component.js'
3
3
 
4
- Component.register('pinstripe-markdown-editor', {
4
+ export default {
5
5
  initialize(...args){
6
6
  this.constructor.parent.prototype.initialize.call(this, ...args);
7
7
 
@@ -41,7 +41,7 @@ Component.register('pinstripe-markdown-editor', {
41
41
  editorTextarea.node.selectionStart = position;
42
42
  editorTextarea.node.selectionEnd = position;
43
43
  }
44
- });
44
+ };
45
45
 
46
46
  Component.register('pinstripe-markdown-editor/line-inserter', {
47
47
  initialize(...args){
@@ -59,11 +59,11 @@ Component.register('pinstripe-markdown-editor/line-inserter', {
59
59
 
60
60
  Component.register('pinstripe-markdown-editor/anchor', {
61
61
  meta(){
62
- this.include('pinstripe-anchor');
62
+ this.include('a');
63
63
  },
64
64
 
65
65
  initialize(...args){
66
- this.constructor.for('pinstripe-anchor').prototype.initialize.call(this, ...args);
66
+ this.constructor.for('a').prototype.initialize.call(this, ...args);
67
67
 
68
68
  this.patch({
69
69
  ...this.attributes,
@@ -1,7 +1,5 @@
1
1
 
2
- import { Component } from "../component.js";
3
-
4
- Component.register('pinstripe-overlay', {
2
+ export default {
5
3
  meta(){
6
4
  this.include('pinstripe-frame');
7
5
  },
@@ -57,4 +55,4 @@ Component.register('pinstripe-overlay', {
57
55
  this.document.body.unclip();
58
56
  }
59
57
  }
60
- });
58
+ };
@@ -1,7 +1,5 @@
1
1
 
2
- import { Component } from "../component.js";
3
-
4
- Component.register('pinstripe-progress-bar', {
2
+ export default {
5
3
  initialize(...args){
6
4
  this.constructor.parent.prototype.initialize.call(this, ...args);
7
5
 
@@ -75,4 +73,4 @@ Component.register('pinstripe-progress-bar', {
75
73
  }
76
74
  }
77
75
  }
78
- });
76
+ };
@@ -0,0 +1,2 @@
1
+
2
+ export default {};
@@ -0,0 +1,26 @@
1
+
2
+ export const SELF_CLOSING_TAGS = [
3
+ 'area',
4
+ 'base',
5
+ 'br',
6
+ 'embed',
7
+ 'hr',
8
+ 'iframe',
9
+ 'img',
10
+ 'input',
11
+ 'link',
12
+ 'meta',
13
+ 'param',
14
+ 'slot',
15
+ 'source',
16
+ 'track'
17
+ ];
18
+
19
+ export const TEXT_ONLY_TAGS = [
20
+ 'script',
21
+ 'style'
22
+ ];
23
+
24
+ export const IS_SERVER = typeof window == 'undefined';
25
+
26
+ export const IS_CLIENT = !IS_SERVER;
package/lib/context.js ADDED
@@ -0,0 +1,40 @@
1
+
2
+ import { Class } from './class.js';
3
+
4
+ export const Context = Class.extend().include({
5
+ meta(){
6
+ this.assignProps({ name: 'context' });
7
+ },
8
+
9
+ initialize(){
10
+ this.assignProps({ root: this });
11
+ },
12
+
13
+ async run(fn){
14
+ let out;
15
+ try {
16
+ out = await fn(this);
17
+ } catch (e){
18
+ await this.destroy();
19
+ throw e;
20
+ }
21
+ await this.destroy();
22
+ return out;
23
+ },
24
+
25
+ fork(){
26
+ const out = this.constructor.new();
27
+ out.assignProps({ parent: this, root: this?.root });
28
+ return out;
29
+ },
30
+
31
+ async destroy(){
32
+ const resources = Object.values(this);
33
+ while(resources.length){
34
+ const resource = await resources.shift();
35
+ if(typeof resource == 'object' && !(resource instanceof Context) && typeof resource.destroy == 'function'){
36
+ await resource.destroy();
37
+ }
38
+ }
39
+ }
40
+ });