lemon-core 4.3.0 → 5.0.1

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 (167) hide show
  1. package/README.md +127 -2
  2. package/dist/common/lemon-error.d.ts +34 -0
  3. package/dist/common/lemon-error.js +52 -0
  4. package/dist/common/lemon-error.js.map +1 -0
  5. package/dist/controllers/general-api-controller.d.ts +7 -0
  6. package/dist/controllers/general-api-controller.js +7 -0
  7. package/dist/controllers/general-api-controller.js.map +1 -1
  8. package/dist/cores/api/api-service.js +10 -43
  9. package/dist/cores/api/api-service.js.map +1 -1
  10. package/dist/cores/aws/aws-kms-service.d.ts +13 -5
  11. package/dist/cores/aws/aws-kms-service.js +23 -9
  12. package/dist/cores/aws/aws-kms-service.js.map +1 -1
  13. package/dist/cores/aws/aws-s3-service.d.ts +30 -4
  14. package/dist/cores/aws/aws-s3-service.js +35 -15
  15. package/dist/cores/aws/aws-s3-service.js.map +1 -1
  16. package/dist/cores/aws/aws-sns-service.js +59 -9
  17. package/dist/cores/aws/aws-sns-service.js.map +1 -1
  18. package/dist/cores/aws/aws-sqs-service.d.ts +1 -1
  19. package/dist/cores/aws/aws-sqs-service.js +54 -12
  20. package/dist/cores/aws/aws-sqs-service.js.map +1 -1
  21. package/dist/cores/cache/cache-service.d.ts +10 -9
  22. package/dist/cores/cache/cache-service.js +9 -346
  23. package/dist/cores/cache/cache-service.js.map +1 -1
  24. package/dist/cores/config/config-service.d.ts +3 -15
  25. package/dist/cores/config/config-service.js +5 -34
  26. package/dist/cores/config/config-service.js.map +1 -1
  27. package/dist/cores/dynamo/dynamo-query-service.js +42 -2
  28. package/dist/cores/dynamo/dynamo-query-service.js.map +1 -1
  29. package/dist/cores/dynamo/dynamo-scan-service.js +42 -2
  30. package/dist/cores/dynamo/dynamo-scan-service.js.map +1 -1
  31. package/dist/cores/dynamo/dynamo-service.d.ts +45 -14
  32. package/dist/cores/dynamo/dynamo-service.js +48 -21
  33. package/dist/cores/dynamo/dynamo-service.js.map +1 -1
  34. package/dist/cores/dynamo/tools/expressions.js +32 -22
  35. package/dist/cores/dynamo/tools/expressions.js.map +1 -1
  36. package/dist/cores/dynamo/tools/lang.d.ts +30 -0
  37. package/dist/cores/dynamo/tools/lang.js +75 -0
  38. package/dist/cores/dynamo/tools/lang.js.map +1 -0
  39. package/dist/cores/dynamo/tools/query.js +20 -21
  40. package/dist/cores/dynamo/tools/query.js.map +1 -1
  41. package/dist/cores/dynamo/tools/scan.js +15 -16
  42. package/dist/cores/dynamo/tools/scan.js.map +1 -1
  43. package/dist/cores/dynamo/tools/serializer.js +40 -38
  44. package/dist/cores/dynamo/tools/serializer.js.map +1 -1
  45. package/dist/cores/dynamo/tools/utils.d.ts +6 -2
  46. package/dist/cores/dynamo/tools/utils.js +11 -8
  47. package/dist/cores/dynamo/tools/utils.js.map +1 -1
  48. package/dist/cores/elastic/elastic6-query-service.d.ts +1 -104
  49. package/dist/cores/elastic/elastic6-query-service.js +15 -489
  50. package/dist/cores/elastic/elastic6-query-service.js.map +1 -1
  51. package/dist/cores/elastic/elastic6-service.d.ts +1 -482
  52. package/dist/cores/elastic/elastic6-service.js +15 -1153
  53. package/dist/cores/elastic/elastic6-service.js.map +1 -1
  54. package/dist/cores/elastic/index.d.ts +2 -2
  55. package/dist/cores/elastic/index.js +3 -2
  56. package/dist/cores/elastic/index.js.map +1 -1
  57. package/dist/cores/elastic/os2-query-service.d.ts +104 -0
  58. package/dist/cores/elastic/os2-query-service.js +495 -0
  59. package/dist/cores/elastic/os2-query-service.js.map +1 -0
  60. package/dist/cores/elastic/os2-service.d.ts +372 -0
  61. package/dist/cores/elastic/os2-service.js +943 -0
  62. package/dist/cores/elastic/os2-service.js.map +1 -0
  63. package/dist/cores/index.d.ts +6 -1
  64. package/dist/cores/index.js +9 -2
  65. package/dist/cores/index.js.map +1 -1
  66. package/dist/cores/lambda/index.js +2 -1
  67. package/dist/cores/lambda/index.js.map +1 -1
  68. package/dist/cores/lambda/lambda-cron-handler.d.ts +1 -0
  69. package/dist/cores/lambda/lambda-cron-handler.js +5 -1
  70. package/dist/cores/lambda/lambda-cron-handler.js.map +1 -1
  71. package/dist/cores/lambda/lambda-dynamo-stream-handler.d.ts +5 -4
  72. package/dist/cores/lambda/lambda-dynamo-stream-handler.js +18 -5
  73. package/dist/cores/lambda/lambda-dynamo-stream-handler.js.map +1 -1
  74. package/dist/cores/lambda/lambda-handler.d.ts +22 -2
  75. package/dist/cores/lambda/lambda-handler.js +85 -23
  76. package/dist/cores/lambda/lambda-handler.js.map +1 -1
  77. package/dist/cores/lambda/lambda-sns-handler.d.ts +1 -0
  78. package/dist/cores/lambda/lambda-sns-handler.js +5 -0
  79. package/dist/cores/lambda/lambda-sns-handler.js.map +1 -1
  80. package/dist/cores/lambda/lambda-sqs-handler.d.ts +1 -0
  81. package/dist/cores/lambda/lambda-sqs-handler.js +20 -5
  82. package/dist/cores/lambda/lambda-sqs-handler.js.map +1 -1
  83. package/dist/cores/lambda/lambda-web-handler.d.ts +10 -0
  84. package/dist/cores/lambda/lambda-web-handler.js +107 -41
  85. package/dist/cores/lambda/lambda-web-handler.js.map +1 -1
  86. package/dist/cores/protocol/aws-lambda-helper.js +58 -11
  87. package/dist/cores/protocol/aws-lambda-helper.js.map +1 -1
  88. package/dist/cores/protocol/index.js +3 -0
  89. package/dist/cores/protocol/index.js.map +1 -1
  90. package/dist/cores/protocol/protocol-service.d.ts +26 -5
  91. package/dist/cores/protocol/protocol-service.js +42 -12
  92. package/dist/cores/protocol/protocol-service.js.map +1 -1
  93. package/dist/cores/protocol/protocol-sign.d.ts +72 -0
  94. package/dist/cores/protocol/protocol-sign.js +194 -0
  95. package/dist/cores/protocol/protocol-sign.js.map +1 -0
  96. package/dist/cores/storage/index.d.ts +0 -1
  97. package/dist/cores/storage/index.js +0 -1
  98. package/dist/cores/storage/index.js.map +1 -1
  99. package/dist/cores/storage/model-fields.d.ts +7 -0
  100. package/dist/cores/storage/model-fields.js +21 -0
  101. package/dist/cores/storage/model-fields.js.map +1 -0
  102. package/dist/cores/storage/model-manager.d.ts +5 -2
  103. package/dist/cores/storage/model-manager.js +11 -3
  104. package/dist/cores/storage/model-manager.js.map +1 -1
  105. package/dist/engine/builder.js +20 -2
  106. package/dist/engine/builder.js.map +1 -1
  107. package/dist/engine/engine.d.ts +2 -2
  108. package/dist/engine/engine.js +5 -5
  109. package/dist/engine/engine.js.map +1 -1
  110. package/dist/engine/utilities.d.ts +20 -12
  111. package/dist/engine/utilities.js +57 -86
  112. package/dist/engine/utilities.js.map +1 -1
  113. package/dist/environ.d.ts +0 -6
  114. package/dist/environ.js +1 -12
  115. package/dist/environ.js.map +1 -1
  116. package/dist/esm/index.mjs +141 -0
  117. package/dist/esm/testing.mjs +12 -0
  118. package/dist/extended/abstract-service.d.ts +48 -139
  119. package/dist/extended/abstract-service.js +46 -382
  120. package/dist/extended/abstract-service.js.map +1 -1
  121. package/dist/extended/cores/abstract-controllers.d.ts +25 -0
  122. package/dist/extended/cores/abstract-controllers.js +77 -7
  123. package/dist/extended/cores/abstract-controllers.js.map +1 -1
  124. package/dist/extended/cores/abstract-rest-apis.d.ts +2 -1
  125. package/dist/extended/cores/abstract-rest-apis.js +2 -1
  126. package/dist/extended/cores/abstract-rest-apis.js.map +1 -1
  127. package/dist/extended/cores/abstract-services.d.ts +48 -87
  128. package/dist/extended/cores/abstract-services.js +121 -248
  129. package/dist/extended/cores/abstract-services.js.map +1 -1
  130. package/dist/extended/cores/commons.d.ts +4 -113
  131. package/dist/extended/cores/commons.js +26 -180
  132. package/dist/extended/cores/commons.js.map +1 -1
  133. package/dist/extended/cores/fields-admin.d.ts +91 -0
  134. package/dist/extended/cores/fields-admin.js +142 -0
  135. package/dist/extended/cores/fields-admin.js.map +1 -0
  136. package/dist/extended/cores/index.d.ts +2 -0
  137. package/dist/extended/cores/index.js +2 -0
  138. package/dist/extended/cores/index.js.map +1 -1
  139. package/dist/extended/cores/types.d.ts +3 -225
  140. package/dist/extended/cores/types.js +28 -0
  141. package/dist/extended/cores/types.js.map +1 -1
  142. package/dist/helpers/helpers.d.ts +10 -5
  143. package/dist/helpers/helpers.js +46 -58
  144. package/dist/helpers/helpers.js.map +1 -1
  145. package/dist/helpers/types.d.ts +22 -10
  146. package/dist/index.d.ts +1 -5
  147. package/dist/index.js +8 -14
  148. package/dist/index.js.map +1 -1
  149. package/dist/lib/http-fetch.d.ts +54 -0
  150. package/dist/lib/http-fetch.js +133 -0
  151. package/dist/lib/http-fetch.js.map +1 -0
  152. package/dist/lib/lazy.d.ts +22 -0
  153. package/dist/lib/lazy.js +54 -0
  154. package/dist/lib/lazy.js.map +1 -0
  155. package/dist/lib/perf.d.ts +35 -0
  156. package/dist/lib/perf.js +52 -0
  157. package/dist/lib/perf.js.map +1 -0
  158. package/dist/tools/tools.d.ts +15 -3
  159. package/dist/tools/tools.js +21 -4
  160. package/dist/tools/tools.js.map +1 -1
  161. package/package.json +96 -39
  162. package/dist/cores/storage/redis-storage-service.d.ts +0 -183
  163. package/dist/cores/storage/redis-storage-service.js +0 -377
  164. package/dist/cores/storage/redis-storage-service.js.map +0 -1
  165. package/dist/generated/field-registry.d.ts +0 -12
  166. package/dist/generated/field-registry.js +0 -21
  167. package/dist/generated/field-registry.js.map +0 -1
