@diphyx/harlemify 1.0.4 → 3.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -2,25 +2,22 @@
2
2
 
3
3
  > Schema-driven state management for Nuxt powered by [Harlem](https://harlemjs.com/)
4
4
 
5
- ![Harlemify](https://raw.githubusercontent.com/diphyx/harlemify/main/docs/_media/icon.svg)
6
-
7
- Define your data schema once with Zod, and Harlemify handles the rest: type-safe API calls, reactive state, request monitoring, and automatic memory management. Your schema becomes the single source of truth for types, validation, and API payloads.
8
-
9
5
  ## Features
10
6
 
11
7
  - **Schema-Driven** - Zod schema defines types, validation, and API payloads
12
- - **Automatic API Client** - Built-in HTTP client with runtime configuration
13
- - **Reactive Memory** - Unit and collection caching with Vue reactivity
14
- - **Request Monitoring** - Track pending, success, and failed states
15
- - **SSR Support** - Server-side rendering via Harlem SSR plugin
8
+ - **Free-form Actions** - Define any action with custom naming
9
+ - **Chainable Builders** - Fluent `Endpoint` and `Memory` APIs
10
+ - **Function-based Monitor** - Track status with `pending()`, `success()`, `failed()`, `idle()`
11
+ - **Custom Adapters** - Override HTTP at module, store, endpoint, or call-time
12
+ - **SSR Support** - Server-side rendering with automatic hydration
16
13
 
17
- ## Installation
14
+ ## Install
18
15
 
19
16
  ```bash
20
17
  npm install @diphyx/harlemify
21
18
  ```
22
19
 
23
- ## Quick Start
20
+ ## Setup
24
21
 
25
22
  ```typescript
26
23
  // nuxt.config.ts
@@ -28,46 +25,61 @@ export default defineNuxtConfig({
28
25
  modules: ["@diphyx/harlemify"],
29
26
  harlemify: {
30
27
  api: {
31
- url: "https://api.example.com",
28
+ adapter: {
29
+ baseURL: "https://api.example.com",
30
+ },
32
31
  },
33
32
  },
34
33
  });
35
34
  ```
36
35
 
36
+ ## Usage
37
+
37
38
  ```typescript
38
39
  // stores/user.ts
39
40
  import { z } from "zod";
40
- import { createStore, Endpoint, EndpointMethod } from "@diphyx/harlemify";
41
41
 
42
- const UserSchema = z.object({
42
+ enum UserAction {
43
+ LIST = "list",
44
+ CREATE = "create",
45
+ }
46
+
47
+ const userSchema = z.object({
43
48
  id: z.number().meta({ indicator: true }),
44
- name: z.string().meta({
45
- methods: [EndpointMethod.POST, EndpointMethod.PATCH],
46
- }),
49
+ name: z.string().meta({ actions: [UserAction.CREATE] }),
50
+ email: z.string().meta({ actions: [UserAction.CREATE] }),
47
51
  });
48
52
 
49
- export type User = z.infer<typeof UserSchema>;
50
-
51
- export const userStore = createStore("user", UserSchema, {
52
- [Endpoint.GET_UNITS]: { method: EndpointMethod.GET, url: "/users" },
53
- [Endpoint.POST_UNITS]: { method: EndpointMethod.POST, url: "/users" },
54
- [Endpoint.PATCH_UNITS]: { method: EndpointMethod.PATCH, url: (p) => `/users/${p.id}` },
55
- [Endpoint.DELETE_UNITS]: { method: EndpointMethod.DELETE, url: (p) => `/users/${p.id}` },
53
+ export const userStore = createStore("user", userSchema, {
54
+ [UserAction.LIST]: {
55
+ endpoint: Endpoint.get("/users"),
56
+ memory: Memory.units(),
57
+ },
58
+ [UserAction.CREATE]: {
59
+ endpoint: Endpoint.post("/users"),
60
+ memory: Memory.units().add(),
61
+ },
56
62
  });
57
63
  ```
58
64
 
59
- ## Why Harlemify?
65
+ ```vue
66
+ <script setup>
67
+ const { users, listUser, userMonitor } = useStoreAlias(userStore);
60
68
 
61
- | | |
62
- | --------------- | ------------------------------------------------- |
63
- | **Type-Safe** | Full TypeScript support with Zod schema inference |
64
- | **Declarative** | Define schema once, derive everything else |
65
- | **Reactive** | Powered by Vue's reactivity through Harlem |
66
- | **Simple** | Minimal boilerplate, maximum productivity |
69
+ await listUser();
70
+ </script>
71
+
72
+ <template>
73
+ <div v-if="userMonitor.list.pending()">Loading...</div>
74
+ <ul v-else>
75
+ <li v-for="user in users" :key="user.id">{{ user.name }}</li>
76
+ </ul>
77
+ </template>
78
+ ```
67
79
 
68
80
  ## Documentation
69
81
 
70
- Full documentation available at [https://diphyx.github.io/harlemify/](https://diphyx.github.io/harlemify/)
82
+ [https://diphyx.github.io/harlemify/](https://diphyx.github.io/harlemify/)
71
83
 
72
84
  ## License
73
85
 
package/dist/module.d.mts CHANGED
@@ -1,9 +1,19 @@
1
1
  import * as _nuxt_schema from '@nuxt/schema';
2
2
 
3
+ interface ApiFetchAdapterOptions {
4
+ baseURL?: string;
5
+ timeout?: number;
6
+ retry?: number | false;
7
+ retryDelay?: number;
8
+ retryStatusCodes?: number[];
9
+ responseType?: "json" | "text" | "blob" | "arrayBuffer";
10
+ }
11
+
3
12
  type SharedConfig = {
4
13
  api?: {
5
- url?: string;
6
- timeout?: number;
14
+ headers?: Record<string, string>;
15
+ query?: Record<string, unknown>;
16
+ adapter?: ApiFetchAdapterOptions;
7
17
  };
8
18
  };
9
19
 
package/dist/module.d.ts CHANGED
@@ -1,9 +1,19 @@
1
1
  import * as _nuxt_schema from '@nuxt/schema';
2
2
 
3
+ interface ApiFetchAdapterOptions {
4
+ baseURL?: string;
5
+ timeout?: number;
6
+ retry?: number | false;
7
+ retryDelay?: number;
8
+ retryStatusCodes?: number[];
9
+ responseType?: "json" | "text" | "blob" | "arrayBuffer";
10
+ }
11
+
3
12
  type SharedConfig = {
4
13
  api?: {
5
- url?: string;
6
- timeout?: number;
14
+ headers?: Record<string, string>;
15
+ query?: Record<string, unknown>;
16
+ adapter?: ApiFetchAdapterOptions;
7
17
  };
8
18
  };
9
19
 
package/dist/module.json CHANGED
@@ -4,7 +4,7 @@
4
4
  "compatibility": {
5
5
  "nuxt": ">=3.0.0 || >=4.0.0"
6
6
  },
7
- "version": "1.0.4",
7
+ "version": "3.0.0",
8
8
  "builder": {
9
9
  "@nuxt/module-builder": "0.8.4",
10
10
  "unbuild": "unknown"
package/dist/module.mjs CHANGED
@@ -9,7 +9,11 @@ const module = defineNuxtModule({
9
9
  }
10
10
  },
11
11
  defaults: {
12
- api: {}
12
+ api: {
13
+ headers: {},
14
+ query: {},
15
+ adapter: {}
16
+ }
13
17
  },
14
18
  setup(options, nuxt) {
15
19
  const { resolve } = createResolver(import.meta.url);
@@ -1,30 +1,22 @@
1
1
  import type { ComputedRef } from "vue";
2
- import { EndpointMethod } from "../utils/endpoint.js";
3
- import type { Store } from "../core/store.js";
4
- import type { Pluralize, Capitalize } from "../utils/transform.js";
5
- import type { EndpointStatusFlag } from "../utils/endpoint.js";
6
- type Indicator<T, I extends keyof T> = Required<Pick<T, I>>;
7
- type PartialWithIndicator<T, I extends keyof T> = Indicator<T, I> & Partial<T>;
2
+ import type { ActionFunction, ActionStatus, ActionsConfig, Store, StoreMemory } from "../core/store.js";
3
+ import type { Capitalize, Pluralize } from "../utils/transform.js";
8
4
  type MemoryState<E extends string, T> = {
9
5
  [P in E]: ComputedRef<T | null>;
10
6
  } & {
11
7
  [P in Pluralize<E>]: ComputedRef<T[]>;
12
8
  };
13
- type MemoryAction<A extends string, E extends string, U> = {
14
- [K in `${A}${Capitalize<E>}`]: (unit: U) => void;
15
- } & {
16
- [K in `${A}${Capitalize<Pluralize<E>>}`]: (units: U[]) => void;
9
+ type AliasActions<E extends string, A extends ActionsConfig<S>, S> = {
10
+ [K in keyof A as `${K & string}${Capitalize<E>}`]: ActionFunction<S>;
17
11
  };
18
- type EndpointAction<E extends string, T> = {
19
- [M in EndpointMethod as `${M}${Capitalize<E>}`]: (unit?: Partial<T>) => Promise<T>;
20
- } & {
21
- [M in EndpointMethod as `${M}${Capitalize<Pluralize<E>>}`]: (units?: Partial<T>[]) => Promise<T[]>;
12
+ type AliasMemory<E extends string, S, I extends keyof S> = {
13
+ [K in `${E}Memory`]: StoreMemory<S, I>;
22
14
  };
23
- type EndpointMonitor<E extends string> = {
24
- [M in EndpointMethod as `${M}${Capitalize<E>}${EndpointStatusFlag}`]: ComputedRef<boolean>;
25
- } & {
26
- [M in EndpointMethod as `${M}${Capitalize<Pluralize<E>>}${EndpointStatusFlag}`]: ComputedRef<boolean>;
15
+ type AliasMonitor<E extends string, A extends ActionsConfig<any>> = {
16
+ [K in `${E}Monitor`]: {
17
+ [ActionName in keyof A]: ActionStatus;
18
+ };
27
19
  };
28
- type StoreAlias<E extends string, T, I extends keyof T = keyof T> = MemoryState<E, T> & MemoryAction<"set", E, T | null> & MemoryAction<"edit", E, PartialWithIndicator<T, I>> & MemoryAction<"drop", E, PartialWithIndicator<T, I>> & EndpointAction<E, T> & EndpointMonitor<E>;
29
- export declare function useStoreAlias<E extends string, T, I extends keyof T = keyof T>(store: Store<E, T, I>): StoreAlias<E, T, I>;
20
+ export type StoreAlias<E extends string, S, I extends keyof S, A extends ActionsConfig<S>> = MemoryState<E, S> & AliasActions<E, A, S> & AliasMemory<E, S, I> & AliasMonitor<E, A>;
21
+ export declare function useStoreAlias<E extends string, S, I extends keyof S, A extends ActionsConfig<S>>(store: Store<E, S, I, A>): StoreAlias<E, S, I, A>;
30
22
  export {};
@@ -1,25 +1,14 @@
1
1
  import { capitalize } from "../utils/transform.js";
2
- import { EndpointMethod, EndpointStatus, makeEndpointStatusFlag } from "../utils/endpoint.js";
3
- import { StoreMemoryAction } from "../core/store.js";
4
2
  export function useStoreAlias(store) {
5
- const capitalizedUnit = capitalize(store.alias.unit);
6
- const capitalizedUnits = capitalize(store.alias.units);
3
+ const capitalizedEntity = capitalize(store.alias.unit);
7
4
  const output = {
8
5
  [store.alias.unit]: store.unit,
9
- [store.alias.units]: store.units
6
+ [store.alias.units]: store.units,
7
+ [`${store.alias.unit}Memory`]: store.memory,
8
+ [`${store.alias.unit}Monitor`]: store.monitor
10
9
  };
11
- for (const action of Object.values(StoreMemoryAction)) {
12
- output[`${action}${capitalizedUnit}`] = store.memory[`${action}Unit`];
13
- output[`${action}${capitalizedUnits}`] = store.memory[`${action}Units`];
14
- }
15
- for (const method of Object.values(EndpointMethod)) {
16
- output[`${method}${capitalizedUnit}`] = store.endpoint[`${method}Unit`];
17
- output[`${method}${capitalizedUnits}`] = store.endpoint[`${method}Units`];
18
- for (const status of Object.values(EndpointStatus)) {
19
- const statusFlag = makeEndpointStatusFlag(status);
20
- output[`${method}${capitalizedUnit}${statusFlag}`] = store.monitor[`${method}Unit${statusFlag}`];
21
- output[`${method}${capitalizedUnits}${statusFlag}`] = store.monitor[`${method}Units${statusFlag}`];
22
- }
10
+ for (const actionName in store.action) {
11
+ output[`${actionName}${capitalizedEntity}`] = store.action[actionName];
23
12
  }
24
13
  return output;
25
14
  }
@@ -1,15 +1,6 @@
1
1
  import type { MaybeRefOrGetter } from "vue";
2
2
  import { EndpointMethod } from "../utils/endpoint.js";
3
- export declare enum ApiResponseType {
4
- JSON = "json",
5
- TEXT = "text",
6
- BLOB = "blob",
7
- ARRAY_BUFFER = "arrayBuffer"
8
- }
9
- export declare enum ApiErrorSource {
10
- REQUEST = "request",
11
- RESPONSE = "response"
12
- }
3
+ import type { ApiAdapter } from "../utils/adapter.js";
13
4
  export type ApiRequestHeader = MaybeRefOrGetter<Record<string, unknown>>;
14
5
  export type ApiRequestQuery = MaybeRefOrGetter<Record<string, unknown>>;
15
6
  export type ApiRequestBody = MaybeRefOrGetter<string | number | ArrayBuffer | FormData | Blob | Record<string, any>>;
@@ -18,43 +9,29 @@ export interface ApiRequestOptions<A extends EndpointMethod = EndpointMethod, H
18
9
  headers?: H;
19
10
  query?: Q;
20
11
  body?: B;
21
- timeout?: number;
22
- responseType?: ApiResponseType;
23
- retry?: number | false;
24
- retryDelay?: number;
25
- retryStatusCodes?: number[];
26
12
  signal?: AbortSignal;
27
13
  }
28
14
  export interface ApiOptions {
29
- url?: string;
30
15
  headers?: ApiRequestHeader;
31
16
  query?: ApiRequestQuery;
32
- timeout?: number;
17
+ adapter?: ApiAdapter<any>;
33
18
  }
34
19
  export type EndpointMethodOptions<A extends EndpointMethod, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery, B extends ApiRequestBody = ApiRequestBody> = Omit<ApiRequestOptions<A, H, Q, B>, "action">;
35
- export interface ApiErrorOptions {
36
- source: ApiErrorSource;
37
- method: string;
38
- url: string;
39
- message?: string;
40
- }
41
- export declare class ApiError extends Error {
42
- source: ApiErrorSource;
43
- method: string;
44
- url: string;
45
- constructor(options: ApiErrorOptions);
46
- }
47
- export declare class ApiRequestError extends ApiError {
48
- constructor(options: Omit<ApiErrorOptions, "source">);
49
- }
50
- export declare class ApiResponseError extends ApiError {
51
- constructor(options: Omit<ApiErrorOptions, "source">);
52
- }
53
20
  export interface Api {
54
- get: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery>(url: string, options?: EndpointMethodOptions<EndpointMethod.GET, H, Q, never>) => Promise<T>;
55
- post: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery, B extends ApiRequestBody = ApiRequestBody>(url: string, options?: EndpointMethodOptions<EndpointMethod.POST, H, Q, B>) => Promise<T>;
56
- put: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery, B extends ApiRequestBody = ApiRequestBody>(url: string, options?: EndpointMethodOptions<EndpointMethod.PUT, H, Q, B>) => Promise<T>;
57
- patch: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery, B extends ApiRequestBody = ApiRequestBody>(url: string, options?: EndpointMethodOptions<EndpointMethod.PATCH, H, Q, B>) => Promise<T>;
58
- del: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery>(url: string, options?: EndpointMethodOptions<EndpointMethod.DELETE, H, Q, never>) => Promise<T>;
21
+ get: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery>(url: string, options?: EndpointMethodOptions<EndpointMethod.GET, H, Q, never> & {
22
+ adapter?: ApiAdapter<T>;
23
+ }) => Promise<T>;
24
+ post: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery, B extends ApiRequestBody = ApiRequestBody>(url: string, options?: EndpointMethodOptions<EndpointMethod.POST, H, Q, B> & {
25
+ adapter?: ApiAdapter<T>;
26
+ }) => Promise<T>;
27
+ put: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery, B extends ApiRequestBody = ApiRequestBody>(url: string, options?: EndpointMethodOptions<EndpointMethod.PUT, H, Q, B> & {
28
+ adapter?: ApiAdapter<T>;
29
+ }) => Promise<T>;
30
+ patch: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery, B extends ApiRequestBody = ApiRequestBody>(url: string, options?: EndpointMethodOptions<EndpointMethod.PATCH, H, Q, B> & {
31
+ adapter?: ApiAdapter<T>;
32
+ }) => Promise<T>;
33
+ del: <T, H extends ApiRequestHeader = ApiRequestHeader, Q extends ApiRequestQuery = ApiRequestQuery>(url: string, options?: EndpointMethodOptions<EndpointMethod.DELETE, H, Q, never> & {
34
+ adapter?: ApiAdapter<T>;
35
+ }) => Promise<T>;
59
36
  }
60
37
  export declare function createApi(options?: ApiOptions): Api;
@@ -1,80 +1,20 @@
1
1
  import { toValue } from "vue";
2
+ import { defineApiAdapter } from "../utils/adapter.js";
2
3
  import { EndpointMethod } from "../utils/endpoint.js";
3
- export var ApiResponseType = /* @__PURE__ */ ((ApiResponseType2) => {
4
- ApiResponseType2["JSON"] = "json";
5
- ApiResponseType2["TEXT"] = "text";
6
- ApiResponseType2["BLOB"] = "blob";
7
- ApiResponseType2["ARRAY_BUFFER"] = "arrayBuffer";
8
- return ApiResponseType2;
9
- })(ApiResponseType || {});
10
- export var ApiErrorSource = /* @__PURE__ */ ((ApiErrorSource2) => {
11
- ApiErrorSource2["REQUEST"] = "request";
12
- ApiErrorSource2["RESPONSE"] = "response";
13
- return ApiErrorSource2;
14
- })(ApiErrorSource || {});
15
- export class ApiError extends Error {
16
- source;
17
- method;
18
- url;
19
- constructor(options) {
20
- super(options.message ?? "Unknown error");
21
- this.name = "ApiError";
22
- this.source = options.source;
23
- this.method = options.method;
24
- this.url = options.url;
25
- }
26
- }
27
- export class ApiRequestError extends ApiError {
28
- constructor(options) {
29
- super({
30
- ...options,
31
- source: "request" /* REQUEST */
32
- });
33
- }
34
- }
35
- export class ApiResponseError extends ApiError {
36
- constructor(options) {
37
- super({
38
- ...options,
39
- source: "response" /* RESPONSE */
40
- });
41
- }
42
- }
43
4
  export function createApi(options) {
5
+ const defaultAdapter = options?.adapter ?? defineApiAdapter();
44
6
  async function request(url, requestOptions) {
45
- return $fetch(url, {
46
- baseURL: options?.url,
7
+ const adapter = requestOptions?.adapter ?? defaultAdapter;
8
+ const adapterRequest = {
47
9
  method: requestOptions?.action ?? EndpointMethod.GET,
48
- headers: {
49
- ...toValue(options?.headers),
50
- ...toValue(requestOptions?.headers)
51
- },
52
- query: {
53
- ...toValue(requestOptions?.query),
54
- ...toValue(options?.query)
55
- },
10
+ url,
56
11
  body: toValue(requestOptions?.body),
57
- timeout: requestOptions?.timeout ?? options?.timeout,
58
- responseType: requestOptions?.responseType,
59
- retry: requestOptions?.retry,
60
- retryDelay: requestOptions?.retryDelay,
61
- retryStatusCodes: requestOptions?.retryStatusCodes,
62
- signal: requestOptions?.signal,
63
- onRequestError({ request: request2, options: options2, error }) {
64
- throw new ApiRequestError({
65
- method: options2.method,
66
- url: request2.toString(),
67
- message: error?.message
68
- });
69
- },
70
- onResponseError({ request: request2, options: options2, error }) {
71
- throw new ApiResponseError({
72
- method: options2.method,
73
- url: request2.toString(),
74
- message: error?.message
75
- });
76
- }
77
- });
12
+ query: Object.assign({}, toValue(options?.query), toValue(requestOptions?.query)),
13
+ headers: Object.assign({}, toValue(options?.headers), toValue(requestOptions?.headers)),
14
+ signal: requestOptions?.signal
15
+ };
16
+ const response = await adapter(adapterRequest);
17
+ return response.data;
78
18
  }
79
19
  async function get(url, options2) {
80
20
  return request(url, {
@@ -1,74 +1,69 @@
1
1
  import type { z } from "zod";
2
2
  import type { ComputedRef } from "vue";
3
3
  import type { Extension, BaseState } from "@harlem/core";
4
- import { Endpoint, EndpointStatus } from "../utils/endpoint.js";
5
- import type { EndpointMethodOptions, ApiOptions } from "./api.js";
6
- import type { EndpointDefinition, EndpointStatusName } from "../utils/endpoint.js";
4
+ import { EndpointStatus } from "../utils/endpoint.js";
5
+ import type { ApiAdapter } from "../utils/adapter.js";
7
6
  import type { Pluralize } from "../utils/transform.js";
8
- export declare enum StoreMemoryAction {
9
- SET = "set",
10
- EDIT = "edit",
11
- DROP = "drop"
7
+ import type { EndpointDefinition } from "../utils/endpoint.js";
8
+ import type { MemoryDefinition } from "../utils/memory.js";
9
+ export interface ActionDefinition<S = Record<string, unknown>> {
10
+ endpoint: EndpointDefinition<S>;
11
+ memory?: MemoryDefinition;
12
12
  }
13
- export declare enum StoreMemoryPosition {
14
- FIRST = "first",
15
- LAST = "last"
13
+ export interface ActionOptions {
14
+ query?: Record<string, unknown>;
15
+ headers?: Record<string, string>;
16
+ body?: unknown;
17
+ signal?: AbortSignal;
18
+ validate?: boolean;
19
+ adapter?: ApiAdapter<any>;
20
+ }
21
+ export interface ActionStatus {
22
+ current: () => EndpointStatus;
23
+ pending: () => boolean;
24
+ success: () => boolean;
25
+ failed: () => boolean;
26
+ idle: () => boolean;
16
27
  }
17
28
  export interface StoreHooks {
18
29
  before?: () => Promise<void> | void;
19
30
  after?: (error?: Error) => Promise<void> | void;
20
31
  }
21
- export interface StoreOptions {
22
- api?: ApiOptions;
32
+ export interface StoreOptions<_A extends ActionsConfig<any> = ActionsConfig<any>> {
33
+ adapter?: ApiAdapter<any>;
23
34
  indicator?: string;
24
35
  hooks?: StoreHooks;
25
36
  extensions?: Extension<BaseState>[];
26
37
  }
27
- type Indicator<T, I extends keyof T> = Required<Pick<T, I>>;
28
- type WithIndicator<T, I extends keyof T> = Indicator<T, I> & T;
29
- type PartialWithIndicator<T, I extends keyof T> = Indicator<T, I> & Partial<T>;
30
- type StoreEndpointReadOptions = Omit<EndpointMethodOptions<any>, "body">;
31
- type StoreEndpointWriteOptions = EndpointMethodOptions<any> & {
32
- validate?: boolean;
38
+ export type ActionsConfig<S = Record<string, unknown>> = Record<string, ActionDefinition<S>>;
39
+ export type ActionFunction<S> = (params?: Partial<S>, options?: ActionOptions) => Promise<S | S[] | boolean>;
40
+ export type StoreActions<A extends ActionsConfig<S>, S> = {
41
+ [K in keyof A]: ActionFunction<S>;
33
42
  };
34
- type StoreEndpointWriteMultipleOptions = StoreEndpointWriteOptions & {
35
- position?: StoreMemoryPosition;
43
+ export type StoreMonitor<A extends ActionsConfig<any>> = {
44
+ [K in keyof A]: ActionStatus;
36
45
  };
37
- type StoreMemory<T = unknown, I extends keyof T = keyof T> = {
38
- setUnit: (unit: T | null) => void;
39
- setUnits: (units: T[]) => void;
40
- editUnit: (unit: PartialWithIndicator<T, I>) => void;
41
- editUnits: (units: PartialWithIndicator<T, I>[]) => void;
42
- dropUnit: (unit: PartialWithIndicator<T, I>) => void;
43
- dropUnits: (units: PartialWithIndicator<T, I>[]) => void;
46
+ export type StoreMemory<T, I extends keyof T> = {
47
+ set: (data: T | T[] | null) => void;
48
+ edit: (data: PartialWithIndicator<T, I> | PartialWithIndicator<T, I>[], options?: {
49
+ deep?: boolean;
50
+ }) => void;
51
+ drop: (data: PartialWithIndicator<T, I> | PartialWithIndicator<T, I>[]) => void;
44
52
  };
45
- type StoreEndpoint<T = unknown, I extends keyof T = keyof T> = {
46
- getUnit: (unit?: PartialWithIndicator<T, I>, options?: StoreEndpointReadOptions) => Promise<T>;
47
- getUnits: (options?: StoreEndpointReadOptions) => Promise<T[]>;
48
- postUnit: (unit: WithIndicator<T, I>, options?: StoreEndpointWriteOptions) => Promise<T>;
49
- postUnits: (units: WithIndicator<T, I>[], options?: StoreEndpointWriteMultipleOptions) => Promise<T[]>;
50
- putUnit: (unit: WithIndicator<T, I>, options?: StoreEndpointWriteOptions) => Promise<T>;
51
- putUnits: (units: WithIndicator<T, I>[], options?: StoreEndpointWriteOptions) => Promise<T[]>;
52
- patchUnit: (unit: PartialWithIndicator<T, I>, options?: StoreEndpointWriteOptions) => Promise<Partial<T>>;
53
- patchUnits: (units: PartialWithIndicator<T, I>[], options?: StoreEndpointWriteOptions) => Promise<Partial<T>[]>;
54
- deleteUnit: (unit: PartialWithIndicator<T, I>, options?: StoreEndpointReadOptions) => Promise<boolean>;
55
- deleteUnits: (units: PartialWithIndicator<T, I>[], options?: StoreEndpointReadOptions) => Promise<boolean>;
56
- };
57
- type StoreMonitor = {
58
- [K in Endpoint as EndpointStatusName<K, EndpointStatus>]: ComputedRef<boolean>;
59
- };
60
- export type Store<E extends string = string, T = unknown, I extends keyof T = keyof T> = {
53
+ export type Store<E extends string = string, S = unknown, I extends keyof S = keyof S, A extends ActionsConfig<S> = ActionsConfig<S>> = {
61
54
  store: any;
62
55
  alias: {
63
56
  unit: E;
64
57
  units: Pluralize<E>;
65
58
  };
66
59
  indicator: I;
67
- unit: ComputedRef<T | null>;
68
- units: ComputedRef<T[]>;
69
- memory: StoreMemory<T, I>;
70
- endpoint: StoreEndpoint<T, I>;
71
- monitor: StoreMonitor;
60
+ unit: ComputedRef<S | null>;
61
+ units: ComputedRef<S[]>;
62
+ action: StoreActions<A, S>;
63
+ memory: StoreMemory<S, I>;
64
+ monitor: StoreMonitor<A>;
72
65
  };
73
- export declare function createStore<E extends string, T extends z.ZodRawShape, S extends z.infer<z.ZodObject<T>> = z.infer<z.ZodObject<T>>, I extends keyof S = "id" & keyof S>(entity: E, schema: z.ZodObject<T>, endpoints?: Partial<Record<Endpoint, EndpointDefinition<Partial<S>>>>, options?: StoreOptions): Store<E, S, I>;
66
+ type Indicator<T, I extends keyof T> = Required<Pick<T, I>>;
67
+ type PartialWithIndicator<T, I extends keyof T> = Indicator<T, I> & Partial<T>;
68
+ export declare function createStore<E extends string, T extends z.ZodRawShape, A extends ActionsConfig<z.infer<z.ZodObject<T>>>, S extends z.infer<z.ZodObject<T>> = z.infer<z.ZodObject<T>>, I extends keyof S = "id" & keyof S>(entity: E, schema: z.ZodObject<T>, actions: A, options?: StoreOptions<A>): Store<E, S, I, A>;
74
69
  export {};