From 711589ff5e020aaa06df3d26af24a0bd15870f32 Mon Sep 17 00:00:00 2001
From: Anton Gunnarsson
Date: Thu, 4 Sep 2025 13:52:56 +0000
Subject: [PATCH] Merged in chore/add-formatjs-linting-to-booking-flow (pull
request #2761)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
chore: Add formatjs linting to booking-flow
* Add formatjs linting to booking-flow
* Fix lock file
Approved-by: Joakim Jäderberg
---
packages/booking-flow/eslint.config.mjs | 14 ++++++++++++++
.../lib/components/ErrorBoundary/ErrorBoundary.tsx | 2 ++
.../components/ListingHotelCardDialog/index.tsx | 6 +++++-
.../SelectHotel/Filters/FilterContent/index.tsx | 1 +
.../RateSummary/MobileSummary/Content/index.tsx | 8 +++-----
.../RoomsContainer/RateSummary/index.tsx | 3 +++
.../RoomsContainer/Rooms/RoomsHeader/index.tsx | 1 +
.../RoomsList/RoomListItem/Details/RoomSize.tsx | 2 ++
.../lib/contexts/SelectRate/DebugButton.tsx | 2 +-
packages/booking-flow/package.json | 1 +
yarn.lock | 1 +
11 files changed, 34 insertions(+), 7 deletions(-)
diff --git a/packages/booking-flow/eslint.config.mjs b/packages/booking-flow/eslint.config.mjs
index a6e872a08..ac74eaf8c 100644
--- a/packages/booking-flow/eslint.config.mjs
+++ b/packages/booking-flow/eslint.config.mjs
@@ -6,6 +6,7 @@ import js from "@eslint/js"
import typescriptEslint from "@typescript-eslint/eslint-plugin"
import tsParser from "@typescript-eslint/parser"
import { defineConfig } from "eslint/config"
+import formatjs from "eslint-plugin-formatjs"
import simpleImportSort from "eslint-plugin-simple-import-sort"
const compat = new FlatCompat({
@@ -21,6 +22,7 @@ export default defineConfig([
plugins: {
"simple-import-sort": simpleImportSort,
"@typescript-eslint": typescriptEslint,
+ formatjs,
},
languageOptions: {
@@ -99,6 +101,18 @@ 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/no-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-unused-vars": [
diff --git a/packages/booking-flow/lib/components/ErrorBoundary/ErrorBoundary.tsx b/packages/booking-flow/lib/components/ErrorBoundary/ErrorBoundary.tsx
index 483d3c832..1625066c2 100644
--- a/packages/booking-flow/lib/components/ErrorBoundary/ErrorBoundary.tsx
+++ b/packages/booking-flow/lib/components/ErrorBoundary/ErrorBoundary.tsx
@@ -34,8 +34,10 @@ export class ErrorBoundary extends React.Component<
return (
<>
{hasFallback && this.props.fallback}
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
{!hasFallback && Something went wrong.
}
{process.env.NODE_ENV === "development" && (
+ // eslint-disable-next-line formatjs/no-literal-string-in-jsx
diff --git a/packages/booking-flow/lib/components/ListingHotelCardDialog/index.tsx b/packages/booking-flow/lib/components/ListingHotelCardDialog/index.tsx
index 00718bfe6..f1ebd77ad 100644
--- a/packages/booking-flow/lib/components/ListingHotelCardDialog/index.tsx
+++ b/packages/booking-flow/lib/components/ListingHotelCardDialog/index.tsx
@@ -128,6 +128,7 @@ export default function ListingHotelCardDialog({
{publicPrice} {currency}
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
{memberPrice && /}
>
) : (
@@ -166,7 +167,8 @@ export default function ListingHotelCardDialog({
}
)}
{chequePrice.additionalPricePerStay > 0
- ? " + " +
+ ? // eslint-disable-next-line formatjs/no-literal-string-in-jsx
+ " + " +
intl.formatMessage(
{
defaultMessage: "{price} {currency}",
@@ -178,6 +180,7 @@ export default function ListingHotelCardDialog({
)
: null}
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
/
{intl.formatMessage({
@@ -199,6 +202,7 @@ export default function ListingHotelCardDialog({
}
)}
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
/
{intl.formatMessage({
diff --git a/packages/booking-flow/lib/components/SelectHotel/Filters/FilterContent/index.tsx b/packages/booking-flow/lib/components/SelectHotel/Filters/FilterContent/index.tsx
index f0f808e27..e1c3b0555 100644
--- a/packages/booking-flow/lib/components/SelectHotel/Filters/FilterContent/index.tsx
+++ b/packages/booking-flow/lib/components/SelectHotel/Filters/FilterContent/index.tsx
@@ -80,6 +80,7 @@ export default function FilterContent({
isDisabled={isDisabled}
/>
{!isDisabled && (
+ // eslint-disable-next-line formatjs/no-literal-string-in-jsx
{`(${combinedFiltersCount > 0 ? combinedFiltersCount : filterCount})`}
)}
diff --git a/packages/booking-flow/lib/components/SelectRate/RoomsContainer/RateSummary/MobileSummary/Content/index.tsx b/packages/booking-flow/lib/components/SelectRate/RoomsContainer/RateSummary/MobileSummary/Content/index.tsx
index 775d405cc..075b197af 100644
--- a/packages/booking-flow/lib/components/SelectRate/RoomsContainer/RateSummary/MobileSummary/Content/index.tsx
+++ b/packages/booking-flow/lib/components/SelectRate/RoomsContainer/RateSummary/MobileSummary/Content/index.tsx
@@ -101,14 +101,13 @@ export default function SummaryContent({
{dt(input.data?.booking.toDate)
.locale(lang)
- .format(longDateFormat[lang])}{" "}
- ({nightsLabel})
+ .format(longDateFormat[lang])}
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
+ {` (${nightsLabel})`}
-
-
{selectedRates.rates.map((room, idx) => {
if (!room) {
return null
@@ -131,7 +130,6 @@ export default function SummaryContent({
/>
)
})}
-
diff --git a/packages/booking-flow/lib/components/SelectRate/RoomsContainer/RateSummary/index.tsx b/packages/booking-flow/lib/components/SelectRate/RoomsContainer/RateSummary/index.tsx
index 497ca8de4..79a91f9ee 100644
--- a/packages/booking-flow/lib/components/SelectRate/RoomsContainer/RateSummary/index.tsx
+++ b/packages/booking-flow/lib/components/SelectRate/RoomsContainer/RateSummary/index.tsx
@@ -12,6 +12,7 @@ import styles from "./rateSummary.module.css"
export function RateSummary() {
return (
+ // eslint-disable-next-line formatjs/no-literal-string-in-jsx
Unable to render summary
}>
@@ -59,6 +60,7 @@ function InnerRateSummary() {
>
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
Unable to render desktop summary
}>
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
Unable to render mobile summary
}>
diff --git a/packages/booking-flow/lib/components/SelectRate/RoomsContainer/Rooms/RoomsHeader/index.tsx b/packages/booking-flow/lib/components/SelectRate/RoomsContainer/Rooms/RoomsHeader/index.tsx
index f2f4b201c..bb52c89a3 100644
--- a/packages/booking-flow/lib/components/SelectRate/RoomsContainer/Rooms/RoomsHeader/index.tsx
+++ b/packages/booking-flow/lib/components/SelectRate/RoomsContainer/Rooms/RoomsHeader/index.tsx
@@ -14,6 +14,7 @@ import styles from "./roomsHeader.module.css"
export function RoomsHeader({ roomIndex }: { roomIndex: number }) {
return (
+ // eslint-disable-next-line formatjs/no-literal-string-in-jsx
Unable to render rooms header }>
diff --git a/packages/booking-flow/lib/components/SelectRate/RoomsContainer/Rooms/RoomsList/RoomListItem/Details/RoomSize.tsx b/packages/booking-flow/lib/components/SelectRate/RoomsContainer/Rooms/RoomsList/RoomListItem/Details/RoomSize.tsx
index ee6994c36..03514545b 100644
--- a/packages/booking-flow/lib/components/SelectRate/RoomsContainer/Rooms/RoomsList/RoomListItem/Details/RoomSize.tsx
+++ b/packages/booking-flow/lib/components/SelectRate/RoomsContainer/Rooms/RoomsList/RoomListItem/Details/RoomSize.tsx
@@ -23,6 +23,7 @@ export default function RoomSize({ roomSize }: RoomSizeProps) {
return (
<>
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
∙
@@ -41,6 +42,7 @@ export default function RoomSize({ roomSize }: RoomSizeProps) {
return (
<>
+ {/* eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
∙
diff --git a/packages/booking-flow/lib/contexts/SelectRate/DebugButton.tsx b/packages/booking-flow/lib/contexts/SelectRate/DebugButton.tsx
index c75721e70..95c110f50 100644
--- a/packages/booking-flow/lib/contexts/SelectRate/DebugButton.tsx
+++ b/packages/booking-flow/lib/contexts/SelectRate/DebugButton.tsx
@@ -1,3 +1,4 @@
+/* eslint-disable formatjs/no-literal-string-in-jsx */
import { Button } from "@scandic-hotels/design-system/Button"
import { useSelectRateContext } from "./SelectRateContext"
@@ -33,7 +34,6 @@ export function DebugButton() {
}}
onClick={handleClick}
>
- {/* // eslint-disable-next-line formatjs/no-literal-string-in-jsx */}
DEBUG
)
diff --git a/packages/booking-flow/package.json b/packages/booking-flow/package.json
index 2f21e68e5..c0a757d85 100644
--- a/packages/booking-flow/package.json
+++ b/packages/booking-flow/package.json
@@ -105,6 +105,7 @@
"@typescript-eslint/parser": "^8.32.0",
"dotenv": "^16.5.0",
"eslint": "^9",
+ "eslint-plugin-formatjs": "^5.3.1",
"eslint-plugin-import": "^2.31.0",
"eslint-plugin-simple-import-sort": "^12.1.1",
"typescript": "5.8.3",
diff --git a/yarn.lock b/yarn.lock
index fc008c920..e25976004 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -6060,6 +6060,7 @@ __metadata:
dotenv: "npm:^16.5.0"
downshift: "npm:^9.0.9"
eslint: "npm:^9"
+ eslint-plugin-formatjs: "npm:^5.3.1"
eslint-plugin-import: "npm:^2.31.0"
eslint-plugin-simple-import-sort: "npm:^12.1.1"
fast-deep-equal: "npm:^3.1.0"