不同面试类型下调用validateRecruiters函数及通用设计模式咨询
解决方案:根据面试类型调用不同参数的验证函数
针对不同面试类型对应验证函数参数数量不同的问题,推荐两种通用的TypeScript实现方案:
方案一:统一参数结构(对象传参)
核心思路是把所有参数封装成一个对象,通过可选属性区分不同面试类型的专属参数,既保证函数签名统一,又能清晰区分参数用途。
步骤1:定义统一参数类型
// 定义验证函数的统一参数结构 type ValidateRecruitersParams = { recruiters: THrInterviewer[]; recruit: TRecruit | THrRecruit; // HR面试专属参数,仅HR场景需要传入 hrSpecificParams?: { param3: any; param4: any; }; };
步骤2:改造处理器对象
import { getHrRecruiters, getRecruiters } from '../queue'; import { validateTechnicalInterview } from './validateTechnicalInterview'; import { matchHrRecruiters } from './matchHrRecruiters'; import { THrInterviewer, THrRecruit, TRecruit } from '../../types'; export const recruitersCategoryHandlers = { TECHNICAL_INTERVIEW: { getter: getRecruiters, setter: { validateRecruiters: ({ recruiters, recruit }: ValidateRecruitersParams) => validateTechnicalInterview(recruiters, recruit), }, }, HR_INTERVIEW: { getter: getHrRecruiters, setter: { validateRecruiters: ({ recruiters, recruit, hrSpecificParams }: ValidateRecruitersParams) => { // 强制校验HR场景的必填参数 if (!hrSpecificParams) { throw new Error("HR面试必须传入专属参数hrSpecificParams"); } return matchHrRecruiters(recruiters, recruit as THrRecruit, hrSpecificParams.param3, hrSpecificParams.param4); }, }, }, };
步骤3:调用验证函数
// 根据面试类型构造参数 const validateParams: ValidateRecruitersParams = { recruiters: /* 实际获取的面试官数组 */, recruit: /* 当前候选人对象 */, // 仅HR场景追加专属参数 ...(interviewCategory === EInterviewCategory.HR_INTERVIEW && { hrSpecificParams: { param3: /* HR专属参数3 */, param4: /* HR专属参数4 */, }, }), }; const matchedSlots = getMatchingSlots( recruitersCategoryHandlers[interviewCategory as EInterviewCategory].setter.validateRecruiters(validateParams), slotsWithEmail );
方案二:适配器模式
核心思路是给不同验证函数做一层适配,对外暴露统一的函数签名,多余参数在非HR场景直接忽略。
步骤1:定义统一函数签名
// 对外统一的验证函数签名 type ValidateRecruitersFn = ( recruiters: THrInterviewer[], recruit: TRecruit | THrRecruit, hrParam3?: any, hrParam4?: any ) => ReturnType<typeof validateTechnicalInterview | typeof matchHrRecruiters>;
步骤2:改造处理器对象
import { getHrRecruiters, getRecruiters } from '../queue'; import { validateTechnicalInterview } from './validateTechnicalInterview'; import { matchHrRecruiters } from './matchHrRecruiters'; import { THrInterviewer, THrRecruit, TRecruit } from '../../types'; export const recruitersCategoryHandlers: Record<EInterviewCategory, { getter: typeof getRecruiters | typeof getHrRecruiters; setter: { validateRecruiters: ValidateRecruitersFn; }; }> = { TECHNICAL_INTERVIEW: { getter: getRecruiters, setter: { // 忽略多余的HR参数 validateRecruiters: (recruiters, recruit) => validateTechnicalInterview(recruiters, recruit), }, }, HR_INTERVIEW: { getter: getHrRecruiters, setter: { validateRecruiters: (recruiters, recruit, param3, param4) => { if (!param3 || !param4) { throw new Error("HR面试必须传入param3和param4"); } return matchHrRecruiters(recruiters, recruit as THrRecruit, param3, param4); }, }, }, };
步骤3:调用验证函数
const matchedSlots = getMatchingSlots( recruitersCategoryHandlers[interviewCategory as EInterviewCategory].setter.validateRecruiters( recruiters, recruit, // 仅HR场景传入对应参数 interviewCategory === EInterviewCategory.HR_INTERVIEW ? param3 : undefined, interviewCategory === EInterviewCategory.HR_INTERVIEW ? param4 : undefined ), slotsWithEmail );
方案对比
- 对象传参方案:可读性强、扩展性好,后续新增参数只需修改参数对象,适合长期维护的项目。
- 适配器模式:贴近原有代码结构,改动量小,适合快速兼容现有逻辑的场景。
内容的提问来源于stack exchange,提问作者Vytautas
相关产品推荐
相关产品推荐

