feat: Astro redesign with industry consolidation - #827
Conversation
Migrate from Phoenix/Elixir to Astro static site with Preact islands. Industry consolidation: - Consolidate 89 freeform industry values into 17 validated categories - Add multi-industry support (1-3 industries per company via Zod enum array) - Add 4 new categories: Professional Services, Media & Entertainment, Government & Non-Profit, Agriculture & Food - All 326 company markdown files migrated with primary/secondary industries - Build-time validation ensures no invalid industry values New Astro site includes: - Static site generation with content collections - Preact search/filter island with URL state sync - Tailwind CSS with dark mode support - Company cards with industry color coding and icons - Related companies based on industry overlap
bbc251b to
c971898
Compare
|
Looking forward to this new era! The Elixir Companies website has made a lot of progress, and this newest design looks amazing!! I noticed that companies with multiple industries show an icon only on the first tag in card/search views, while the company detail page shows icons on all industry tags.
Proposed fix: a single One component, always renders ---
// src/components/IndustryTag.astro
const { industry, size = 'sm' } = Astro.props;
const icon = getIndustryIcon(industry);
const color = getIndustryColor(industry);
const sizeClass = size === 'sm' ? 'text-[0.65rem]' : 'text-sm';
---
<span class={`industry-tag inline-flex ${color} ${sizeClass}`}>
<span class="mr-1">{icon}</span>
{industry}
</span>Then The icon is part of the tag's identity (it helps users pattern-match industries while scanning). Stripping it from some instances defeats that purpose. |
|
The project defines the list of valid industries in two separate places:
These are maintained by hand independently. If you add a new industry to the schema but forget to add it in utils/industries.ts, nothing breaks loudly — the UI just silently falls back to a gray badge with a generic icon. The reverse (adding to utils but not the schema) means the color/icon exists but no company can ever use that industry. The fix is to have one canonical list. For example, define everything in utils/industries.ts: export const INDUSTRIES = {
"Financials": { color: "blue", icon: "💰" },
"Health Care": { color: "red", icon: "🏥" },
// ...
} as const;
export const INDUSTRY_VALUES = Object.keys(INDUSTRIES) as [string, ...string[]];Then in config.ts, just import it: import { INDUSTRY_VALUES } from '../utils/industries';
z.array(z.enum(INDUSTRY_VALUES)).min(1).max(3)One place to add/remove/rename an industry, and both the build validation and the UI styling stay in sync automatically. |
- Create shared IndustryTag component (Astro + Preact mirror) that always renders icon + label, using size prop for visual hierarchy - Consolidate INDUSTRY_DATA into a single canonical object in utils/industries.ts; derive INDUSTRY_VALUES from its keys - config.ts now imports INDUSTRY_VALUES from utils/industries.ts instead of maintaining a duplicate list - All three rendering contexts (CompanyCard, SearchFilter, [slug]) now use the same tag contract: icon always present, size varies Addresses feedback from @burden on PR #827.
|
Re: IndustryTag component feedback Done — created a shared For the Preact island ( All three contexts now render tags identically — icon is always present, hierarchy is communicated through size only. Great catch on the visual inconsistency. Re: Single source of truth for industries Done — consolidated everything into a single |
The Astro build validates everything — Zod schema, TypeScript, templates — not just company files. Renamed to ci.yml, broadened triggers to run on all PRs and pushes to main (not just company file changes), since schema or component changes can also break the build.
Company descriptions containing markdown links like [text](url) were rendering raw syntax on cards. Now strips link syntax and formatting characters before truncation so cards show clean plain text.
Summary
Complete site redesign migrating from Phoenix/Elixir to an Astro static site with Preact interactive islands.
Industry consolidation — The existing 89 freeform industry values have been consolidated into 17 validated categories based on GICS, with 4 new additions (Professional Services, Media & Entertainment, Government & Non-Profit, Agriculture & Food). Companies now support 1–3 industries each, enforced at build time via Zod enum validation.
industryfield changed fromz.string()toz.array(z.enum(INDUSTRY_VALUES)).min(1).max(3)Complexity Notes
scripts/migrate-industries.mjs) contains the complete 89→17 mapping. This ran with 0 warnings across all 326 files.Test Steps
npm install && npm run build— should complete with 0 errors (validates all 326 company frontmatter against Zod enum schema)npm run devand check the home page:Checklist