From a14b8c2d93bed8dfd450f14b3582a7334196e4f7 Mon Sep 17 00:00:00 2001
From: Jesse-Ma <24167796@qq.com>
Date: Tue, 14 Mar 2023 10:50:55 +0800
Subject: [PATCH] suspend
---
package.json | 2 +
public/redirect.html | 73 ++++
src/api/note.js | 35 +-
src/libs/page.js | 197 +++++++++
src/libs/storage.js | 14 +-
src/router/index.js | 137 +-----
src/views/{ErrorRoute.vue => ErrorView.vue} | 2 +-
src/views/NoteView.vue | 449 ++++++++++++++++++++
vue.config.js | 4 +-
yarn.lock | 23 +-
10 files changed, 786 insertions(+), 150 deletions(-)
create mode 100644 public/redirect.html
create mode 100644 src/libs/page.js
rename src/views/{ErrorRoute.vue => ErrorView.vue} (91%)
create mode 100644 src/views/NoteView.vue
diff --git a/package.json b/package.json
index 06efb07..06c2a13 100644
--- a/package.json
+++ b/package.json
@@ -11,10 +11,12 @@
},
"dependencies": {
"axios": "^0.27.2",
+ "bluebird": "^3.7.2",
"clipboard": "^2.0.11",
"crypto-js": "^4.1.1",
"escape-html": "^1.0.3",
"file-saver": "^2.0.5",
+ "localforage": "^1.10.0",
"pako": "^2.1.0",
"qrcodejs2": "^0.0.2",
"view-design": "^4.7.0",
diff --git a/public/redirect.html b/public/redirect.html
new file mode 100644
index 0000000..0407f57
--- /dev/null
+++ b/public/redirect.html
@@ -0,0 +1,73 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ flagnote.com
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/src/api/note.js b/src/api/note.js
index e046c94..a42f225 100644
--- a/src/api/note.js
+++ b/src/api/note.js
@@ -1,7 +1,7 @@
import axios from "axios";
import { getStoreKey } from "@/api/lock";
import storage from "@/libs/storage";
-import { md5, wrap} from "@/libs/secret";
+import { md5, wrap } from "@/libs/secret";
import NoteConstant from "@/libs/constants";
axios.interceptors.response.use(undefined, (err) => {
@@ -17,10 +17,10 @@ axios.interceptors.response.use(undefined, (err) => {
}
});
-export function saveNote(noteForm, secret) {
+export async function saveNote(noteForm, secret) {
let storeKey = secret.storeKey;
- let storeInfo = storage.local.getText(storeKey);
+ const storeInfo = await storage.local.getText(storeKey);
let starray = storeInfo.split("|");
if (starray[2] == "1") {
@@ -71,14 +71,13 @@ export function saveNote(noteForm, secret) {
});
}
-export function deleteNote(key) {
+export async function deleteNote(key) {
let storeKey = getStoreKey(key);
- let storeInfo = storage.local.getText(storeKey);
+ const storeInfo = await storage.local.getText(storeKey);
let note = {
cipher: storeInfo.substring(2, 34),
key: key,
};
-
return axios({
url: NoteConstant.servicePath + "/note/" + key + "/delete",
method: "post",
@@ -97,6 +96,28 @@ export function getNoteBlob(key) {
});
}
+export function getNoteMetaNew(key) {
+ let url = NoteConstant.servicePath + "/note/" + key + "/noteMeta";
+ return axios({
+ url: url,
+ method: "get",
+ ignoreError: 1,
+ original: true,
+ source: true,
+ });
+}
+
+export function getKeyMetaNew() {
+ let url = NoteConstant.servicePath + "/note/keyMeta";
+ return axios({
+ url: url,
+ method: "get",
+ ignoreError: 1,
+ original: true,
+ source: true,
+ });
+}
+
export function getNoteMeta(key) {
let url = NoteConstant.servicePath + "/note/" + key + "/noteMeta";
let noteMeta = null;
@@ -137,4 +158,4 @@ export function ajaxGet(url) {
};
xmlhttp.send();
return data;
-}
+}
\ No newline at end of file
diff --git a/src/libs/page.js b/src/libs/page.js
new file mode 100644
index 0000000..e426280
--- /dev/null
+++ b/src/libs/page.js
@@ -0,0 +1,197 @@
+import { getStoreKey } from "@/api/lock";
+import storage from "@/libs/storage";
+import { getNoteMetaNew, getNoteBlob } from "@/api/note";
+import { reject } from "bluebird";
+import { unwrap, md5 } from '@/libs/secret'
+
+
+export async function initPageData(view) {
+
+ let noteKey = view.noteForm.key;
+
+ let storeKey = getStoreKey(noteKey);
+ view.secret.storeKey = storeKey;
+
+ let keyMeta = storage.session.getObject("keyMeta");
+ if (keyMeta) {
+ view.state.lock = 0;
+ view.secret.cipher = keyMeta.cipher;
+ view.secret.secretKey = keyMeta.secretKey;
+ view.state.serverTime = keyMeta.serverTime;
+ // key init Time
+ view.state.initTime = keyMeta.serverTime;
+
+ await storage.local.setText(storeKey, "0|" + view.secret.cipher + "|0|" + view.state.initTime + "|");
+ storage.session.delete("keyMeta");
+ return "000000";
+ }
+
+ let noteMeta = storage.session.getObject(noteKey+".noteMeta");
+
+ if(null==noteMeta){
+ let resp = await getNoteMetaNew(view.noteForm.key);
+ if (null == resp || null == resp.data) {
+ return "100006";
+ }
+ let result = resp.data;
+ if (result.code != '000000') {
+ return result.code;
+ }
+ let noteMeta = result.data;
+ if (null == noteMeta) {
+ return "100001";
+ }
+ if (null == noteMeta.key) {
+ return "100002";
+ }
+ storage.session.setObject(noteKey+".noteMeta",noteMeta);
+ }else{
+ getNoteMetaNew(view.noteForm.key).then(function(resp){
+ if (null == resp || null == resp.data) {
+ return "100006";
+ }
+ let result = resp.data;
+ if (result.code != '000000') {
+ return result.code;
+ }
+ let noteMeta = result.data;
+ if (null == noteMeta) {
+ return "100001";
+ }
+ if (null == noteMeta.key) {
+ return "100002";
+ }
+ });
+ }
+
+ //view
+ if (1 == noteMeta.state) {
+
+ view.secret.secretKey = noteMeta.secretKey;
+
+ view.state.lock = noteMeta.lock;
+ view.state.initTime = new Date().getTime();
+ view.state.initTtl = noteMeta.ttl;
+ view.state.ttl = noteMeta.ttl;
+ view.state.serverTime = noteMeta.serverTime;
+
+ view.secret.cipher = "00000000000000000000000000000000";//noteMeta.cipher; //读者有没有值可配置
+ view.secret.md5 = noteMeta.md5;
+
+ await loadText(view);
+ return "000000";
+ }
+
+ //deleted
+ if (0 == noteMeta.state) {
+ let storeKey = getStoreKey(noteKey);
+ storage.local.delete(storeKey);
+ // user deleted
+ if (noteMeta.ttl > 0) {
+ // errorMeta = 100003;
+ return "100003";
+ //return errorRouter(100003);
+ } else {// timeout
+ // errorMeta = 100004;
+ return "100004";
+ //return errorRouter(100004);
+ }
+ }
+
+ //edit or unsubmitted
+ if (null == noteMeta.state) {
+ let storeKey = getStoreKey(noteKey);
+ const storeInfo = await storage.local.getText(storeKey);
+
+ //if has storage , then edit
+ if (null != storeInfo) {
+ view.secret.secretKey = noteMeta.secretKey;
+
+ let starray = storeInfo.split('|');
+ view.state.lock = parseInt(starray[0]);
+ view.secret.cipher = starray[1];
+ view.state.initTime = parseInt(starray[3]);
+ //draw text;
+ if (starray[4]) {
+ view.noteForm.text = unwrap(starray[4], view.secret.secretKey);
+ }
+
+ return "000000";
+ }
+
+ //storage is empty
+ let df = storage.session.getText(storeKey + "_delete")
+ if (df) {//unsubmitted,user deleted.
+ // errorMeta = 100003;
+ return "100003";
+ } else {//unsubmitted
+ // errorMeta = 100005;
+ return "100005";
+ }
+ }
+
+
+}
+
+async function loadText(view) {
+
+ let storeInfo = await storage.local.getText(view.secret.storeKey);
+
+ let starray = [];
+ if (storeInfo) {
+ starray = storeInfo.split('|');
+ }
+
+ if (!storeInfo || !starray[4] || (md5(starray[4]) != view.secret.md5)) {
+
+ let bytesString = await getServerNote(view.noteForm.key);
+ view.noteForm.text = unwrap(bytesString, view.secret.secretKey);
+ } else {
+ starray = storeInfo.split('|');
+
+ if (!starray[4]) {
+ return;
+ }
+
+ view.noteForm.text = unwrap(starray[4], view.secret.secretKey);
+ //this.noteForm.escapeText = getEscapeText(this.noteForm.text);
+
+ // local is usable, and set commited flag
+ if ("0" == starray[2]) {
+ storage.local.setText(this.secret.storeKey, starray[0] + "|" + starray[1] + "|1|" + starray[3] + "|" + starray[4]);
+ }
+ }
+}
+
+async function getServerNote(key) {
+ let resp = await getNoteBlob(key)
+ if (!resp.data || resp.data.size == 0) {
+ return "100006";
+ }
+
+ let blob = new Blob([resp.data], {
+ type: resp.data.type
+ });
+
+ let bytesString = await fileReader(blob);
+
+ return bytesString;
+
+
+}
+
+async function fileReader(blob) {
+ return new Promise(function (resolve) {
+ let reader = new FileReader();
+ reader.onload = function (e) {
+ if (!e.target.result || e.target.result.byteLength == 0) {
+ reject("");
+ }
+ var bytes = new Uint8Array(e.target.result);
+ bytes = bytes.subarray(7, bytes.length - 7);
+ let bytesString = bytes.join(",");
+ resolve(bytesString);
+ };
+ reader.readAsArrayBuffer(blob)
+ });
+}
\ No newline at end of file
diff --git a/src/libs/storage.js b/src/libs/storage.js
index 2d9ce6d..66564cd 100644
--- a/src/libs/storage.js
+++ b/src/libs/storage.js
@@ -1,3 +1,5 @@
+import localforage from "localforage";
+
class Storage {
constructor() {
this.session = new Session();
@@ -29,23 +31,23 @@ class Session {
class Local {
setObject(key, value) {
- localStorage.setItem(key, JSON.stringify(value));
+ return localforage.setItem(key, JSON.stringify(value));
}
getObject(key) {
- return JSON.parse(localStorage.getItem(key));
+ return JSON.parse(localforage.getItem(key));
}
delete(key) {
- localStorage.removeItem(key);
+ return localforage.removeItem(key);
}
setText(key, value) {
- localStorage.setItem(key, value);
+ return localforage.setItem(key, value);
}
getText(key) {
- return localStorage.getItem(key);
+ return localforage.getItem(key);
}
getUseSize() {
@@ -129,4 +131,4 @@ class Local {
}
const storage = new Storage();
-export default storage;
+export default storage;
\ No newline at end of file
diff --git a/src/router/index.js b/src/router/index.js
index 74c425c..bed69a1 100644
--- a/src/router/index.js
+++ b/src/router/index.js
@@ -1,144 +1,17 @@
import Vue from "vue";
import VueRouter from "vue-router";
-import EditNote from "@/views/EditNote.vue";
-import ViewNote from "@/views/ViewNote.vue";
-import ErrorRoute from "@/views/ErrorRoute.vue";
-import ErrorNote from "@/views/ErrorNote.vue";
-import { getKeyMeta, getNoteMeta } from "@/api/note";
-import { getStoreKey } from "@/api/lock";
-import storage from "@/libs/storage";
+import NoteView from "@/views/NoteView.vue";
+import ErrorView from "@/views/ErrorView.vue";
Vue.use(VueRouter);
-var keyMeta = null;
-var noteMeta = null;
-var errorMeta = null;
-
-function getKeyMetaParam() {
- return keyMeta;
-}
-
-function getNoteMetaParam() {
- return noteMeta;
-}
-
-function getErrorMetaParam() {
- return errorMeta;
-}
-
-function getNoteView() {
- if (errorMeta) {
- return;
- }
-
- let path = location.pathname;
-
- let key = path.substring(1, path.length);
-
- if (keyMeta && keyMeta.key) {
- key = keyMeta.key;
- }
-
- let regKey = /^[abcdefhikmnopqstuvwxyz23456789]{16}$/;
- if (!regKey.test(key)) {
- errorMeta = 100002;
- return ErrorNote;
- }
-
- if (keyMeta && keyMeta.key) {
- //firstEdit
- return EditNote;
- }
-
- //set noteMeta
- noteMeta = getNoteMeta(key);
-
- //server error
- if (!noteMeta) {
- errorMeta = 100006;
- return ErrorNote;
- }
-
- //invalidated key
- if (!noteMeta.key) {
- errorMeta = 100002;
- return ErrorNote;
- }
-
- //validated state
- if (1 == noteMeta.state) {
- return ViewNote;
- }
-
- //deleted
- if (0 == noteMeta.state) {
- let storeKey = getStoreKey(key);
- storage.local.delete(storeKey);
- // user deleted
- if (noteMeta.ttl > 0) {
- errorMeta = 100003;
- return ErrorNote;
- } else {// timeout
- errorMeta = 100004;
- return ErrorNote;
- }
- }
-
- if (null == noteMeta.state) {
- let storeKey = getStoreKey(key);
- //if has storage , then edit
- if (storage.local.getText(storeKey)) {
- return EditNote;
- } else {
- //storage is empty
- let df = storage.session.getText(storeKey + "_delete")
- if (df) {//unsubmitted,user deleted.
- errorMeta = 100003;
- return ErrorNote;
- } else {//unsubmitted
- errorMeta = 100005;
- return ErrorNote;
- }
- }
- }
-
- // other exception
- errorMeta = 100001;
- return ErrorNote;
-}
-
-function getHomeRedirect() {
- let path = location.pathname;
- if (path != "/") {
- return;
- }
-
- //setKeyMeta
- keyMeta = getKeyMeta();
-
- // server error
- if (!keyMeta) {
- errorMeta = 100006;
- return "/error_"+errorMeta;
- }
-
- return "/" + keyMeta.key;
-}
-
const routes = [
{
- path: "/",
- name: "home",
- redirect: getHomeRedirect(),
- },
- { path: "/error_:code([0-9]{6})", component: ErrorNote },
- {
- path: "/:name([a-z0-9]{10,20})",
+ path: "/:name([abcdefhikmnopqstuvwxyz23456789]{16})",
name: "note",
- component: getNoteView(),
- meta: { keyMeta: getKeyMetaParam(), noteMeta: getNoteMetaParam(), errorMeta: getErrorMetaParam() },
+ component: NoteView,
},
- { path: "/:path(.*)", component: ErrorRoute }
+ { path: "/:path(.*)", component: ErrorView }
];
const router = new VueRouter({
diff --git a/src/views/ErrorRoute.vue b/src/views/ErrorView.vue
similarity index 91%
rename from src/views/ErrorRoute.vue
rename to src/views/ErrorView.vue
index 70f2502..7a97afc 100644
--- a/src/views/ErrorRoute.vue
+++ b/src/views/ErrorView.vue
@@ -6,7 +6,7 @@
diff --git a/vue.config.js b/vue.config.js
index f24bc72..e9e9663 100644
--- a/vue.config.js
+++ b/vue.config.js
@@ -65,8 +65,8 @@ module.exports = defineConfig({
devServer: {
proxy: {
"/note": {
-// target: "https://flagnote.com/", // 后台接口域名
- target: "http://localhost:10000/", // 后台接口域名
+ target: "https://flagnote.com/", // 后台接口域名
+// target: "http://localhost:10000/", // 后台接口域名
secure: false, // 如果是https接口,需要配置这个参数
changeOrigin: true, //是否跨域
pathRewrite: {
diff --git a/yarn.lock b/yarn.lock
index 9e63f41..ebaca6f 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -2047,7 +2047,7 @@ bl@^4.1.0:
inherits "^2.0.4"
readable-stream "^3.4.0"
-bluebird@^3.1.1:
+bluebird@^3.1.1, bluebird@^3.7.2:
version "3.7.2"
resolved "https://registry.yarnpkg.com/bluebird/-/bluebird-3.7.2.tgz#9f229c15be272454ffa973ace0dbee79a1b0c36f"
integrity sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg==
@@ -3743,6 +3743,11 @@ ignore@^5.2.0:
resolved "https://registry.yarnpkg.com/ignore/-/ignore-5.2.1.tgz#c2b1f76cb999ede1502f3a226a9310fdfe88d46c"
integrity sha512-d2qQLzTJ9WxQftPAuEQpSPmKqzxePjzVbpAVv62AQ64NTL+wR4JkrVqR/LqFsFEUsHDAiId52mJteHDFuDkElA==
+immediate@~3.0.5:
+ version "3.0.6"
+ resolved "https://registry.yarnpkg.com/immediate/-/immediate-3.0.6.tgz#9db1dbd0faf8de6fbe0f5dd5e56bb606280de69b"
+ integrity sha512-XXOFtyqDjNDAQxVfYxuF7g9Il/IbWmmlQg2MYKOH8ExIT1qg6xc4zyS3HaEEATgs1btfzxq15ciUiY7gjSXRGQ==
+
import-fresh@^3.0.0, import-fresh@^3.2.1:
version "3.3.0"
resolved "https://registry.yarnpkg.com/import-fresh/-/import-fresh-3.3.0.tgz#37162c25fcb9ebaa2e6e53d5b4d88ce17d9e0c2b"
@@ -4145,6 +4150,13 @@ libphonenumber-js@^1.9.43:
resolved "https://registry.yarnpkg.com/libphonenumber-js/-/libphonenumber-js-1.10.14.tgz#e29da7f539751f724ac54017a098e3c7ca23de94"
integrity sha512-McGS7GV/WjJ2KjfOGhJU1oJn29RYeo7Q+RpANRbUNMQ9gj5XArpbjurSuyYPTejFwbaUojstQ4XyWCrAzGOUXw==
+lie@3.1.1:
+ version "3.1.1"
+ resolved "https://registry.yarnpkg.com/lie/-/lie-3.1.1.tgz#9a436b2cc7746ca59de7a41fa469b3efb76bd87e"
+ integrity sha512-RiNhHysUjhrDQntfYSfY4MU24coXXdEOgw9WGcKHNeEwffDYbF//u87M1EWaMGzuFoSbqW0C9C6lEEhDOAswfw==
+ dependencies:
+ immediate "~3.0.5"
+
lilconfig@^2.0.3:
version "2.0.6"
resolved "https://registry.yarnpkg.com/lilconfig/-/lilconfig-2.0.6.tgz#32a384558bd58af3d4c6e077dd1ad1d397bc69d4"
@@ -4178,6 +4190,13 @@ loader-utils@^2.0.0:
emojis-list "^3.0.0"
json5 "^2.1.2"
+localforage@^1.10.0:
+ version "1.10.0"
+ resolved "https://registry.yarnpkg.com/localforage/-/localforage-1.10.0.tgz#5c465dc5f62b2807c3a84c0c6a1b1b3212781dd4"
+ integrity sha512-14/H1aX7hzBBmmh7sGPd+AOMkkIrHM3Z1PAyGgZigA1H1p5O5ANnMyWzvpAETtG68/dC4pC0ncy3+PPGzXZHPg==
+ dependencies:
+ lie "3.1.1"
+
locate-path@^5.0.0:
version "5.0.0"
resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-5.0.0.tgz#1afba396afd676a6d42504d0a67a3a7eb9f62aa0"
@@ -6204,7 +6223,7 @@ vue-loader@^17.0.0:
hash-sum "^2.0.0"
loader-utils "^2.0.0"
-vue-router@^3.5.4:
+vue-router@^3.6.5:
version "3.6.5"
resolved "https://registry.yarnpkg.com/vue-router/-/vue-router-3.6.5.tgz#95847d52b9a7e3f1361cb605c8e6441f202afad8"
integrity sha512-VYXZQLtjuvKxxcshuRAwjHnciqZVoXAjTjcqBTz4rKc8qih9g9pI3hbDjmqXaHdgL3v8pV6P8Z335XvHzESxLQ==