Skip to content

Instantly share code, notes, and snippets.

@fostyfost
Created April 20, 2022 19:10
Show Gist options
  • Save fostyfost/712f7d4bd3a57655fa37e1a9a8c9ba14 to your computer and use it in GitHub Desktop.
Save fostyfost/712f7d4bd3a57655fa37e1a9a8c9ba14 to your computer and use it in GitHub Desktop.
Magic steps
import { FlightSearchStep, getNextStep, getPrevStep, SeatType } from './index'
const VALID_STEPS_MAP: {
[key: string]: {
[key: string]: {
prev: FlightSearchStep | undefined
next: FlightSearchStep | undefined
}
}
} = {
[FlightSearchStep.POINTS]: {
[SeatType.CHARTER]: {
prev: undefined,
next: FlightSearchStep.PLANE_CLASS,
},
[SeatType.SEATS]: {
prev: undefined,
next: FlightSearchStep.DATES,
},
},
[FlightSearchStep.PLANE_CLASS]: {
[SeatType.CHARTER]: {
prev: FlightSearchStep.POINTS,
next: FlightSearchStep.DATES,
},
[SeatType.SEATS]: {
prev: FlightSearchStep.POINTS,
next: FlightSearchStep.DATES,
},
},
[FlightSearchStep.DATES]: {
[SeatType.CHARTER]: {
prev: FlightSearchStep.PLANE_CLASS,
next: FlightSearchStep.RESULTS,
},
[SeatType.SEATS]: {
prev: FlightSearchStep.POINTS,
next: FlightSearchStep.RESULTS,
},
},
[FlightSearchStep.RESULTS]: {
[SeatType.CHARTER]: {
prev: FlightSearchStep.DATES,
next: FlightSearchStep.RESULTS_ITEM,
},
[SeatType.SEATS]: {
prev: FlightSearchStep.DATES,
next: FlightSearchStep.RESULTS_ITEM,
},
},
[FlightSearchStep.RESULTS_ITEM]: {
[SeatType.CHARTER]: {
prev: FlightSearchStep.RESULTS,
next: undefined,
},
[SeatType.SEATS]: {
prev: FlightSearchStep.RESULTS,
next: undefined,
},
},
}
const getExpectedStep = (currentStep: any, seatType: any, direction: 'prev' | 'next') => {
return VALID_STEPS_MAP[currentStep]?.[seatType]?.[direction]
}
test('`getPrevStep` should work correctly', () => {
expect(getPrevStep('', '')).toBeUndefined()
expect(getPrevStep('4', '1')).toBe(FlightSearchStep.DATES)
expect(getPrevStep(FlightSearchStep.RESULTS, '1')).toBe(FlightSearchStep.DATES)
expect(getPrevStep('4', SeatType.CHARTER)).toBe(FlightSearchStep.DATES)
Object.values(SeatType).forEach(seatType => {
Object.values(FlightSearchStep).forEach(currentStep => {
expect(getPrevStep(currentStep, seatType)).toBe(getExpectedStep(currentStep, seatType, 'prev'))
})
})
})
test('`getNextStep` should work correctly', () => {
expect(getNextStep('', '')).toBeUndefined()
expect(getNextStep('4', '1')).toBe(FlightSearchStep.RESULTS_ITEM)
expect(getNextStep(FlightSearchStep.RESULTS, '1')).toBe(FlightSearchStep.RESULTS_ITEM)
expect(getNextStep('4', SeatType.CHARTER)).toBe(FlightSearchStep.RESULTS_ITEM)
Object.values(SeatType).forEach(seatType => {
Object.values(FlightSearchStep).forEach(currentStep => {
expect(getNextStep(currentStep, seatType)).toBe(getExpectedStep(currentStep, seatType, 'next'))
})
})
})
export enum FlightSearchStep {
POINTS = 1,
PLANE_CLASS = 2,
DATES = 3,
RESULTS = 4,
RESULTS_ITEM = 5,
}
export enum SeatType {
CHARTER = 1,
SEATS = 2
}
type StepsMap = {
[key: string]: {
[key: string]: {
prev: number | undefined
next: number | undefined
}
}
}
const getValue = (valueIndex: number): FlightSearchStep | undefined => {
const key = FlightSearchStep[valueIndex] as unknown as number
return FlightSearchStep[key] as unknown as FlightSearchStep | undefined
}
const STEPS_MAP = (Object.entries(FlightSearchStep) as [string, string | number][])
.reduce<StepsMap>((acc, [key, valueIndex]) => {
if (typeof valueIndex === 'number') {
const prev = getValue(valueIndex - 1)
const next = getValue(valueIndex + 1)
acc[FlightSearchStep[key as unknown as FlightSearchStep]] = {
[SeatType.CHARTER]: { prev, next },
[SeatType.SEATS]: {
prev: key === FlightSearchStep[FlightSearchStep.DATES] ? FlightSearchStep.POINTS : prev,
next: key === FlightSearchStep[FlightSearchStep.POINTS] ? FlightSearchStep.DATES : next,
},
}
}
return acc
}, {})
export const getPrevStep = (
currentStep: string | FlightSearchStep,
seatType: string | SeatType,
): FlightSearchStep | undefined => {
return STEPS_MAP[currentStep]?.[seatType]?.prev
}
export const getNextStep = (
currentStep: string | FlightSearchStep,
seatType: string | SeatType,
): FlightSearchStep | undefined => {
return STEPS_MAP[currentStep]?.[seatType]?.next
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment