Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add nitrobase-client package #327

Open
wants to merge 12 commits into
base: next
Choose a base branch
from
661 changes: 661 additions & 0 deletions packages/client/LICENSE

Large diffs are not rendered by default.

25 changes: 25 additions & 0 deletions packages/client/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# Nitrobase Client

## Installation

```bash
npm install @alwatr/nitrobase
```

## Getting Started

```js
import {} from '@alwatr/nitrobase';
```

## Sponsors

The following companies, organizations, and individuals support Nitrobase ongoing maintenance and development. Become a Sponsor to get your logo on our README and website.

### Contributing

Contributions are welcome! Please read our [contribution guidelines](https://github.com/Alwatr/.github/blob/next/CONTRIBUTING.md) before submitting a pull request.

### License

This project is licensed under the [AGPL-3.0 License](LICENSE).
76 changes: 76 additions & 0 deletions packages/client/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
{
"name": "@alwatr/nitrobase-client",
"version": "7.4.0",
"description": "",
"author": "S. Ali Mihandoost <ali.mihandoost@gmail.com>",
"keywords": [
"client",
"database",
"storage",
"json",
"nosql",
"no-sql",
"data",
"data-storage",
"file",
"typescript",
"esm",
"alwatr"
],
"type": "module",
"main": "./dist/main.cjs",
"module": "./dist/main.mjs",
"types": "./dist/main.d.ts",
"exports": {
".": {
"types": "./dist/main.d.ts",
"import": "./dist/main.mjs",
"require": "./dist/main.cjs"
}
},
"license": "AGPL-3.0-only",
"files": [
"**/*.{js,mjs,cjs,map,d.ts,html,md}",
"!demo/**/*"
],
"publishConfig": {
"access": "public"
},
"repository": {
"type": "git",
"url": "https://github.com/Alwatr/nitrobase",
"directory": "packages/client"
},
"homepage": "https://github.com/Alwatr/nitrobase/tree/next/packages/client#readme",
"bugs": {
"url": "https://github.com/Alwatr/nitrobase/issues"
},
"prettier": "@alwatr/prettier-config",
"scripts": {
"b": "yarn run build",
"w": "yarn run watch",
"c": "yarn run clean",
"cb": "yarn run clean && yarn run build",
"d": "yarn node --enable-source-maps --trace-warnings",
"build": "yarn run build:ts & yarn run build:es",
"build:es": "nano-build --preset=module",
"build:ts": "tsc --build",
"watch": "yarn run watch:ts & yarn run watch:es",
"watch:es": "yarn run build:es --watch",
"watch:ts": "yarn run build:ts --watch --preserveWatchOutput",
"clean": "rm -rfv dist *.tsbuildinfo"
},
"dependencies": {
"@alwatr/nanolib": "^5.2.1",
"@alwatr/nitrobase-helper": "workspace:^",
"@alwatr/nitrobase-types": "workspace:^"
},
"devDependencies": {
"@alwatr/nano-build": "^5.0.0",
"@alwatr/prettier-config": "^5.0.0",
"@alwatr/tsconfig-base": "^5.0.0",
"@alwatr/type-helper": "^5.0.0",
"@types/node": "^22.9.0",
"typescript": "^5.6.3"
}
}
99 changes: 99 additions & 0 deletions packages/client/src/client.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
import {createLogger, fetchJson, HttpStatusCodes, resolveUrl, type FetchOptions, type ResponseError} from '@alwatr/nanolib';
import {getStorePath} from '@alwatr/nitrobase-helper';
import {
StoreFileType,
type AlwatrAuth,
type CollectionContext,
type StoreFileContext,
type StoreFileId,
type StoreFileStat,
} from '@alwatr/nitrobase-types';

const logger = /* #__PURE__ */ createLogger('alwatr-client-nitrobase');

export type NitrobaseDocumentContext<TData extends JsonObject = JsonObject> = StoreFileContext<TData>;

/**
* Recommended config
* ```
* apiUrl = '/api/s7';
*
* alwatrAuthorization: AlwatrAuth = {
* userId: 'anonymous',
* userToken: 'anonymous',
* };
*
* fetchOptions: Partial<FetchOptions> = {
* retry: 3,
* retryDelay: '1s',
* timeout: '8s',
* removeDuplicate: 'until_load',
* cacheStorageName: 'nitrobase',
* cacheStrategy: 'network_first',
* priority: 'high',
* };
* ```
*/
export interface AlwatrClientNitrobaseConfig {
apiUrl: string;
alwatrAuthorization: AlwatrAuth;
fetchOptions: Partial<FetchOptions>;
}

export abstract class AlwatrClientNitrobaseRepository {
reloadOnSchemaVersionMismatch = true;

constructor(readonly config_: AlwatrClientNitrobaseConfig) {
logger.logMethod?.('new');
}

abstract fetchDocument<TDoc extends JsonObject>(documentId: StoreFileStat): Promise<ResponseError | NitrobaseDocumentContext<TDoc>>;
abstract fetchCollection<TItem extends JsonObject>(collectionId: StoreFileStat): Promise<ResponseError | CollectionContext<TItem>>;
}

export class AlwatrClientNitrobase extends AlwatrClientNitrobaseRepository {
private async fetch__<T extends StoreFileContext>(storeStat: StoreFileStat): Promise<ResponseError | T> {
const response = await fetchJson<T>({
...this.config_.fetchOptions,
url: resolveUrl(this.config_.apiUrl, getStorePath(storeStat)),
alwatrAuth: this.config_.alwatrAuthorization,
});

if (response.ok === true && response.meta?.schemaVer !== undefined && response.meta.schemaVer !== (storeStat.schemaVer ?? 1)) {
logger.accident?.('fetch__', 'schema_version_mismatch', {
requestedStoreId: storeStat,
responseMeta: response.meta,
});

if (this.reloadOnSchemaVersionMismatch) {
location.reload();
}

return {
ok: false,
statusCode: HttpStatusCodes.Error_Client_400_Bad_Request,
errorCode: 'schema_version_mismatch',
errorMessage: 'Schema version mismatch',
meta: response.meta,
} as ResponseError;
}

return response;
}

async fetchDocument<TDoc extends JsonObject>(documentId: StoreFileId): Promise<ResponseError | NitrobaseDocumentContext<TDoc>> {
logger.logMethodArgs?.('fetchDocument', documentId);
return this.fetch__<NitrobaseDocumentContext<TDoc>>({
...documentId,
type: StoreFileType.Document,
});
}

async fetchCollection<TItem extends JsonObject>(collectionId: StoreFileId): Promise<ResponseError | CollectionContext<TItem>> {
logger.logMethodArgs?.('fetchCollection', collectionId);
return this.fetch__<CollectionContext<TItem>>({
...collectionId,
type: StoreFileType.Collection,
});
}
}
1 change: 1 addition & 0 deletions packages/client/src/main.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export * from './client.js';
12 changes: 12 additions & 0 deletions packages/client/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
{
"extends": "@alwatr/tsconfig-base/tsconfig.json",
"compilerOptions": {
"rootDir": "src",
"outDir": "dist",
"emitDeclarationOnly": true,
"composite": true,
"types": ["node", "@alwatr/nano-build", "@alwatr/type-helper"]
},
"include": ["src/**/*.ts"],
"references": [{"path": "../types"}, {"path": "../helper"}]
}
1 change: 1 addition & 0 deletions packages/nitrobase/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@
},
"dependencies": {
"@alwatr/nanolib": "^5.2.1",
"@alwatr/nitrobase-client": "workspace:^",
"@alwatr/nitrobase-engine": "workspace:^",
"@alwatr/nitrobase-helper": "workspace:^",
"@alwatr/nitrobase-reference": "workspace:^",
Expand Down
1 change: 1 addition & 0 deletions packages/nitrobase/src/client.ts
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
export * from '@alwatr/nitrobase-helper';
export * from '@alwatr/nitrobase-types';
export * from '@alwatr/nitrobase-client';
1 change: 1 addition & 0 deletions packages/nitrobase/src/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,6 @@ export * from '@alwatr/nitrobase-reference';
export * from '@alwatr/nitrobase-helper';
export * from '@alwatr/nitrobase-types';
export * from '@alwatr/nitrobase-user-management';
export * from '@alwatr/nitrobase-client';

__dev_mode__: packageTracer.add(__package_name__, __package_version__);
3 changes: 1 addition & 2 deletions packages/user-management/package.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"name": "@alwatr/nitrobase-user-management",
"version": "7.4.0",
"description": "",
"description": "User management module for Nitrobase, providing user creation, authentication, and data management capabilities.",
"author": "S. Ali Mihandoost <ali.mihandoost@gmail.com>",
"keywords": [
"user",
Expand Down Expand Up @@ -64,7 +64,6 @@
"dependencies": {
"@alwatr/nanolib": "^5.2.1",
"@alwatr/nitrobase-engine": "workspace:^",
"@alwatr/nitrobase-reference": "workspace:^",
"@alwatr/nitrobase-types": "workspace:^"
},
"devDependencies": {
Expand Down
17 changes: 17 additions & 0 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,22 @@ __metadata:
languageName: node
linkType: hard

"@alwatr/nitrobase-client@workspace:^, @alwatr/nitrobase-client@workspace:packages/client":
version: 0.0.0-use.local
resolution: "@alwatr/nitrobase-client@workspace:packages/client"
dependencies:
"@alwatr/nano-build": "npm:^5.0.0"
"@alwatr/nanolib": "npm:^5.2.1"
"@alwatr/nitrobase-helper": "workspace:^"
"@alwatr/nitrobase-types": "workspace:^"
"@alwatr/prettier-config": "npm:^5.0.0"
"@alwatr/tsconfig-base": "npm:^5.0.0"
"@alwatr/type-helper": "npm:^5.0.0"
"@types/node": "npm:^22.9.0"
typescript: "npm:^5.6.3"
languageName: unknown
linkType: soft

"@alwatr/nitrobase-engine@workspace:^, @alwatr/nitrobase-engine@workspace:packages/engine":
version: 0.0.0-use.local
resolution: "@alwatr/nitrobase-engine@workspace:packages/engine"
Expand Down Expand Up @@ -290,6 +306,7 @@ __metadata:
dependencies:
"@alwatr/nano-build": "npm:^5.0.0"
"@alwatr/nanolib": "npm:^5.2.1"
"@alwatr/nitrobase-client": "workspace:^"
"@alwatr/nitrobase-engine": "workspace:^"
"@alwatr/nitrobase-helper": "workspace:^"
"@alwatr/nitrobase-reference": "workspace:^"
Expand Down
Loading