@@ -1,10 +1,13 @@
1
- import { SearchType, Elastic6Service, Elastic6Option, Elastic6QueryService } from '../../cores/';
1
+ import { SearchType, OS2CoreService, OS2BaseOption, OS2QueryService } from '../../cores/';
2
2
  import { DynamoScanFilter, ApiHttpProxy } from '../../cores/';
3
- import { elasticsearch, SearchResponse, Elastic6Item } from '../../cores/';
4
- import { Elastic6Synchronizer, CoreManager, CoreService, SearchResult, ManagerProxy, AbstractProxy, Elastic6Instance } from '../abstract-service';
3
+ import { OS2Item } from '../../cores/';
4
+ import type { Client } from '@opensearch-project/opensearch';
5
+ import { OS2Synchronizer, CoreManager, CoreService, SearchResult, ManagerProxy, AbstractProxy, AbstractOS2Instance, OS2ConstructParams } from '../abstract-service';
6
+ export { sourceToItem } from '../abstract-service';
5
7
  import { Incrementable, CoreModel, SearchBody, SearchQuery, NextContext, NextIdentity, SortTerm, SimpleSet, GeneralItem } from 'lemon-model';
6
8
  import { BulkItemsResult, IdentityToken, ListResult, PaginateParam } from './types';
7
9
  import { CrendentialForAWS } from '../../environ';
