Skip to content

Commit

Permalink
chore: i18n translation keys for the search feature (#208)
Browse files Browse the repository at this point in the history
  • Loading branch information
darrenvong authored Sep 22, 2022
1 parent 8f03d26 commit f3be4bb
Show file tree
Hide file tree
Showing 22 changed files with 214 additions and 163 deletions.
82 changes: 53 additions & 29 deletions features/search/FilterDialog.test.tsx
Original file line number Diff line number Diff line change
@@ -1,16 +1,6 @@
import { render, screen, waitFor } from "@testing-library/react";
import userEvent from "@testing-library/user-event";
import { hostingStatusLabels } from "features/profile/constants";
import {
APPLY_FILTER,
HOSTING_STATUS,
LAST_ACTIVE,
LAST_WEEK,
LOCATION,
MUST_HAVE_LOCATION,
NUM_GUESTS,
PROFILE_KEYWORDS,
} from "features/search/constants";
import useRouteWithSearchFilters from "features/search/useRouteWithSearchFilters";
import mockRouter from "next-router-mock";
import { HostingStatus } from "proto/api_pb";
Expand Down Expand Up @@ -48,19 +38,29 @@ describe("FilterDialog", () => {
wrapper,
});

const locationInput = screen.getByLabelText(LOCATION);
const locationInput = screen.getByLabelText(
t("search:form.location_field_label")
);
userEvent.type(locationInput, "tes{enter}");
const locationItem = await screen.findByText("test city, test country");
userEvent.click(locationItem);

const keywordsInput = screen.getByLabelText(PROFILE_KEYWORDS);
const keywordsInput = screen.getByLabelText(
t("search:form.keywords.field_label")
);
userEvent.type(keywordsInput, "keyword1");

const lastActiveInput = screen.getByLabelText(LAST_ACTIVE);
const lastActiveInput = screen.getByLabelText(
t("search:form.host_filters.last_active_field_label")
);
userEvent.click(lastActiveInput);
userEvent.click(screen.getByText(LAST_WEEK));
userEvent.click(
screen.getByText(t("search:last_active_options.last_week"))
);

const hostStatusInput = screen.getByLabelText(HOSTING_STATUS);
const hostStatusInput = screen.getByLabelText(
t("search:form.host_filters.hosting_status_field_label")
);
userEvent.click(hostStatusInput);
userEvent.click(
screen.getByText(
Expand All @@ -74,7 +74,9 @@ describe("FilterDialog", () => {
)
);

const numGuestsInput = screen.getByLabelText(NUM_GUESTS);
const numGuestsInput = screen.getByLabelText(
t("search:form.accommodation_filters.guests_field_label")
);
userEvent.type(numGuestsInput, "3");

const expectedFilters = {
Expand All @@ -87,7 +89,11 @@ describe("FilterDialog", () => {
numGuests: 3,
};

userEvent.click(screen.getByRole("button", { name: APPLY_FILTER }));
userEvent.click(
screen.getByRole("button", {
name: t("search:form.submit_button_label"),
})
);

await waitFor(() => {
expect(parsedQueryToSearchFilters(mockRouter.query)).toMatchObject(
Expand All @@ -106,23 +112,27 @@ describe("FilterDialog", () => {
wrapper,
});

const locationInput = screen.getByLabelText(LOCATION) as HTMLInputElement;
const locationInput = screen.getByLabelText(
t("search:form.location_field_label")
) as HTMLInputElement;
const keywordInput = screen.getByLabelText(
PROFILE_KEYWORDS
t("search:form.keywords.field_label")
) as HTMLInputElement;
const lastActiveInput = screen.getByLabelText(
LAST_ACTIVE
t("search:form.host_filters.last_active_field_label")
) as HTMLInputElement;
const hostStatusInput = screen.getByLabelText(
HOSTING_STATUS
t("search:form.host_filters.hosting_status_field_label")
) as HTMLInputElement;
const numGuestsInput = screen.getByLabelText(
NUM_GUESTS
t("search:form.accommodation_filters.guests_field_label")
) as HTMLInputElement;

expect(locationInput).toHaveValue("test location");
expect(keywordInput).toHaveValue("keyword1");
expect(lastActiveInput).toHaveValue(LAST_WEEK);
expect(lastActiveInput).toHaveValue(
t("search:last_active_options.last_week")
);
expect(
screen.getByRole("button", {
name: hostingStatusLabels(t)[HostingStatus.HOSTING_STATUS_CAN_HOST],
Expand Down Expand Up @@ -164,11 +174,17 @@ describe("FilterDialog", () => {
render(<Dialog />, {
wrapper,
});
const lastActiveInput = screen.getByLabelText(LAST_ACTIVE);
const lastActiveInput = screen.getByLabelText(
t("search:form.host_filters.last_active_field_label")
);
userEvent.click(lastActiveInput);
userEvent.click(screen.getByText(LAST_WEEK));
userEvent.click(
screen.getByText(t("search:last_active_options.last_week"))
);

const hostStatusInput = screen.getByLabelText(HOSTING_STATUS);
const hostStatusInput = screen.getByLabelText(
t("search:form.host_filters.hosting_status_field_label")
);
userEvent.click(hostStatusInput);
userEvent.click(
screen.getByText(
Expand All @@ -182,12 +198,20 @@ describe("FilterDialog", () => {
)
);

const numGuestsInput = screen.getByLabelText(NUM_GUESTS);
const numGuestsInput = screen.getByLabelText(
t("search:form.accommodation_filters.guests_field_label")
);
userEvent.type(numGuestsInput, "3");

userEvent.click(screen.getByRole("button", { name: APPLY_FILTER }));
userEvent.click(
screen.getByRole("button", {
name: t("search:form.submit_button_label"),
})
);
await waitFor(() => {
const errors = screen.getAllByText(MUST_HAVE_LOCATION);
const errors = screen.getAllByText(
t("search:form.missing_location_validation_error")
);
expect(errors).toHaveLength(3);
expect(parsedQueryToSearchFilters(mockRouter.query)).toMatchObject({});
});
Expand Down
56 changes: 29 additions & 27 deletions features/search/FilterDialog.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -31,21 +31,7 @@ import { useQueryClient } from "react-query";
import { GeocodeResult } from "utils/hooks";
import SearchFilters from "utils/searchFilters";

import {
ACCOMODATION_FILTERS,
APPLY_FILTER,
CLEAR_SEARCH,
FILTER_DIALOG_TITLE_DESKTOP,
FILTER_DIALOG_TITLE_MOBILE,
HOST_FILTERS,
HOSTING_STATUS,
LAST_ACTIVE,
lastActiveOptions,
LOCATION,
MUST_HAVE_LOCATION,
NUM_GUESTS,
PROFILE_KEYWORDS,
} from "./constants";
import { getLastActiveOptions } from "./constants";

const hostingStatusOptions = [
HostingStatus.HOSTING_STATUS_CAN_HOST,
Expand All @@ -64,7 +50,7 @@ const useStyles = makeStyles((theme) => ({
interface FilterDialogFormData
extends Omit<SearchFilters, "location" | "lastActive"> {
location: GeocodeResult | "";
lastActive: typeof lastActiveOptions[number];
lastActive: ReturnType<typeof getLastActiveOptions>[number];
}

export default function FilterDialog({
Expand Down Expand Up @@ -135,22 +121,26 @@ export default function FilterDialog({
)
return true;
return getValues("location") === "" || !getValues("location")
? MUST_HAVE_LOCATION
? t("search:form.missing_location_validation_error")
: true;
};

const isSmDown = useMediaQuery((theme: Theme) =>
theme.breakpoints.down("sm")
);

const lastActiveOptions = getLastActiveOptions(t);

return (
<Dialog
open={isOpen}
onClose={onClose}
aria-labelledby="filter-dialog-title"
>
<DialogTitle id="filter-dialog-title">
{isSmDown ? FILTER_DIALOG_TITLE_MOBILE : FILTER_DIALOG_TITLE_DESKTOP}
{isSmDown
? t("search:filter_dialog.mobile_title")
: t("search:filter_dialog.desktop_title")}
</DialogTitle>
<form onSubmit={onSubmit}>
<DialogContent>
Expand All @@ -170,23 +160,25 @@ export default function FilterDialog({
}
: ""
}
label={LOCATION}
label={t("search:form.location_field_label")}
fieldError={errors.location?.message}
disableRegions
/>
<TextField
fullWidth
defaultValue={searchFilters.active.query ?? ""}
id="keywords-filter"
label={PROFILE_KEYWORDS}
label={t("search:form.keywords.field_label")}
name="query"
inputRef={register}
variant="standard"
InputProps={{
endAdornment: (
<InputAdornment position="end">
<IconButton
aria-label={CLEAR_SEARCH}
aria-label={t(
"search:form.keywords.clear_field_action_a11y_label"
)}
onClick={() => {
setValue("query", "");
}}
Expand All @@ -202,7 +194,9 @@ export default function FilterDialog({
<Divider />
<Grid container spacing={2}>
<Grid item xs={12} md={6} className={classes.container}>
<Typography variant="h3">{HOST_FILTERS}</Typography>
<Typography variant="h3">
{t("search:form.host_filters.title")}
</Typography>
<Controller
control={control}
name="lastActive"
Expand All @@ -214,7 +208,9 @@ export default function FilterDialog({
render={({ onChange, value }) => (
<Autocomplete
id="last-active-filter"
label={LAST_ACTIVE}
label={t(
"search:form.host_filters.last_active_field_label"
)}
options={lastActiveOptions}
getOptionLabel={(o) => o.label}
onChange={(_e, option) => onChange(option)}
Expand All @@ -235,7 +231,9 @@ export default function FilterDialog({
render={({ onChange, value }) => (
<Autocomplete<HostingStatus, true, false, false>
id="host-status-filter"
label={HOSTING_STATUS}
label={t(
"search:form.host_filters.hosting_status_field_label"
)}
options={hostingStatusOptions}
onChange={(_e, options) => {
onChange(options);
Expand All @@ -255,7 +253,9 @@ export default function FilterDialog({
/>
</Grid>
<Grid item xs={12} md={6} className={classes.container}>
<Typography variant="h3">{ACCOMODATION_FILTERS}</Typography>
<Typography variant="h3">
{t("search:form.accommodation_filters.title")}
</Typography>
<TextField
type="number"
variant="standard"
Expand All @@ -266,7 +266,9 @@ export default function FilterDialog({
})}
name="numGuests"
fullWidth
label={NUM_GUESTS}
label={t(
"search:form.accommodation_filters.guests_field_label"
)}
defaultValue={searchFilters.active.numGuests ?? ""}
error={!!errors.numGuests}
helperText={errors.numGuests?.message}
Expand All @@ -275,7 +277,7 @@ export default function FilterDialog({
</Grid>
</DialogContent>
<DialogActions>
<Button type="submit">{APPLY_FILTER}</Button>
<Button type="submit">{t("search:form.submit_button_label")}</Button>
</DialogActions>
</form>
</Dialog>
Expand Down
Loading

0 comments on commit f3be4bb

Please sign in to comment.