check password
This commit is contained in:
parent
cc0c4fe224
commit
7fc38a942a
@ -8,6 +8,9 @@ import {
|
||||
|
||||
const DEFAULT_ITER = 10000;
|
||||
|
||||
// base32.stringify(Buffer.from('Salted__'))
|
||||
export const MAGIC_ENCRYPTED_PREFIX_BASE32 = "KNQWY5DFMRPV";
|
||||
|
||||
const getKeyIVFromPassword = async (
|
||||
salt: Uint8Array,
|
||||
password: string,
|
||||
|
||||
22
src/main.ts
22
src/main.ts
@ -26,8 +26,8 @@ import {
|
||||
insertSyncPlanRecord,
|
||||
} from "./localdb";
|
||||
|
||||
import type { SyncStatusType } from "./sync";
|
||||
import { getSyncPlan, doActualSync } from "./sync";
|
||||
import type { SyncStatusType, PasswordCheckType } from "./sync";
|
||||
import { isPasswordOk, getSyncPlan, doActualSync } from "./sync";
|
||||
import {
|
||||
DEFAULT_S3_CONFIG,
|
||||
getS3Client,
|
||||
@ -98,7 +98,17 @@ export default class SaveRemotePlugin extends Plugin {
|
||||
// console.log(local);
|
||||
// console.log(localHistory);
|
||||
|
||||
new Notice("4/6 Starting to generate sync plan.");
|
||||
new Notice("4/7 Checking password correct or not.");
|
||||
this.syncStatus = "checking_password";
|
||||
const passwordCheckResult = await isPasswordOk(
|
||||
remoteRsp.Contents,
|
||||
this.settings.password
|
||||
);
|
||||
if (!passwordCheckResult.ok) {
|
||||
throw Error(passwordCheckResult.reason);
|
||||
}
|
||||
|
||||
new Notice("5/7 Starting to generate sync plan.");
|
||||
this.syncStatus = "generating_plan";
|
||||
const syncPlan = await getSyncPlan(
|
||||
remoteRsp.Contents,
|
||||
@ -113,7 +123,7 @@ export default class SaveRemotePlugin extends Plugin {
|
||||
// The operations above are read only and kind of safe.
|
||||
// The operations below begins to write or delete (!!!) something.
|
||||
|
||||
new Notice("5/6 Save Remote Sync data exchanging!");
|
||||
new Notice("6/7 Save Remote Sync data exchanging!");
|
||||
|
||||
this.syncStatus = "syncing";
|
||||
await doActualSync(
|
||||
@ -125,7 +135,7 @@ export default class SaveRemotePlugin extends Plugin {
|
||||
this.settings.password
|
||||
);
|
||||
|
||||
new Notice("6/6 Save Remote finish!");
|
||||
new Notice("7/7 Save Remote finish!");
|
||||
this.syncStatus = "finish";
|
||||
this.syncStatus = "idle";
|
||||
} catch (error) {
|
||||
@ -133,7 +143,7 @@ export default class SaveRemotePlugin extends Plugin {
|
||||
console.log(msg);
|
||||
console.log(error);
|
||||
new Notice(msg);
|
||||
new Notice(error);
|
||||
new Notice(error.message);
|
||||
this.syncStatus = "idle";
|
||||
}
|
||||
});
|
||||
|
||||
67
src/sync.ts
67
src/sync.ts
@ -17,13 +17,18 @@ import {
|
||||
downloadFromRemote,
|
||||
} from "./s3";
|
||||
import { mkdirpInVault, SUPPORTED_SERVICES_TYPE, isHiddenPath } from "./misc";
|
||||
import { decryptBase32ToString, encryptStringToBase32 } from "./encrypt";
|
||||
import {
|
||||
decryptBase32ToString,
|
||||
encryptStringToBase32,
|
||||
MAGIC_ENCRYPTED_PREFIX_BASE32,
|
||||
} from "./encrypt";
|
||||
|
||||
export type SyncStatusType =
|
||||
| "idle"
|
||||
| "preparing"
|
||||
| "getting_remote_meta"
|
||||
| "getting_local_meta"
|
||||
| "checking_password"
|
||||
| "generating_plan"
|
||||
| "syncing"
|
||||
| "finish";
|
||||
@ -61,6 +66,66 @@ export interface SyncPlanType {
|
||||
mixedStates: Record<string, FileOrFolderMixedState>;
|
||||
}
|
||||
|
||||
export interface PasswordCheckType {
|
||||
ok: boolean;
|
||||
reason:
|
||||
| "ok"
|
||||
| "empty_remote"
|
||||
| "remote_encrypted_local_no_password"
|
||||
| "password_matched"
|
||||
| "password_not_matched"
|
||||
| "remote_not_encrypted_local_has_password"
|
||||
| "no_password_both_sides";
|
||||
}
|
||||
|
||||
export const isPasswordOk = async (
|
||||
remote: S3ObjectType[],
|
||||
password: string = ""
|
||||
) => {
|
||||
if (remote === undefined || remote.length === 0) {
|
||||
// remote empty
|
||||
return {
|
||||
ok: true,
|
||||
reason: "empty_remote",
|
||||
} as PasswordCheckType;
|
||||
}
|
||||
const santyCheckKey = remote[0].Key;
|
||||
if (santyCheckKey.startsWith(MAGIC_ENCRYPTED_PREFIX_BASE32)) {
|
||||
// this is encrypted!
|
||||
// try to decrypt it using the provided password.
|
||||
if (password === "") {
|
||||
return {
|
||||
ok: false,
|
||||
reason: "remote_encrypted_local_no_password",
|
||||
} as PasswordCheckType;
|
||||
}
|
||||
try {
|
||||
const res = await decryptBase32ToString(santyCheckKey, password);
|
||||
return {
|
||||
ok: true,
|
||||
reason: "password_matched",
|
||||
} as PasswordCheckType;
|
||||
} catch (error) {
|
||||
return {
|
||||
ok: false,
|
||||
reason: "password_not_matched",
|
||||
} as PasswordCheckType;
|
||||
}
|
||||
} else {
|
||||
// it is not encrypted!
|
||||
if (password !== "") {
|
||||
return {
|
||||
ok: false,
|
||||
reason: "remote_not_encrypted_local_has_password",
|
||||
} as PasswordCheckType;
|
||||
}
|
||||
return {
|
||||
ok: true,
|
||||
reason: "no_password_both_sides",
|
||||
} as PasswordCheckType;
|
||||
}
|
||||
};
|
||||
|
||||
const ensembleMixedStates = async (
|
||||
remote: S3ObjectType[],
|
||||
local: TAbstractFile[],
|
||||
|
||||
Loading…
Reference in New Issue
Block a user