Set up monorepo workspace
This commit is contained in:
parent
ae3acb9e1e
commit
eb88d35c2e
10 changed files with 207 additions and 26 deletions
4
.gitignore
vendored
4
.gitignore
vendored
|
|
@ -7,8 +7,8 @@ node_modules
|
|||
# Rust build folder
|
||||
backend/target
|
||||
|
||||
# Obsidian plugin build folder
|
||||
plugin/dist
|
||||
obsidian-plugin/dist
|
||||
sync-client/dist
|
||||
|
||||
backend/db.sqlite3*
|
||||
backend/config.yml
|
||||
|
|
|
|||
|
|
@ -4,10 +4,16 @@ import unusedImports from "eslint-plugin-unused-imports";
|
|||
|
||||
export default tseslint.config({
|
||||
plugins: {
|
||||
"unused-imports": unusedImports,
|
||||
"unused-imports": unusedImports
|
||||
},
|
||||
extends: [eslint.configs.recommended, tseslint.configs.all],
|
||||
ignores: ["**/types.ts", "**/*.test.ts"],
|
||||
ignores: [
|
||||
"**/types.ts",
|
||||
"**/*.test.ts",
|
||||
"**/dist/**/*",
|
||||
"**/*.mjs",
|
||||
"**/*.js"
|
||||
],
|
||||
rules: {
|
||||
"no-unused-vars": "off",
|
||||
"@typescript-eslint/no-unused-vars": "off",
|
||||
|
|
@ -20,8 +26,8 @@ export default tseslint.config({
|
|||
"@typescript-eslint/max-params": [
|
||||
"error",
|
||||
{
|
||||
max: 5,
|
||||
},
|
||||
max: 5
|
||||
}
|
||||
],
|
||||
"unused-imports/no-unused-imports": "error",
|
||||
"@typescript-eslint/no-magic-numbers": "off",
|
||||
|
|
@ -33,14 +39,14 @@ export default tseslint.config({
|
|||
vars: "all",
|
||||
varsIgnorePattern: "^_",
|
||||
args: "after-used",
|
||||
argsIgnorePattern: "^_",
|
||||
},
|
||||
],
|
||||
argsIgnorePattern: "^_"
|
||||
}
|
||||
]
|
||||
},
|
||||
languageOptions: {
|
||||
parserOptions: {
|
||||
projectService: true,
|
||||
tsconfigRootDir: import.meta.dirname,
|
||||
},
|
||||
},
|
||||
tsconfigRootDir: import.meta.dirname
|
||||
}
|
||||
}
|
||||
});
|
||||
10
obsidian-plugin/manifest.json
Normal file
10
obsidian-plugin/manifest.json
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
{
|
||||
"id": "vault-link",
|
||||
"name": "VaultLink",
|
||||
"version": "0.0.30",
|
||||
"minAppVersion": "0.0.0",
|
||||
"description": "Self-hosted synchronization and collaboration for your Vault.",
|
||||
"author": "Andras Schmelczer",
|
||||
"authorUrl": "https://schmelczer.dev",
|
||||
"isDesktopOnly": false
|
||||
}
|
||||
26
package.json
Normal file
26
package.json
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
{
|
||||
"name": "my-workspace",
|
||||
"private": true,
|
||||
"workspaces": [
|
||||
"sync-client",
|
||||
"obsidian-plugin"
|
||||
],
|
||||
"prettier": {
|
||||
"trailingComma": "none",
|
||||
"tabWidth": 4,
|
||||
"useTabs": true,
|
||||
"endOfLine": "lf"
|
||||
},
|
||||
"scripts": {
|
||||
"build": "npm run build --workspaces",
|
||||
"dev": "npm run dev --workspaces",
|
||||
"test": "npm run test --workspaces",
|
||||
"lint": "eslint --fix sync-client obsidian-plugin; prettier --write \"sync-client/**/*.(ts|scss|json|html)\" \"obsidian-plugin/**/*.(ts|scss|json|html)\""
|
||||
},
|
||||
"devDependencies": {
|
||||
"prettier": "^3.4.2",
|
||||
"eslint": "9.17.0",
|
||||
"typescript-eslint": "8.18.0",
|
||||
"eslint-plugin-unused-imports": "^4.1.4"
|
||||
}
|
||||
}
|
||||
|
|
@ -1,8 +0,0 @@
|
|||
import type { TAbstractFile } from "obsidian";
|
||||
|
||||
export interface FileEventHandler {
|
||||
onCreate: (path: TAbstractFile) => Promise<void>;
|
||||
onDelete: (path: TAbstractFile) => Promise<void>;
|
||||
onRename: (path: TAbstractFile, oldPath: string) => Promise<void>;
|
||||
onModify: (path: TAbstractFile) => Promise<void>;
|
||||
}
|
||||
28
sync-client/package.json
Normal file
28
sync-client/package.json
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
{
|
||||
"name": "sync-client",
|
||||
"version": "1.0.0",
|
||||
"main": "dist/index.js",
|
||||
"types": "dist/types/src/index.d.ts",
|
||||
"scripts": {
|
||||
"dev": "webpack watch --mode development",
|
||||
"build": "webpack --mode production",
|
||||
"test": "NODE_OPTIONS=\"$NODE_OPTIONS --experimental-vm-modules\" jest"
|
||||
},
|
||||
"devDependencies": {
|
||||
"tslib": "2.4.0",
|
||||
"typescript": "5.7.2",
|
||||
"sync_lib": "file:../backend/sync_lib/pkg",
|
||||
"@types/jest": "^29.5.14",
|
||||
"@types/node": "^16.11.6",
|
||||
"jest": "^29.7.0",
|
||||
"ts-jest": "^29.2.5",
|
||||
"p-queue": "^8.0.1",
|
||||
"fetch-retry": "^6.0.0",
|
||||
"byte-base64": "^1.1.0",
|
||||
"openapi-fetch": "0.13.3",
|
||||
"openapi-typescript": "7.4.4",
|
||||
"ts-loader": "^9.5.1",
|
||||
"webpack": "^5.97.1",
|
||||
"webpack-cli": "^6.0.1"
|
||||
}
|
||||
}
|
||||
48
sync-client/src/index.ts
Normal file
48
sync-client/src/index.ts
Normal file
|
|
@ -0,0 +1,48 @@
|
|||
export { applyRemoteChangesLocally } from "./sync-operations/apply-remote-changes-locally";
|
||||
|
||||
export {
|
||||
type RelativePath,
|
||||
type DocumentId,
|
||||
type VaultUpdateId,
|
||||
type DocumentMetadata
|
||||
} from "./database/document-metadata";
|
||||
|
||||
export { Database } from "./database/database";
|
||||
|
||||
export {
|
||||
SyncService,
|
||||
type CheckConnectionResult
|
||||
} from "./services/sync-service";
|
||||
|
||||
export { Syncer } from "./sync-operations/syncer";
|
||||
|
||||
export {
|
||||
SyncHistory,
|
||||
SyncType,
|
||||
SyncSource,
|
||||
SyncStatus,
|
||||
type HistoryStats,
|
||||
type HistoryEntry
|
||||
} from "./tracing/sync-history";
|
||||
|
||||
export { Logger, LogLevel } from "./tracing/logger";
|
||||
|
||||
export { type FileOperations } from "./file-operations";
|
||||
|
||||
import init from "sync_lib";
|
||||
import wasmBin from "sync_lib/sync_lib_bg.wasm";
|
||||
|
||||
export const initialize = async (): Promise<void> => {
|
||||
await init(
|
||||
// eslint-disable-next-line
|
||||
(wasmBin as any).default // it is loaded as a base64 string by webpack
|
||||
);
|
||||
};
|
||||
export {
|
||||
isFileTypeMergable,
|
||||
mergeText,
|
||||
bytesToBase64,
|
||||
base64ToBytes,
|
||||
merge,
|
||||
isBinary
|
||||
} from "sync_lib";
|
||||
|
|
@ -1,9 +1,9 @@
|
|||
import type { Database } from "src/database/database";
|
||||
import type { Database } from "../database/database";
|
||||
import type {
|
||||
DocumentMetadata,
|
||||
RelativePath
|
||||
} from "src/database/document-metadata";
|
||||
import type { FileOperations } from "src/file-operations/file-operations";
|
||||
import type { FileOperations } from "src/file-operations";
|
||||
import type { SyncService } from "src/services/sync-service";
|
||||
import { Logger } from "src/tracing/logger";
|
||||
import type { SyncHistory } from "src/tracing/sync-history";
|
||||
|
|
@ -102,7 +102,7 @@ export class Syncer {
|
|||
|
||||
try {
|
||||
const allLocalFiles = await this.operations.listAllFiles();
|
||||
const locallyDeletedFiles = [
|
||||
let locallyDeletedFiles = [
|
||||
...this.database.getDocuments().entries()
|
||||
].filter(([path, _]) => !allLocalFiles.includes(path));
|
||||
|
||||
|
|
@ -126,7 +126,10 @@ export class Syncer {
|
|||
);
|
||||
if (originalFile !== undefined) {
|
||||
// `originalFile` hasn't been deleted but it got moved instead
|
||||
locallyDeletedFiles.remove(originalFile);
|
||||
locallyDeletedFiles =
|
||||
locallyDeletedFiles.filter(
|
||||
(item) => item != originalFile
|
||||
);
|
||||
|
||||
Logger.getInstance().debug(
|
||||
`Document ${relativePath} was not found under its current path in the database but was found under a different path ${originalFile[0]}, scheduling sync to move it`
|
||||
|
|
@ -231,7 +234,9 @@ export class Syncer {
|
|||
this.history.addHistoryEntry({
|
||||
status: SyncStatus.ERROR,
|
||||
relativePath,
|
||||
message: `File size exceeds the maximum file size limit of ${this.database.getSettings().maxFileSizeMB}MB`,
|
||||
message: `File size exceeds the maximum file size limit of ${
|
||||
this.database.getSettings().maxFileSizeMB
|
||||
}MB`,
|
||||
type: SyncType.CREATE
|
||||
});
|
||||
return;
|
||||
|
|
@ -332,7 +337,9 @@ export class Syncer {
|
|||
this.history.addHistoryEntry({
|
||||
status: SyncStatus.ERROR,
|
||||
relativePath,
|
||||
message: `File size exceeds the maximum file size limit of ${this.database.getSettings().maxFileSizeMB}MB`,
|
||||
message: `File size exceeds the maximum file size limit of ${
|
||||
this.database.getSettings().maxFileSizeMB
|
||||
}MB`,
|
||||
type: SyncType.CREATE
|
||||
});
|
||||
return;
|
||||
15
sync-client/tsconfig.json
Normal file
15
sync-client/tsconfig.json
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
{
|
||||
"compilerOptions": {
|
||||
"composite": true,
|
||||
"baseUrl": ".",
|
||||
"target": "ES2022",
|
||||
"noImplicitAny": true,
|
||||
"moduleResolution": "node",
|
||||
"strictNullChecks": true,
|
||||
"esModuleInterop": true,
|
||||
"lib": [
|
||||
"DOM",
|
||||
"ESNext"
|
||||
]
|
||||
}
|
||||
}
|
||||
49
sync-client/webpack.config.js
Normal file
49
sync-client/webpack.config.js
Normal file
|
|
@ -0,0 +1,49 @@
|
|||
const path = require("path");
|
||||
|
||||
module.exports = (_env, _argv) => ({
|
||||
entry: "./src/index.ts",
|
||||
devtool: "source-map",
|
||||
module: {
|
||||
rules: [
|
||||
{
|
||||
test: /\.ts$/,
|
||||
use: [
|
||||
{
|
||||
loader: "ts-loader",
|
||||
options: {
|
||||
compilerOptions: {
|
||||
declaration: true,
|
||||
declarationDir: "./dist/types"
|
||||
},
|
||||
transpileOnly: false
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
test: /\.wasm$/,
|
||||
type: "asset/inline"
|
||||
}
|
||||
]
|
||||
},
|
||||
optimization: {
|
||||
minimize: false
|
||||
},
|
||||
resolve: {
|
||||
extensions: [".ts", ".js"],
|
||||
alias: {
|
||||
root: __dirname,
|
||||
src: path.resolve(__dirname, "src")
|
||||
}
|
||||
},
|
||||
output: {
|
||||
clean: true,
|
||||
filename: "index.js",
|
||||
library: {
|
||||
name: "SyncClient",
|
||||
type: "umd"
|
||||
},
|
||||
globalObject: "this",
|
||||
path: path.resolve(__dirname, "dist")
|
||||
}
|
||||
});
|
||||
Loading…
Add table
Add a link
Reference in a new issue