Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
8d286a79a1 | ||
|
|
e69674e34e | ||
|
|
c3ed69af66 |
+1
-1
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"id": "remotely-save",
|
||||
"name": "Remotely Save",
|
||||
"version": "0.3.30",
|
||||
"version": "0.3.31",
|
||||
"minAppVersion": "0.13.21",
|
||||
"description": "Yet another unofficial plugin allowing users to synchronize notes between local device and the cloud service.",
|
||||
"author": "fyears",
|
||||
|
||||
+52
-2
@@ -330,7 +330,7 @@ export const clearDeleteRenameHistoryOfKeyAndVault = async (
|
||||
|
||||
export const insertDeleteRecordByVault = async (
|
||||
db: InternalDBs,
|
||||
fileOrFolder: TAbstractFile,
|
||||
fileOrFolder: TAbstractFile | string,
|
||||
vaultRandomID: string
|
||||
) => {
|
||||
// log.info(fileOrFolder);
|
||||
@@ -347,6 +347,7 @@ export const insertDeleteRecordByVault = async (
|
||||
renameTo: "",
|
||||
vaultRandomID: vaultRandomID,
|
||||
};
|
||||
await db.fileHistoryTbl.setItem(`${vaultRandomID}\t${k.key}`, k);
|
||||
} else if (fileOrFolder instanceof TFolder) {
|
||||
// key should endswith "/"
|
||||
const key = fileOrFolder.path.endsWith("/")
|
||||
@@ -365,8 +366,57 @@ export const insertDeleteRecordByVault = async (
|
||||
renameTo: "",
|
||||
vaultRandomID: vaultRandomID,
|
||||
};
|
||||
await db.fileHistoryTbl.setItem(`${vaultRandomID}\t${k.key}`, k);
|
||||
} else if (typeof fileOrFolder === "string") {
|
||||
// always the deletions in .obsidian folder
|
||||
// so annoying that the path doesn't exists
|
||||
// and we have to guess whether the path is folder or file
|
||||
k = {
|
||||
key: fileOrFolder,
|
||||
ctime: 0,
|
||||
mtime: 0,
|
||||
size: 0,
|
||||
actionWhen: Date.now(),
|
||||
actionType: "delete",
|
||||
keyType: "file",
|
||||
renameTo: "",
|
||||
vaultRandomID: vaultRandomID,
|
||||
};
|
||||
await db.fileHistoryTbl.setItem(`${vaultRandomID}\t${k.key}`, k);
|
||||
for (const ext of [
|
||||
"json",
|
||||
"js",
|
||||
"mjs",
|
||||
"ts",
|
||||
"md",
|
||||
"txt",
|
||||
"css",
|
||||
"png",
|
||||
"gif",
|
||||
"jpg",
|
||||
"jpeg",
|
||||
"gitignore",
|
||||
"gitkeep",
|
||||
]) {
|
||||
if (fileOrFolder.endsWith(`.${ext}`)) {
|
||||
// stop here, no more need to insert the folder record later
|
||||
return;
|
||||
}
|
||||
}
|
||||
// also add a deletion record as folder if not ending with special exts
|
||||
k = {
|
||||
key: `${fileOrFolder}/`,
|
||||
ctime: 0,
|
||||
mtime: 0,
|
||||
size: 0,
|
||||
actionWhen: Date.now(),
|
||||
actionType: "delete",
|
||||
keyType: "folder",
|
||||
renameTo: "",
|
||||
vaultRandomID: vaultRandomID,
|
||||
};
|
||||
await db.fileHistoryTbl.setItem(`${vaultRandomID}\t${k.key}`, k);
|
||||
}
|
||||
await db.fileHistoryTbl.setItem(`${vaultRandomID}\t${k.key}`, k);
|
||||
};
|
||||
|
||||
/**
|
||||
|
||||
+27
@@ -7,6 +7,8 @@ import {
|
||||
setIcon,
|
||||
FileSystemAdapter,
|
||||
Platform,
|
||||
TFile,
|
||||
TFolder,
|
||||
} from "obsidian";
|
||||
import cloneDeep from "lodash/cloneDeep";
|
||||
import { createElement, RotateCcw, RefreshCcw, FileText } from "lucide";
|
||||
@@ -496,6 +498,31 @@ export default class RemotelySavePlugin extends Plugin {
|
||||
})
|
||||
);
|
||||
|
||||
function getMethods(obj: any) {
|
||||
var result = [];
|
||||
for (var id in obj) {
|
||||
try {
|
||||
if (typeof obj[id] == "function") {
|
||||
result.push(id + ": " + obj[id].toString());
|
||||
}
|
||||
} catch (err) {
|
||||
result.push(id + ": inaccessible");
|
||||
}
|
||||
}
|
||||
return result.join("\n");
|
||||
}
|
||||
this.registerEvent(
|
||||
this.app.vault.on("raw" as any, async (fileOrFolder) => {
|
||||
// special track on .obsidian folder
|
||||
const name = `${fileOrFolder}`;
|
||||
if (name.startsWith(this.app.vault.configDir)) {
|
||||
if (!(await this.app.vault.adapter.exists(name))) {
|
||||
await insertDeleteRecordByVault(this.db, name, this.vaultRandomID);
|
||||
}
|
||||
}
|
||||
})
|
||||
);
|
||||
|
||||
this.registerObsidianProtocolHandler(COMMAND_URI, async (inputParams) => {
|
||||
const parsed = importQrCodeUri(inputParams, this.app.vault.getName());
|
||||
if (parsed.status === "error") {
|
||||
|
||||
+28
@@ -427,3 +427,31 @@ export const statFix = async (vault: Vault, path: string) => {
|
||||
}
|
||||
return s;
|
||||
};
|
||||
|
||||
export const isFolderToSkip = (x: string, more: string[] | undefined) => {
|
||||
let specialFolders = [
|
||||
".git",
|
||||
".github",
|
||||
".gitlab",
|
||||
".svn",
|
||||
"node_modules",
|
||||
".DS_Store",
|
||||
"__MACOSX ",
|
||||
"Icon\r", // https://superuser.com/questions/298785/icon-file-on-os-x-desktop
|
||||
"desktop.ini",
|
||||
"Desktop.ini",
|
||||
"thumbs.db",
|
||||
"Thumbs.db",
|
||||
].concat(more !== undefined ? more : []);
|
||||
for (const iterator of specialFolders) {
|
||||
if (
|
||||
x === iterator ||
|
||||
x === `${iterator}/` ||
|
||||
x.endsWith(`/${iterator}`) ||
|
||||
x.endsWith(`/${iterator}/`)
|
||||
) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
};
|
||||
|
||||
+3
-25
@@ -2,7 +2,7 @@ import { Vault, Stat, ListedFiles } from "obsidian";
|
||||
import { Queue } from "@fyears/tsqueue";
|
||||
import chunk from "lodash/chunk";
|
||||
import flatten from "lodash/flatten";
|
||||
import { statFix } from "./misc";
|
||||
import { statFix, isFolderToSkip } from "./misc";
|
||||
|
||||
export interface ObsConfigDirFileType {
|
||||
key: string;
|
||||
@@ -12,28 +12,6 @@ export interface ObsConfigDirFileType {
|
||||
type: "folder" | "file";
|
||||
}
|
||||
|
||||
const isFolderToSkip = (x: string) => {
|
||||
let specialFolders = [
|
||||
".git",
|
||||
".github",
|
||||
".gitlab",
|
||||
".svn",
|
||||
"node_modules",
|
||||
".DS_Store",
|
||||
];
|
||||
for (const iterator of specialFolders) {
|
||||
if (
|
||||
x === iterator ||
|
||||
x === `${iterator}/` ||
|
||||
x.endsWith(`/${iterator}`) ||
|
||||
x.endsWith(`/${iterator}/`)
|
||||
) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
};
|
||||
|
||||
const isPluginDirItself = (x: string, pluginId: string) => {
|
||||
return (
|
||||
x === pluginId ||
|
||||
@@ -106,7 +84,7 @@ export const listFilesInObsFolder = async (
|
||||
const isInsideSelfPlugin = isPluginDirItself(iter.itself.key, pluginId);
|
||||
if (iter.children !== undefined) {
|
||||
for (const iter2 of iter.children.folders) {
|
||||
if (isFolderToSkip(iter2)) {
|
||||
if (isFolderToSkip(iter2, ["workspace", "workspace.json"])) {
|
||||
continue;
|
||||
}
|
||||
if (isInsideSelfPlugin && !isLikelyPluginSubFiles(iter2)) {
|
||||
@@ -116,7 +94,7 @@ export const listFilesInObsFolder = async (
|
||||
q.push(iter2);
|
||||
}
|
||||
for (const iter2 of iter.children.files) {
|
||||
if (isFolderToSkip(iter2)) {
|
||||
if (isFolderToSkip(iter2, ["workspace", "workspace.json"])) {
|
||||
continue;
|
||||
}
|
||||
if (isInsideSelfPlugin && !isLikelyPluginSubFiles(iter2)) {
|
||||
|
||||
@@ -39,6 +39,7 @@ import {
|
||||
atWhichLevel,
|
||||
unixTimeToStr,
|
||||
statFix,
|
||||
isFolderToSkip,
|
||||
} from "./misc";
|
||||
import { RemoteClient } from "./remote";
|
||||
import {
|
||||
@@ -307,6 +308,10 @@ const isSkipItem = (
|
||||
if (syncConfigDir && isInsideObsFolder(key, configDir)) {
|
||||
return false;
|
||||
}
|
||||
if (isFolderToSkip(key, [])) {
|
||||
// some special dirs and files are always skipped
|
||||
return true;
|
||||
}
|
||||
return (
|
||||
isHiddenPath(key, true, false) ||
|
||||
(!syncUnderscoreItems && isHiddenPath(key, false, true)) ||
|
||||
|
||||
Reference in New Issue
Block a user