@everyonesoftware/common 1.0.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 (163) hide show
  1. package/.c8rc.json +12 -0
  2. package/.github/workflows/publish.yml +38 -0
  3. package/.mocharc.json +9 -0
  4. package/README.md +9 -0
  5. package/package.json +36 -0
  6. package/sources/assertMessageParameters.ts +22 -0
  7. package/sources/asyncIterator.ts +437 -0
  8. package/sources/asyncIteratorToJavascriptAsyncIteratorAdapter.ts +48 -0
  9. package/sources/asyncResult.ts +95 -0
  10. package/sources/basicDisposable.ts +57 -0
  11. package/sources/byteList.ts +202 -0
  12. package/sources/byteListStream.ts +121 -0
  13. package/sources/byteReadStream.ts +24 -0
  14. package/sources/byteWriteStream.ts +16 -0
  15. package/sources/bytes.ts +25 -0
  16. package/sources/characterList.ts +195 -0
  17. package/sources/characterListStream.ts +151 -0
  18. package/sources/characterReadStream.ts +81 -0
  19. package/sources/characterReadStreamIterator.ts +128 -0
  20. package/sources/characterWriteStream.ts +45 -0
  21. package/sources/commandLineParameter.ts +45 -0
  22. package/sources/commandLineParameters.ts +21 -0
  23. package/sources/comparable.ts +144 -0
  24. package/sources/comparer.ts +133 -0
  25. package/sources/comparison.ts +20 -0
  26. package/sources/concatenateIterable.ts +119 -0
  27. package/sources/concatenateIterator.ts +165 -0
  28. package/sources/condition.ts +329 -0
  29. package/sources/currentProcess.ts +158 -0
  30. package/sources/dateTime.ts +130 -0
  31. package/sources/depthFirstSearch.ts +230 -0
  32. package/sources/disposable.ts +31 -0
  33. package/sources/emptyError.ts +10 -0
  34. package/sources/english.ts +45 -0
  35. package/sources/equalFunctions.ts +123 -0
  36. package/sources/fetchHttpClient.ts +89 -0
  37. package/sources/fetchHttpResponse.ts +106 -0
  38. package/sources/flatMapIterable.ts +104 -0
  39. package/sources/flatMapIterator.ts +152 -0
  40. package/sources/generator.ts +251 -0
  41. package/sources/httpClient.ts +36 -0
  42. package/sources/httpHeader.ts +37 -0
  43. package/sources/httpHeaders.ts +216 -0
  44. package/sources/httpIncomingRequest.ts +30 -0
  45. package/sources/httpIncomingResponse.ts +19 -0
  46. package/sources/httpMethod.ts +164 -0
  47. package/sources/httpOutgoingRequest.ts +119 -0
  48. package/sources/httpOutgoingResponse.ts +113 -0
  49. package/sources/httpServer.ts +34 -0
  50. package/sources/inMemoryCharacterWriteStream.ts +78 -0
  51. package/sources/index.ts +101 -0
  52. package/sources/iterable.ts +345 -0
  53. package/sources/iterator.ts +481 -0
  54. package/sources/iteratorToJavascriptIteratorAdapter.ts +48 -0
  55. package/sources/javascript.ts +59 -0
  56. package/sources/javascriptArrayList.ts +175 -0
  57. package/sources/javascriptAsyncIteratorToAsyncIteratorAdapter.ts +124 -0
  58. package/sources/javascriptIteratorToIteratorAdapter.ts +133 -0
  59. package/sources/javascriptMapMap.ts +143 -0
  60. package/sources/javascriptSetSet.ts +134 -0
  61. package/sources/list.ts +330 -0
  62. package/sources/listQueue.ts +62 -0
  63. package/sources/listStack.ts +62 -0
  64. package/sources/luxonDateTime.ts +109 -0
  65. package/sources/map.ts +302 -0
  66. package/sources/mapAsyncIterator.ts +141 -0
  67. package/sources/mapIterable.ts +105 -0
  68. package/sources/mapIterator.ts +145 -0
  69. package/sources/mutableCondition.ts +451 -0
  70. package/sources/mutableHttpHeaders.ts +204 -0
  71. package/sources/mutableMap.ts +292 -0
  72. package/sources/network.ts +18 -0
  73. package/sources/node.ts +37 -0
  74. package/sources/nodeJSCharacterWriteStream.ts +42 -0
  75. package/sources/nodeJSHttpIncomingRequest.ts +132 -0
  76. package/sources/nodeJSHttpServer.ts +134 -0
  77. package/sources/notFoundError.ts +12 -0
  78. package/sources/postCondition.ts +284 -0
  79. package/sources/postConditionError.ts +12 -0
  80. package/sources/preCondition.ts +284 -0
  81. package/sources/preConditionError.ts +12 -0
  82. package/sources/promiseAsyncResult.ts +174 -0
  83. package/sources/property.ts +63 -0
  84. package/sources/queue.ts +49 -0
  85. package/sources/realNetwork.ts +28 -0
  86. package/sources/recreationDotGovClient.ts +259 -0
  87. package/sources/searchControl.ts +42 -0
  88. package/sources/set.ts +244 -0
  89. package/sources/skipAsyncIterator.ts +145 -0
  90. package/sources/skipIterator.ts +155 -0
  91. package/sources/stack.ts +48 -0
  92. package/sources/stringComparer.ts +33 -0
  93. package/sources/stringIterator.ts +149 -0
  94. package/sources/strings.ts +322 -0
  95. package/sources/syncResult.ts +300 -0
  96. package/sources/takeAsyncIterator.ts +141 -0
  97. package/sources/takeIterator.ts +151 -0
  98. package/sources/toStringFunctions.ts +185 -0
  99. package/sources/types.ts +371 -0
  100. package/sources/whereAsyncIterator.ts +143 -0
  101. package/sources/whereIterable.ts +108 -0
  102. package/sources/whereIterator.ts +157 -0
  103. package/sources/wonderlandTrailClient.ts +1503 -0
  104. package/tests/assertTest.ts +113 -0
  105. package/tests/assertTestTests.ts +75 -0
  106. package/tests/basicTestSkip.ts +51 -0
  107. package/tests/byteListStreamTests.ts +390 -0
  108. package/tests/byteListTests.ts +27 -0
  109. package/tests/bytesTests.ts +43 -0
  110. package/tests/characterListStreamTests.ts +391 -0
  111. package/tests/characterListTests.ts +250 -0
  112. package/tests/characterWriteStreamTests.ts +12 -0
  113. package/tests/comparerTests.ts +92 -0
  114. package/tests/conditionTests.ts +877 -0
  115. package/tests/consoleTestRunner.ts +404 -0
  116. package/tests/consoleTestRunnerTests.ts +651 -0
  117. package/tests/dateTimeTests.ts +30 -0
  118. package/tests/depthFirstSearchTests.ts +106 -0
  119. package/tests/disposableTests.ts +121 -0
  120. package/tests/englishTests.ts +103 -0
  121. package/tests/equalFunctionsTests.ts +223 -0
  122. package/tests/failedTest.ts +43 -0
  123. package/tests/fetchHttpClientTests.ts +33 -0
  124. package/tests/generatorTests.ts +86 -0
  125. package/tests/httpClientTests.ts +18 -0
  126. package/tests/inMemoryCharacterWriteStreamTests.ts +117 -0
  127. package/tests/iterableTests.ts +141 -0
  128. package/tests/iteratorTests.ts +1086 -0
  129. package/tests/javascriptMapMapTests.ts +21 -0
  130. package/tests/listTests.ts +338 -0
  131. package/tests/mapIteratorTests.ts +55 -0
  132. package/tests/mapTests.ts +104 -0
  133. package/tests/mutableConditionTests.ts +273 -0
  134. package/tests/mutableMapTests.ts +154 -0
  135. package/tests/nodeJSHttpServerTests.ts +75 -0
  136. package/tests/notFoundErrorTests.ts +24 -0
  137. package/tests/postConditionErrorTests.ts +24 -0
  138. package/tests/preConditionErrorTests.ts +24 -0
  139. package/tests/promiseAsyncResultTests.ts +688 -0
  140. package/tests/propertyTests.ts +63 -0
  141. package/tests/queueTests.ts +29 -0
  142. package/tests/recreationDotGovClientTests.ts +191 -0
  143. package/tests/setTests.ts +140 -0
  144. package/tests/skippedTest.ts +39 -0
  145. package/tests/stackTests.ts +66 -0
  146. package/tests/stringComparerTests.ts +60 -0
  147. package/tests/stringIteratorTests.ts +156 -0
  148. package/tests/stringsTests.ts +516 -0
  149. package/tests/syncResultTests.ts +1251 -0
  150. package/tests/test.ts +228 -0
  151. package/tests/testAction.ts +75 -0
  152. package/tests/testActionTests.ts +93 -0
  153. package/tests/testFailureTests.ts +12 -0
  154. package/tests/testRunner.ts +267 -0
  155. package/tests/testRunnerTests.ts +895 -0
  156. package/tests/testSkip.ts +34 -0
  157. package/tests/tests.ts +103 -0
  158. package/tests/toStringFunctionsTests.ts +55 -0
  159. package/tests/typesTests.ts +257 -0
  160. package/tests/whereIteratorTests.ts +77 -0
  161. package/tests/wonderlandTrailClientTests.ts +452 -0
  162. package/tsconfig.json +17 -0
  163. package/tsup.config.ts +13 -0
