Netnyahoo
Mac용 실질적인 Chromium으로, Arc 사이드바와 Dia 폴리시를 갖추고 계정 없이 무료·오픈소스이며 광고·추적·소송에 면역이다
아직 감지된 업데이트가 없습니다. GitHub 릴리스가 나오면 여기에 보입니다.
개인 계정의 공개 저장소 소유자는 GitHub로 로그인해 운영자를 확인하고 소개를 직접 관리할 수 있습니다. 관리자 승인은 필요하지 않습니다.
로그인한 뒤 확인 파일을 만들어 이 저장소의 기본 브랜치에 30분 안에 커밋해 주세요. 다른 브랜치나 포크의 파일은 인정하지 않습니다. 파일을 올린 뒤 아래에서 확인하면 관리자 승인 없이 관리할 수 있습니다. 자격을 유지하려면 파일을 남겨 두세요.
로그인이 필요하면 로그인 화면으로 이동합니다. 로그인 후 이곳으로 돌아와 원하는 확인 버튼을 다시 눌러 주세요.
프로젝트 폴더에서 /nomorevibe verify를 실행하면 소유권을 확인하고 소개를 직접 관리할 수 있습니다.
1분 만에 확인하기An interactive civic intelligence platform visualizing Seattle neighborhood conditions, service requests, and trends using public city data.
저장소 README에서 가져옴
README 전체를 불러오는 중입니다.
README 전문 보기 ↗An interactive civic intelligence dashboard for exploring what Seattle residents report to the City: where requests are concentrated, which neighborhoods report the most, what kinds of issues dominate, and how volume changes over time. Every number comes live from the City of Seattle's open data.
This is an exercise in agentic development using Claude Code.
Map of Seattle. Three backgrounds you can switch between:
Clustered markers on top show the newest 2,000 matching requests. Click a cluster to zoom in, or a marker to see its details. The legend states each layer's scope.
Filters: date range (presets or custom), request type, current status, neighborhood (Community Reporting Area) and council district. Filters live in the URL, so any view can be shared. Every filter updates the map, metrics, charts and list together.
Summary metrics: total requests, daily average, most reported type, and the share with usable coordinates.
Period-over-period change: the total and every neighborhood/district bar show the change versus the equally long period just before, with the same filters (e.g. "▼ −2.0% vs Aug 21 – Sep 19"). When the previous count is under 20, the absolute change is shown instead of a volatile percentage. Changes use neutral arrows, not red/green, because more reports isn't necessarily worse.
Trends: requests per day, week (Mon–Sun) or month, chosen from the range length. Days with no requests are zero-filled, and buckets cut short by the range are drawn dashed and labelled.
Is the City responding equally?: compares how quickly tracked requests get a "Closed" update across census tracts grouped by the City's Racial and Social Equity Index. Each group is adjusted for its mix of request types and shown with a 95% margin of error. It also breaks results down by request type and lists the neighborhoods furthest from expected.
Response times: for the five request types the City tracks (abandoned vehicles, graffiti, illegal dumping, public litter cans, streetlights), the share that got a "Closed" status update within 7 and 30 days and the median days. Measured on a cohort old enough to judge, so recent requests can't skew it.
Breakdowns: request types, current status, and an area comparison by neighborhood or council district. Neighborhoods can be compared by raw count or per 1,000 residents (2020 Census). Areas with fewer than 5,000 residents are listed separately rather than ranked, because their rates aren't comparable. Each bar is a keyboard-accessible button that toggles that filter.
The count / per-capita choice drives the map shading too.
Recent requests: newest first and paged. Selecting one flies the map to it and opens its detail card. Requests without coordinates are listed and flagged, never placed on the map.
Loading, empty, partial and error states throughout. If a refresh fails, the last good results stay visible with a retry button.
For the story behind the build (data findings, scope decisions and the bugs verification caught), see the case study.
Requires Node.js 22.12+ and npm. Node 24 LTS is recommended and pinned in .nvmrc (nvm use).
git clone https://github.com/joshduplaa/seattle-neighborhood-pulse.git
cd seattle-neighborhood-pulse
npm ci
npm run dev # http://localhost:3000
No API key or database is needed. Optionally, copy .env.example to .env.local and set SOCRATA_APP_TOKEN to raise Socrata's throttling limits.
| Command | What it does |
|---|---|
npm run dev | Development server (copies the MapLibre worker first) |
npm run build / npm start | Production build and server |
npm test | Unit and component tests (Vitest + React Testing Library) |
npm run typecheck | tsc --noEmit (strict, noUncheckedIndexedAccess) |
npm run lint | ESLint (Next.js core-web-vitals + TypeScript rules) |
npm run check | Typecheck, lint and test together |
| Dataset | Customer Service Requests, City of Seattle (public domain) |
| Dataset ID | 5ngg-rpne |
| API | Socrata SODA 2 / SoQL: https://data.seattle.gov/resource/5ngg-rpne.json (API docs) |
| Scope | Requests submitted through the Find It, Fix It app, the Customer Service Request portal, phone, email and other channels, for request types that are or were offered to the public |
| Size and freshness | ~2.53 million rows, Jan 2013 → present; refreshed once a day (as of 2026-10-20) |
All dataset constants live in src/lib/socrata/config.ts.
| Dataset | Customer Service Request Tracking Data (43nw-pkdq), City of Seattle |
| Coverage | ~446,500 requests since 2023-01-01: Abandoned Vehicle, Graffiti Report, Illegal Dumping, Public Place Litter & Recycling, Streetlight Repair |
| Fields used | servicerequestnumber, servicerequesttype, createddate, updateddate, statuscategory (Routed to Department / In Progress / Closed) |
How it's measured:
Closed update came within 7 days and within 30 days, plus the median days. Requests never closed stay in the denominator.… GROUP BY servicerequestnumber |> SELECT date_diff_d(u, c) …); no per-request rows are downloaded.TRACKED_TYPES).| Equity data | Racial and Social Equity Composite Index Current, City of Seattle (2026 index) |
| Geography | Seattle's 179 census tracts (2020), each with COMPOSITE_QUINTILE from Highest Equity Priority (most disadvantaged) to Lowest; 34–38 tracts per quintile |
| Stored as | src/data/equity-tracts.json, regenerated with node scripts/fetch-equity-tracts.mjs (server-side only) |
How the equity analysis is calculated:
| Dataset | Community Reporting Areas (2020) – Redistricting Data 1990–2020, City of Seattle |
| Hosted at | Seattle GeoData (ArcGIS): services.arcgis.com/ZOyb2t4B0UYuYNYH/arcgis/rest/services/CRA_90_20_PL/FeatureServer/0 |
| Used | 53 area polygons (simplified to ~10 m) and F2020_PL_data_TOT_POP, the 2020 Census P.L. 94-171 total population (sums to 737,015, Seattle's 2020 count) |
| Stored as | Static files in src/data/, regenerated with node scripts/fetch-cra-data.mjs |
All 53 area names match the requests dataset's community_reporting_area values exactly, ignoring case (verified on 2026-10-20). Boundaries and 2020 population change rarely, so they ship with the app instead of being fetched at runtime.
servicerequestnumber, webintakeservicerequests (request type), departmentname, createddate, methodreceivedname, servicerequeststatusname, location (address), latitude/longitude, latitude_longitude (point), zipcode, councildistrict, policeprecinct and community_reporting_area.createddate is a floating timestamp (no UTC offset) in Seattle local time. The app treats it as a local calendar date and never shifts it through a timezone.Closed, Open, Reported, New, Transferred to Other Dept, Duplicate (Closed), Duplicate (Open), Closed as Duplicate, Closed -Incomplete Information, Canceled. They are shown verbatim, not regrouped.Browser (client components) Next.js server Seattle Open Data
────────────────────────── ────────────────── ─────────────────
useFilterState ── URL search params
useDashboardData ── GET /api/dashboard ──▶ route.ts
├─ parseFilters (validate/clamp)
└─ getDashboardDataCached ── TTL cache (15 min, in-flight de-dupe)
└─ getDashboardData ── 8 SoQL queries in parallel ──▶ /resource/5ngg-rpne.json
├─ normalize (zod)
└─ aggregate (zero-fill, buckets, totals)
src/
app/
page.tsx, layout.tsx page shell, header, nav, footer
api/dashboard/route.ts the only server endpoint: validation, error mapping, gzip
lib/
socrata/config.ts dataset IDs, URLs, field names, limits
population.ts 2020 population, per-1,000 rates, quantile classes
equity.ts, geo.ts equity-of-response analysis; point-in-polygon lookup
socrata/soql.ts SoQL query builders (escaping, half-open date range)
socrata/client.ts fetch with timeout, retries, typed SocrataError
socrata/normalize.ts zod validation and normalization of raw rows
aggregate.ts time-series bucketing, totals, top-N folding
dashboard.ts assembles one coherent DashboardData response
dashboard-cache.ts, cache.ts in-process TTL cache
filters.ts, dates.ts, format.ts, types.ts
components/
map/ MapLibre map (client-only), layers, legend, overlays
charts/ TrendChart (Recharts), RankedBars (semantic HTML)
dashboard/ filters, metrics, panels, recent list, detail, provenance
hooks/ URL filter state, data fetching with abort
data/ CRA boundaries + 2020 population (generated by scripts/fetch-cra-data.mjs)
Aggregate on the server, never in the browser. Each filter change triggers ten SoQL queries server-side:
snap_to_grid density grid of about 550 m cells;The browser receives about 76 KB gzipped, never millions of rows.
Explicit data scopes. Totals, charts, breakdowns and the density layer cover all matching requests. Markers and the recent list are a labelled sample of the newest 2,000. The total is derived from the type facet, and tests check that the facets and the time series sum to the same number.
One filter model everywhere. parseFilters normalizes the URL on the client and the query on the server identically. Invalid input is corrected and reported, never silently trusted. SoQL literals are escaped.
Caching. The source updates once a day, so results are cached in-process for 15 minutes, keyed by the normalized filters, and concurrent identical requests share one upstream call. Failures are never cached. Responses also carry Cache-Control: s-maxage=300, stale-while-revalidate=600 for CDNs.
'use cache' was tried and dropped: errors thrown inside it are serialized and lose their class, which broke the typed error mapping (timeout → 504, rate limit → 503, and so on).Presets end yesterday. The City publishes once a day, so "today" is almost always incomplete and would look like a sudden drop. Custom ranges can include today, and the chart then warns that the last day may be incomplete.
Ranked bars are HTML, not SVG. Category, status and area breakdowns double as filter controls, so they are real buttons with aria-pressed and wrap long Seattle place names. Recharts draws the time series, where a crosshair and tooltip matter.
Map. MapLibre GL 6 with the key-less OpenFreeMap Positron basemap (OpenStreetMap data). MapLibre 6 loads its web worker relative to its own module, which bundlers relocate, so copies the worker into before and , and the app calls .
npm ci, npm run check and npm run build on Node 24 for every pull request and every push to main.npm run typecheck, npm run lint, npm test and npm run build all pass (CI runs them on every pull request).src/lib/__fixtures__/), malformed input, time-series bucketing and partial buckets, cache behaviour, HTTP client retry and error classification, the API route's error mapping and gzip, and key components.Last-Modified header.It's a standard Next.js app with no database or secrets.
SOCRATA_APP_TOKEN.npm ci && npm run build && npm start (set PORT as needed). The prebuild script copies the MapLibre worker, so always build with npm run build, not next build directly.data.seattle.gov (server) and tiles.openfreemap.org (browser) must be allowed.Data: City of Seattle, Customer Service Requests (public domain). Basemap © OpenStreetMap contributors, OpenFreeMap. This is an independent project, not affiliated with the City of Seattle.
scripts/copy-maplibre-worker.mjspublic/vendor/devbuildsetWorkerUrl()Visual system. A neutral fog canvas and slate ink, one data hue (Puget Sound teal #00789a), a one-hue sequential ramp for density, and ferry orange reserved for the selected request. The data colors were checked for colour-vision-deficiency separation and contrast.