Skip to content

Instantly share code, notes, and snippets.

@maietta
Created November 16, 2024 21:10
Show Gist options
  • Save maietta/cd4ec5e8b02a10d296c4ca49838a737e to your computer and use it in GitHub Desktop.
Save maietta/cd4ec5e8b02a10d296c4ca49838a737e to your computer and use it in GitHub Desktop.
The secret formula search form.
<script lang="ts">
import { goto } from '$app/navigation';
import { page } from '$app/stores';
import { onMount } from 'svelte';
import { queryParameters } from 'sveltekit-search-params';
// Initialize query parameters management
const params = queryParameters(
{
test: {
encode: (value) => (value && value.trim() ? value : undefined),
decode: (value) => (value && value.trim() ? value : undefined)
}
},
{
pushHistory: true, // Enables updating the browser history
showDefaults: false, // Don't include default values in the query string
debounceHistory: 500
}
);
let form = $state({
Class: '',
Type: ''
});
let records = $state();
let initialLoad = true;
// Initialize form from URL path and query parameters
onMount(() => {
const [_, classSegment, typeSegment] = $page.url.pathname.split('/').filter(Boolean);
form.Class = classSegment || '';
form.Type = typeSegment || '';
// Load query parameters
const urlSearchParams = new URLSearchParams(form);
for (const [key, value] of urlSearchParams.entries()) {
if (params[key] !== undefined) {
params[key] = value; // Initialize query parameters
}
}
initialLoad = false; // Initial load is complete
});
// Reactive effect: Update URL and fetch data when form changes
$effect(() => {
if (initialLoad) return; // Prevent URL update during initial load
let url = '/search';
if (form.Class) {
url += `/${encodeURIComponent(form.Class)}`;
if (form.Type) url += `/${encodeURIComponent(form.Type)}`;
}
let searchParams = new URLSearchParams($page.url.searchParams);
// If Class or Type is present, remove them.
if (form.Class) searchParams.delete('Class');
if (form.Type) searchParams.delete('Type');
// Add the query parameters to the URL
url += `?` + searchParams.toString();
if (typeof window !== 'undefined' && window.location.href !== url)
goto(url, { replaceState: true });
fetchData(form);
});
// Fetch data from API
async function fetchData(formData: typeof form) {
try {
const response = await fetch('/search', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(formData)
});
if (!response.ok) throw new Error('Failed to fetch data');
records = await response.json();
} catch (error) {
console.error('Error fetching data:', error);
}
}
</script>
<form id="search" class="shadow-inset flex flex-col gap-4 rounded border bg-white p-4">
<label for="procpertyClass"><span class="font-bold">Property Type: </span></label>
<select name="procpertyClass" class="border border-red-300" bind:value={form.Class}>
<option value="">— choose a property type —</option>
<option value="residential">Traditional Residential</option>
<option value="multi-family">Multi-family Residential</option>
<option value="land">Lots and Land</option>
<option value="commercial">Commercial</option>
</select>
<input name="test" type="text" class="border border-red-300" bind:value={params.test} />
{#if form.Class === 'residential'}
<label for="Type"><span class="font-bold">Residence Type: </span></label>
<select bind:value={form.Type} name="Type" class="w-full">
<option value="">— any type of residential —</option>
<option value="single-family">Single Family Residence</option>
<option value="single-family-w-guest">Single Family w/Guest Addition(s)</option>
<option value="manufactured-on-land">Manufactured Residence on Land</option>
<option value="mobile-only">Mobile Only</option>
</select>
<!-- Additional fields for Residential -->
<!-- <label for="bedrooms"><span class="font-bold">Bedrooms:</span></label>
<input type="number" bind:value={form.Bedrooms} placeholder="Number of bedrooms" />
<label for="bathrooms"><span class="font-bold">Bathrooms:</span></label>
<input type="number" bind:value={form.Bathrooms} placeholder="Number of bathrooms" /> -->
{/if}
</form>
<pre>
{JSON.stringify(params, null, 2)}
</pre>
<pre>
{JSON.stringify(records, null, 2)}
</pre>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment