wardens 0.4.0 → 0.4.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.
package/CHANGELOG.md CHANGED
@@ -6,6 +6,12 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
6
6
 
7
7
  ## [Unreleased]
8
8
 
9
+ ## [0.4.1] - 2023-01-14
10
+
11
+ ### Fixed
12
+
13
+ - Newer versions of TypeScript complained about signatures in `bindContext(...)`.
14
+
9
15
  ## [0.4.0] - 2022-06-19
10
16
 
11
17
  ### Added
@@ -54,7 +60,8 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
54
60
  - `mount`/`unmount` hooks to provision resources
55
61
  - `allocate`/`deallocate` for creating hierarchies of resources
56
62
 
57
- [Unreleased]: https://github.com/PsychoLlama/wardens/compare/v0.4.0...HEAD
63
+ [Unreleased]: https://github.com/PsychoLlama/wardens/compare/v0.4.1...HEAD
64
+ [0.4.1]: https://github.com/PsychoLlama/wardens/compare/v0.4.0...v0.4.1
58
65
  [0.4.0]: https://github.com/PsychoLlama/wardens/compare/v0.3.0...v0.4.0
59
66
  [0.3.0]: https://github.com/PsychoLlama/wardens/compare/v0.2.0...v0.3.0
60
67
  [0.2.0]: https://github.com/PsychoLlama/wardens/compare/v0.1.0...v0.2.0
package/README.md CHANGED
@@ -1,7 +1,7 @@
1
1
  <div align="center">
2
2
  <h1>Wardens</h1>
3
3
  <p>A tiny framework for managing resources.</p>
4
- <img alt="Build status" src="https://img.shields.io/github/workflow/status/PsychoLlama/wardens/Test/main" />
4
+ <img alt="Build status" src="https://img.shields.io/github/actions/workflow/status/PsychoLlama/wardens/test.yml?branch=main" />
5
5
  <img alt="TypeScript" src="https://img.shields.io/npm/types/wardens" />
6
6
  <img alt="npm version" src="https://img.shields.io/npm/v/wardens" />
7
7
  </div>
@@ -14,7 +14,7 @@ Here's an example: let's say you've got a thread pool, one per CPU. Each thread
14
14
 
15
15
  ```typescript
16
16
  async function Worker() {
17
- const thread = await spawn()
17
+ const thread = await spawn();
18
18
 
19
19
  return {
20
20
  // The value returned after initialization completes
@@ -22,24 +22,27 @@ async function Worker() {
22
22
 
23
23
  // Called when the resource is destroyed
24
24
  destroy: () => thread.close(),
25
- }
25
+ };
26
26
  }
27
27
  ```
28
28
 
29
29
  Now define a pool that creates and manages workers:
30
30
 
31
31
  ```typescript
32
- async function WorkerPool({ create }: ResourceContext, config: { poolSize: number }) {
33
- const promises = Array(config.poolSize).fill(Worker).map(create)
34
- const threads = await Promise.all(promises)
32
+ async function WorkerPool(
33
+ { create }: ResourceContext,
34
+ config: { poolSize: number },
35
+ ) {
36
+ const promises = Array(config.poolSize).fill(Worker).map(create);
37
+ const threads = await Promise.all(promises);
35
38
 
36
39
  return {
37
40
  // ... External API goes here ...
38
41
  value: {
39
42
  doSomeWork() {},
40
43
  doSomethingElse() {},
41
- }
42
- }
44
+ },
45
+ };
43
46
  }
44
47
  ```
45
48
 
@@ -48,17 +51,17 @@ Finally, create the pool:
48
51
  ```typescript
49
52
  const pool = await create(WorkerPool, {
50
53
  poolSize: cpus().length,
51
- })
54
+ });
52
55
 
53
56
  // Provisioned and ready to go!
54
- pool.doSomeWork()
55
- pool.doSomethingElse()
57
+ pool.doSomeWork();
58
+ pool.doSomethingElse();
56
59
  ```
