Browser Support Test — Zig source
Audit your real browser against 30 modern web capabilities - WebGPU, WASM, WebAuthn, Service Workers and more. Get a weighted readiness score, copy-paste detection snippets, and a shareable link.
This is the Zig implementation — the same logic the interactive tool runs, in a shareable, citable form.
// browser-support-test — Zig polyglot showcase port.
//
// Runtime capability probe, weighted score, and support tier.
//
// This is the Zig sibling of src/tools/BrowserSupportTest.tsx (+ the
// browser-support/* modules) that powers the live tool.
//
// ILLUSTRATIVE PORT: the live tool detects *browser* features at runtime
// (navigator/window probes) — a browser-only concern that cannot run in a
// native Zig process. This port shows the ANALOGOUS pattern for a Zig
// build: it probes comptime-known `builtin` facts (target OS, CPU arch,
// feature flags, @sizeOf) — the mechanism Zig uses to gate platform code,
// and the direct equivalent of Rust's cfg!(). The scoring algorithm and
// tier thresholds below are byte-for-byte the same as the TypeScript
// lib's; only the probe targets differ.
//
// Language: Zig (0.13, standard library only).
// Ported from src/tools/BrowserSupportTest.tsx (+ browser-support/* modules).
// Source: CosmoDev polyglot showcase port.
// License: display source — part of CosmoDev's polyglot tool pages.
const std = @import("std");
const builtin = @import("builtin");
const Target = std.Target;
const SUPPORTED = "supported";
const UNSUPPORTED = "unsupported";
const LIMITED = "limited";
const UNKNOWN = "unknown";
/// One capability the audit can check; `probe` returns true when the
/// capability is present in THIS build.
const Check = struct {
id: []const u8,
title: []const u8,
category: []const u8,
weight: f64,
probe: *const fn () bool,
};
/// Outcome of one probe.
const FeatureResult = struct {
id: []const u8,
status: []const u8,
};
/// A support tier: display label + tone class.
const Tier = struct {
label: []const u8,
tone: []const u8,
};
/// contribution × weight. Same values as src/tools/browser-support/score.ts.
fn contribution(status: []const u8) f64 {
if (std.mem.eql(u8, status, "supported")) return 1.0;
if (std.mem.eql(u8, status, "limited")) return 0.5;
if (std.mem.eql(u8, status, "needs-https")) return 0.3;
return 0.0; // unsupported, unknown
}
/// Weighted readiness 0–100; matches computeScore() exactly. Results whose
/// id isn't in the catalog are ignored.
fn computeScore(results: []const FeatureResult, catalog: []const Check) i32 {
var earned: f64 = 0.0;
var possible: f64 = 0.0;
for (results) |r| {
// Look up this result's weight in the catalog (skip unknown ids).
for (catalog) |c| {
if (std.mem.eql(u8, c.id, r.id)) {
earned += contribution(r.status) * c.weight;
possible += c.weight;
break;
}
}
}
if (possible == 0.0) return 0;
return @intFromFloat(@round(earned / possible * 100.0));
}
/// tier_for mirrors tierFor() in the island — same thresholds.
fn tierFor(score: i32) Tier {
if (score >= 90) return .{ .label = "Fully modern", .tone = "text-success" };
if (score >= 75) return .{ .label = "Very capable", .tone = "text-success" };
if (score >= 55) return .{ .label = "Capable, minor gaps", .tone = "text-accent" };
if (score >= 35) return .{ .label = "Showing its age", .tone = "text-fg-muted" };
return .{ .label = "Legacy browser", .tone = "text-danger" };
}
// Probes. `builtin` facts are comptime-known, resolved from the target
// triple at build time — Zig's equivalent of Rust's cfg!() / the
// browser's `'feature' in window`.
fn is64Bit() bool {
return @sizeOf(usize) == 8;
}
fn isUnix() bool {
return switch (builtin.os.tag) {
.macos, .ios, .tvos, .watchos, .linux, .freebsd, .netbsd, .openbsd, .dragonfly, .solaris => true,
else => false,
};
}
fn isWasm() bool {
return builtin.cpu.arch.isWasm();
}
fn hasAvx2() bool {
return Target.x86.featureSetHas(builtin.cpu.features, .avx2);
}
fn hasNeon() bool {
// NEON is baseline on aarch64, but the feature flag is still tracked.
return Target.aarch64.featureSetHas(builtin.cpu.features, .neon);
}
fn hasNativeAtomics() bool {
// wasm32 without the threads feature has no native pointer atomics.
return !builtin.cpu.arch.isWasm();
}
/// Representative catalog of comptime-gated capabilities. (File-scope so
/// `catalog.len` is a comptime constant the results buffer can size on.)
const catalog = [_]Check{
.{ .id = "ptr-64", .title = "64-bit pointers", .category = "Platform", .weight = 1.0, .probe = is64Bit },
.{ .id = "unix", .title = "Unix target", .category = "Platform", .weight = 2.0, .probe = isUnix },
.{ .id = "wasm", .title = "WASM target", .category = "Platform", .weight = 2.0, .probe = isWasm },
.{ .id = "avx2", .title = "AVX2", .category = "Cpu", .weight = 2.0, .probe = hasAvx2 },
.{ .id = "neon", .title = "NEON", .category = "Cpu", .weight = 2.0, .probe = hasNeon },
.{ .id = "atomics", .title = "Atomic ops", .category = "Runtime", .weight = 3.0, .probe = hasNativeAtomics },
};
/// Run probes. Zig has no exceptions and these probes are total functions,
/// so every check lands on supported/unsupported — the references'
/// degrade-to-'unknown' arm has nothing to intercept.
fn runChecks(checks: []const Check, out: []FeatureResult) void {
for (checks, 0..) |c, i| {
out[i] = .{ .id = c.id, .status = if (c.probe()) SUPPORTED else UNSUPPORTED };
}
}
pub fn main() !void {
// The results buffer mirrors the catalog 1:1; no allocator needed.
var results: [catalog.len]FeatureResult = undefined;
runChecks(&catalog, &results);
const score = computeScore(&results, &catalog);
const tier = tierFor(score);
var supported: usize = 0;
for (results) |r| {
if (std.mem.eql(u8, r.status, SUPPORTED)) supported += 1;
}
const stdout_file = std.io.getStdOut();
var bw = std.io.bufferedWriter(stdout_file.writer());
const stdout = bw.writer();
// LIMITED/UNKNOWN are intentionally absent from probes — kept for
// vocabulary parity with the sibling ports.
try stdout.print("browser-support-test (Zig) on {s}/{s}\n", .{
@tagName(builtin.os.tag), @tagName(builtin.cpu.arch),
});
try stdout.print("{d}/{d} capabilities · readiness {d} · {s}\n", .{
supported, results.len, score, tier.label,
});
try bw.flush();
}
Also available in 13 other languages
Every CosmoDev tool ships its pure logic in TypeScript (web) and Go (CLI), with authored implementations in a dozen-plus languages — the same contract, ported. Compare all languages side by side →