|
|
@ -1,13 +1,15 @@
|
|
|
|
import { useState } from 'react';
|
|
|
|
import { useEffect, useState } from 'react';
|
|
|
|
import { ArrowSmallRightIcon } from '@heroicons/react/24/outline';
|
|
|
|
import { ArrowSmallRightIcon } from '@heroicons/react/24/outline';
|
|
|
|
import type { QuestionsQuestionType } from '@prisma/client';
|
|
|
|
import type { QuestionsQuestionType } from '@prisma/client';
|
|
|
|
import { Button, Select } from '@tih/ui';
|
|
|
|
import { Button, Select } from '@tih/ui';
|
|
|
|
|
|
|
|
|
|
|
|
import {
|
|
|
|
import { QUESTION_TYPES } from '~/utils/questions/constants';
|
|
|
|
COMPANIES,
|
|
|
|
import useDefaultCompany from '~/utils/questions/useDefaultCompany';
|
|
|
|
LOCATIONS,
|
|
|
|
import useDefaultLocation from '~/utils/questions/useDefaultLocation';
|
|
|
|
QUESTION_TYPES,
|
|
|
|
|
|
|
|
} from '~/utils/questions/constants';
|
|
|
|
import type { FilterChoice } from './filter/FilterSection';
|
|
|
|
|
|
|
|
import CompanyTypeahead from './typeahead/CompanyTypeahead';
|
|
|
|
|
|
|
|
import LocationTypeahead from './typeahead/LocationTypeahead';
|
|
|
|
|
|
|
|
|
|
|
|
export type LandingQueryData = {
|
|
|
|
export type LandingQueryData = {
|
|
|
|
company: string;
|
|
|
|
company: string;
|
|
|
@ -22,76 +24,109 @@ export type LandingComponentProps = {
|
|
|
|
export default function LandingComponent({
|
|
|
|
export default function LandingComponent({
|
|
|
|
onLanded: handleLandingQuery,
|
|
|
|
onLanded: handleLandingQuery,
|
|
|
|
}: LandingComponentProps) {
|
|
|
|
}: LandingComponentProps) {
|
|
|
|
const [landingQueryData, setLandingQueryData] = useState<LandingQueryData>({
|
|
|
|
const defaultCompany = useDefaultCompany();
|
|
|
|
company: 'Google',
|
|
|
|
const defaultLocation = useDefaultLocation();
|
|
|
|
location: 'Singapore',
|
|
|
|
|
|
|
|
questionType: 'CODING',
|
|
|
|
const [company, setCompany] = useState<FilterChoice | undefined>(
|
|
|
|
});
|
|
|
|
defaultCompany,
|
|
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
const [location, setLocation] = useState<FilterChoice | undefined>(
|
|
|
|
|
|
|
|
defaultLocation,
|
|
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
const [questionType, setQuestionType] =
|
|
|
|
|
|
|
|
useState<QuestionsQuestionType>('CODING');
|
|
|
|
|
|
|
|
|
|
|
|
const handleChangeCompany = (company: string) => {
|
|
|
|
const handleChangeCompany = (newCompany: FilterChoice) => {
|
|
|
|
setLandingQueryData((prev) => ({ ...prev, company }));
|
|
|
|
setCompany(newCompany);
|
|
|
|
};
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
const handleChangeLocation = (location: string) => {
|
|
|
|
const handleChangeLocation = (newLocation: FilterChoice) => {
|
|
|
|
setLandingQueryData((prev) => ({ ...prev, location }));
|
|
|
|
setCompany(newLocation);
|
|
|
|
};
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
const handleChangeType = (questionType: QuestionsQuestionType) => {
|
|
|
|
const handleChangeType = (newQuestionType: QuestionsQuestionType) => {
|
|
|
|
setLandingQueryData((prev) => ({ ...prev, questionType }));
|
|
|
|
setQuestionType(newQuestionType);
|
|
|
|
};
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
useEffect(() => {
|
|
|
|
|
|
|
|
if (company === undefined) {
|
|
|
|
|
|
|
|
setCompany(defaultCompany);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}, [defaultCompany, company]);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
useEffect(() => {
|
|
|
|
|
|
|
|
if (location !== undefined) {
|
|
|
|
|
|
|
|
setLocation(defaultLocation);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}, [defaultLocation, location]);
|
|
|
|
|
|
|
|
|
|
|
|
return (
|
|
|
|
return (
|
|
|
|
<main className="flex flex-1 flex-col items-stretch overflow-y-auto bg-white">
|
|
|
|
<main className="flex flex-1 flex-col items-center overflow-y-auto bg-white">
|
|
|
|
<div className="pb-4"></div>
|
|
|
|
<div className="flex flex-1 flex-col items-start justify-center gap-12 px-4">
|
|
|
|
<div className="flex flex-1 flex-col justify-center gap-3">
|
|
|
|
<header className="flex flex-col items-start">
|
|
|
|
<div className="flex items-center justify-center">
|
|
|
|
<div className="flex items-center justify-center">
|
|
|
|
<img alt="app logo" className=" h-20 w-20" src="/logo.svg"></img>
|
|
|
|
<h1 className="text-3xl font-semibold text-slate-900">
|
|
|
|
<h1 className="text-primary-600 p-4 text-center text-5xl font-bold">
|
|
|
|
|
|
|
|
Tech Interview Question Bank
|
|
|
|
Tech Interview Question Bank
|
|
|
|
</h1>
|
|
|
|
</h1>
|
|
|
|
|
|
|
|
<img alt="app logo" className="h-20 w-20" src="/logo.svg"></img>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
<p className="mx-auto max-w-lg p-6 text-center text-xl text-black sm:max-w-3xl">
|
|
|
|
<p className="mb-2 max-w-lg text-5xl font-semibold text-slate-900 sm:max-w-3xl">
|
|
|
|
Get to know the latest SWE interview questions asked by top companies
|
|
|
|
Know the{' '}
|
|
|
|
|
|
|
|
<span className="text-primary-700">
|
|
|
|
|
|
|
|
latest SWE interview questions
|
|
|
|
|
|
|
|
</span>{' '}
|
|
|
|
|
|
|
|
asked by top companies.
|
|
|
|
</p>
|
|
|
|
</p>
|
|
|
|
|
|
|
|
</header>
|
|
|
|
<div className="mx-auto flex max-w-lg items-baseline gap-3 p-4 text-center text-xl text-black sm:max-w-3xl">
|
|
|
|
<div className="flex flex-col items-start gap-3 text-xl font-semibold text-slate-900">
|
|
|
|
<p>Find</p>
|
|
|
|
<p className="text-3xl">Find questions</p>
|
|
|
|
<div className=" space-x-2">
|
|
|
|
<div className="grid grid-cols-2">
|
|
|
|
|
|
|
|
<p className="text-slate-600">about</p>
|
|
|
|
<Select
|
|
|
|
<Select
|
|
|
|
isLabelHidden={true}
|
|
|
|
isLabelHidden={true}
|
|
|
|
label="Type"
|
|
|
|
label="Type"
|
|
|
|
options={QUESTION_TYPES}
|
|
|
|
options={QUESTION_TYPES}
|
|
|
|
value={landingQueryData.questionType}
|
|
|
|
value={questionType}
|
|
|
|
onChange={(value) => {
|
|
|
|
onChange={(value) => {
|
|
|
|
handleChangeType(value.toUpperCase() as QuestionsQuestionType);
|
|
|
|
handleChangeType(value.toUpperCase() as QuestionsQuestionType);
|
|
|
|
}}
|
|
|
|
}}
|
|
|
|
/>
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
<p className="text-slate-600">from</p>
|
|
|
|
<p>questions from</p>
|
|
|
|
<CompanyTypeahead
|
|
|
|
<Select
|
|
|
|
|
|
|
|
isLabelHidden={true}
|
|
|
|
isLabelHidden={true}
|
|
|
|
label="Company"
|
|
|
|
value={company}
|
|
|
|
options={COMPANIES}
|
|
|
|
onSelect={(value) => {
|
|
|
|
value={landingQueryData.company}
|
|
|
|
handleChangeCompany(value);
|
|
|
|
onChange={handleChangeCompany}
|
|
|
|
}}
|
|
|
|
/>
|
|
|
|
/>
|
|
|
|
<p>in</p>
|
|
|
|
<p className="text-slate-600">in</p>
|
|
|
|
<Select
|
|
|
|
<LocationTypeahead
|
|
|
|
isLabelHidden={true}
|
|
|
|
isLabelHidden={true}
|
|
|
|
label="Location"
|
|
|
|
value={location}
|
|
|
|
options={LOCATIONS}
|
|
|
|
onSelect={(value) => {
|
|
|
|
value={landingQueryData.location}
|
|
|
|
handleChangeLocation(value);
|
|
|
|
onChange={handleChangeLocation}
|
|
|
|
}}
|
|
|
|
/>
|
|
|
|
/>
|
|
|
|
|
|
|
|
</div>
|
|
|
|
<Button
|
|
|
|
<Button
|
|
|
|
addonPosition="end"
|
|
|
|
addonPosition="end"
|
|
|
|
icon={ArrowSmallRightIcon}
|
|
|
|
icon={ArrowSmallRightIcon}
|
|
|
|
label="Go"
|
|
|
|
label="Go"
|
|
|
|
size="md"
|
|
|
|
size="md"
|
|
|
|
variant="primary"
|
|
|
|
variant="primary"
|
|
|
|
onClick={() => handleLandingQuery(landingQueryData)}></Button>
|
|
|
|
onClick={() => {
|
|
|
|
|
|
|
|
if (company !== undefined && location !== undefined) {
|
|
|
|
|
|
|
|
return handleLandingQuery({
|
|
|
|
|
|
|
|
company: company.value,
|
|
|
|
|
|
|
|
location: location.value,
|
|
|
|
|
|
|
|
questionType,
|
|
|
|
|
|
|
|
});
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}}
|
|
|
|
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
<div className="flex justify-center p-4">
|
|
|
|
<div className="flex justify-center">
|
|
|
|
<iframe
|
|
|
|
<iframe
|
|
|
|
height={30}
|
|
|
|
height={30}
|
|
|
|
src="https://ghbtns.com/github-btn.html?user=yangshun&repo=tech-interview-handbook&type=star&count=true&size=large"
|
|
|
|
src="https://ghbtns.com/github-btn.html?user=yangshun&repo=tech-interview-handbook&type=star&count=true&size=large"
|
|
|
|