fix(#32): location hook to include the search property
Resolves #32 Now any component that uses the useLocation() hook will have access to the search property. The search page was also refactored to be a real server component. The form was split off into a client component that uses server state.
This commit is contained in:
parent
e85227a0b9
commit
c242319d6d
38
packages/dev/src/components/SearchForm.client.jsx
Normal file
38
packages/dev/src/components/SearchForm.client.jsx
Normal file
|
@ -0,0 +1,38 @@
|
|||
import {useState} from 'react';
|
||||
import {useServerState} from '@shopify/hydrogen/client';
|
||||
import {useHistory} from 'react-router-dom';
|
||||
|
||||
export default function Search({query}) {
|
||||
const [newQuery, setNewQuery] = useState(query);
|
||||
const {pending, setServerState} = useServerState('query', query);
|
||||
const history = useHistory();
|
||||
|
||||
return (
|
||||
<form
|
||||
onSubmit={(event) => {
|
||||
event.preventDefault();
|
||||
history.push(`/search?query=${newQuery}`);
|
||||
setServerState('query', newQuery);
|
||||
}}
|
||||
className={`mt-4 space-x-2 ${pending ? 'opacity-50' : undefined}`}
|
||||
>
|
||||
<label htmlFor="search">Search Products:</label>
|
||||
<input
|
||||
autoComplete="off"
|
||||
name="search"
|
||||
id="search"
|
||||
type="search"
|
||||
value={newQuery}
|
||||
onChange={(event) => setNewQuery(event.target.value)}
|
||||
className="px-2 py-1 placeholder-gray-400 text-gray-600 relative bg-white bg-white rounded text-sm border border-gray-400 outline-none focus:outline-none focus:ring"
|
||||
/>
|
||||
<button
|
||||
type="submit"
|
||||
className="bg-black text-white font-bold p-1"
|
||||
disabled={pending}
|
||||
>
|
||||
Search
|
||||
</button>
|
||||
</form>
|
||||
);
|
||||
}
|
79
packages/dev/src/pages/search.server.jsx
Normal file
79
packages/dev/src/pages/search.server.jsx
Normal file
|
@ -0,0 +1,79 @@
|
|||
import {useLocation} from 'react-router-dom';
|
||||
import {useShopQuery, Money, Image} from '@shopify/hydrogen';
|
||||
import gql from 'graphql-tag';
|
||||
|
||||
import Layout from '../components/Layout.server';
|
||||
import ProductCard from '../components/ProductCard.server';
|
||||
import SearchForm from '../components/SearchForm.client';
|
||||
|
||||
export default function Search({query}) {
|
||||
const {search} = useLocation();
|
||||
const searchQuery = query || new URLSearchParams(search).get('query');
|
||||
|
||||
return (
|
||||
<Layout>
|
||||
<h1 className="text-2xl font-bold">Search</h1>
|
||||
<SearchForm query={searchQuery} />
|
||||
{searchQuery && <SearchResults query={searchQuery} />}
|
||||
</Layout>
|
||||
);
|
||||
}
|
||||
|
||||
function SearchResults({query}) {
|
||||
const {data} = useShopQuery({query: QUERY, variables: {query}});
|
||||
|
||||
return (
|
||||
<>
|
||||
<h2 className="text-xl font-medium mt-8">Search results for: {query}</h2>
|
||||
|
||||
{data.products.edges.length ? (
|
||||
<ul className="grid lg:grid-cols-3 gap-6 mt-4">
|
||||
{data.products.edges.map((edge) => (
|
||||
<li key={edge.node.id}>
|
||||
<ProductCard product={edge.node} />
|
||||
</li>
|
||||
))}
|
||||
</ul>
|
||||
) : (
|
||||
<p>No results found.</p>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
const QUERY = gql`
|
||||
fragment SearchProductDetails on Product {
|
||||
id
|
||||
title
|
||||
handle
|
||||
variants(first: 1) {
|
||||
edges {
|
||||
node {
|
||||
availableForSale
|
||||
image {
|
||||
...ImageFragment
|
||||
}
|
||||
priceV2 {
|
||||
...MoneyFragment
|
||||
}
|
||||
compareAtPriceV2 {
|
||||
...MoneyFragment
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
query ProductSearch($query: String!) {
|
||||
products(query: $query, first: 10) {
|
||||
edges {
|
||||
node {
|
||||
...SearchProductDetails
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
${Image.Fragment}
|
||||
${Money.Fragment}
|
||||
`;
|
|
@ -25,6 +25,7 @@ and adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html).
|
|||
- fix: remove console logs for caching
|
||||
- fix: lowercased SVG tags in RSC
|
||||
- fix: make the URL search property available via hooks
|
||||
- feat: add search page
|
||||
|
||||
## 0.5.8 - 2021-11-04
|
||||
|
||||
|
|
Loading…
Reference in a new issue