igorkamyshev/farfetched

How do I get promise from the query?

falkomerr opened this issue · 3 comments

Promise can be useful to render queries in promise oriented frameworks such as svelte

Example:
image

Use case form the chat:

image

In most form management solutions, APIs outside the Effector ecosystem typically rely on promises rather than event-based APIs. I've observed this in the React ecosystem with the libraries listed below, and I believe the same holds true for Vue:

  • react-hook-form, @tanstack/react-form (@tanstack-form/core)
  • zod, including .refine for async validation
  • react-router-dom, specifically loaders for preloading route initial data
  • Notification libraries such as @mantine/notifications
  • Locally implemented libraries with promise-based APIs

To address this, I've developed an Effector operator that converts a remote operation (e.g., a query) into an Effector effect. This operator injects additional metadata into the query call parameters, requiring object constraints for these parameters.

/**
 * Converts a Farfetched Query or Mutation instance to an Effector effect.
 * @template Params - Operation parameters with Record<string, unknown> constraints.
 * @template Data - Operation success data.
 * @param operation - Farfetched Query or Mutation instance.
 * @returns An effect with parameters matching the operation's start event.
 *
 * @throws {OperationAbortError} If the operation was aborted.
 * @throws {OperationSkipError} If the operation was skipped.
 * @throws {Error} If the parameters are not an object.
 */
function toEffect<Params extends Record<string, unknown>, Data, Err>(
  operation: Query<Params, Data, Err> | Mutation<Params, Data, Err>
): Effect<Params, Data, Error>;

export class OperationSkipError extends Error {}
export class OperationAbortError extends Error {}

I have covered operator with unit tests to check

  • work correctness with plain query success, fail, skip, abort cases
  • params object constraints
  • work correctness with enabled option
  • work correctness with concurrency operator and it's strategies
  • work correct with cache adapter

It is working good and cover my cases at the moment, but have such operator in the farfetched will be very helpful for others + will cover operations with void params

implementation