mirror of
https://github.com/streetwriters/notesnook.git
synced 2025-12-23 23:19:40 +01:00
feat: migrate from delta to tiny
This commit is contained in:
@@ -100,6 +100,11 @@ describe.each([
|
|||||||
).toBeTruthy();
|
).toBeTruthy();
|
||||||
|
|
||||||
expect(db.notebooks.all.every((v) => v.title != null)).toBeTruthy();
|
expect(db.notebooks.all.every((v) => v.title != null)).toBeTruthy();
|
||||||
|
|
||||||
|
const allContent = await db.content.all();
|
||||||
|
expect(
|
||||||
|
allContent.every((v) => v.type === "tiny" || v.deleted)
|
||||||
|
).toBeTruthy();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -14,10 +14,12 @@ beforeEach(async () => {
|
|||||||
StorageInterface.clear();
|
StorageInterface.clear();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const content = { ...TEST_NOTE.content, data: "<p>5</p>" };
|
||||||
|
|
||||||
//TODO
|
//TODO
|
||||||
test("search notes", () =>
|
test("search notes", () =>
|
||||||
noteTest({
|
noteTest({
|
||||||
content: { type: "delta", data: [{ insert: "5" }] },
|
content: content,
|
||||||
}).then(async ({ db }) => {
|
}).then(async ({ db }) => {
|
||||||
await db.notes.add(TEST_NOTE);
|
await db.notes.add(TEST_NOTE);
|
||||||
let filtered = await db.lookup.notes(db.notes.all, "5");
|
let filtered = await db.lookup.notes(db.notes.all, "5");
|
||||||
@@ -26,7 +28,7 @@ test("search notes", () =>
|
|||||||
|
|
||||||
test("search notes with a locked note", () =>
|
test("search notes with a locked note", () =>
|
||||||
noteTest({
|
noteTest({
|
||||||
content: { type: "delta", data: [{ insert: "5" }] },
|
content: content,
|
||||||
}).then(async ({ db }) => {
|
}).then(async ({ db }) => {
|
||||||
const noteId = await db.notes.add(TEST_NOTE);
|
const noteId = await db.notes.add(TEST_NOTE);
|
||||||
await db.vault.create("password");
|
await db.vault.create("password");
|
||||||
@@ -37,11 +39,11 @@ test("search notes with a locked note", () =>
|
|||||||
|
|
||||||
test("search notes with an empty note", () =>
|
test("search notes with an empty note", () =>
|
||||||
noteTest({
|
noteTest({
|
||||||
content: { type: "delta", data: [{ insert: "5" }] },
|
content: content,
|
||||||
}).then(async ({ db }) => {
|
}).then(async ({ db }) => {
|
||||||
await db.notes.add({
|
await db.notes.add({
|
||||||
title: "hello world",
|
title: "hello world",
|
||||||
content: { type: "delta", data: [{ insert: "\n" }] },
|
content: { type: "tiny", data: "<p><br></p>" },
|
||||||
});
|
});
|
||||||
let filtered = await db.lookup.notes(db.notes.all, "hello world");
|
let filtered = await db.lookup.notes(db.notes.all, "hello world");
|
||||||
expect(filtered.length).toBe(1);
|
expect(filtered.length).toBe(1);
|
||||||
|
|||||||
@@ -60,7 +60,7 @@ test("get all notes", () =>
|
|||||||
test("note without a title should get title from content", () =>
|
test("note without a title should get title from content", () =>
|
||||||
noteTest().then(async ({ db, id }) => {
|
noteTest().then(async ({ db, id }) => {
|
||||||
let note = db.notes.note(id);
|
let note = db.notes.note(id);
|
||||||
expect(note.title).toBe("Hello This is colorful");
|
expect(note.title).toBe("HelloThis is colorful");
|
||||||
}));
|
}));
|
||||||
|
|
||||||
test("note title should allow trailing space", () =>
|
test("note title should allow trailing space", () =>
|
||||||
@@ -85,8 +85,8 @@ test("update note", () =>
|
|||||||
id,
|
id,
|
||||||
title: "I am a new title",
|
title: "I am a new title",
|
||||||
content: {
|
content: {
|
||||||
type: "delta",
|
type: TEST_NOTE.content.type,
|
||||||
data: [],
|
data: "<p><br></p>",
|
||||||
},
|
},
|
||||||
pinned: true,
|
pinned: true,
|
||||||
favorite: true,
|
favorite: true,
|
||||||
@@ -106,8 +106,8 @@ test("updating empty note should delete it", () =>
|
|||||||
id,
|
id,
|
||||||
title: "\n",
|
title: "\n",
|
||||||
content: {
|
content: {
|
||||||
type: "delta",
|
type: TEST_NOTE.content.type,
|
||||||
data: [{ insert: "\n" }],
|
data: "<p><br></p>",
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
expect(id).toBeUndefined();
|
expect(id).toBeUndefined();
|
||||||
@@ -221,7 +221,7 @@ test("export note to html", () =>
|
|||||||
const html = await db.notes.note(id).export("html");
|
const html = await db.notes.note(id).export("html");
|
||||||
expect(
|
expect(
|
||||||
html.includes(
|
html.includes(
|
||||||
`<p>Hello<br/><span style="color:#f00">This is colorful</span></p>`
|
`<p>Hello<br/><span style='color:#f00'>This is colorful</span></p>`
|
||||||
)
|
)
|
||||||
).toBeTruthy();
|
).toBeTruthy();
|
||||||
}));
|
}));
|
||||||
@@ -229,7 +229,7 @@ test("export note to html", () =>
|
|||||||
test("export note to md", () =>
|
test("export note to md", () =>
|
||||||
noteTest().then(async ({ db, id }) => {
|
noteTest().then(async ({ db, id }) => {
|
||||||
const md = await db.notes.note(id).export("md");
|
const md = await db.notes.note(id).export("md");
|
||||||
expect(md.includes(`Hello\nThis is colorful\n`)).toBeTruthy();
|
expect(md.includes(`Hello \nThis is colorful\n`)).toBeTruthy();
|
||||||
}));
|
}));
|
||||||
|
|
||||||
test("export note to txt", () =>
|
test("export note to txt", () =>
|
||||||
|
|||||||
@@ -69,7 +69,7 @@ test("get topic", () =>
|
|||||||
await topics.add("Home");
|
await topics.add("Home");
|
||||||
let topic = topics.topic("Home");
|
let topic = topics.topic("Home");
|
||||||
let noteId = await db.notes.add({
|
let noteId = await db.notes.add({
|
||||||
content: { type: "delta", data: [{ insert: "Hello" }] },
|
content: TEST_NOTE.content,
|
||||||
});
|
});
|
||||||
await topic.add(noteId);
|
await topic.add(noteId);
|
||||||
topic = topics.topic("Home");
|
topic = topics.topic("Home");
|
||||||
|
|||||||
@@ -27,11 +27,8 @@ const notebookTest = (notebook = TEST_NOTEBOOK) =>
|
|||||||
|
|
||||||
var TEST_NOTE = {
|
var TEST_NOTE = {
|
||||||
content: {
|
content: {
|
||||||
type: "delta",
|
type: "tiny",
|
||||||
data: [
|
data: `<p>Hello<br/><span style='color:#f00'>This is colorful</span></p>`,
|
||||||
{ insert: "Hello\n" },
|
|
||||||
{ insert: "This is colorful", attributes: { color: "#f00" } },
|
|
||||||
],
|
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -61,7 +61,7 @@ test("unlock a note", () =>
|
|||||||
const note = await db.vault.open(id, "password");
|
const note = await db.vault.open(id, "password");
|
||||||
expect(note.id).toBe(id);
|
expect(note.id).toBe(id);
|
||||||
expect(note.content.data).toBeDefined();
|
expect(note.content.data).toBeDefined();
|
||||||
expect(note.content.type).toBe("delta");
|
expect(note.content.type).toBe(TEST_NOTE.content.type);
|
||||||
}));
|
}));
|
||||||
|
|
||||||
test("unlock a note permanently", () =>
|
test("unlock a note permanently", () =>
|
||||||
@@ -74,7 +74,7 @@ test("unlock a note permanently", () =>
|
|||||||
expect(note.headline).not.toBe("");
|
expect(note.headline).not.toBe("");
|
||||||
const content = await db.content.raw(note.data.contentId);
|
const content = await db.content.raw(note.data.contentId);
|
||||||
expect(content.data).toBeDefined();
|
expect(content.data).toBeDefined();
|
||||||
expect(typeof content.data).toBe("object");
|
expect(typeof content.data).toBe("string");
|
||||||
}));
|
}));
|
||||||
|
|
||||||
test("save a locked note", () =>
|
test("save a locked note", () =>
|
||||||
|
|||||||
@@ -49,6 +49,7 @@ class Migrations {
|
|||||||
{
|
{
|
||||||
index: [this._db.settings.raw],
|
index: [this._db.settings.raw],
|
||||||
dbCollection: this._db.settings,
|
dbCollection: this._db.settings,
|
||||||
|
type: "settings",
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
await this._migrator.migrate(collections, (item) => item, this.dbVersion);
|
await this._migrator.migrate(collections, (item) => item, this.dbVersion);
|
||||||
|
|||||||
@@ -47,7 +47,7 @@ test("sync without merge conflicts, cause merge conflicts, resolve them and then
|
|||||||
// 4. edit the note's content
|
// 4. edit the note's content
|
||||||
await db.notes.add({
|
await db.notes.add({
|
||||||
id: noteId,
|
id: noteId,
|
||||||
content: { type: "delta", data: [{ insert: "text" }] },
|
content: { ...TEST_NOTE.content },
|
||||||
});
|
});
|
||||||
|
|
||||||
// 5. sync again and expect conflicts
|
// 5. sync again and expect conflicts
|
||||||
@@ -57,10 +57,10 @@ test("sync without merge conflicts, cause merge conflicts, resolve them and then
|
|||||||
v: CURRENT_DATABASE_VERSION,
|
v: CURRENT_DATABASE_VERSION,
|
||||||
...(await getEncrypted({
|
...(await getEncrypted({
|
||||||
id: contentId,
|
id: contentId,
|
||||||
type: "delta",
|
type: TEST_NOTE.content.type,
|
||||||
dateEdited: Date.now(),
|
dateEdited: Date.now(),
|
||||||
conflicted: false,
|
conflicted: false,
|
||||||
data: [{ insert: "text" }],
|
data: TEST_NOTE.content.data,
|
||||||
})),
|
})),
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -88,8 +88,8 @@ test("sync without merge conflicts, cause merge conflicts, resolve them and then
|
|||||||
id: noteId,
|
id: noteId,
|
||||||
conflicted: false,
|
conflicted: false,
|
||||||
content: {
|
content: {
|
||||||
type: "delta",
|
type: TEST_NOTE.content.type,
|
||||||
data: [{ insert: "text" }],
|
data: TEST_NOTE.content.data,
|
||||||
resolved: true,
|
resolved: true,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -31,4 +31,4 @@ export const EVENTS = {
|
|||||||
noteRemoved: "note:removed",
|
noteRemoved: "note:removed",
|
||||||
};
|
};
|
||||||
|
|
||||||
export const CURRENT_DATABASE_VERSION = 4.3;
|
export const CURRENT_DATABASE_VERSION = 5.0;
|
||||||
|
|||||||
@@ -1,68 +0,0 @@
|
|||||||
import { QuillDeltaToHtmlConverter } from "quill-delta-to-html";
|
|
||||||
import { deltaToMarkdown } from "quill-delta-to-markdown";
|
|
||||||
|
|
||||||
const splitter = /\W+/gm;
|
|
||||||
class Delta {
|
|
||||||
constructor(data) {
|
|
||||||
this.data = data;
|
|
||||||
}
|
|
||||||
|
|
||||||
toHTML() {
|
|
||||||
const deltaConverter = new QuillDeltaToHtmlConverter(this.data, {
|
|
||||||
classPrefix: "nn",
|
|
||||||
inlineStyles: true,
|
|
||||||
});
|
|
||||||
return deltaConverter.convert();
|
|
||||||
}
|
|
||||||
|
|
||||||
toTXT() {
|
|
||||||
return this.data.reduce(function (text, op) {
|
|
||||||
if (!op.insert) return text;
|
|
||||||
if (typeof op.insert !== "string") return text + " ";
|
|
||||||
return text + op.insert;
|
|
||||||
}, "");
|
|
||||||
}
|
|
||||||
|
|
||||||
toMD() {
|
|
||||||
return deltaToMarkdown(this.data);
|
|
||||||
}
|
|
||||||
|
|
||||||
toTitle() {
|
|
||||||
return getSubstringFromDelta(this.data, 30);
|
|
||||||
}
|
|
||||||
|
|
||||||
toHeadline() {
|
|
||||||
return getSubstringFromDelta(this.data, 80);
|
|
||||||
}
|
|
||||||
|
|
||||||
isEmpty() {
|
|
||||||
return this.toTXT().trim().length <= 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @returns {Boolean}
|
|
||||||
*/
|
|
||||||
search(query) {
|
|
||||||
const tokens = query.toLowerCase().split(splitter);
|
|
||||||
return this.data.some((item) => {
|
|
||||||
if (item.insert && item.insert.indexOf) {
|
|
||||||
return tokens.some(
|
|
||||||
(token) => item.insert.toLowerCase().indexOf(token) > -1
|
|
||||||
);
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
export default Delta;
|
|
||||||
|
|
||||||
function getSubstringFromDelta(data, limit) {
|
|
||||||
let substr = "";
|
|
||||||
for (var i = 0; i < data.length; ++i) {
|
|
||||||
const item = data[i];
|
|
||||||
if (item.insert && typeof item.insert === "string")
|
|
||||||
substr += item.insert.replace(/\r?\n/g, " ");
|
|
||||||
if (substr.length > limit) return substr.substring(0, limit);
|
|
||||||
}
|
|
||||||
return substr;
|
|
||||||
}
|
|
||||||
@@ -1,9 +1,9 @@
|
|||||||
import Delta from "./delta";
|
import Tiny from "./tiny";
|
||||||
|
|
||||||
export function getContentFromData(type, data) {
|
export function getContentFromData(type, data) {
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case "delta":
|
case "tiny":
|
||||||
return new Delta(data);
|
return new Tiny(data);
|
||||||
default:
|
default:
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|||||||
48
packages/core/content-types/tiny.js
Normal file
48
packages/core/content-types/tiny.js
Normal file
@@ -0,0 +1,48 @@
|
|||||||
|
import TurndownService from "turndown";
|
||||||
|
var turndownService = new TurndownService();
|
||||||
|
|
||||||
|
const splitter = /\W+/gm;
|
||||||
|
class Tiny {
|
||||||
|
constructor(data) {
|
||||||
|
this.data = data;
|
||||||
|
}
|
||||||
|
|
||||||
|
toHTML() {
|
||||||
|
return this.data;
|
||||||
|
}
|
||||||
|
|
||||||
|
toTXT() {
|
||||||
|
if (window.DOMParser) {
|
||||||
|
let doc = new DOMParser().parseFromString(this.data, "text/html");
|
||||||
|
return doc.body.textContent || "";
|
||||||
|
} else {
|
||||||
|
return this.data.replace(/<br>/gm, "\n").replace(/<[^>]+>/g, "");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
toMD() {
|
||||||
|
return turndownService.turndown(this.data);
|
||||||
|
}
|
||||||
|
|
||||||
|
toTitle() {
|
||||||
|
return this.toTXT().substring(0, 30);
|
||||||
|
}
|
||||||
|
|
||||||
|
toHeadline() {
|
||||||
|
return this.toTXT().substring(0, 80);
|
||||||
|
}
|
||||||
|
|
||||||
|
isEmpty() {
|
||||||
|
return this.toTXT().trim().length <= 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @returns {Boolean}
|
||||||
|
*/
|
||||||
|
search(query) {
|
||||||
|
const tokens = query.toLowerCase().split(splitter);
|
||||||
|
const lowercase = this.toTXT().toLowerCase();
|
||||||
|
return tokens.some((token) => lowercase.indexOf(token) > -1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
export default Tiny;
|
||||||
@@ -97,6 +97,7 @@ export default class Backup {
|
|||||||
case 4:
|
case 4:
|
||||||
case 4.1:
|
case 4.1:
|
||||||
case 4.2:
|
case 4.2:
|
||||||
|
case 4.3:
|
||||||
case 3:
|
case 3:
|
||||||
case 2: {
|
case 2: {
|
||||||
return backup;
|
return backup;
|
||||||
@@ -144,6 +145,7 @@ export default class Backup {
|
|||||||
{
|
{
|
||||||
index: data["delta"],
|
index: data["delta"],
|
||||||
dbCollection: this._db.content,
|
dbCollection: this._db.content,
|
||||||
|
type: "delta",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
index: data["content"],
|
index: data["content"],
|
||||||
@@ -152,6 +154,7 @@ export default class Backup {
|
|||||||
{
|
{
|
||||||
index: ["settings"],
|
index: ["settings"],
|
||||||
dbCollection: this._db.settings,
|
dbCollection: this._db.settings,
|
||||||
|
type: "settings",
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
|
|||||||
@@ -15,7 +15,7 @@ class Migrator {
|
|||||||
if (item.deleted)
|
if (item.deleted)
|
||||||
return await collection.dbCollection._collection.addItem(item);
|
return await collection.dbCollection._collection.addItem(item);
|
||||||
|
|
||||||
const migrate = migrations[version][item.type || id];
|
const migrate = migrations[version][item.type || collection.type];
|
||||||
if (migrate) item = migrate(item);
|
if (migrate) item = migrate(item);
|
||||||
|
|
||||||
if (!!collection.dbCollection.merge) {
|
if (!!collection.dbCollection.merge) {
|
||||||
|
|||||||
@@ -1,3 +1,5 @@
|
|||||||
|
import { QuillDeltaToHtmlConverter } from "quill-delta-to-html";
|
||||||
|
|
||||||
export const migrations = {
|
export const migrations = {
|
||||||
0: {
|
0: {
|
||||||
note: function (item) {
|
note: function (item) {
|
||||||
@@ -14,7 +16,7 @@ export const migrations = {
|
|||||||
item.data = item.data.ops;
|
item.data = item.data.ops;
|
||||||
item.type = "delta";
|
item.type = "delta";
|
||||||
item.migrated = true;
|
item.migrated = true;
|
||||||
return item;
|
return migrations["2"].delta(item);
|
||||||
},
|
},
|
||||||
trash: function (item) {
|
trash: function (item) {
|
||||||
item.itemType = item.type;
|
item.itemType = item.type;
|
||||||
@@ -40,6 +42,7 @@ export const migrations = {
|
|||||||
|
|
||||||
return migrations[3].note(item);
|
return migrations[3].note(item);
|
||||||
},
|
},
|
||||||
|
delta: (item) => migrations["3"].delta(item),
|
||||||
},
|
},
|
||||||
3: {
|
3: {
|
||||||
note: function (item) {
|
note: function (item) {
|
||||||
@@ -49,6 +52,7 @@ export const migrations = {
|
|||||||
|
|
||||||
return migrations[4].note(item);
|
return migrations[4].note(item);
|
||||||
},
|
},
|
||||||
|
delta: (item) => migrations["4"].delta(item),
|
||||||
},
|
},
|
||||||
4: {
|
4: {
|
||||||
note: function (item) {
|
note: function (item) {
|
||||||
@@ -57,11 +61,13 @@ export const migrations = {
|
|||||||
}
|
}
|
||||||
return migrations["4.1"].note(item);
|
return migrations["4.1"].note(item);
|
||||||
},
|
},
|
||||||
|
delta: (item) => migrations["4.1"].delta(item),
|
||||||
},
|
},
|
||||||
4.1: {
|
4.1: {
|
||||||
note: function (item) {
|
note: function (item) {
|
||||||
return migrations["4.2"].note(item);
|
return migrations["4.2"].note(item);
|
||||||
},
|
},
|
||||||
|
delta: (item) => migrations["4.2"].delta(item),
|
||||||
},
|
},
|
||||||
4.2: {
|
4.2: {
|
||||||
note: function (item) {
|
note: function (item) {
|
||||||
@@ -73,8 +79,21 @@ export const migrations = {
|
|||||||
item.migrated = true;
|
item.migrated = true;
|
||||||
return item;
|
return item;
|
||||||
},
|
},
|
||||||
|
delta: (item) => migrations["4.3"].delta(item),
|
||||||
},
|
},
|
||||||
4.3: {
|
4.3: {
|
||||||
|
delta: function (item) {
|
||||||
|
const deltaConverter = new QuillDeltaToHtmlConverter(item.data, {
|
||||||
|
classPrefix: "nn",
|
||||||
|
inlineStyles: true,
|
||||||
|
});
|
||||||
|
item.data = deltaConverter.convert();
|
||||||
|
item.type = "tiny";
|
||||||
|
item.migrated = true;
|
||||||
|
return item;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
5.0: {
|
||||||
note: false,
|
note: false,
|
||||||
notebook: false,
|
notebook: false,
|
||||||
tag: false,
|
tag: false,
|
||||||
|
|||||||
@@ -28,6 +28,7 @@
|
|||||||
"qclone": "^1.0.4",
|
"qclone": "^1.0.4",
|
||||||
"quill-delta-to-html": "^0.12.0",
|
"quill-delta-to-html": "^0.12.0",
|
||||||
"quill-delta-to-markdown": "https://github.com/streetwriters/quill-delta-to-markdown",
|
"quill-delta-to-markdown": "https://github.com/streetwriters/quill-delta-to-markdown",
|
||||||
"transfun": "^1.0.2"
|
"transfun": "^1.0.2",
|
||||||
|
"turndown": "^7.0.0"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2237,6 +2237,11 @@ domexception@^1.0.1:
|
|||||||
dependencies:
|
dependencies:
|
||||||
webidl-conversions "^4.0.2"
|
webidl-conversions "^4.0.2"
|
||||||
|
|
||||||
|
domino@^2.1.6:
|
||||||
|
version "2.1.6"
|
||||||
|
resolved "https://registry.yarnpkg.com/domino/-/domino-2.1.6.tgz#fe4ace4310526e5e7b9d12c7de01b7f485a57ffe"
|
||||||
|
integrity sha512-3VdM/SXBZX2omc9JF9nOPCtDaYQ67BGp5CoLpIQlO2KCAPETs8TcDHacF26jXadGbvUteZzRTeos2fhID5+ucQ==
|
||||||
|
|
||||||
ecc-jsbn@~0.1.1:
|
ecc-jsbn@~0.1.1:
|
||||||
version "0.1.2"
|
version "0.1.2"
|
||||||
resolved "https://registry.yarnpkg.com/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz#3a83a904e54353287874c564b7549386849a98c9"
|
resolved "https://registry.yarnpkg.com/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz#3a83a904e54353287874c564b7549386849a98c9"
|
||||||
@@ -4782,6 +4787,13 @@ tunnel-agent@^0.6.0:
|
|||||||
dependencies:
|
dependencies:
|
||||||
safe-buffer "^5.0.1"
|
safe-buffer "^5.0.1"
|
||||||
|
|
||||||
|
turndown@^7.0.0:
|
||||||
|
version "7.0.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/turndown/-/turndown-7.0.0.tgz#19b2a6a2d1d700387a1e07665414e4af4fec5225"
|
||||||
|
integrity sha512-G1FfxfR0mUNMeGjszLYl3kxtopC4O9DRRiMlMDDVHvU1jaBkGFg4qxIyjIk2aiKLHyDyZvZyu4qBO2guuYBy3Q==
|
||||||
|
dependencies:
|
||||||
|
domino "^2.1.6"
|
||||||
|
|
||||||
tweetnacl@^0.14.3, tweetnacl@~0.14.0:
|
tweetnacl@^0.14.3, tweetnacl@~0.14.0:
|
||||||
version "0.14.5"
|
version "0.14.5"
|
||||||
resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64"
|
resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64"
|
||||||
|
|||||||
Reference in New Issue
Block a user