### Refactored

- `ModuleTargetFilter`, which was responsible for checking if a file is a target file, has been ported to a serviceFeature.
  - And also tests have been added. The middleware-style-power.
- `ModuleObsidianAPI` has been removed and implemented in `APIService` and `RemoteService`.
- Now `APIService` is responsible for the network-online-status, not `databaseService.managers.networkManager`.
This commit is contained in:
vorotamoroz
2026-02-25 09:38:31 +00:00
parent be1642f1c1
commit 19c03ec8d8
14 changed files with 92 additions and 546 deletions

View File

@@ -1,5 +1,5 @@
import { getLanguage } from "@/deps";
import { createServiceFeature } from "../types.ts";
import { createServiceFeature } from "@lib/interfaces/ServiceModule";
import { SUPPORTED_I18N_LANGS, type I18N_LANGS } from "@lib/common/rosetta";
import { $msg, setLang } from "@lib/common/i18n";

View File

@@ -1,78 +0,0 @@
import type { IServiceHub } from "@lib/services/base/IService";
import type { DatabaseFileAccess } from "@lib/interfaces/DatabaseFileAccess";
import type { Rebuilder } from "@lib/interfaces/DatabaseRebuilder";
import type { IFileHandler } from "@lib/interfaces/FileHandler";
import type { StorageAccess } from "@lib/interfaces/StorageAccess";
import type { LogFunction } from "@/lib/src/services/lib/logUtils";
export interface ServiceModules {
storageAccess: StorageAccess;
/**
* Database File Accessor for handling file operations related to the database, such as exporting the database, importing from a file, etc.
*/
databaseFileAccess: DatabaseFileAccess;
/**
* File Handler for handling file operations related to replication, such as resolving conflicts, applying changes from replication, etc.
*/
fileHandler: IFileHandler;
/**
* Rebuilder for handling database rebuilding operations.
*/
rebuilder: Rebuilder;
}
export type RequiredServices<T extends keyof IServiceHub> = Pick<IServiceHub, T>;
export type RequiredServiceModules<T extends keyof ServiceModules> = Pick<ServiceModules, T>;
export type NecessaryServices<T extends keyof IServiceHub, U extends keyof ServiceModules> = {
services: RequiredServices<T>;
serviceModules: RequiredServiceModules<U>;
};
export type ServiceFeatureFunction<T extends keyof IServiceHub, U extends keyof ServiceModules, TR> = (
host: NecessaryServices<T, U>
) => TR;
type ServiceFeatureContext<T> = T & {
_log: LogFunction;
};
export type ServiceFeatureFunctionWithContext<T extends keyof IServiceHub, U extends keyof ServiceModules, C, TR> = (
host: NecessaryServices<T, U>,
context: ServiceFeatureContext<C>
) => TR;
/**
* Helper function to create a service feature with proper typing.
* @param featureFunction The feature function to be wrapped.
* @returns The same feature function with proper typing.
* @example
* const myFeatureDef = createServiceFeature(({ services: { API }, serviceModules: { storageAccess } }) => {
* // ...
* });
* const myFeature = myFeatureDef.bind(null, this); // <- `this` may `ObsidianLiveSyncPlugin` or a custom context object
* appLifecycle.onLayoutReady(myFeature);
*/
export function createServiceFeature<T extends keyof IServiceHub, U extends keyof ServiceModules, TR>(
featureFunction: ServiceFeatureFunction<T, U, TR>
): ServiceFeatureFunction<T, U, TR> {
return featureFunction;
}
type ContextFactory<T extends keyof IServiceHub, U extends keyof ServiceModules, C> = (
host: NecessaryServices<T, U>
) => ServiceFeatureContext<C>;
export function serviceFeature<T extends keyof IServiceHub, U extends keyof ServiceModules>() {
return {
create<TR>(featureFunction: ServiceFeatureFunction<T, U, TR>) {
return featureFunction;
},
withContext<C extends object = object>(ContextFactory: ContextFactory<T, U, C>) {
return {
create:
<TR>(featureFunction: ServiceFeatureFunctionWithContext<T, U, C, TR>) =>
(host: NecessaryServices<T, U>, context: ServiceFeatureContext<C>) =>
featureFunction(host, ContextFactory(host)),
};
},
};
}