57
60
 
58
61
  The magic of this framework is that resources never outlive their owners. If you tear down the pool, it will deallocate everything beneath it first:
59
62
 
60
63
  ```typescript
61
- await destroy(pool)
64
+ await destroy(pool);
62
65
 
63
66
  // [info] closing worker
64
67
  // [info] closing worker
@@ -0,0 +1,87 @@
1
+ var p = Object.defineProperty;
2
+ var x = (n, e, t) => e in n ? p(n, e, { enumerable: !0, configurable: !0, writable: !0, value: t }) : n[e] = t;
3
+ var a = (n, e, t) => (x(n, typeof e != "symbol" ? e + "" : e, t), t), f = (n, e, t) => {
4
+ if (!e.has(n))
5
+ throw TypeError("Cannot " + t);
6
+ };
7
+ var i = (n, e, t) => (f(n, e, "read from private field"), t ? t.call(n) : e.get(n)), y = (n, e, t) => {
8
+ if (e.has(n))
9
+ throw TypeError("Cannot add the same private member more than once");
10
+ e instanceof WeakSet ? e.add(n) : e.set(n, t);
11
+ }, l = (n, e, t, o) => (f(n, e, "write to private field"), o ? o.call(n, t) : e.set(n, t), t);
12
+ function g(n) {
13
+ const e = /* @__PURE__ */ new WeakMap();
14
+ return new Proxy(n, {
15
+ get(t, o) {
16
+ const r = Reflect.get(t, o, t);
17
+ if (typeof r == "function") {
18
+ if (e.has(r) === !1) {
19
+ const c = r.bind(t);
20
+ Object.defineProperties(
21
+ c,
22
+ Object.getOwnPropertyDescriptors(r)
23
+ ), e.set(r, c);
24
+ }
25
+ return e.get(r);
26
+ }
27
+ return r;
28
+ },
29
+ set(t, o, r) {
30
+ return Reflect.set(t, o, r, t);
31
+ }
32
+ });
33
+ }
34
+ const u = /* @__PURE__ */ new WeakMap();
35
+ function m(n) {
36
+ return Proxy.revocable(n, {});
37
+ }
38
+ var s;
39
+ class v {
40
+ constructor(e) {
41
+ y(this, s, void 0);
42
+ /** Provision an owned resource and make sure it doesn't outlive us. */
43
+ a(this, "create", async (e, ...t) => {
44
+ const o = await P(e, ...t);
45
+ return i(this, s).add(o), o;
46
+ });
47
+ /**
48
+ * Tear down a resource. Happens automatically when resource owners are
49
+ * deallocated.
50
+ */
51
+ a(this, "destroy", async (e) => {
52
+ if (!i(this, s).has(e))
53
+ throw new Error("You do not own this resource.");
54
+ try {
55
+ await w(e);
56
+ } finally {
57
+ i(this, s).delete(e);
58
+ }
59
+ });
60
+ l(this, s, e);
61
+ }
62
+ }
63
+ s = new WeakMap();
64
+ async function P(n, ...e) {
65
+ const t = /* @__PURE__ */ new Set(), o = new v(t), r = await n(o, ...e), c = r.value, { proxy: d, revoke: h } = m(c);
66
+ return u.set(d, {
67
+ resource: r,
68
+ children: t,
69
+ revoke: h
70
+ }), d;
71
+ }
72
+ async function w(n) {
73
+ const e = u.get(n);
74
+ if (e) {
75
+ u.delete(n), e.revoke();
76
+ const t = Array.from(e.children).map(w), o = await Promise.allSettled(t);
77
+ e.resource.destroy && await e.resource.destroy(), o.forEach((r) => {
78
+ if (r.status === "rejected")
79
+ throw r.reason;
80
+ });
81
+ }
82
+ }
83
+ export {
84
+ g as bindContext,
85
+ P as create,
86
+ w as destroy
87
+ };
@@ -1 +1 @@
1
- var P=Object.defineProperty;var g=(e,t,n)=>t in e?P(e,t,{enumerable:!0,configurable:!0,writable:!0,value:n}):e[t]=n;var y=(e,t,n)=>(g(e,typeof t!="symbol"?t+"":t,n),n),p=(e,t,n)=>{if(!t.has(e))throw TypeError("Cannot "+n)};var f=(e,t,n)=>(p(e,t,"read from private field"),n?n.call(e):t.get(e)),b=(e,t,n)=>{if(t.has(e))throw TypeError("Cannot add the same private member more than once");t instanceof WeakSet?t.add(e):t.set(e,n)},m=(e,t,n,u)=>(p(e,t,"write to private field"),u?u.call(e,n):t.set(e,n),n);(function(e,t){typeof exports=="object"&&typeof module!="undefined"?t(exports):typeof define=="function"&&define.amd?define(["exports"],t):(e=typeof globalThis!="undefined"?globalThis:e||self,t(e.wardens={}))})(this,function(e){var a;"use strict";function t(c){const o=new WeakMap;return new Proxy(c,{get(s,i){const r=Reflect.get(s,i,s);if(typeof r=="function"){if(o.has(r)===!1){const d=r.bind(s);Object.defineProperties(d,Object.getOwnPropertyDescriptors(r)),o.set(r,d)}return o.get(r)}return r},set(s,i,r){return Reflect.set(s,i,r,s)}})}const n=new WeakMap;function u(c){return Proxy.revocable(c,{})}class v{constructor(o){b(this,a,void 0);y(this,"create",async(o,...s)=>{const i=await h(o,...s);return f(this,a).add(i),i});y(this,"destroy",async o=>{if(!f(this,a).has(o))throw new Error("You do not own this resource.");try{await l(o)}finally{f(this,a).delete(o)}});m(this,a,o)}}a=new WeakMap;async function h(c,...o){const s=new Set,i=new v(s),r=await c(i,...o),d=r.value,{proxy:w,revoke:x}=u(d);return n.set(w,{resource:r,children:s,revoke:x}),w}async function l(c){const o=n.get(c);if(o){n.delete(c),o.revoke();const s=Array.from(o.children).map(l),i=await Promise.allSettled(s);o.resource.destroy&&await o.resource.destroy(),i.forEach(r=>{if(r.status==="rejected")throw r.reason})}}e.bindContext=t,e.create=h,e.destroy=l,Object.defineProperties(e,{__esModule:{value:!0},[Symbol.toStringTag]:{value:"Module"}})});
1
+ var P=Object.defineProperty;var g=(e,t,n)=>t in e?P(e,t,{enumerable:!0,configurable:!0,writable:!0,value:n}):e[t]=n;var l=(e,t,n)=>(g(e,typeof t!="symbol"?t+"":t,n),n),p=(e,t,n)=>{if(!t.has(e))throw TypeError("Cannot "+n)};var f=(e,t,n)=>(p(e,t,"read from private field"),n?n.call(e):t.get(e)),b=(e,t,n)=>{if(t.has(e))throw TypeError("Cannot add the same private member more than once");t instanceof WeakSet?t.add(e):t.set(e,n)},m=(e,t,n,d)=>(p(e,t,"write to private field"),d?d.call(e,n):t.set(e,n),n);(function(e,t){typeof exports=="object"&&typeof module<"u"?t(exports):typeof define=="function"&&define.amd?define(["exports"],t):(e=typeof globalThis<"u"?globalThis:e||self,t(e.wardens={}))})(this,function(e){var a;"use strict";function t(c){const o=new WeakMap;return new Proxy(c,{get(s,i){const r=Reflect.get(s,i,s);if(typeof r=="function"){if(o.has(r)===!1){const u=r.bind(s);Object.defineProperties(u,Object.getOwnPropertyDescriptors(r)),o.set(r,u)}return o.get(r)}return r},set(s,i,r){return Reflect.set(s,i,r,s)}})}const n=new WeakMap;function d(c){return Proxy.revocable(c,{})}class x{constructor(o){b(this,a,void 0);l(this,"create",async(o,...s)=>{const i=await h(o,...s);return f(this,a).add(i),i});l(this,"destroy",async o=>{if(!f(this,a).has(o))throw new Error("You do not own this resource.");try{await y(o)}finally{f(this,a).delete(o)}});m(this,a,o)}}a=new WeakMap;async function h(c,...o){const s=new Set,i=new x(s),r=await c(i,...o),u=r.value,{proxy:w,revoke:v}=d(u);return n.set(w,{resource:r,children:s,revoke:v}),w}async function y(c){const o=n.get(c);if(o){n.delete(c),o.revoke();const s=Array.from(o.children).map(y),i=await Promise.allSettled(s);o.resource.destroy&&await o.resource.destroy(),i.forEach(r=>{if(r.status==="rejected")throw r.reason})}}e.bindContext=t,e.create=h,e.destroy=y,Object.defineProperty(e,Symbol.toStringTag,{value:"Module"})});
package/package.json CHANGED
@@ -1,9 +1,10 @@
1
1
  {
2
2
  "name": "wardens",
3
- "version": "0.4.0",
3
+ "version": "0.4.1",
4
4
  "description": "A framework for resource management",
5
5
  "main": "./dist/wardens.umd.js",
6
6
  "module": "./dist/wardens.es.js",
7
+ "types": "./src/index.ts",
7
8
  "repository": "git@github.com:PsychoLlama/wardens.git",
8
9
  "author": "Jesse Gibson <JesseTheGibson@gmail.com>",
9
10
  "license": "MIT",
@@ -31,7 +32,7 @@
31
32
  "exports": {
32
33
  ".": {
33
34
  "require": "./dist/wardens.umd.js",
34
- "import": "./dist/wardens.es.js"
35
+ "import": "./dist/wardens.mjs"
35
36
  }
36
37
  },
37
38
  "husky": {
@@ -82,17 +83,16 @@
82
83
  "preset": "ts-jest"
83
84
  },
84
85
  "devDependencies": {
85
- "@types/jest": "28.1.2",
86
- "@typescript-eslint/eslint-plugin": "5.28.0",
87
- "@typescript-eslint/parser": "5.28.0",
88
- "eslint": "8.18.0",
89
- "husky": "8.0.1",
90
- "jest": "28.1.1",
91
- "lint-staged": "13.0.2",
92
- "prettier": "2.7.1",
93
- "ts-jest": "28.0.5",
94
- "typescript": "4.7.4",
95
- "vite": "2.9.12",
96
- "vite-dts": "1.0.4"
86
+ "@types/jest": "29.2.5",
87
+ "@typescript-eslint/eslint-plugin": "5.48.1",
88
+ "@typescript-eslint/parser": "5.48.1",
89
+ "eslint": "8.31.0",
90
+ "husky": "8.0.3",
91
+ "jest": "29.3.1",
92
+ "lint-staged": "13.1.0",
93
+ "prettier": "2.8.3",
94
+ "ts-jest": "29.0.5",
95
+ "typescript": "4.9.4",
96
+ "vite": "4.0.4"
97
97
  }
98
98
  }
@@ -15,7 +15,7 @@
15
15
  *
16
16
  */
17
17
  export default function bindContext<T extends object>(value: T) {
18
- const methodBindings = new WeakMap<Fn, Fn>();
18
+ const methodBindings = new WeakMap<object, AnyMethod>();
19
19
 
20
20
  return new Proxy(value, {
21
21
  get(target, property) {
@@ -48,5 +48,4 @@ export default function bindContext<T extends object>(value: T) {
48
48
  });
49
49
  }
50
50
 
51
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
52
- type Fn = (...args: any) => any;
51
+ type AnyMethod = (...args: Array<unknown>) => unknown;
@@ -1 +0,0 @@
1
- export * from "../src/index"
@@ -1,102 +0,0 @@
1
- var __defProp = Object.defineProperty;
2
- var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
3
- var __publicField = (obj, key, value) => {
4
- __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
5
- return value;
6
- };
7
- var __accessCheck = (obj, member, msg) => {
8
- if (!member.has(obj))
9
- throw TypeError("Cannot " + msg);
10
- };
11
- var __privateGet = (obj, member, getter) => {
12
- __accessCheck(obj, member, "read from private field");
13
- return getter ? getter.call(obj) : member.get(obj);
14
- };
15
- var __privateAdd = (obj, member, value) => {
16
- if (member.has(obj))
17
- throw TypeError("Cannot add the same private member more than once");
18
- member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
19
- };
20
- var __privateSet = (obj, member, value, setter) => {
21
- __accessCheck(obj, member, "write to private field");
22
- setter ? setter.call(obj, value) : member.set(obj, value);
23
- return value;
24
- };
25
- var _resources;
26
- function bindContext(value) {
27
- const methodBindings = /* @__PURE__ */ new WeakMap();
28
- return new Proxy(value, {
29
- get(target, property) {
30
- const value2 = Reflect.get(target, property, target);
31
- if (typeof value2 === "function") {
32
- if (methodBindings.has(value2) === false) {
33
- const methodBinding = value2.bind(target);
34
- Object.defineProperties(methodBinding, Object.getOwnPropertyDescriptors(value2));
35
- methodBindings.set(value2, methodBinding);
36
- }
37
- return methodBindings.get(value2);
38
- }
39
- return value2;
40
- },
41
- set(target, property, newValue) {
42
- return Reflect.set(target, property, newValue, target);
43
- }
44
- });
45
- }
46
- const resources = /* @__PURE__ */ new WeakMap();
47
- function wrapWithProxy(value) {
48
- return Proxy.revocable(value, {});
49
- }
50
- class ResourceContext {
51
- constructor(ownedResources) {
52
- __privateAdd(this, _resources, void 0);
53
- __publicField(this, "create", async (factory, ...args) => {
54
- const controls = await create(factory, ...args);
55
- __privateGet(this, _resources).add(controls);
56
- return controls;
57
- });
58
- __publicField(this, "destroy", async (resource) => {
59
- if (!__privateGet(this, _resources).has(resource)) {
60
- throw new Error("You do not own this resource.");
61
- }
62
- try {
63
- await destroy(resource);
64
- } finally {
65
- __privateGet(this, _resources).delete(resource);
66
- }
67
- });
68
- __privateSet(this, _resources, ownedResources);
69
- }
70
- }
71
- _resources = new WeakMap();
72
- async function create(provision, ...args) {
73
- const children = /* @__PURE__ */ new Set();
74
- const context = new ResourceContext(children);
75
- const resource = await provision(context, ...args);
76
- const controls = resource.value;
77
- const { proxy, revoke } = wrapWithProxy(controls);
78
- resources.set(proxy, {
79
- resource,
80
- children,
81
- revoke
82
- });
83
- return proxy;
84
- }
85
- async function destroy(controls) {
86
- const entry = resources.get(controls);
87
- if (entry) {
88
- resources.delete(controls);
89
- entry.revoke();
90
- const recursiveUnmounts = Array.from(entry.children).map(destroy);
91
- const results = await Promise.allSettled(recursiveUnmounts);
92
- if (entry.resource.destroy) {
93
- await entry.resource.destroy();
94
- }
95
- results.forEach((result) => {
96
- if (result.status === "rejected") {
97
- throw result.reason;
98
- }
99
- });
100
- }
101
- }
102
- export { bindContext, create, destroy };
@@ -1 +0,0 @@
1
- export * from "../src/index"