Skip to content

Commit

Permalink
feat: new version announcement (#53)
Browse files Browse the repository at this point in the history
* fix: handle no data when importing visited country data (wrong branch)

* feat: new version announcement
  • Loading branch information
johanohly authored Oct 4, 2024
1 parent 0594c90 commit e337e54
Show file tree
Hide file tree
Showing 11 changed files with 218 additions and 56 deletions.
Binary file modified bun.lockb
Binary file not shown.
3 changes: 3 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,9 @@
"mode-watcher": "^0.4.1",
"openid-client": "^5.7.0",
"pg": "^8.12.0",
"semver": "^7.6.3",
"svelte-maplibre": "^0.9.11",
"svelte-markdown": "^0.4.1",
"svelte-motion": "^0.12.2",
"svelte-sonner": "^0.3.27",
"sveltekit-superforms": "^2.16.1",
Expand All @@ -63,6 +65,7 @@
"@types/d3-shape": "^3.1.6",
"@types/lru-cache": "^7.10.10",
"@types/pg": "^8.11.8",
"@types/semver": "^7.5.8",
"@types/topojson-client": "^3.1.5",
"@types/topojson-specification": "^1.0.5",
"autoprefixer": "^10.4.19",
Expand Down
143 changes: 88 additions & 55 deletions src/app.css
Original file line number Diff line number Diff line change
Expand Up @@ -5,96 +5,129 @@
@tailwind utilities;

@layer base {
:root {
--background: 0 0% 100%;
--foreground: 240 10% 3.9%;
:root {
--background: 0 0% 100%;
--foreground: 240 10% 3.9%;

--muted: 240 4.8% 95.9%;
--muted-foreground: 240 3.8% 46.1%;
--muted: 240 4.8% 95.9%;
--muted-foreground: 240 3.8% 46.1%;

--popover: 0 0% 100%;
--popover-foreground: 240 10% 3.9%;
--popover: 0 0% 100%;
--popover-foreground: 240 10% 3.9%;

--card: 0 0% 100%;
--card-hover: 0 0% 95%;
--card-foreground: 240 10% 3.9%;
--card: 0 0% 100%;
--card-hover: 0 0% 95%;
--card-foreground: 240 10% 3.9%;

--border: 240 5.9% 90%;
--input: 240 5.9% 90%;
--border: 240 5.9% 90%;
--input: 240 5.9% 90%;

--primary: 217 91% 60%;
--primary-foreground: 0 0% 98%;
--primary: 217 91% 60%;
--primary-foreground: 0 0% 98%;

--secondary: 240 4.8% 95.9%;
--secondary-foreground: 240 5.9% 10%;
--secondary: 240 4.8% 95.9%;
--secondary-foreground: 240 5.9% 10%;

--accent: 240 4.8% 95.9%;
--accent-foreground: 240 5.9% 10%;
--accent: 240 4.8% 95.9%;
--accent-foreground: 240 5.9% 10%;

--destructive: 0 72.2% 50.6%;
--destructive-foreground: 0 0% 98%;
--destructive: 0 72.2% 50.6%;
--destructive-foreground: 0 0% 98%;

--ring: 240 10% 3.9%;
--ring: 240 10% 3.9%;

--radius: 0.5rem;
}
--radius: 0.5rem;
}

.dark {
--background: 240 10% 3.9%;
--foreground: 0 0% 98%;
.dark {
--background: 240 10% 3.9%;
--foreground: 0 0% 98%;

--muted: 240 3.7% 15.9%;
--muted-foreground: 240 5% 64.9%;
--muted: 240 3.7% 15.9%;
--muted-foreground: 240 5% 64.9%;

--popover: 240 10% 3.9%;
--popover-foreground: 0 0% 98%;
--popover: 240 10% 3.9%;
--popover-foreground: 0 0% 98%;

--card: 240 10% 3.9%;
--card-hover: 240 10% 12%;
--card-foreground: 0 0% 98%;
--card: 240 10% 3.9%;
--card-hover: 240 10% 12%;
--card-foreground: 0 0% 98%;

--border: 240 3.7% 15.9%;
--input: 240 3.7% 15.9%;
--border: 240 3.7% 15.9%;
--input: 240 3.7% 15.9%;

--primary: 217 91% 60%;
--primary-foreground: 240 5.9% 10%;
--primary: 217 91% 60%;
--primary-foreground: 240 5.9% 10%;

--secondary: 240 3.7% 15.9%;
--secondary-foreground: 0 0% 98%;
--secondary: 240 3.7% 15.9%;
--secondary-foreground: 0 0% 98%;

--accent: 240 3.7% 15.9%;
--accent-foreground: 0 0% 98%;
--accent: 240 3.7% 15.9%;
--accent-foreground: 0 0% 98%;

--destructive: 0 68% 45%;
--destructive-foreground: 0 0% 98%;
--destructive: 0 68% 45%;
--destructive-foreground: 0 0% 98%;

--ring: 240 4.9% 83.9%;
}
--ring: 240 4.9% 83.9%;
}
}

@layer base {
* {
@apply border-border;
}
* {
@apply border-border;
}

body {
@apply bg-background text-foreground;
}
body {
@apply bg-background text-foreground;
}
}

html,
body {
@apply h-full;
@apply h-full;
}

.page-container {
@apply container mx-auto px-4 md:px-10 py-10 space-y-10;
@apply container mx-auto px-4 md:px-10 py-10 space-y-10;
}

.maplibregl-popup-content {
@apply !p-0 !bg-popover dark:!bg-dark-2 !text-popover-foreground !drop-shadow-2xl !rounded-lg;
@apply !p-0 !bg-popover dark:!bg-dark-2 !text-popover-foreground !drop-shadow-2xl !rounded-lg;
}

.maplibregl-popup-tip {
@apply !border-none;
@apply !border-none;
}

/* Basic prose styles */
.prose h1 {
@apply text-4xl leading-[1.11] font-bold;
}

.prose h2 {
@apply text-2xl leading-[1.33] font-bold mt-[1em];
}

.prose h3 {
@apply text-xl leading-[1.6] font-semibold mb-2 mt-5;
}

:where(.prose > :first-child) {
@apply !mt-0;
}

.prose :where(h3 + *) {
@apply !mt-0;
}

.prose ul {
@apply list-disc pl-6;
}

.prose a {
@apply font-medium border-b border-b-primary;
}

.prose a:hover {
@apply border-b-2
}
1 change: 1 addition & 0 deletions src/lib/components/modals/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,3 +5,4 @@ export { default as StatisticsModal } from './statistics/StatisticsModal.svelte'
export { default as EditFlightModal } from './edit-flight/EditFlightModal.svelte';
export { default as SetupVisitedCountries } from './visited-countries/SetupVisitedCountries.svelte';
export { default as EditVisitedCountry } from './visited-countries/EditVisitedCountry.svelte';
export { default as NewVersionAnnouncement } from './new-version-announcement/NewVersionAnnouncement.svelte';
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<script lang="ts">
import type { Snippet } from 'svelte';
let {
href,
title,
children,
}: { href: string; title: string | undefined; children: Snippet } = $props();
let prNum = $derived(href.match(/pull\/(\d+)/)?.[1]);
</script>

<a target="_blank" {href} {title}>
{#if prNum}
#{prNum}
{:else}
{@render children()}
{/if}
</a>
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
<script lang="ts">
import * as Dialog from '$lib/components/ui/alert-dialog';
import SvelteMarkdown from 'svelte-markdown';
import NewTabLink from './NewTabLink.svelte';
import { Badge } from '$lib/components/ui/badge';
import { version } from '$app/environment';
import semver, { SemVer } from 'semver';
import { Button } from '$lib/components/ui/button';
let open = $state(false);
let changelog: { name: string; body: string } | null = $state(null);
$effect(() => {
fetch(
'https://api.github.com/repos/johanohly/AirTrail/releases/latest',
).then(async (response) => {
if (!response.ok) return;
const data = await response.json();
const latestVersion = new SemVer(data.tag_name);
const dismissedVersion = localStorage.getItem('dismissedVersion');
// If the latest version is the same as the current version or the new version has been dismissed, return
if (
semver.lte(latestVersion, version) ||
(dismissedVersion && semver.lte(latestVersion, dismissedVersion))
) {
return;
}
changelog = {
name: data.tag_name,
body: data.body,
};
open = true;
});
});
const dismissVersion = () => {
if (!changelog) return;
localStorage.setItem('dismissedVersion', changelog?.name);
};
</script>

{#if changelog}
<Dialog.Root bind:open>
<Dialog.Content>
<Dialog.Header>
<Dialog.Title class="flex items-center gap-4">
New version available!
<Badge>{changelog.name}</Badge>
</Dialog.Title>
</Dialog.Header>
<div class="prose max-h-[80dvh] overflow-y-auto">
<SvelteMarkdown
source={changelog.body}
renderers={{ link: NewTabLink }}
/>
</div>
<Dialog.Footer>
<Button
variant="outline"
href="https://johanohly.github.io/AirTrail/docs/install/updating"
target="_blank"
>
How to update
</Button>
<Dialog.Action onclick={dismissVersion}>Got it</Dialog.Action>
</Dialog.Footer>
</Dialog.Content>
</Dialog.Root>
{/if}
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
import { Modal } from '$lib/components/ui/modal';
import { Button } from '$lib/components/ui/button';
import { api, trpc } from '$lib/trpc';
import { toast } from 'svelte-sonner';
let { visitedCountries }: { visitedCountries: any[] } = $props();
Expand All @@ -16,6 +17,8 @@
const success = await api.visitedCountries.importFlights.mutate();
if (success) {
await trpc.visitedCountries.list.utils.invalidate();
} else {
toast.error('Failed to import flights (possibly due to no past flights)');
}
loading = false;
};
Expand Down
18 changes: 18 additions & 0 deletions src/lib/components/ui/badge/badge.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
<script lang="ts">
import { type Variant, badgeVariants } from './index.js';
import { cn } from '$lib/utils';
let className: string | undefined | null = undefined;
export let href: string | undefined = undefined;
export let variant: Variant = 'default';
export { className as class };
</script>

<svelte:element
this={href ? 'a' : 'span'}
{href}
class={cn(badgeVariants({ variant, className }))}
{...$$restProps}
>
<slot />
</svelte:element>
4 changes: 4 additions & 0 deletions src/lib/server/routes/visited-countries.ts
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,10 @@ export const visitedCountriesRouter = router({
countries.push(originCountry.numeric);
}

if (countries.length === 0) {
return false;
}

const result = await db
.insertInto('visitedCountry')
.values(
Expand Down
11 changes: 10 additions & 1 deletion src/routes/+layout.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,11 @@
import { openModalsState } from '$lib/stores.svelte';
import { page } from '$app/stores';
import { flyAndScale } from '$lib/utils/other';
import { AddFlightModal, SettingsModal } from '$lib/components/modals';
import {
AddFlightModal,
NewVersionAnnouncement,
SettingsModal,
} from '$lib/components/modals';
const { data, children } = $props();
Expand Down Expand Up @@ -77,6 +81,11 @@
<ModeWatcher />
<ScreenSize />
<Toaster />

{#if data.user?.role !== 'user'}
<NewVersionAnnouncement />
{/if}

<QueryClientProvider client={queryClient}>
<SettingsModal bind:open={openModalsState.settings} />
<AddFlightModal bind:open={openModalsState.addFlight} />
Expand Down
1 change: 1 addition & 0 deletions svelte.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ const config = {
preprocess: sequence([vitePreprocess(), preprocessMeltUI()]),
kit: {
adapter: adapter(),
version: { name: process.env.npm_package_version },
},
};
export default config;

0 comments on commit e337e54

Please sign in to comment.