summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLucas Caro <lucascaro@gmail.com>2019-07-03 08:13:22 -0700
committerRyan Dahl <ry@tinyclouds.org>2019-07-03 11:13:22 -0400
commit6a0858bd5d9d327ac7f46bee5f5b2fab642f2a3f (patch)
tree1459f0757fd5ac9bfe3c3a650606f7cd8f4ac848
parent78a9a27e6fcecdac9a11cb01adf585feceed9e18 (diff)
add UUID module (denoland/deno_std#479)
Original: https://github.com/denoland/deno_std/commit/f52b3ec002ac38aa9146695283aa491bc2d115b6
-rwxr-xr-xtest.ts1
-rw-r--r--uuid/README.md15
-rw-r--r--uuid/mod.ts26
-rwxr-xr-xuuid/test.ts13
-rw-r--r--uuid/tests/generate.ts32
-rw-r--r--uuid/tests/isNil.ts16
-rw-r--r--uuid/tests/v4/generate.ts23
-rw-r--r--uuid/tests/v4/validate.ts17
-rw-r--r--uuid/v4.ts19
9 files changed, 162 insertions, 0 deletions
diff --git a/test.ts b/test.ts
index 1f41003f3..07e57e35b 100755
--- a/test.ts
+++ b/test.ts
@@ -21,6 +21,7 @@ import "./strings/test.ts";
import "./testing/test.ts";
import "./textproto/test.ts";
import "./util/test.ts";
+import "./uuid/test.ts";
import "./ws/test.ts";
import "./encoding/test.ts";
import "./os/test.ts";
diff --git a/uuid/README.md b/uuid/README.md
new file mode 100644
index 000000000..513a6ed53
--- /dev/null
+++ b/uuid/README.md
@@ -0,0 +1,15 @@
+# UUID
+
+Support for version 1, 3, 4, and 5 UUIDs.
+
+## Usage
+
+```ts
+import uuid, { validate } from "https://deno.land/std/uuid/mod.ts";
+
+// Generate a v4 uuid
+const myUUID = uuid();
+
+// Validate a v4 uuid
+const isValid = validate(aString);
+```
diff --git a/uuid/mod.ts b/uuid/mod.ts
new file mode 100644
index 000000000..64ca45385
--- /dev/null
+++ b/uuid/mod.ts
@@ -0,0 +1,26 @@
+// Based on https://github.com/kelektiv/node-uuid
+// Copyright 2018-2019 the Deno authors. All rights reserved. MIT license.
+
+export const NIL_UUID = "00000000-0000-0000-0000-000000000000";
+
+export function isNil(val: string): boolean {
+ return val === NIL_UUID;
+}
+
+const NOT_IMPLEMENTED = (): void => {
+ throw new Error("Not implemented");
+};
+
+// TODO Implement
+export const v1 = NOT_IMPLEMENTED;
+// TODO Implement
+export const v3 = NOT_IMPLEMENTED;
+
+import _v4 from "./v4.ts";
+export const v4 = _v4;
+
+// TODO Implement
+export const v5 = NOT_IMPLEMENTED;
+
+export default v4;
+export * from "./v4.ts";
diff --git a/uuid/test.ts b/uuid/test.ts
new file mode 100755
index 000000000..72616d3ef
--- /dev/null
+++ b/uuid/test.ts
@@ -0,0 +1,13 @@
+#!/usr/bin/env deno run
+// Copyright 2018-2019 the Deno authors. All rights reserved. MIT license.
+import { runIfMain } from "../testing/mod.ts";
+
+// Generic Tests
+import "./tests/isNil.ts";
+import "./tests/generate.ts";
+
+// V4 Tests
+import "./tests/v4/validate.ts";
+import "./tests/v4/generate.ts";
+
+runIfMain(import.meta);
diff --git a/uuid/tests/generate.ts b/uuid/tests/generate.ts
new file mode 100644
index 000000000..723740641
--- /dev/null
+++ b/uuid/tests/generate.ts
@@ -0,0 +1,32 @@
+// Copyright 2018-2019 the Deno authors. All rights reserved. MIT license.
+import { assert, assertEquals } from "../../testing/asserts.ts";
+import { test } from "../../testing/mod.ts";
+import mod, { validate, v4 } from "../mod.ts";
+import { validate as validate4 } from "../v4.ts";
+
+test({
+ name: "[UUID] uuid_v4",
+ fn(): void {
+ const u = mod();
+ assertEquals(typeof u, "string", "returns a string");
+ assert(u !== "", "return string is not empty");
+ }
+});
+
+test({
+ name: "[UUID] uuid_v4_format",
+ fn(): void {
+ for (let i = 0; i < 10000; i++) {
+ const u = mod() as string;
+ assert(validate(u), `${u} is not a valid uuid v4`);
+ }
+ }
+});
+
+test({
+ name: "[UUID] default_is_v4",
+ fn(): void {
+ assertEquals(mod, v4, "default is v4");
+ assertEquals(validate, validate4, "validate is v4");
+ }
+});
diff --git a/uuid/tests/isNil.ts b/uuid/tests/isNil.ts
new file mode 100644
index 000000000..29f0feb62
--- /dev/null
+++ b/uuid/tests/isNil.ts
@@ -0,0 +1,16 @@
+// Copyright 2018-2019 the Deno authors. All rights reserved. MIT license.
+import { assert } from "../../testing/asserts.ts";
+import { test } from "../../testing/mod.ts";
+// @ts-ignore
+import { NIL_UUID, isNil } from "../mod.ts";
+
+test({
+ name: "[UUID] isNil",
+ fn(): void {
+ const nil = NIL_UUID;
+ const u = "582cbcff-dad6-4f28-888a-e062ae36bafc";
+ assert(isNil(nil));
+ assert(!isNil(u));
+ console.log("");
+ }
+});
diff --git a/uuid/tests/v4/generate.ts b/uuid/tests/v4/generate.ts
new file mode 100644
index 000000000..829183d97
--- /dev/null
+++ b/uuid/tests/v4/generate.ts
@@ -0,0 +1,23 @@
+// Copyright 2018-2019 the Deno authors. All rights reserved. MIT license.
+import { assert, assertEquals } from "../../../testing/asserts.ts";
+import { test } from "../../../testing/mod.ts";
+import generate, { validate } from "../../v4.ts";
+
+test({
+ name: "[UUID] test_uuid_v4",
+ fn(): void {
+ const u = generate();
+ assertEquals(typeof u, "string", "returns a string");
+ assert(u !== "", "return string is not empty");
+ }
+});
+
+test({
+ name: "[UUID] test_uuid_v4_format",
+ fn(): void {
+ for (let i = 0; i < 10000; i++) {
+ const u = generate() as string;
+ assert(validate(u), `${u} is not a valid uuid v4`);
+ }
+ }
+});
diff --git a/uuid/tests/v4/validate.ts b/uuid/tests/v4/validate.ts
new file mode 100644
index 000000000..fdec8383a
--- /dev/null
+++ b/uuid/tests/v4/validate.ts
@@ -0,0 +1,17 @@
+// Copyright 2018-2019 the Deno authors. All rights reserved. MIT license.
+import { assert } from "../../../testing/asserts.ts";
+import { test } from "../../../testing/mod.ts";
+import generate, { validate } from "../../v4.ts";
+
+test({
+ name: "[UUID] is_valid_uuid_v4",
+ fn(): void {
+ const u = generate();
+ const t = "84fb7824-b951-490e-8afd-0c13228a8282";
+ const n = "84fb7824-b951-490g-8afd-0c13228a8282";
+
+ assert(validate(u), `generated ${u} should be valid`);
+ assert(validate(t), `${t} should be valid`);
+ assert(!validate(n), `${n} should not be valid`);
+ }
+});
diff --git a/uuid/v4.ts b/uuid/v4.ts
new file mode 100644
index 000000000..eeb9c4f14
--- /dev/null
+++ b/uuid/v4.ts
@@ -0,0 +1,19 @@
+// Copyright 2018-2019 the Deno authors. All rights reserved. MIT license.
+
+const UUID_RE = new RegExp(
+ "^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$",
+ "i"
+);
+
+export function validate(id: string): boolean {
+ return UUID_RE.test(id);
+}
+
+export default function generate(): string {
+ return "00000000-0000-4000-8000-000000000000".replace(
+ /[0]/g,
+ (): string =>
+ // random integer from 0 to 15 as a hex digit.
+ (crypto.getRandomValues(new Uint8Array(1))[0] % 16).toString(16)
+ );
+}