Merged in fix/booking-flow-eslint-fix (pull request #3342)

fix: Upgrade booking-flow eslint config

* Upgrade booking-flow eslint config


Approved-by: Bianca Widstam
This commit is contained in:
Anton Gunnarsson
2025-12-12 11:40:45 +00:00
parent 92391fdbd7
commit 3e3b15940f
23 changed files with 61 additions and 64 deletions

View File

@@ -1,50 +1,30 @@
import path from "node:path"
import { fileURLToPath } from "node:url"
import { FlatCompat } from "@eslint/eslintrc"
import js from "@eslint/js"
import typescriptEslint from "@typescript-eslint/eslint-plugin"
import tsParser from "@typescript-eslint/parser"
import { defineConfig } from "eslint/config"
import { defineConfig, globalIgnores } from "eslint/config"
import nextVitals from "eslint-config-next/core-web-vitals"
import nextTs from "eslint-config-next/typescript"
import formatjs from "eslint-plugin-formatjs"
import simpleImportSort from "eslint-plugin-simple-import-sort"
const compat = new FlatCompat({
recommendedConfig: js.configs.recommended,
allConfig: js.configs.all,
})
const packageDir = path.dirname(fileURLToPath(import.meta.url))
export default defineConfig([
...nextVitals,
...nextTs,
globalIgnores([
".next/**",
"node_modules/**",
"dist/**",
"build/**",
"coverage/**",
"*.config.js",
"*.config.ts",
"*.config.mjs",
]),
{
extends: compat.extends(
"next/core-web-vitals",
"plugin:@typescript-eslint/recommended"
),
files: ["**/*.{js,jsx,ts,tsx,mts}"],
plugins: {
"simple-import-sort": simpleImportSort,
"@typescript-eslint": typescriptEslint,
formatjs,
},
languageOptions: {
parser: tsParser,
},
settings: {
// Ensure the plugin can resolve workspace packages and TS path aliases
"import/resolver": {
typescript: {
project: [path.join(packageDir, "tsconfig.json")],
alwaysTryTypes: true,
},
node: {
extensions: [".js", ".jsx", ".ts", ".tsx"],
},
},
},
rules: {
"no-console": "warn",
"no-unused-vars": "off",
@@ -57,15 +37,8 @@ export default defineConfig([
propElementValues: "always",
},
],
"react-hooks/incompatible-library": "off",
"import/no-relative-packages": "error",
"import/no-extraneous-dependencies": [
"warn",
{
includeInternal: true,
includeTypes: true,
packageDir: [packageDir],
},
],
"simple-import-sort/imports": [
"warn",
{
@@ -113,19 +86,9 @@ export default defineConfig([
},
],
"formatjs/enforce-default-message": ["error", "literal"],
"formatjs/enforce-placeholders": ["error"],
"formatjs/enforce-plural-rules": ["error"],
"formatjs/no-literal-string-in-jsx": ["error"],
"formatjs/no-multiple-whitespaces": ["error"],
"formatjs/no-multiple-plurals": ["error"],
"formatjs/no-invalid-icu": ["error"],
"formatjs/enforce-id": ["error"],
"formatjs/no-complex-selectors": ["error"],
"formatjs/no-useless-message": ["error"],
"formatjs/prefer-pound-in-plural": ["error"],
"@typescript-eslint/consistent-type-imports": "error",
"@typescript-eslint/no-empty-object-type": "off",
"@typescript-eslint/no-require-imports": "off",
"@typescript-eslint/no-unused-vars": [
"error",
@@ -141,6 +104,18 @@ export default defineConfig([
],
"@next/next/no-html-link-for-pages": "off",
"formatjs/enforce-default-message": ["error", "literal"],
"formatjs/enforce-placeholders": ["error"],
"formatjs/enforce-plural-rules": ["error"],
"formatjs/no-literal-string-in-jsx": ["error"],
"formatjs/no-multiple-whitespaces": ["error"],
"formatjs/no-multiple-plurals": ["error"],
"formatjs/no-invalid-icu": ["error"],
"formatjs/enforce-id": ["error"],
"formatjs/no-complex-selectors": ["error"],
"formatjs/no-useless-message": ["error"],
"formatjs/prefer-pound-in-plural": ["error"],
},
},
])

View File

@@ -30,6 +30,7 @@ export default function MemberPriceModal() {
useEffect(() => {
if (join) {
// eslint-disable-next-line react-hooks/set-state-in-effect
setIsOpen(true)
}
}, [join])

View File

@@ -49,6 +49,7 @@ export default function Signup({
<div className={styles.additionalFormData}>
<div
ref={(el) => {
// eslint-disable-next-line react-hooks/immutability
refs.current.zipCode = el
}}
>
@@ -64,6 +65,7 @@ export default function Signup({
<div
className={styles.dateField}
ref={(el) => {
// eslint-disable-next-line react-hooks/immutability
refs.current.dateOfBirth = el
}}
>
@@ -110,6 +112,7 @@ export default function Signup({
return (
<div
ref={(el) => {
// eslint-disable-next-line react-hooks/immutability
refs.current.membershipNo = el
}}
>

View File

@@ -40,6 +40,7 @@ function useBookingErrorAlert() {
const selectRateReturnUrl = getSelectRateReturnUrl()
useEffect(() => {
// eslint-disable-next-line react-hooks/set-state-in-effect
setShowAlert(!!errorCode)
}, [errorCode])

View File

@@ -147,6 +147,7 @@ export default function PaymentClient({
if (booking.reservationStatus == BookingStatusEnum.BookingCompleted) {
clearBookingWidgetState()
// Cookie is used by Booking Confirmation page to validate that the user came from payment callback
// eslint-disable-next-line react-hooks/immutability
document.cookie = `bcsig=${result.sig}; Path=/; Max-Age=60; Secure; SameSite=Strict`
const confirmationUrl = `${bookingConfirmation(lang)}?RefId=${encodeURIComponent(mainRoom.refId)}`
router.push(confirmationUrl)

View File

@@ -44,6 +44,7 @@ export default function Section({
useEffect(() => {
if (step === EnterDetailsStepEnum.selectBed && bedType) {
// eslint-disable-next-line react-hooks/set-state-in-effect
setTitle(bedType.description)
}
// If breakfast step, check if an option has been selected

View File

@@ -66,6 +66,7 @@ export function MapContainer({ children }: { children: React.ReactNode }) {
if (scrollHeightWhenOpened === 0) {
const scrollY = window.scrollY
// eslint-disable-next-line react-hooks/set-state-in-effect
setScrollHeightWhenOpened(scrollY)
window.scrollTo({ top: 0, behavior: "instant" })
}

View File

@@ -67,6 +67,7 @@ export default function FilterAndSortModal({
useEffect(() => {
if (activeFilters.length) {
// eslint-disable-next-line react-hooks/set-state-in-effect
setSelectedFilters(activeFilters)
}
}, [activeFilters])

View File

@@ -64,6 +64,7 @@ export default function FilterContent({
selectedFilters[0] || []
)
// eslint-disable-next-line react-hooks/set-state-in-effect
setFilteredHotelIds(filteredIds)
}, [filters, activeFilters, setFilteredHotelIds, showOnlyBookingCodeRates])

View File

@@ -66,6 +66,7 @@ export default function EnterDetailsProvider({
const [hasInitializedStore, setHasInitializedStore] = useState(false)
const storeRef = useRef<EnterDetailsStore>(undefined)
const pointsCurrency = useGetPointsCurrency()
// eslint-disable-next-line react-hooks/refs
if (!storeRef.current) {
const initialData: InitialState = {
booking,
@@ -242,6 +243,7 @@ export default function EnterDetailsProvider({
}, [booking, rooms, user])
return (
// eslint-disable-next-line react-hooks/refs
<EnterDetailsContext.Provider value={storeRef.current}>
{hasInitializedStore ? children : <LoadingSpinner fullPage />}
</EnterDetailsContext.Provider>

View File

@@ -427,6 +427,7 @@ export function SelectRateProvider({
return
}
// eslint-disable-next-line react-hooks/immutability
updatedRoom.packages = packages
updateBooking(selectRateBooking)
setActiveRoomIndex(roomIndex)
@@ -448,6 +449,7 @@ export function SelectRateProvider({
return
}
// eslint-disable-next-line react-hooks/immutability
updatedRoom.rateCode = rateCode
updatedRoom.roomTypeCode = roomTypeCode
updatedRoom.counterRateCode = counterRateCode || null

View File

@@ -17,6 +17,7 @@ export function useAvailablePaymentOptions(
useEffect(() => {
if (window.ApplePaySession) {
// eslint-disable-next-line react-hooks/set-state-in-effect
setAvailablePaymentOptions(otherPaymentOptions)
}
}, [otherPaymentOptions, setAvailablePaymentOptions])

View File

@@ -51,6 +51,7 @@ export function useBookingWidgetState() {
storedTo.isAfter(storedFrom)
if (isDateParamValid && stored.rooms?.length) {
// eslint-disable-next-line react-hooks/set-state-in-effect
setBookingState({
fromDate: storedFrom.format("YYYY-MM-DD"),
toDate: storedTo.format("YYYY-MM-DD"),

View File

@@ -57,6 +57,7 @@ export function useHandleBookingStatus({
return {
...query,
// eslint-disable-next-line react-hooks/refs
isTimeout: retries.current >= maxRetries,
}
}

View File

@@ -38,6 +38,7 @@ export async function BookingConfirmationPage({
}
const expire = Number(decrypt(sig))
// eslint-disable-next-line react-hooks/purity
const now = Math.floor(Date.now() / 1000)
if (typeof expire === "number" && !isNaN(expire) && now > expire) {
redirect(`/${lang}`)

View File

@@ -1,6 +1,7 @@
import { notFound } from "next/navigation"
import { PaymentCallbackStatusEnum } from "@scandic-hotels/common/constants/paymentCallbackStatusEnum"
import { PaymentMethodEnum } from "@scandic-hotels/common/constants/paymentMethod"
import {
bookingConfirmation,
details,
@@ -17,10 +18,9 @@ import { HandleSuccessCallback } from "../components/EnterDetails/Payment/Paymen
import { serverClient } from "../trpc"
import type { Lang } from "@scandic-hotels/common/constants/language"
import type { CreateBookingSchema } from "@scandic-hotels/trpc/routers/booking/mutation/create/schema"
import type { NextSearchParams } from "../types"
import { CreateBookingSchema } from "@scandic-hotels/trpc/routers/booking/mutation/create/schema"
import { PaymentMethodEnum } from "@scandic-hotels/common/constants/paymentMethod"
type PaymentCallbackPageProps = {
lang: Lang
@@ -118,6 +118,7 @@ export async function PaymentCallbackPage({
await caller.booking.validatePartnerPayment({ confirmationNumber })
}
// eslint-disable-next-line react-hooks/purity
const expire = Math.floor(Date.now() / 1000) + 60
const sig = encrypt(expire.toString())
const confirmationUrl = `${bookingConfirmation(lang)}?RefId=${encodeURIComponent(refId)}`

View File

@@ -49,6 +49,7 @@ export async function SelectRatePage({
// If someone tries to update the url with
// a bookingCode also, then we need to remove it
if (isRedemption && searchParams.bookingCode) {
// eslint-disable-next-line react-hooks/immutability
delete searchParams.bookingCode
}

View File

@@ -26,6 +26,7 @@ export function BookingConfirmationProvider({
const intl = useIntl()
const storeRef = useRef<BookingConfirmationStore>(undefined)
// eslint-disable-next-line react-hooks/refs
if (!storeRef.current) {
const totalBookingPrice = rooms.reduce((acc, room) => {
const reservationTotalPrice = room?.totalPrice || 0
@@ -105,6 +106,7 @@ export function BookingConfirmationProvider({
}
return (
// eslint-disable-next-line react-hooks/refs
<BookingConfirmationContext.Provider value={storeRef.current}>
{children}
</BookingConfirmationContext.Provider>