10
+ import { ModelClass } from '../../cores/storage/model-fields';
8
11
  export type SearchParam<T> = T & {
9
12
  [key: string]: string | number;
10
13
  };
@@ -87,22 +90,21 @@ export declare abstract class MyCoreService<Model extends CoreModel<ModelType>,
87
90
  abstract createProxy(context: NextContext): Proxy;
88
91
  /**
89
92
  * make proxy, and use callback to handle.
90
- * - it will save automatically.
93
+ * - it will save automatically on success.
94
+ * - v5: on exception it saves only when `options.saveOnError` is true (default false, B5 § 6.7).
91
95
  */
92
- guardProxy: <T>(context: NextContext, callback: (proxy: Proxy) => Promise<T>) => Promise<T>;
96
+ guardProxy: <T>(context: NextContext, callback: (proxy: Proxy) => Promise<T>, options?: {
97
+ saveOnError?: boolean;
98
+ }) => Promise<T>;
93
99
  /**
94
- * run search
95
- * - override this to hide `$ES6`
100
+ * run search (via `$OS2`)
101
+ * - override this to hide `$OS2`
96
102
  */
97
103
  doSearch<T>(body: SearchBody): Promise<SearchResult<T>>;
98
104
  /**
99
105
  * check if using useSession from environ.
100
106
  */
101
107
  isUseSession(): boolean;
102
- /**
103
- * @deprecated typo kept for 1 minor as a non-breaking alias — use `isUseSession()` instead. (cores-migration P1, decision #2)
104
- */
105
- isUseSssion(): boolean;
106
108
  /**
107
109
  * check if search-engine is supportable
108
110
  * @returns
@@ -117,7 +119,7 @@ export declare abstract class MyCoreService<Model extends CoreModel<ModelType>,
117
119
  */
118
120
  export declare abstract class MyCoreManager<Model extends CoreModel<ModelType>, ModelType extends string, Service extends MyCoreService<Model, ModelType, any>> extends CoreManager<Model, ModelType, Service> {
119
121
  readonly options?: {
120
- /** enable to sync with es6 (default true) */
122
+ /** enable to sync with the search engine (v5 default false — B5 § 6.7) */
121
123
  enableSync?: boolean;
122
124
  /** unique field */
123
125
  uniqueField?: string;
@@ -132,8 +134,8 @@ export declare abstract class MyCoreManager<Model extends CoreModel<ModelType>,
132
134
  * constructor
133
135
  * @protected
134
136
  */
135
- protected constructor(type: ModelType, parent: Service, fields: string[], options?: {
136
- /** enable to sync with es6 (default true) */
137
+ protected constructor(type: ModelType, parent: Service, fields: string[] | ModelClass, options?: {
138
+ /** enable to sync with the search engine (v5 default false — B5 § 6.7) */
137
139
  enableSync?: boolean;
138
140
  /** unique field */
139
141
  uniqueField?: string;
@@ -356,7 +358,7 @@ export declare class MyCoreProxy<U extends string, MyService extends MyCoreServi
356
358
  }): boolean;
357
359
  /**
358
360
  * check if current context has `admin` access
359
- * 1. run in local environ (or internal protocol with domin='localhost')
361
+ * 1. run in local mode (`$U.isLocalMode()`, v5 — no longer `domain='localhost'`)
360
362
  * 2. access via signed access-key
361
363
  * 3. authorized cognito and has `admin` role in identity-token.
362
364
  *
@@ -525,10 +527,6 @@ interface ElasticParams<T extends object = any> {
525
527
  * body content.
526
528
  */
527
529
  body: T;
528
- /**
529
- * document type (optional).
530
- */
531
- type?: string;
532
530
  }
533
531
  /**
534
532
  * parameters for Elasticsearch search operations.
@@ -544,47 +542,27 @@ interface ElasticSearchParams<T extends object = any> {
544
542
  * search body content.
545
543
  */
546
544
  body: T;
547
- /**
548
- * document type (optional).
549
- */
550
- type?: string;
551
545
  /**
552
546
  * search type
553
547
  * (e.g., 'query_then_fetch', 'dfs_query_then_fetch').
554
548
  */
555
- searchType: SearchType;
549
+ search_type?: SearchType;
556
550
  }
557
551
  /**
558
552
  * class: `OS2Service`
559
553
  * - Master 권한 전용 Elasticsearch 관리 서비스
560
- * - elasticsearch service for OS2.
554
+ * - service for OS2: data path via FGAC (`$fgac`), index management via the master client.
561
555
  */
562
- export declare class OS2Service<T extends Elastic6Item = any> extends Elastic6Service<any> {
563
- protected _options: Elastic6Option;
564
- readonly _client: elasticsearch.Client;
556
+ export declare class OS2Service<T extends OS2Item = any> extends OS2CoreService<any> {
565
557
  readonly $fgac: OS2FGACManager;
566
- static instance(endpoint: string): {
567
- client: elasticsearch.Client;
568
- };
569
- constructor(options: Elastic6Option, fgac: OS2FGACManager);
570
- get client(): elasticsearch.Client;
571
- get options(): Elastic6Option;
572
558
  /**
573
- * describe `settings` and `mappings` of index.
559
+ * constructor (no client here; the master client is created on first `client` access)
574
560
  */
575
- describe(): Promise<{
576
- settings: any;
577
- mappings: any;
578
- }>;
561
+ constructor(options: OS2BaseOption, fgac: OS2FGACManager);
579
562
  /**
580
- * create index by name
581
- * @param settings - creating settings
563
+ * build the master client: `auth` is read from config now (after engine init), and set only when both exist.
582
564
  */
583
- createIndex(settings?: any): Promise<{
584
- status: any;
585
- index: string;
586
- acknowledged: any;
587
- }>;
565
+ protected createClient(): Client;
588
566
  /**
589
567
  * delete index by name
590
568
  */
@@ -606,12 +584,11 @@ export declare class OS2Service<T extends Elastic6Item = any> extends Elastic6Se
606
584
  idName?: string;
607
585
  }): Promise<BulkItemsResult>;
608
586
  /**
609
- * push item for time-series data.
587
+ * push item for time-series data (via FGAC; the result is the response body itself).
610
588
  *
611
589
  * @param item - item to push
612
- * @param type - document type (default: doc-type given at construction time)
613
590
  */
614
- pushItem(item: T, type?: string): Promise<T>;
591
+ pushItem(item: T): Promise<T>;
615
592
  /**
616
593
  * read item with projections
617
594
  *
@@ -647,13 +624,6 @@ export declare class OS2Service<T extends Elastic6Item = any> extends Elastic6Se
647
624
  * @param searchType - type of search (e.g., 'query_then_fetch', 'dfs_query_then_fetch').
648
625
  */
649
626
  searchRaw<T extends object = any>(body: SearchBody, searchType?: SearchType): Promise<T>;
650
- /**
651
- * run search, and get the formatmted response.
652
- * @param body - Elasticsearch Query DSL that defines the search request (e.g., size, query, filters).
653
- * @param searchType - type of search (e.g., 'query_then_fetch', 'dfs_query_then_fetch').
654
- *
655
- */
656
- search(body: SearchBody, searchType?: SearchType): Promise<SearchResponse>;
657
627
  }
658
628
  /**
659
629
  * type: `OS2FGACManager`
@@ -661,8 +631,8 @@ export declare class OS2Service<T extends Elastic6Item = any> extends Elastic6Se
661
631
  */
662
632
  export declare class OS2FGACManager {
663
633
  private _fgacProxy;
664
- readonly options: Elastic6Option;
665
- constructor(options: Elastic6Option);
634
+ readonly options: OS2BaseOption;
635
+ constructor(options: OS2BaseOption);
666
636
  hello: () => string;
667
637
  get proxy(): ApiHttpProxy;
668
638
  /** FGAC 기반 검색 */
@@ -714,7 +684,7 @@ export declare class OS2FGACManager {
714
684
  doFgacOpenIndex<R = any>(index: string): Promise<R>;
715
685
  }
716
686
  /** extended option for `OS2Instance` */
717
- export interface OS2Option extends Elastic6Option {
687
+ export interface OS2Option extends OS2BaseOption {
718
688
  /** (optional) role-name in FGAC */
719
689
  roleName?: string;
720
690
  /** (optional) user-name in FGAC */
@@ -723,35 +693,27 @@ export interface OS2Option extends Elastic6Option {
723
693
  /**
724
694
  * OS2 인스턴스
725
695
  * - describeIndex(), destroyIndex(), search() with elastic initialized by master-key
696
+ * - one service set (fgac, elastic, query, synchronizer) only when `endpoint && indexName`.
726
697
  */
727
- export declare class OS2Instance extends Elastic6Instance {
728
- readonly client?: elasticsearch.Client;
698
+ export declare class OS2Instance extends AbstractOS2Instance {
729
699
  readonly elastic?: OS2Service;
730
- readonly query?: Elastic6QueryService<any>;
731
- readonly synchronizer?: Elastic6Synchronizer;
700
+ readonly query?: OS2QueryService<any>;
701
+ readonly synchronizer?: OS2Synchronizer;
732
702
  readonly fgac?: OS2FGACManager;
733
- constructor({ endpoint, indexName, idName, esVersion, esDocType, tableName, autocompleteFields, roleName, userName, }: {
734
- endpoint: string;
735
- indexName: string;
703
+ /**
704
+ * build one service set when `endpoint && indexName` (no client: it is created on first use).
705
+ */
706
+ constructor({ endpoint, indexName, idName, tableName, autocompleteFields, roleName, userName, }: OS2ConstructParams & {
707
+ /** (optional) id-name (default `$id`, `null` = unset) */
736
708
  idName?: string;
737
- esVersion: string;
738
- esDocType: string;
739
- tableName: string;
740
- autocompleteFields: string[];
709
+ /** (optional) role-name in FGAC */
741
710
  roleName?: string;
711
+ /** (optional) user-name in FGAC */
742
712
  userName?: string;
743
713
  });
744
714
  hello: () => string;
745
715
  get options(): OS2Option;
746
716
  get $X2(): typeof $X2;
747
- /**
748
- * display index settings and mappings
749
- */
750
- describeIndex(): Promise<any>;
751
- /**
752
- * create Elasticsearch index with ES7+ mapping structure
753
- */
754
- createIndex(): Promise<any>;
755
717
  /**
756
718
  * search
757
719
  */
@@ -773,7 +735,6 @@ export declare class OS2Instance extends Elastic6Instance {
773
735
  idName?: string;
774
736
  }): Promise<BulkItemsResult>;
775
737
  }
776
- export declare function sourceToItem<T>(_source: T, idName?: string): T;
777
738
  /**
778
739
  * internal tools
779
740
  */
@@ -795,16 +756,16 @@ declare const $X2: {
795
756
  };
796
757
  /**
797
758
  * factory of `OS2Instance`
759
+ * - reads `OS2_ENDPOINT`, `OS2_INDEX`, `MY_DYNAMO_TABLE`, `OS2_AUTOCOMPLETE_FIELDS` (no version, no doc-type).
798
760
  */
799
761
  export declare const _OS2: (options?: OS2Option) => OS2Instance;
762
+ /**
763
+ * the default `OS2Instance`, built lazily by `_OS2()` on first access (S-25).
764
+ * - nothing is built at import: no client, no dynamo-stream listener.
765
+ * - without `OS2_ENDPOINT` it is an `OS2Instance` with `options === null`.
766
+ */
800
767
  export declare const $OS2: OS2Instance;
801
- export declare const $ES6: Elastic6Instance;
802
768
  /**
803
- * explicit alias for the OS2-routing `$ES6` above (decision #3, cores-migration P1).
804
- * - kept as `$ES6` here for deep-import compatibility (`lemon-core/dist/extended/cores`).
805
- * - exported at root ONLY under this name: root `$ES6` stays pinned to the L1
806
- * (non-OS2) `extended/abstract-service` version, so consumers must opt in by
807
- * name instead of silently getting OS2-routing behavior via the root barrel.
769
+ * explicit alias of `$OS2` (the same object). The name is kept; the meaning is OS2.
808
770
  */
809
- export declare const $ES6Routed: Elastic6Instance;
810
- export {};
771
+ export declare const $ES6Routed: OS2Instance;