@@ -0,0 +1,95 @@
1
+ import { PromiseAsyncResult } from "./promiseAsyncResult";
2
+ import { isPromise, Type } from "./types";
3
+
4
+ /**
5
+ * A result object that adds extra behavior beyond the standard {@link Promise}.
6
+ */
7
+ export abstract class AsyncResult<T> implements Promise<T>
8
+ {
9
+ public static create<T>(action: () => (T | Promise<T>)): AsyncResult<T>;
10
+ public static create<T>(promise: Promise<T>): AsyncResult<T>;
11
+ static create<T>(actionOrPromise: (() => (T | Promise<T>)) | Promise<T>): AsyncResult<T>
12
+ {
13
+ return PromiseAsyncResult.create<T>(isPromise<T>(actionOrPromise) ? actionOrPromise : new Promise<T>(actionOrPromise));
14
+ }
15
+
16
+ /**
17
+ * Create a new {@link AsyncResult} that contains the provided value.
18
+ * @param value The value to wrap in a {@link AsyncResult}.
19
+ */
20
+ public static value<T>(value: T): AsyncResult<T>
21
+ {
22
+ return PromiseAsyncResult.value(value);
23
+ }
24
+
25
+ /**
26
+ * Create a new {@link AsyncResult} that contains the provided error.
27
+ * @param error The error to wrap in a {@link AsyncResult}.
28
+ */
29
+ public static error<T>(error: Error): AsyncResult<T>
30
+ {
31
+ return PromiseAsyncResult.error<T>(error);
32
+ }
33
+
34
+ public static yield(): AsyncResult<void>
35
+ {
36
+ return PromiseAsyncResult.yield();
37
+ }
38
+
39
+ /**
40
+ * Get a {@link AsyncResult} that runs the provided function if this {@link AsyncResult} is successful.
41
+ * @param thenFunction The function to run if this {@link AsyncResult} is successful.
42
+ */
43
+ public abstract then<TResult1 = T, TResult2 = never>(onfulfilled?: ((value: T) => TResult1 | PromiseLike<TResult1>) | null | undefined, onrejected?: ((reason: any) => TResult2 | PromiseLike<TResult2>) | null | undefined): AsyncResult<TResult1 | TResult2>
44
+
45
+ /**
46
+ * Run the provided onValueFunction if this {@link AsyncResult} is successful. The value or error
47
+ * contained by this {@link AsyncResult} will be contained by the returned {@link AsyncResult}.
48
+ * @param onValueFunction The function to run if this {@link AsyncResult} is successful.
49
+ */
50
+ public abstract onValue(onValueFunction: (value: T) => (void | Promise<void>)): AsyncResult<T>
51
+
52
+ /**
53
+ * Run the provided catchFunction if this {@link AsyncResult} contains an error.
54
+ * @param catchFunction The function to run if an error is caught.
55
+ */
56
+ public abstract catch<TResult = never>(onrejected?: ((reason: unknown) => TResult | PromiseLike<TResult>) | null): AsyncResult<T | TResult>
57
+ /**
58
+ * Run the provided catchFunction if this {@link AsyncResult} contains an error of the provided type.
59
+ * @param errorType The type of error to catch.
60
+ * @param catchFunction The function to run if the error is caught.
61
+ */
62
+ public abstract catch<TError,TResult = never>(errorType: Type<TError>, onrejected: (reason: TError) => (TResult | PromiseLike<TResult>)): AsyncResult<T | TResult>
63
+
64
+ /**
65
+ * Run the provided onErrorFunction if this {@link AsyncResult} contains an error.
66
+ * @param onErrorFunction The function to run if an error is found.
67
+ */
68
+ public abstract onError(onErrorFunction: (reason: unknown) => (void | PromiseLike<void>)): AsyncResult<T>;
69
+ /**
70
+ * Run the provided onErrorFunction if this {@link AsyncResult} contains an error of the provided
71
+ * type.
72
+ * @param errorType The type of error to respond to.
73
+ * @param onErrorFunction The function to run if the error is found.
74
+ */
75
+ public abstract onError<TError>(errorType: Type<TError>, onErrorFunction: (reason: TError) => (void | PromiseLike<void>)): AsyncResult<T>;
76
+
77
+ /**
78
+ * Run the provided convertErrorFunction if this {@link AsyncResult} contains an error. The value
79
+ * returned from the convertErrorFunction will be the error for the returned {@link AsyncResult}.
80
+ * @param convertErrorFunction The function that will return the new error.
81
+ */
82
+ public abstract convertError(convertErrorFunction: (reason: unknown) => (unknown | PromiseLike<unknown>)): AsyncResult<T>;
83
+ /**
84
+ * Run the provided convertErrorFunction if this {@link AsyncResult} contains an error of the
85
+ * provided type. The value returned from the convertErrorFunction will be the error for the
86
+ * returned {@link AsyncResult}.
87
+ * @param errorType The type of error to respond to.
88
+ * @param convertErrorFunction The function that will return the new error.
89
+ */
90
+ public abstract convertError<TError>(errorType: Type<TError>, convertErrorFunction: (reason: TError) => (unknown | PromiseLike<unknown>)): AsyncResult<T>;
91
+
92
+ public abstract finally(onfinally?: (() => (void | Promise<void>)) | null): AsyncResult<T>;
93
+
94
+ readonly abstract [Symbol.toStringTag]: string;
95
+ }
@@ -0,0 +1,57 @@
1
+ import { Disposable } from "./disposable";
2
+ import { PreCondition } from "./preCondition";
3
+ import { SyncResult } from "./syncResult";
4
+
5
+ /**
6
+ * A {@link Disposable} type that can be configured with a function that will be invoked when the
7
+ * object is disposed.
8
+ */
9
+ export class SyncDisposable implements Disposable
10
+ {
11
+ private readonly disposedFunction: () => void;
12
+ private disposed: boolean;
13
+
14
+ protected constructor(disposedFunction: () => void)
15
+ {
16
+ PreCondition.assertNotUndefinedAndNotNull(disposedFunction, "disposedFunction");
17
+
18
+ this.disposedFunction = disposedFunction;
19
+ this.disposed = false;
20
+ }
21
+
22
+ /**
23
+ * Create a new {@link Disposable} that will invoke the provided {@link Function} when it is
24
+ * disposed.
25
+ * @param disposedFunction The function to invoke when the returned {@link Disposable} is
26
+ * disposed.
27
+ */
28
+ public static create(disposedFunction: () => void): SyncDisposable
29
+ {
30
+ return new SyncDisposable(disposedFunction);
31
+ }
32
+
33
+ public dispose(): SyncResult<boolean>
34
+ {
35
+ return SyncResult.create(() =>
36
+ {
37
+ const result: boolean = !this.disposed;
38
+ if (result)
39
+ {
40
+ try
41
+ {
42
+ this.disposedFunction();
43
+ }
44
+ finally
45
+ {
46
+ this.disposed = true;
47
+ }
48
+ }
49
+ return result;
50
+ });
51
+ }
52
+
53
+ public isDisposed(): boolean
54
+ {
55
+ return this.disposed;
56
+ }
57
+ }
@@ -0,0 +1,202 @@
1
+ import { EqualFunctions } from "./equalFunctions";
2
+ import { Iterable } from "./iterable";
3
+ import { Iterator } from "./iterator";
4
+ import { JavascriptIterable, JavascriptIterator } from "./javascript";
5
+ import { List } from "./list";
6
+ import { PreCondition } from "./preCondition";
7
+ import { SyncResult } from "./syncResult";
8
+ import { ToStringFunctions } from "./toStringFunctions";
9
+ import { Type } from "./types";
10
+
11
+ /**
12
+ * A {@link List} of bytes.
13
+ */
14
+ export class ByteList implements List<number>
15
+ {
16
+ private bytes: Uint8Array;
17
+ private count: number;
18
+
19
+ private constructor()
20
+ {
21
+ this.bytes = new Uint8Array(0);
22
+ this.count = 0;
23
+ }
24
+
25
+ public static create(initialValues?: JavascriptIterable<number>): ByteList
26
+ {
27
+ const result: ByteList = new ByteList();
28
+ if (initialValues)
29
+ {
30
+ result.addAll(initialValues);
31
+ }
32
+ return result;
33
+ }
34
+
35
+ public add(value: number): this
36
+ {
37
+ return List.add(this, value);
38
+ }
39
+
40
+ public addAll(values: JavascriptIterable<number>): this
41
+ {
42
+ return List.addAll(this, values);
43
+ }
44
+
45
+ public insert(index: number, value: number): this
46
+ {
47
+ PreCondition.assertInsertIndex(index, this.getCount().await(), "index");
48
+ PreCondition.assertByte(value, "value");
49
+
50
+ if (this.count < this.bytes.length)
51
+ {
52
+ if (index < this.count)
53
+ {
54
+ this.bytes.copyWithin(index + 1, index, this.count);
55
+ }
56
+ this.bytes[index] = value;
57
+ }
58
+ else
59
+ {
60
+ const newCapacity: number = (this.bytes.length * 2) + 1;
61
+ const newBytes: Uint8Array = new Uint8Array(newCapacity);
62
+ if (index > 0)
63
+ {
64
+ newBytes.set(this.bytes.subarray(0, index));
65
+ }
66
+ newBytes[index] = value;
67
+ if (index < this.count)
68
+ {
69
+ newBytes.set(this.bytes.subarray(index), index + 1);
70
+ }
71
+ this.bytes = newBytes;
72
+ }
73
+ this.count++;
74
+
75
+ return this;
76
+ }
77
+
78
+ public insertAll(index: number, values: JavascriptIterable<number>): this
79
+ {
80
+ return List.insertAll(this, index, values);
81
+ }
82
+
83
+ public remove(value: number, equalFunctions?: EqualFunctions): SyncResult<number>
84
+ {
85
+ PreCondition.assertByte(value, "value");
86
+
87
+ return List.remove(this, value, equalFunctions);
88
+ }
89
+
90
+ public removeAt(index: number): SyncResult<number>
91
+ {
92
+ PreCondition.assertAccessIndex(index, this.count, "index");
93
+
94
+ const result: number = this.bytes[index];
95
+ this.bytes.copyWithin(index, index + 1, this.count);
96
+ this.count--;
97
+
98
+ return SyncResult.value(result);
99
+ }
100
+
101
+ public removeFirst(): SyncResult<number>
102
+ {
103
+ return List.removeFirst(this);
104
+ }
105
+
106
+ public removeLast(): SyncResult<number>
107
+ {
108
+ return List.removeLast(this);
109
+ }
110
+
111
+ public set(index: number, value: number): this
112
+ {
113
+ PreCondition.assertAccessIndex(index, this.getCount().await(), "index");
114
+ PreCondition.assertByte(value, "value");
115
+
116
+ this.bytes[index] = value;
117
+
118
+ return this;
119
+ }
120
+
121
+ public iterate(): Iterator<number>
122
+ {
123
+ return Iterator.create(this.bytes[Symbol.iterator]().take(this.count));
124
+ }
125
+
126
+ public get(index: number): SyncResult<number>
127
+ {
128
+ PreCondition.assertAccessIndex(index, this.getCount().await(), "index");
129
+
130
+ return SyncResult.value(this.bytes.at(index)!);
131
+ }
132
+
133
+ public toArray(): SyncResult<number[]>
134
+ {
135
+ return List.toArray(this);
136
+ }
137
+
138
+ public any(): SyncResult<boolean>
139
+ {
140
+ return this.getCount().then(count => count > 0);
141
+ }
142
+
143
+ public getCount(): SyncResult<number>
144
+ {
145
+ return SyncResult.value(this.count);
146
+ }
147
+
148
+ public equals(right: JavascriptIterable<number>, equalFunctions?: EqualFunctions): SyncResult<boolean>
149
+ {
150
+ return List.equals(this, right, equalFunctions);
151
+ }
152
+
153
+ public toString(toStringFunctions?: ToStringFunctions): string
154
+ {
155
+ return List.toString(this, toStringFunctions);
156
+ }
157
+
158
+ public concatenate(...toConcatenate: JavascriptIterable<number>[]): Iterable<number>
159
+ {
160
+ return List.concatenate(this, ...toConcatenate);
161
+ }
162
+
163
+ public map<TOutput>(mapping: (value: number) => TOutput | SyncResult<TOutput>): Iterable<TOutput>
164
+ {
165
+ return List.map(this, mapping);
166
+ }
167
+
168
+ public flatMap<TOutput>(mapping: (value: number) => JavascriptIterable<TOutput>): Iterable<TOutput>
169
+ {
170
+ return List.flatMap(this, mapping);
171
+ }
172
+
173
+ public where(condition: (value: number) => (boolean | SyncResult<boolean>)): Iterable<number>
174
+ {
175
+ return List.where(this, condition);
176
+ }
177
+
178
+ public instanceOf<TOutput extends number>(typeOrTypeCheck: Type<TOutput> | ((value: number) => value is TOutput)): Iterable<TOutput>
179
+ {
180
+ return List.instanceOf(this, typeOrTypeCheck);
181
+ }
182
+
183
+ public first(condition?: ((value: number) => (boolean | SyncResult<boolean>)) | undefined): SyncResult<number>
184
+ {
185
+ return List.first(this, condition);
186
+ }
187
+
188
+ public last(condition?: ((value: number) => (boolean | SyncResult<boolean>)) | undefined): SyncResult<number>
189
+ {
190
+ return List.last(this, condition);
191
+ }
192
+
193
+ public contains(value: number, equalFunctions?: EqualFunctions): SyncResult<boolean>
194
+ {
195
+ return List.contains(this, value, equalFunctions);
196
+ }
197
+
198
+ public [Symbol.iterator](): JavascriptIterator<number>
199
+ {
200
+ return List[Symbol.iterator](this);
201
+ }
202
+ }
@@ -0,0 +1,121 @@
1
+ import { ByteList } from "./byteList";
2
+ import { ByteReadStream } from "./byteReadStream";
3
+ import { ByteWriteStream } from "./byteWriteStream";
4
+ import { EmptyError } from "./emptyError";
5
+ import { PreCondition } from "./preCondition";
6
+ import { SyncResult } from "./syncResult";
7
+ import { isArray, isNumber, isUndefinedOrNull } from "./types";
8
+
9
+ /**
10
+ * A {@link ByteReadStream} and {@link ByteWriteStream} implementation that is implemented using a
11
+ * {@link ByteList}.
12
+ */
13
+ export class ByteListStream implements ByteReadStream, ByteWriteStream
14
+ {
15
+ private readonly list: ByteList;
16
+
17
+ private constructor()
18
+ {
19
+ this.list = ByteList.create();
20
+ }
21
+
22
+ public static create(initialValues?: Uint8Array | number[]): ByteListStream
23
+ {
24
+ const result: ByteListStream = new ByteListStream();
25
+ if (initialValues)
26
+ {
27
+ result.writeBytes(initialValues).await();
28
+ }
29
+ return result;
30
+ }
31
+
32
+ /**
33
+ * Get the number of bytes that are available to be read.
34
+ */
35
+ public getAvailableByteCount(): number
36
+ {
37
+ return this.list.getCount().await();
38
+ }
39
+
40
+ public writeBytes(bytes: Uint8Array | number[], startIndex?: number, length?: number): SyncResult<number>
41
+ {
42
+ PreCondition.assertNotUndefinedAndNotNull(bytes, "bytes");
43
+
44
+ if (isArray(bytes))
45
+ {
46
+ bytes = new Uint8Array(bytes);
47
+ }
48
+ if (isUndefinedOrNull(startIndex))
49
+ {
50
+ startIndex = 0;
51
+ }
52
+ if (isUndefinedOrNull(length))
53
+ {
54
+ length = bytes.length - startIndex;
55
+ }
56
+
57
+ PreCondition.assertInsertIndex(startIndex, bytes.length, "startIndex");
58
+ PreCondition.assertBetween(0, length, bytes.length - startIndex, "length");
59
+
60
+ this.list.addAll(bytes.subarray(startIndex, length + startIndex));
61
+
62
+ return SyncResult.value(length);
63
+ }
64
+
65
+ public readBytes(count: number): SyncResult<Uint8Array>;
66
+ public readBytes(output: Uint8Array, startIndex?: number, count?: number): SyncResult<number>;
67
+ readBytes(countOrOutput: number | Uint8Array, startIndex?: number, count?: number): SyncResult<number> | SyncResult<Uint8Array>
68
+ {
69
+ let result: SyncResult<number> | SyncResult<Uint8Array>;
70
+ if (isNumber(countOrOutput))
71
+ {
72
+ PreCondition.assertGreaterThanOrEqualTo(countOrOutput, 0, "count");
73
+
74
+ if (!this.list.any().await())
75
+ {
76
+ result = SyncResult.error<Uint8Array>(new EmptyError());
77
+ }
78
+ else
79
+ {
80
+ const bytesReadCount: number = Math.min(countOrOutput, this.list.getCount().await());
81
+ const output: Uint8Array = new Uint8Array(bytesReadCount);
82
+ for (let i = 0; i < bytesReadCount; i++)
83
+ {
84
+ output[i] = this.list.removeFirst().await();
85
+ }
86
+ result = SyncResult.value(output);
87
+ }
88
+ }
89
+ else
90
+ {
91
+ PreCondition.assertNotUndefinedAndNotNull(countOrOutput, "output");
92
+
93
+ if (isUndefinedOrNull(startIndex))
94
+ {
95
+ startIndex = 0;
96
+ }
97
+ if (isUndefinedOrNull(count))
98
+ {
99
+ count = countOrOutput.length - startIndex;
100
+ }
101
+
102
+ PreCondition.assertInsertIndex(startIndex, countOrOutput.length, "startIndex");
103
+ PreCondition.assertBetween(0, count, countOrOutput.length - startIndex, "count");
104
+
105
+ if (!this.list.any().await())
106
+ {
107
+ result = SyncResult.error<number>(new EmptyError());
108
+ }
109
+ else
110
+ {
111
+ const bytesReadCount: number = Math.min(count, this.list.getCount().await());
112
+ for (let i = 0; i < bytesReadCount; i++)
113
+ {
114
+ countOrOutput[startIndex + i] = this.list.removeFirst().await();
115
+ }
116
+ result = SyncResult.value(bytesReadCount);
117
+ }
118
+ }
119
+ return result;
120
+ }
121
+ }
@@ -0,0 +1,24 @@
1
+ import { AsyncResult } from "./asyncResult";
2
+
3
+ /**
4
+ * A stream that reads bytes.
5
+ */
6
+ export abstract class ByteReadStream
7
+ {
8
+ /**
9
+ * Attempt to read the provided {@link count} number of bytes. Returns the bytes that were read.
10
+ * The number of bytes returned may be less than the number requested.
11
+ * @param count The number of bytes to attempt to read.
12
+ */
13
+ public abstract readBytes(count: number): AsyncResult<Uint8Array>;
14
+ /**
15
+ * Attempt to read bytes into the provided output array. Returns the number of bytes that were
16
+ * read.
17
+ * @param output The array that the read bytes will be written to.
18
+ * @param startIndex The index in the {@link output} array to start writting the read bytes to.
19
+ * Defaults to 0.
20
+ * @param count The maximum number of bytes to read. Defaults to the length of the output array
21
+ * minus the startIndex.
22
+ */
23
+ public abstract readBytes(output: Uint8Array, startIndex?: number, count?: number): AsyncResult<number>;
24
+ }
@@ -0,0 +1,16 @@
1
+ import { AsyncResult } from "./asyncResult";
2
+
3
+ /**
4
+ * A stream that writes bytes.
5
+ */
6
+ export abstract class ByteWriteStream
7
+ {
8
+ /**
9
+ * Write the provided bytes to this {@link ByteWriteStream}.
10
+ * @param bytes The bytes to write.
11
+ * @param startIndex The index to start writing from.
12
+ * @param length The number of bytes to write.
13
+ * @returns The number of bytes that were written.
14
+ */
15
+ public abstract writeBytes(bytes: Uint8Array | number[], startIndex?: number, length?: number): AsyncResult<number>
16
+ }
@@ -0,0 +1,25 @@
1
+ /**
2
+ * A collection of values and functions for interacting with bytes.
3
+ */
4
+ export abstract class Bytes
5
+ {
6
+ /**
7
+ * The minimum value that a byte can have.
8
+ */
9
+ public static readonly minimumValue: number = 0;
10
+
11
+ /**
12
+ * The maximum value (inclusive) that a byte can have.
13
+ */
14
+ public static readonly maximumValue: number = 255;
15
+
16
+ /**
17
+ * Get whether the provided value is within the range of a valid byte (between 0 and
18
+ * 255).
19
+ * @param value The value to check.
20
+ */
21
+ public static isByte(value: number): boolean
22
+ {
23
+ return Bytes.minimumValue <= value && value <= Bytes.maximumValue;
24
+ }
25
+ }