⚑

Qwik

Resumable framework with O(1) loading time regardless of app complexity

Results Summary

Performance

98%
Lighthouse Score

Bundle Size

33.8KB
Gzipped

Build Time

1.8s
Average

Load Time

2.4s
LCP

Complexity

83
Cyclomatic

Performance Metrics

CLS
0.0002
FCP
1498ms
LCP
2375ms
TBT
28ms

Bundle Analysis

Compression
2.6x
File Count
13
JS %
100.0%
Total Size
89.0KB

Build Info

Build Time
1.8s
Output Size
2.2MB
HMR Time
112ms
Dev Startup
1.0s

About the Qwik Weather Front App

Status

  • Lint
  • Build
  • Test

Usage Instructions

First, follow the repo setup instructions.
Then cd into ./apps/qwik/ and and use the following commands:

  • Dev Command npm run dev
  • Test Command npm run test
  • Lint Command npm run lint
  • Build Command npm run build
  • Start npm start
For troubleshooting, use npm run verify from the root of the project.

App Requirements

The purpose of this project, was to build the same identical app in every frontend framework, in order to benchmark and compare their performance. As such, each app is built to meet identical requirements, which are then verified with the test suite.

Technical Requirements

  • Binding user input and validation
  • Fetching external data asynchronously
  • Basic state management of components
  • Handling fallback views (loading, errors)
  • Using browser features (location, storage, etc)
  • Logic blocks, for iterative content and conditionals
  • Lifecycle methods (mounting, updating, unmounting)

Feature Requirements

  • 🌦️ Live weather conditions
  • πŸ“… 7-day weather forecast
  • πŸ” City search functionality
  • πŸ“ Geolocation support
  • πŸ’Ύ Persistent location storage
  • πŸ“± Responsive design
  • β™Ώ Accessible interface
  • 🎨 Multi-theme support
  • πŸ§ͺ Fully unit tested
  • 🌐 Internationalized

Qwik Implementation

Resumability & Serialization

Qwik's defining feature is resumability - the app can be paused on the server and resumed on the client without re-execution. Functions prefixed with $ like $(async (city: string) => {...}) create serialization boundaries.

useSignal for State

The App.tsx uses useSignal<WeatherData | null>(null) for reactive state management, similar to React but optimized for Qwik's lazy execution model.

Context API

The weatherStore.ts defines a context using createContextId<WeatherState>('weather') for sharing state across components without prop drilling.

useVisibleTask$ Optimization

Qwik's useVisibleTask$() only runs when the component becomes visible, enabling fine-grained lazy loading and reducing initial JavaScript execution.

File-based Routing

Uses Qwik City's file-based routing system with routes/index.tsx automatically mapping to the root path, similar to Next.js but with Qwik's resumability benefits.

About Qwik

Real-world App

Since the weather app is very simple, and doesn't show of the full features of a framework, it may be helpful to see a more practical implementation of a Qwik app. So, checkout:
Digital Defense Logo

Digital Defense

Interactive personal security checklist

Intro to Qwik

About Qwik

Qwik is all about instant load times and fine-grained lazy loading. It serialises app state into HTML, letting pages become interactive with almost zero JS upfront. It’s built for the modern web where performance and SEO matter. It feels experimental but it’s pushing interesting ideas around resumability.

My thoughts on Qwik

Qwik is kinda wild. It completely rethinks how web apps work by doing something called "resumability" - your page loads instantly with zero JavaScript, then individual components wake up only when you interact with them. It's like having a webpage that's asleep until you poke it.

The secret is those $ symbols everywhere. component$(), useTask$(), onClick$() - these aren't just weird syntax, they're lazy loading boundaries. Each $ tells Qwik "this code can be loaded later when needed." So clicking a button doesn't load the entire app, it just loads that specific button's handler.

For our weather app, this means the initial page render is lightning fast - just HTML and CSS. Search for a city, and only then does the search logic get loaded. Click to expand a forecast day, and only the expansion code gets fetched. It's incremental interactivity taken to its logical extreme.

The state management feels familiar but with superpowers. Qwik stores automatically serialize to HTML, so when components resume, they pick up exactly where they left off. No hydration mismatch, no loading spinners, just seamless continuation. For that reason, I used Qwik to build the interactive stuff on my Digital Defense website.

The trade-off is developer complexity - all those $ symbols take getting used to, and debugging can be tricky when code loads on-demand. But for performance-critical apps, especially content-heavy sites, Qwik's approach is genuinely revolutionary. Your Core Web Vitals scores will thank you.

Choosing a Framework

Stack Match Stack Match

Not sure if Qwik is right for your project? Use Stack Match to select your preferences and get a tailored recommendation based on the benchmark data.

Stack Match Screenshot