string
| | |
+| [options] | object
| | Optional settings |
+| [options.relaxed] | boolean
| true
| Attempt to return native JS types where possible, rather than BSON types (if true) |
+
+Parse an Extended JSON string, constructing the JavaScript value or object described by that
+string.
+
+**Example**
+
+```js
+const { EJSON } = require('bson');
+const text = '{ "int32": { "$numberInt": "10" } }';
+
+// prints { int32: { [String: '10'] _bsontype: 'Int32', value: '10' } }
+console.log(EJSON.parse(text, { relaxed: false }));
+
+// prints { int32: 10 }
+console.log(EJSON.parse(text));
+```
+
+
+
+#### _EJSON_.stringify(value, [replacer], [space], [options])
+
+| Param | Type | Default | Description |
+| ----------------- | ------------------------------------------- | ----------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
+| value | object
| | The value to convert to extended JSON |
+| [replacer] | function
\| array
| | A function that alters the behavior of the stringification process, or an array of String and Number objects that serve as a whitelist for selecting/filtering the properties of the value object to be included in the JSON string. If this value is null or not provided, all properties of the object are included in the resulting JSON string |
+| [space] | string
\| number
| | A String or Number object that's used to insert white space into the output JSON string for readability purposes. |
+| [options] | object
| | Optional settings |
+| [options.relaxed] | boolean
| true
| Enabled Extended JSON's `relaxed` mode |
+| [options.legacy] | boolean
| true
| Output in Extended JSON v1 |
+
+Converts a BSON document to an Extended JSON string, optionally replacing values if a replacer
+function is specified or optionally including only the specified properties if a replacer array
+is specified.
+
+**Example**
+
+```js
+const { EJSON } = require('bson');
+const Int32 = require('mongodb').Int32;
+const doc = { int32: new Int32(10) };
+
+// prints '{"int32":{"$numberInt":"10"}}'
+console.log(EJSON.stringify(doc, { relaxed: false }));
+
+// prints '{"int32":10}'
+console.log(EJSON.stringify(doc));
+```
+
+
+
+#### _EJSON_.serialize(bson, [options])
+
+| Param | Type | Description |
+| --------- | ------------------- | ---------------------------------------------------- |
+| bson | object
| The object to serialize |
+| [options] | object
| Optional settings passed to the `stringify` function |
+
+Serializes an object to an Extended JSON string, and reparse it as a JavaScript object.
+
+
+
+#### _EJSON_.deserialize(ejson, [options])
+
+| Param | Type | Description |
+| --------- | ------------------- | -------------------------------------------- |
+| ejson | object
| The Extended JSON object to deserialize |
+| [options] | object
| Optional settings passed to the parse method |
+
+Deserializes an Extended JSON object into a plain JavaScript object with native/BSON types
+
+## Error Handling
+
+It is our recommendation to use `BSONError.isBSONError()` checks on errors and to avoid relying on parsing `error.message` and `error.name` strings in your code. We guarantee `BSONError.isBSONError()` checks will pass according to semver guidelines, but errors may be sub-classed or their messages may change at any time, even patch releases, as we see fit to increase the helpfulness of the errors.
+
+Any new errors we add to the driver will directly extend an existing error class and no existing error will be moved to a different parent class outside of a major release.
+This means `BSONError.isBSONError()` will always be able to accurately capture the errors that our BSON library throws.
+
+Hypothetical example: A collection in our Db has an issue with UTF-8 data:
+
+```ts
+let documentCount = 0;
+const cursor = collection.find({}, { utf8Validation: true });
+try {
+ for await (const doc of cursor) documentCount += 1;
+} catch (error) {
+ if (BSONError.isBSONError(error)) {
+ console.log(`Found the troublemaker UTF-8!: ${documentCount} ${error.message}`);
+ return documentCount;
+ }
+ throw error;
+}
+```
+
+## React Native
+
+BSON vendors the required polyfills for `TextEncoder`, `TextDecoder`, `atob`, `btoa` imported from React Native and therefore doesn't expect users to polyfill these. One additional polyfill, `crypto.getRandomValues` is recommended and can be installed with the following command:
+
+```sh
+npm install --save react-native-get-random-values
+```
+
+The following snippet should be placed at the top of the entrypoint (by default this is the root `index.js` file) for React Native projects using the BSON library. These lines must be placed for any code that imports `BSON`.
+
+```typescript
+// Required Polyfills For ReactNative
+import 'react-native-get-random-values';
+```
+
+Finally, import the `BSON` library like so:
+
+```typescript
+import { BSON, EJSON } from 'bson';
+```
+
+This will cause React Native to import the `node_modules/bson/lib/bson.rn.cjs` bundle (see the `"react-native"` setting we have in the `"exports"` section of our [package.json](./package.json).)
+
+### Technical Note about React Native module import
+
+The `"exports"` definition in our `package.json` will result in BSON's CommonJS bundle being imported in a React Native project instead of the ES module bundle. Importing the CommonJS bundle is necessary because BSON's ES module bundle of BSON uses top-level await, which is not supported syntax in [React Native's runtime hermes](https://hermesengine.dev/).
+
+## FAQ
+
+#### Why does `undefined` get converted to `null`?
+
+The `undefined` BSON type has been [deprecated for many years](http://bsonspec.org/spec.html), so this library has dropped support for it. Use the `ignoreUndefined` option (for example, from the [driver](http://mongodb.github.io/node-mongodb-native/2.2/api/MongoClient.html#connect) ) to instead remove `undefined` keys.
+
+#### How do I add custom serialization logic?
+
+This library looks for `toBSON()` functions on every path, and calls the `toBSON()` function to get the value to serialize.
+
+```javascript
+const BSON = require('bson');
+
+class CustomSerialize {
+ toBSON() {
+ return 42;
+ }
+}
+
+const obj = { answer: new CustomSerialize() };
+// "{ answer: 42 }"
+console.log(BSON.deserialize(BSON.serialize(obj)));
+```
diff --git a/backend/node_modules/bson/bson.d.ts b/backend/node_modules/bson/bson.d.ts
new file mode 100644
index 0000000..5a02fd1
--- /dev/null
+++ b/backend/node_modules/bson/bson.d.ts
@@ -0,0 +1,1465 @@
+/**
+ * A class representation of the BSON Binary type.
+ * @public
+ * @category BSONType
+ */
+export declare class Binary extends BSONValue {
+ get _bsontype(): 'Binary';
+ /* Excluded from this release type: BSON_BINARY_SUBTYPE_DEFAULT */
+ /** Initial buffer default size */
+ static readonly BUFFER_SIZE = 256;
+ /** Default BSON type */
+ static readonly SUBTYPE_DEFAULT = 0;
+ /** Function BSON type */
+ static readonly SUBTYPE_FUNCTION = 1;
+ /** Byte Array BSON type */
+ static readonly SUBTYPE_BYTE_ARRAY = 2;
+ /** Deprecated UUID BSON type @deprecated Please use SUBTYPE_UUID */
+ static readonly SUBTYPE_UUID_OLD = 3;
+ /** UUID BSON type */
+ static readonly SUBTYPE_UUID = 4;
+ /** MD5 BSON type */
+ static readonly SUBTYPE_MD5 = 5;
+ /** Encrypted BSON type */
+ static readonly SUBTYPE_ENCRYPTED = 6;
+ /** Column BSON type */
+ static readonly SUBTYPE_COLUMN = 7;
+ /** Sensitive BSON type */
+ static readonly SUBTYPE_SENSITIVE = 8;
+ /** User BSON type */
+ static readonly SUBTYPE_USER_DEFINED = 128;
+ buffer: Uint8Array;
+ sub_type: number;
+ position: number;
+ /**
+ * Create a new Binary instance.
+ * @param buffer - a buffer object containing the binary data.
+ * @param subType - the option binary type.
+ */
+ constructor(buffer?: BinarySequence, subType?: number);
+ /**
+ * Updates this binary with byte_value.
+ *
+ * @param byteValue - a single byte we wish to write.
+ */
+ put(byteValue: string | number | Uint8Array | number[]): void;
+ /**
+ * Writes a buffer to the binary.
+ *
+ * @param sequence - a string or buffer to be written to the Binary BSON object.
+ * @param offset - specify the binary of where to write the content.
+ */
+ write(sequence: BinarySequence, offset: number): void;
+ /**
+ * Reads **length** bytes starting at **position**.
+ *
+ * @param position - read from the given position in the Binary.
+ * @param length - the number of bytes to read.
+ */
+ read(position: number, length: number): BinarySequence;
+ /** returns a view of the binary value as a Uint8Array */
+ value(): Uint8Array;
+ /** the length of the binary sequence */
+ length(): number;
+ toJSON(): string;
+ toString(encoding?: 'hex' | 'base64' | 'utf8' | 'utf-8'): string;
+ /* Excluded from this release type: toExtendedJSON */
+ toUUID(): UUID;
+ /** Creates an Binary instance from a hex digit string */
+ static createFromHexString(hex: string, subType?: number): Binary;
+ /** Creates an Binary instance from a base64 string */
+ static createFromBase64(base64: string, subType?: number): Binary;
+ /* Excluded from this release type: fromExtendedJSON */
+ inspect(depth?: number, options?: unknown, inspect?: InspectFn): string;
+}
+
+/** @public */
+export declare interface BinaryExtended {
+ $binary: {
+ subType: string;
+ base64: string;
+ };
+}
+
+/** @public */
+export declare interface BinaryExtendedLegacy {
+ $type: string;
+ $binary: string;
+}
+
+/** @public */
+export declare type BinarySequence = Uint8Array | number[];
+
+declare namespace BSON {
+ export {
+ setInternalBufferSize,
+ serialize,
+ serializeWithBufferAndIndex,
+ deserialize,
+ calculateObjectSize,
+ deserializeStream,
+ UUIDExtended,
+ BinaryExtended,
+ BinaryExtendedLegacy,
+ BinarySequence,
+ CodeExtended,
+ DBRefLike,
+ Decimal128Extended,
+ DoubleExtended,
+ EJSONOptions,
+ Int32Extended,
+ LongExtended,
+ MaxKeyExtended,
+ MinKeyExtended,
+ ObjectIdExtended,
+ ObjectIdLike,
+ BSONRegExpExtended,
+ BSONRegExpExtendedLegacy,
+ BSONSymbolExtended,
+ LongWithoutOverrides,
+ TimestampExtended,
+ TimestampOverrides,
+ LongWithoutOverridesClass,
+ SerializeOptions,
+ DeserializeOptions,
+ Code,
+ BSONSymbol,
+ DBRef,
+ Binary,
+ ObjectId,
+ UUID,
+ Long,
+ Timestamp,
+ Double,
+ Int32,
+ MinKey,
+ MaxKey,
+ BSONRegExp,
+ Decimal128,
+ BSONValue,
+ BSONError,
+ BSONVersionError,
+ BSONRuntimeError,
+ BSONOffsetError,
+ BSONType,
+ EJSON,
+ onDemand,
+ OnDemand,
+ Document,
+ CalculateObjectSizeOptions
+ }
+}
+export { BSON }
+
+/**
+ * @public
+ * @experimental
+ */
+declare type BSONElement = [
+type: number,
+nameOffset: number,
+nameLength: number,
+offset: number,
+length: number
+];
+
+/**
+ * @public
+ * @category Error
+ *
+ * `BSONError` objects are thrown when BSON encounters an error.
+ *
+ * This is the parent class for all the other errors thrown by this library.
+ */
+export declare class BSONError extends Error {
+ /* Excluded from this release type: bsonError */
+ get name(): string;
+ constructor(message: string, options?: {
+ cause?: unknown;
+ });
+ /**
+ * @public
+ *
+ * All errors thrown from the BSON library inherit from `BSONError`.
+ * This method can assist with determining if an error originates from the BSON library
+ * even if it does not pass an `instanceof` check against this class' constructor.
+ *
+ * @param value - any javascript value that needs type checking
+ */
+ static isBSONError(value: unknown): value is BSONError;
+}
+
+/**
+ * @public
+ * @category Error
+ *
+ * @experimental
+ *
+ * An error generated when BSON bytes are invalid.
+ * Reports the offset the parser was able to reach before encountering the error.
+ */
+export declare class BSONOffsetError extends BSONError {
+ get name(): 'BSONOffsetError';
+ offset: number;
+ constructor(message: string, offset: number, options?: {
+ cause?: unknown;
+ });
+}
+
+/**
+ * A class representation of the BSON RegExp type.
+ * @public
+ * @category BSONType
+ */
+export declare class BSONRegExp extends BSONValue {
+ get _bsontype(): 'BSONRegExp';
+ pattern: string;
+ options: string;
+ /**
+ * @param pattern - The regular expression pattern to match
+ * @param options - The regular expression options
+ */
+ constructor(pattern: string, options?: string);
+ static parseOptions(options?: string): string;
+ /* Excluded from this release type: toExtendedJSON */
+ /* Excluded from this release type: fromExtendedJSON */
+ inspect(depth?: number, options?: unknown, inspect?: InspectFn): string;
+}
+
+/** @public */
+export declare interface BSONRegExpExtended {
+ $regularExpression: {
+ pattern: string;
+ options: string;
+ };
+}
+
+/** @public */
+export declare interface BSONRegExpExtendedLegacy {
+ $regex: string | BSONRegExp;
+ $options: string;
+}
+
+/**
+ * @public
+ * @category Error
+ *
+ * An error generated when BSON functions encounter an unexpected input
+ * or reaches an unexpected/invalid internal state
+ *
+ */
+export declare class BSONRuntimeError extends BSONError {
+ get name(): 'BSONRuntimeError';
+ constructor(message: string);
+}
+
+/**
+ * A class representation of the BSON Symbol type.
+ * @public
+ * @category BSONType
+ */
+export declare class BSONSymbol extends BSONValue {
+ get _bsontype(): 'BSONSymbol';
+ value: string;
+ /**
+ * @param value - the string representing the symbol.
+ */
+ constructor(value: string);
+ /** Access the wrapped string value. */
+ valueOf(): string;
+ toString(): string;
+ toJSON(): string;
+ /* Excluded from this release type: toExtendedJSON */
+ /* Excluded from this release type: fromExtendedJSON */
+ inspect(depth?: number, options?: unknown, inspect?: InspectFn): string;
+}
+
+/** @public */
+export declare interface BSONSymbolExtended {
+ $symbol: string;
+}
+
+/** @public */
+export declare const BSONType: Readonly<{
+ readonly double: 1;
+ readonly string: 2;
+ readonly object: 3;
+ readonly array: 4;
+ readonly binData: 5;
+ readonly undefined: 6;
+ readonly objectId: 7;
+ readonly bool: 8;
+ readonly date: 9;
+ readonly null: 10;
+ readonly regex: 11;
+ readonly dbPointer: 12;
+ readonly javascript: 13;
+ readonly symbol: 14;
+ readonly javascriptWithScope: 15;
+ readonly int: 16;
+ readonly timestamp: 17;
+ readonly long: 18;
+ readonly decimal: 19;
+ readonly minKey: -1;
+ readonly maxKey: 127;
+}>;
+
+/** @public */
+export declare type BSONType = (typeof BSONType)[keyof typeof BSONType];
+
+/** @public */
+export declare abstract class BSONValue {
+ /** @public */
+ abstract get _bsontype(): string;
+ /**
+ * @public
+ * Prints a human-readable string of BSON value information
+ * If invoked manually without node.js.inspect function, this will default to a modified JSON.stringify
+ */
+ abstract inspect(depth?: number, options?: unknown, inspect?: InspectFn): string;
+ /* Excluded from this release type: toExtendedJSON */
+}
+
+/**
+ * @public
+ * @category Error
+ */
+export declare class BSONVersionError extends BSONError {
+ get name(): 'BSONVersionError';
+ constructor();
+}
+
+/**
+ * @public
+ * @experimental
+ *
+ * A collection of functions that help work with data in a Uint8Array.
+ * ByteUtils is configured at load time to use Node.js or Web based APIs for the internal implementations.
+ */
+declare type ByteUtils = {
+ /** Transforms the input to an instance of Buffer if running on node, otherwise Uint8Array */
+ toLocalBufferType: (buffer: Uint8Array | ArrayBufferView | ArrayBuffer) => Uint8Array;
+ /** Create empty space of size */
+ allocate: (size: number) => Uint8Array;
+ /** Create empty space of size, use pooled memory when available */
+ allocateUnsafe: (size: number) => Uint8Array;
+ /** Check if two Uint8Arrays are deep equal */
+ equals: (a: Uint8Array, b: Uint8Array) => boolean;
+ /** Check if two Uint8Arrays are deep equal */
+ fromNumberArray: (array: number[]) => Uint8Array;
+ /** Create a Uint8Array from a base64 string */
+ fromBase64: (base64: string) => Uint8Array;
+ /** Create a base64 string from bytes */
+ toBase64: (buffer: Uint8Array) => string;
+ /** **Legacy** binary strings are an outdated method of data transfer. Do not add public API support for interpreting this format */
+ fromISO88591: (codePoints: string) => Uint8Array;
+ /** **Legacy** binary strings are an outdated method of data transfer. Do not add public API support for interpreting this format */
+ toISO88591: (buffer: Uint8Array) => string;
+ /** Create a Uint8Array from a hex string */
+ fromHex: (hex: string) => Uint8Array;
+ /** Create a lowercase hex string from bytes */
+ toHex: (buffer: Uint8Array) => string;
+ /** Create a string from utf8 code units, fatal=true will throw an error if UTF-8 bytes are invalid, fatal=false will insert replacement characters */
+ toUTF8: (buffer: Uint8Array, start: number, end: number, fatal: boolean) => string;
+ /** Get the utf8 code unit count from a string if it were to be transformed to utf8 */
+ utf8ByteLength: (input: string) => number;
+ /** Encode UTF8 bytes generated from `source` string into `destination` at byteOffset. Returns the number of bytes encoded. */
+ encodeUTF8Into: (destination: Uint8Array, source: string, byteOffset: number) => number;
+ /** Generate a Uint8Array filled with random bytes with byteLength */
+ randomBytes: (byteLength: number) => Uint8Array;
+};
+
+/* Excluded declaration from this release type: ByteUtils */
+
+/**
+ * Calculate the bson size for a passed in Javascript object.
+ *
+ * @param object - the Javascript object to calculate the BSON byte size for
+ * @returns size of BSON object in bytes
+ * @public
+ */
+export declare function calculateObjectSize(object: Document, options?: CalculateObjectSizeOptions): number;
+
+/** @public */
+export declare type CalculateObjectSizeOptions = PickWelcome back, ' + escapeHtml(name) + '!
'); + } else { + res.write('Hello, new visitor!
'); + } + + res.write(''); +} + +http.createServer(onRequest).listen(3000); +``` + +## Testing + +```sh +$ npm test +``` + +## Benchmark + +``` +$ npm run bench + +> cookie@0.5.0 bench +> node benchmark/index.js + + node@18.18.2 + acorn@8.10.0 + ada@2.6.0 + ares@1.19.1 + brotli@1.0.9 + cldr@43.1 + icu@73.2 + llhttp@6.0.11 + modules@108 + napi@9 + nghttp2@1.57.0 + nghttp3@0.7.0 + ngtcp2@0.8.1 + openssl@3.0.10+quic + simdutf@3.2.14 + tz@2023c + undici@5.26.3 + unicode@15.0 + uv@1.44.2 + uvwasi@0.0.18 + v8@10.2.154.26-node.26 + zlib@1.2.13.1-motley + +> node benchmark/parse-top.js + + cookie.parse - top sites + + 14 tests completed. + + parse accounts.google.com x 2,588,913 ops/sec ±0.74% (186 runs sampled) + parse apple.com x 2,370,002 ops/sec ±0.69% (186 runs sampled) + parse cloudflare.com x 2,213,102 ops/sec ±0.88% (188 runs sampled) + parse docs.google.com x 2,194,157 ops/sec ±1.03% (184 runs sampled) + parse drive.google.com x 2,265,084 ops/sec ±0.79% (187 runs sampled) + parse en.wikipedia.org x 457,099 ops/sec ±0.81% (186 runs sampled) + parse linkedin.com x 504,407 ops/sec ±0.89% (186 runs sampled) + parse maps.google.com x 1,230,959 ops/sec ±0.98% (186 runs sampled) + parse microsoft.com x 926,294 ops/sec ±0.88% (184 runs sampled) + parse play.google.com x 2,311,338 ops/sec ±0.83% (185 runs sampled) + parse support.google.com x 1,508,850 ops/sec ±0.86% (186 runs sampled) + parse www.google.com x 1,022,582 ops/sec ±1.32% (182 runs sampled) + parse youtu.be x 332,136 ops/sec ±1.02% (185 runs sampled) + parse youtube.com x 323,833 ops/sec ±0.77% (183 runs sampled) + +> node benchmark/parse.js + + cookie.parse - generic + + 6 tests completed. + + simple x 3,214,032 ops/sec ±1.61% (183 runs sampled) + decode x 587,237 ops/sec ±1.16% (187 runs sampled) + unquote x 2,954,618 ops/sec ±1.35% (183 runs sampled) + duplicates x 857,008 ops/sec ±0.89% (187 runs sampled) + 10 cookies x 292,133 ops/sec ±0.89% (187 runs sampled) + 100 cookies x 22,610 ops/sec ±0.68% (187 runs sampled) +``` + +## References + +- [RFC 6265: HTTP State Management Mechanism][rfc-6265] +- [Same-site Cookies][rfc-6265bis-09-5.4.7] + +[rfc-cutler-httpbis-partitioned-cookies]: https://tools.ietf.org/html/draft-cutler-httpbis-partitioned-cookies/ +[rfc-west-cookie-priority-00-4.1]: https://tools.ietf.org/html/draft-west-cookie-priority-00#section-4.1 +[rfc-6265bis-09-5.4.7]: https://tools.ietf.org/html/draft-ietf-httpbis-rfc6265bis-09#section-5.4.7 +[rfc-6265]: https://tools.ietf.org/html/rfc6265 +[rfc-6265-5.1.4]: https://tools.ietf.org/html/rfc6265#section-5.1.4 +[rfc-6265-5.2.1]: https://tools.ietf.org/html/rfc6265#section-5.2.1 +[rfc-6265-5.2.2]: https://tools.ietf.org/html/rfc6265#section-5.2.2 +[rfc-6265-5.2.3]: https://tools.ietf.org/html/rfc6265#section-5.2.3 +[rfc-6265-5.2.4]: https://tools.ietf.org/html/rfc6265#section-5.2.4 +[rfc-6265-5.2.5]: https://tools.ietf.org/html/rfc6265#section-5.2.5 +[rfc-6265-5.2.6]: https://tools.ietf.org/html/rfc6265#section-5.2.6 +[rfc-6265-5.3]: https://tools.ietf.org/html/rfc6265#section-5.3 + +## License + +[MIT](LICENSE) + +[ci-image]: https://badgen.net/github/checks/jshttp/cookie/master?label=ci +[ci-url]: https://github.com/jshttp/cookie/actions/workflows/ci.yml +[coveralls-image]: https://badgen.net/coveralls/c/github/jshttp/cookie/master +[coveralls-url]: https://coveralls.io/r/jshttp/cookie?branch=master +[node-image]: https://badgen.net/npm/node/cookie +[node-url]: https://nodejs.org/en/download +[npm-downloads-image]: https://badgen.net/npm/dm/cookie +[npm-url]: https://npmjs.org/package/cookie +[npm-version-image]: https://badgen.net/npm/v/cookie diff --git a/backend/node_modules/cookie/SECURITY.md b/backend/node_modules/cookie/SECURITY.md new file mode 100644 index 0000000..fd4a6c5 --- /dev/null +++ b/backend/node_modules/cookie/SECURITY.md @@ -0,0 +1,25 @@ +# Security Policies and Procedures + +## Reporting a Bug + +The `cookie` team and community take all security bugs seriously. Thank +you for improving the security of the project. We appreciate your efforts and +responsible disclosure and will make every effort to acknowledge your +contributions. + +Report security bugs by emailing the current owner(s) of `cookie`. This +information can be found in the npm registry using the command +`npm owner ls cookie`. +If unsure or unable to get the information from the above, open an issue +in the [project issue tracker](https://github.com/jshttp/cookie/issues) +asking for the current contact information. + +To ensure the timely response to your report, please ensure that the entirety +of the report is contained within the email body and not solely behind a web +link or an attachment. + +At least one owner will acknowledge your email within 48 hours, and will send a +more detailed response within 48 hours indicating the next steps in handling +your report. After the initial reply to your report, the owners will +endeavor to keep you informed of the progress towards a fix and full +announcement, and may ask for additional information or guidance. diff --git a/backend/node_modules/cookie/index.js b/backend/node_modules/cookie/index.js new file mode 100644 index 0000000..03d4c38 --- /dev/null +++ b/backend/node_modules/cookie/index.js @@ -0,0 +1,274 @@ +/*! + * cookie + * Copyright(c) 2012-2014 Roman Shtylman + * Copyright(c) 2015 Douglas Christopher Wilson + * MIT Licensed + */ + +'use strict'; + +/** + * Module exports. + * @public + */ + +exports.parse = parse; +exports.serialize = serialize; + +/** + * Module variables. + * @private + */ + +var __toString = Object.prototype.toString + +/** + * RegExp to match field-content in RFC 7230 sec 3.2 + * + * field-content = field-vchar [ 1*( SP / HTAB ) field-vchar ] + * field-vchar = VCHAR / obs-text + * obs-text = %x80-FF + */ + +var fieldContentRegExp = /^[\u0009\u0020-\u007e\u0080-\u00ff]+$/; + +/** + * Parse a cookie header. + * + * Parse the given cookie header string into an object + * The object has the various cookies as keys(names) => values + * + * @param {string} str + * @param {object} [options] + * @return {object} + * @public + */ + +function parse(str, options) { + if (typeof str !== 'string') { + throw new TypeError('argument str must be a string'); + } + + var obj = {} + var opt = options || {}; + var dec = opt.decode || decode; + + var index = 0 + while (index < str.length) { + var eqIdx = str.indexOf('=', index) + + // no more cookie pairs + if (eqIdx === -1) { + break + } + + var endIdx = str.indexOf(';', index) + + if (endIdx === -1) { + endIdx = str.length + } else if (endIdx < eqIdx) { + // backtrack on prior semicolon + index = str.lastIndexOf(';', eqIdx - 1) + 1 + continue + } + + var key = str.slice(index, eqIdx).trim() + + // only assign once + if (undefined === obj[key]) { + var val = str.slice(eqIdx + 1, endIdx).trim() + + // quoted values + if (val.charCodeAt(0) === 0x22) { + val = val.slice(1, -1) + } + + obj[key] = tryDecode(val, dec); + } + + index = endIdx + 1 + } + + return obj; +} + +/** + * Serialize data into a cookie header. + * + * Serialize the a name value pair into a cookie string suitable for + * http headers. An optional options object specified cookie parameters. + * + * serialize('foo', 'bar', { httpOnly: true }) + * => "foo=bar; httpOnly" + * + * @param {string} name + * @param {string} val + * @param {object} [options] + * @return {string} + * @public + */ + +function serialize(name, val, options) { + var opt = options || {}; + var enc = opt.encode || encode; + + if (typeof enc !== 'function') { + throw new TypeError('option encode is invalid'); + } + + if (!fieldContentRegExp.test(name)) { + throw new TypeError('argument name is invalid'); + } + + var value = enc(val); + + if (value && !fieldContentRegExp.test(value)) { + throw new TypeError('argument val is invalid'); + } + + var str = name + '=' + value; + + if (null != opt.maxAge) { + var maxAge = opt.maxAge - 0; + + if (isNaN(maxAge) || !isFinite(maxAge)) { + throw new TypeError('option maxAge is invalid') + } + + str += '; Max-Age=' + Math.floor(maxAge); + } + + if (opt.domain) { + if (!fieldContentRegExp.test(opt.domain)) { + throw new TypeError('option domain is invalid'); + } + + str += '; Domain=' + opt.domain; + } + + if (opt.path) { + if (!fieldContentRegExp.test(opt.path)) { + throw new TypeError('option path is invalid'); + } + + str += '; Path=' + opt.path; + } + + if (opt.expires) { + var expires = opt.expires + + if (!isDate(expires) || isNaN(expires.valueOf())) { + throw new TypeError('option expires is invalid'); + } + + str += '; Expires=' + expires.toUTCString() + } + + if (opt.httpOnly) { + str += '; HttpOnly'; + } + + if (opt.secure) { + str += '; Secure'; + } + + if (opt.partitioned) { + str += '; Partitioned' + } + + if (opt.priority) { + var priority = typeof opt.priority === 'string' + ? opt.priority.toLowerCase() + : opt.priority + + switch (priority) { + case 'low': + str += '; Priority=Low' + break + case 'medium': + str += '; Priority=Medium' + break + case 'high': + str += '; Priority=High' + break + default: + throw new TypeError('option priority is invalid') + } + } + + if (opt.sameSite) { + var sameSite = typeof opt.sameSite === 'string' + ? opt.sameSite.toLowerCase() : opt.sameSite; + + switch (sameSite) { + case true: + str += '; SameSite=Strict'; + break; + case 'lax': + str += '; SameSite=Lax'; + break; + case 'strict': + str += '; SameSite=Strict'; + break; + case 'none': + str += '; SameSite=None'; + break; + default: + throw new TypeError('option sameSite is invalid'); + } + } + + return str; +} + +/** + * URL-decode string value. Optimized to skip native call when no %. + * + * @param {string} str + * @returns {string} + */ + +function decode (str) { + return str.indexOf('%') !== -1 + ? decodeURIComponent(str) + : str +} + +/** + * URL-encode value. + * + * @param {string} val + * @returns {string} + */ + +function encode (val) { + return encodeURIComponent(val) +} + +/** + * Determine if value is a Date. + * + * @param {*} val + * @private + */ + +function isDate (val) { + return __toString.call(val) === '[object Date]' || + val instanceof Date +} + +/** + * Try decoding a string using a decoding function. + * + * @param {string} str + * @param {function} decode + * @private + */ + +function tryDecode(str, decode) { + try { + return decode(str); + } catch (e) { + return str; + } +} diff --git a/backend/node_modules/cookie/package.json b/backend/node_modules/cookie/package.json new file mode 100644 index 0000000..0c3f006 --- /dev/null +++ b/backend/node_modules/cookie/package.json @@ -0,0 +1,44 @@ +{ + "name": "cookie", + "description": "HTTP server cookie parsing and serialization", + "version": "0.6.0", + "author": "Roman ShtylmanLocation ' + escapeHtml(url) + ' not found
' + + // send a 404 + res.statusCode = 404 + res.setHeader('Content-Type', 'text/html; charset=UTF-8') + res.setHeader('Content-Length', String(Buffer.byteLength(body, 'utf-8'))) + res.end(body, 'utf-8') +}) +``` + +### Encode a URL for use in a header field + +```js +var encodeUrl = require('encodeurl') +var escapeHtml = require('escape-html') +var url = require('url') + +http.createServer(function onRequest (req, res) { + // parse inbound url + var href = url.parse(req) + + // set new host for redirect + href.host = 'localhost' + href.protocol = 'https:' + href.slashes = true + + // create location header + var location = encodeUrl(url.format(href)) + + // create html message + var body = 'Redirecting to new site: ' + escapeHtml(location) + '
' + + // send a 301 + res.statusCode = 301 + res.setHeader('Content-Type', 'text/html; charset=UTF-8') + res.setHeader('Content-Length', String(Buffer.byteLength(body, 'utf-8'))) + res.setHeader('Location', location) + res.end(body, 'utf-8') +}) +``` + +## Testing + +```sh +$ npm test +$ npm run lint +``` + +## References + +- [RFC 3986: Uniform Resource Identifier (URI): Generic Syntax][rfc-3986] +- [WHATWG URL Living Standard][whatwg-url] + +[rfc-3986]: https://tools.ietf.org/html/rfc3986 +[whatwg-url]: https://url.spec.whatwg.org/ + +## License + +[MIT](LICENSE) + +[npm-image]: https://img.shields.io/npm/v/encodeurl.svg +[npm-url]: https://npmjs.org/package/encodeurl +[node-version-image]: https://img.shields.io/node/v/encodeurl.svg +[node-version-url]: https://nodejs.org/en/download +[travis-image]: https://img.shields.io/travis/pillarjs/encodeurl.svg +[travis-url]: https://travis-ci.org/pillarjs/encodeurl +[coveralls-image]: https://img.shields.io/coveralls/pillarjs/encodeurl.svg +[coveralls-url]: https://coveralls.io/r/pillarjs/encodeurl?branch=master +[downloads-image]: https://img.shields.io/npm/dm/encodeurl.svg +[downloads-url]: https://npmjs.org/package/encodeurl diff --git a/backend/node_modules/encodeurl/index.js b/backend/node_modules/encodeurl/index.js new file mode 100644 index 0000000..fc4906c --- /dev/null +++ b/backend/node_modules/encodeurl/index.js @@ -0,0 +1,60 @@ +/*! + * encodeurl + * Copyright(c) 2016 Douglas Christopher Wilson + * MIT Licensed + */ + +'use strict' + +/** + * Module exports. + * @public + */ + +module.exports = encodeUrl + +/** + * RegExp to match non-URL code points, *after* encoding (i.e. not including "%") + * and including invalid escape sequences. + * @private + */ + +var ENCODE_CHARS_REGEXP = /(?:[^\x21\x25\x26-\x3B\x3D\x3F-\x5B\x5D\x5F\x61-\x7A\x7E]|%(?:[^0-9A-Fa-f]|[0-9A-Fa-f][^0-9A-Fa-f]|$))+/g + +/** + * RegExp to match unmatched surrogate pair. + * @private + */ + +var UNMATCHED_SURROGATE_PAIR_REGEXP = /(^|[^\uD800-\uDBFF])[\uDC00-\uDFFF]|[\uD800-\uDBFF]([^\uDC00-\uDFFF]|$)/g + +/** + * String to replace unmatched surrogate pair with. + * @private + */ + +var UNMATCHED_SURROGATE_PAIR_REPLACE = '$1\uFFFD$2' + +/** + * Encode a URL to a percent-encoded form, excluding already-encoded sequences. + * + * This function will take an already-encoded URL and encode all the non-URL + * code points. This function will not encode the "%" character unless it is + * not part of a valid sequence (`%20` will be left as-is, but `%foo` will + * be encoded as `%25foo`). + * + * This encode is meant to be "safe" and does not throw errors. It will try as + * hard as it can to properly encode the given URL, including replacing any raw, + * unpaired surrogate pairs with the Unicode replacement character prior to + * encoding. + * + * @param {string} url + * @return {string} + * @public + */ + +function encodeUrl (url) { + return String(url) + .replace(UNMATCHED_SURROGATE_PAIR_REGEXP, UNMATCHED_SURROGATE_PAIR_REPLACE) + .replace(ENCODE_CHARS_REGEXP, encodeURI) +} diff --git a/backend/node_modules/encodeurl/package.json b/backend/node_modules/encodeurl/package.json new file mode 100644 index 0000000..b9f25ef --- /dev/null +++ b/backend/node_modules/encodeurl/package.json @@ -0,0 +1,40 @@ +{ + "name": "encodeurl", + "description": "Encode a URL to a percent-encoded form, excluding already-encoded sequences", + "version": "1.0.2", + "contributors": [ + "Douglas Christopher Wilson