Home > Net >  How to pass interface to the generic?
How to pass interface to the generic?

Time:01-17

How can I pass interface as a type to generic? Generic will expand in the future. Maybe that code absolutely wrong for my problem?

This code will be duplicated in multiple files. 2 lines(without interface) vs 12. I try to pass interface but I see an error.

Expected 5 arguments, but passed 1.

helpers.ts
export const httpRequestsActions = <
  TAllData,
  TSingleData,
  TCreate,
  TEdit,
  TDelete
>() => {
  const getAllDataAction: IActionFn<TAllData> = (payload) => {
    return "data";
  };
  const getSingleDataAction: IActionFn<TSingleData> = (payload) => {
    return "data";
  };
  const createDataAction: IActionFn<TCreate> = (payload, params) => {
    return "data";
  };
  const editDataAction: IActionFn<TEdit> = (payload, params) => {
    return "data";
  };
  const deleteDataAction: IActionFn<TDelete> = (payload) => {
    return "data";
  };

  return {
    getAllDataAction,
    getSingleDataAction,
    createDataAction,
    editDataAction,
    deleteDataAction,
  };
};

==Current code==
actions.ts, sagas.ts
import {
  ICreateEmployee,
  IEditEmployee,
  IGetEmployees,
} from "interfaces/employees";

export const employeesActions = httpRequestsActions<
  IGetEmployees,
  { id: string },
  ICreateEmployee,
  IEditEmployee,
  { id: string }
>(EMPLOYEES);

==I want==
inteface.ts
export interface ITypeEmployees {
  TAllData: IGetEmployees;
  TSingle: { id: string };
  TCreate: ICreateEmployee;
  TEdit: IEditEmployee;
  TDelete: { id: string };
}

actions.ts, sagas.ts
import { ITypeEmployees } from "interfaces/employees";
export const employeesActions = httpRequestsActions<ITypeEmployees>(EMPLOYEES);

CodePudding user response:

To use a single type parameter such as in

export const employeesActions = httpRequestsActions<ITypeEmployees>(EMPLOYEES);

you will need to declare a function with only one type parameter matching that interface:

export const httpRequestsActions = <T extends {
  TAllData: unknown;
  TSingleData: unknown;
  TCreate: unknown;
  TEdit: unknown;
  TDelete: unknown;
}>(): {
  getAllDataAction: IActionFn<T["TAllData"]>;
  getSingleDataAction: IActionFn<T["TSingleData"]>;
  createDataAction: IActionFn<T["TCreate"]>;
  editDataAction: IActionFn<T["TEdit"]>;
  deleteDataAction: IActionFn<T["TDelete"]>;
} => ({
  getAllDataAction(payload) {
    return "data";
  },
  getSingleDataAction(payload) {
    return "data";
  },
  createDataAction(payload, params) {
    return "data";
  },
  editDataAction(payload, params) {
    return "data";
  },
  deleteDataAction(payload) {
    return "data";
  },
});

CodePudding user response:

So you have your types separated like so

    export const httpRequestsActions = <TAllData, TSingleData, TCreate, TEdit, TDelete>() => {
        // rest of your code
    };

and you are calling it like so:

export const employeesActions = httpRequestsActions<ITypeEmployees>(EMPLOYEES)

Because you have these TAllData, TSingleData, TCreate, TEdit, TDelete separated by commas, httpRequestsActions expects 5 types to be passed in. You are only passing in one interface ITypeEmployees. Because I don't know what your end intention is, my suggestion based on what I can see would be to do this:

    type TAllData = IGetEmployees;
    interface TSingle { id: string };
    type TCreate = ICreateEmployee;
    type TEdit = IEditEmployee;
    interface TDelete { id: string };
    
    export const employeesActions = httpRequestsActions<TAllData, TSingleData, TCreate, TEdit, TDelete>(EMPLOYEES)
  •  Tags:  
  • Related