HTML Fundamentals: Building the Web's Structure
Master HTML from the ground up β DOCTYPE, semantic elements, forms, accessibility, and building a complete personal bio page.
HTML Fundamentals: Building the Web's Structure
HTML is not a programming language. It is a markup language β a way of annotating content so browsers know what each piece means and how to present it. Understanding this distinction matters because it shapes how you think about your job when writing HTML: you are not writing logic, you are describing meaning.
Every website you have ever visited starts with HTML. JavaScript makes things interactive, CSS makes them beautiful, but HTML is the skeleton everything else hangs on. Get it right and the rest of your frontend work becomes easier. Get it wrong and you spend weeks fighting accessibility audits, SEO penalties, and browser quirks.
This guide walks you through HTML from first principles to a complete, accessible personal bio page.
The DOCTYPE Declaration
Every HTML document starts with a DOCTYPE declaration. This is not an HTML tag β it is an instruction to the browser about which version of HTML you are using.
<!DOCTYPE html>That single line tells the browser: "Render this document using modern HTML5 standards." Without it, browsers fall into "quirks mode" β a compatibility mode that tries to emulate the broken behavior of 1990s browsers. You do not want that.
Historically, DOCTYPE declarations were verbose:
<!-- Old HTML 4.01 Strict DOCTYPE β do not use this -->
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">HTML5 simplified this to the short form. Always use <!DOCTYPE html>.
The Basic HTML Document Structure
Every HTML document follows this fundamental structure:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta name="description" content="A brief description of the page for search engines." />
<title>Page Title</title>
<link rel="stylesheet" href="styles.css" />
</head>
<body>
<!-- Your visible content goes here -->
</body>
</html>Let's break down each piece:
<html lang="en"> β The root element of the document. The lang attribute tells browsers and screen readers what language the content is in. This matters for correct text-to-speech pronunciation and search engine indexing. Use the appropriate BCP 47 language tag (en, fr, de, ar, etc.).
<head> β Contains metadata about the document β information that is not displayed on the page but is essential for the browser, search engines, and social media scrapers.
<meta charset="UTF-8"> β Declares the character encoding. UTF-8 supports virtually every character in every language. Without this, special characters like Γ©, ΓΌ, Γ±, and emoji may display as garbage. Always include it as the first element in <head>.
<meta name="viewport"> β Critical for responsive design on mobile devices. Without it, mobile browsers render the page at desktop width and then scale it down, making text tiny. width=device-width makes the viewport match the screen width, and initial-scale=1.0 prevents automatic zooming.
<title> β The text shown in the browser tab and in search engine results. Keep it under 60 characters. It is the single most important piece of SEO text on the page.
Semantic HTML: Why It Matters
Semantic HTML means using elements that describe the meaning of content, not just its appearance. Compare these two approaches:
<!-- Non-semantic: all divs, no meaning -->
<div class="header">
<div class="nav">
<div class="nav-item">Home</div>
<div class="nav-item">About</div>
</div>
</div>
<div class="main-content">
<div class="article">
<div class="article-title">My First Post</div>
<div class="article-body">Content here...</div>
</div>
</div>
<div class="footer">Copyright 2026</div><!-- Semantic: elements carry meaning -->
<header>
<nav>
<a href="/">Home</a>
<a href="/about">About</a>
</nav>
</header>
<main>
<article>
<h1>My First Post</h1>
<p>Content here...</p>
</article>
</main>
<footer>
<p>Copyright 2026</p>
</footer>The second version communicates meaning to:
- Screen readers β A blind user's screen reader announces "navigation landmark" when reaching
<nav>, letting them jump straight to it. With<div>, it just reads everything sequentially. - Search engines β Google understands that content inside
<article>is a self-contained piece of writing and weights it differently than sidebar content. - Other developers β Anyone reading your code immediately understands the page structure without needing to decode class names.
Core Semantic Elements
<header>
Introductory content for a section or the whole page. Usually contains a logo, site title, and primary navigation. A page can have multiple headers β one for the page, one inside each <article>.
<header>
<img src="logo.svg" alt="Learnixo Logo" />
<h1>Learnixo</h1>
<nav>...</nav>
</header><nav>
A section of the page dedicated to navigation links. Use it for the main site navigation and for a table of contents, but not for every group of links (footer links about terms and privacy usually do not need a <nav>).
<nav aria-label="Main navigation">
<ul>
<li><a href="/">Home</a></li>
<li><a href="/courses">Courses</a></li>
<li><a href="/articles">Articles</a></li>
<li><a href="/about">About</a></li>
</ul>
</nav><main>
The dominant content of the document. There should be only one <main> per page, and it should not contain headers, footers, or sidebars that repeat across pages. Screen reader users use this as a "skip to main content" landmark.
<article>
A self-contained piece of content that could be distributed or syndicated independently β a blog post, a news article, a forum post, a product card, a comment. Ask yourself: "If I extracted this element and put it on a different page, would it still make sense?" If yes, it is an article.
<article>
<header>
<h2>Understanding CSS Grid</h2>
<p>Published on <time datetime="2026-04-17">April 17, 2026</time></p>
</header>
<p>CSS Grid is a two-dimensional layout system...</p>
</article><section>
A thematic grouping of content that belongs together. Unlike <article>, a section is part of a larger whole. Use it to divide a long page into logical chapters. Every section should have a heading.
<section>
<h2>My Skills</h2>
<ul>
<li>HTML & CSS</li>
<li>JavaScript</li>
<li>React</li>
</ul>
</section><aside>
Content tangentially related to the surrounding content β a sidebar, a pull quote, an advertising block, a related links panel.
<aside>
<h3>Related Articles</h3>
<ul>
<li><a href="/css-fundamentals">CSS Fundamentals</a></li>
<li><a href="/js-basics">JavaScript Basics</a></li>
</ul>
</aside><footer>
Closing content for a section or the whole page. Contains copyright notices, secondary navigation, contact information, social links.
Headings: The Document Outline
HTML has six levels of headings: <h1> through <h6>. They create a hierarchical outline of your document.
<h1>My Personal Portfolio</h1> <!-- Page title β one per page -->
<h2>About Me</h2> <!-- Major section -->
<h3>Education</h3> <!-- Subsection -->
<h3>Work Experience</h3> <!-- Subsection -->
<h4>Senior Developer at Acme</h4> <!-- Sub-subsection -->
<h2>My Projects</h2>
<h2>Contact</h2>Critical rules:
- One
<h1>per page. It is the main title of the page, equivalent to the title of a book. - Do not skip levels. Going from
<h2>to<h4>confuses screen readers and breaks the outline. If you want a visually smaller heading under an<h2>, use an<h3>and style it with CSS. - Do not use headings for big text. If you want large bold text that is not a section heading, use a
<p>and style it. Headings are for structure, not decoration.
Text Content
Paragraphs
<p> is for paragraphs of prose. The browser adds default margin between paragraphs. Never use <br> tags to create space between paragraphs β that is what CSS margin is for.
<p>
Hi, I'm Asma. I'm a software engineer specializing in .NET and React.
I've been building web applications for over eight years.
</p>
<p>
When I'm not coding, I enjoy hiking and reading about distributed systems.
</p>Inline Text Elements
<!-- Strong importance β screen readers may emphasize these -->
<p>Never store passwords in <strong>plain text</strong>.</p>
<!-- Emphasis β stress emphasis, like tone of voice -->
<p>I said I wanted the <em>blue</em> one, not the red one.</p>
<!-- Generic inline container β use for styling only, no semantic meaning -->
<p>Press <span class="key">Ctrl</span> + <span class="key">C</span> to copy.</p>
<!-- Inline code -->
<p>Use the <code>querySelector()</code> method to find elements.</p>
<!-- Abbreviations with full form -->
<p><abbr title="HyperText Markup Language">HTML</abbr> is a markup language.</p>
<!-- Time with machine-readable format -->
<p>The event is on <time datetime="2026-05-20T14:00">May 20, 2026 at 2pm</time>.</p>Links
Links are the foundation of the web. Every link is an <a> (anchor) element.
<!-- External link β open in same tab by default -->
<a href="https://developer.mozilla.org">MDN Web Docs</a>
<!-- External link β open in new tab -->
<!-- Add rel="noopener noreferrer" for security when using target="_blank" -->
<a href="https://github.com/asmahafeez" target="_blank" rel="noopener noreferrer">
My GitHub Profile
</a>
<!-- Internal link β relative URL -->
<a href="/about">About Me</a>
<!-- Link to section on same page -->
<a href="#contact">Jump to Contact Section</a>
<!-- Email link -->
<a href="mailto:hello@example.com">Email Me</a>
<!-- Phone link -->
<a href="tel:+15551234567">Call Me</a>
<!-- Download link -->
<a href="/resume.pdf" download="Asma-Hafeez-Resume.pdf">Download Resume</a>Accessibility rule: Link text must describe the destination. Never write <a href="...">Click here</a>. Screen reader users often navigate by listing all links on a page β "Click here" tells them nothing.
<!-- Bad: meaningless out of context -->
<a href="/css-guide">Click here</a> to learn CSS.
<!-- Good: descriptive link text -->
<a href="/css-guide">Learn CSS in our complete guide</a>.Images
<!-- Basic image -->
<img src="profile-photo.jpg" alt="Asma Hafeez smiling at a conference" />
<!-- Decorative image β empty alt means screen readers skip it -->
<img src="divider.svg" alt="" />
<!-- Image with width and height to prevent layout shift -->
<img
src="hero-banner.jpg"
alt="Code editor showing a JavaScript file"
width="1200"
height="600"
/>
<!-- Responsive image with srcset -->
<img
src="photo-800w.jpg"
srcset="photo-400w.jpg 400w, photo-800w.jpg 800w, photo-1200w.jpg 1200w"
sizes="(max-width: 600px) 400px, (max-width: 1000px) 800px, 1200px"
alt="Mountain landscape at sunset"
width="800"
height="533"
/>
<!-- Figure with caption -->
<figure>
<img src="architecture-diagram.png" alt="Microservices architecture diagram showing 5 services" />
<figcaption>Figure 1: Microservices architecture with API Gateway pattern</figcaption>
</figure>The alt attribute is mandatory. If an image has meaning β a photo, a chart, a diagram β describe it clearly. If it is purely decorative, use alt="" so screen readers skip it. Never omit the alt attribute entirely.
Lists
HTML has three types of lists:
<!-- Unordered list β for items where order doesn't matter -->
<ul>
<li>HTML</li>
<li>CSS</li>
<li>JavaScript</li>
</ul>
<!-- Ordered list β for steps, rankings, sequences where order matters -->
<ol>
<li>Create the HTML structure</li>
<li>Add CSS styling</li>
<li>Write JavaScript for interactivity</li>
</ol>
<!-- Nested list -->
<ul>
<li>Frontend
<ul>
<li>React</li>
<li>Vue</li>
</ul>
</li>
<li>Backend
<ul>
<li>Node.js</li>
<li>.NET</li>
</ul>
</li>
</ul>
<!-- Description list β for key-value pairs, glossaries, metadata -->
<dl>
<dt>HTML</dt>
<dd>HyperText Markup Language β the structure layer of the web</dd>
<dt>CSS</dt>
<dd>Cascading Style Sheets β the presentation layer</dd>
<dt>JavaScript</dt>
<dd>The behavior layer β makes pages interactive</dd>
</dl>Use <ul> when items are unordered. Use <ol> when sequence matters. A navigation menu is typically a <ul> because the links themselves are not ordered β they are just a collection.
Tables
Tables are for tabular data β information that has rows and columns and where the relationship between a cell and its row/column header carries meaning. Do not use tables for layout.
<table>
<caption>Programming Language Popularity 2026</caption>
<thead>
<tr>
<th scope="col">Language</th>
<th scope="col">Primary Use</th>
<th scope="col">Job Listings</th>
</tr>
</thead>
<tbody>
<tr>
<td>JavaScript</td>
<td>Web Frontend & Backend</td>
<td>142,000</td>
</tr>
<tr>
<td>Python</td>
<td>Data Science, AI, Backend</td>
<td>128,000</td>
</tr>
<tr>
<td>C#</td>
<td>Enterprise, Games, Backend</td>
<td>87,000</td>
</tr>
<tr>
<td>TypeScript</td>
<td>Typed JavaScript</td>
<td>96,000</td>
</tr>
</tbody>
<tfoot>
<tr>
<td colspan="2">Total</td>
<td>453,000</td>
</tr>
</tfoot>
</table>Key table accessibility elements:
<caption>β A visible title for the table. Screen readers announce it before reading the table.<thead>,<tbody>,<tfoot>β Semantic groupings of rows.<th scope="col">or<th scope="row">β Thescopeattribute tells screen readers which direction each header applies.
Forms
Forms are how users send data to your server. They are one of the most important parts of any web application.
<form action="/submit" method="POST" novalidate>
<!-- Text input -->
<div class="form-group">
<label for="fullname">Full Name <span aria-label="required">*</span></label>
<input
type="text"
id="fullname"
name="fullname"
placeholder="Jane Doe"
required
autocomplete="name"
/>
</div>
<!-- Email input -->
<div class="form-group">
<label for="email">Email Address <span aria-label="required">*</span></label>
<input
type="email"
id="email"
name="email"
placeholder="jane@example.com"
required
autocomplete="email"
/>
</div>
<!-- Password input -->
<div class="form-group">
<label for="password">Password</label>
<input
type="password"
id="password"
name="password"
minlength="8"
aria-describedby="password-hint"
/>
<p id="password-hint" class="hint">Must be at least 8 characters.</p>
</div>
<!-- Number input -->
<div class="form-group">
<label for="age">Age</label>
<input
type="number"
id="age"
name="age"
min="18"
max="120"
/>
</div>
<!-- Select dropdown -->
<div class="form-group">
<label for="role">Role</label>
<select id="role" name="role">
<option value="">-- Select a role --</option>
<option value="frontend">Frontend Developer</option>
<option value="backend">Backend Developer</option>
<option value="fullstack">Full Stack Developer</option>
<option value="devops">DevOps Engineer</option>
</select>
</div>
<!-- Select with option groups -->
<div class="form-group">
<label for="experience">Experience Level</label>
<select id="experience" name="experience">
<optgroup label="Junior">
<option value="0-1">0β1 years</option>
<option value="1-2">1β2 years</option>
</optgroup>
<optgroup label="Mid-Level">
<option value="2-4">2β4 years</option>
<option value="4-6">4β6 years</option>
</optgroup>
<optgroup label="Senior">
<option value="6-10">6β10 years</option>
<option value="10+">10+ years</option>
</optgroup>
</select>
</div>
<!-- Textarea -->
<div class="form-group">
<label for="bio">Short Bio</label>
<textarea
id="bio"
name="bio"
rows="5"
cols="40"
maxlength="500"
placeholder="Tell us about yourself..."
></textarea>
</div>
<!-- Checkboxes -->
<fieldset>
<legend>Technologies You Use</legend>
<label>
<input type="checkbox" name="tech" value="react" checked />
React
</label>
<label>
<input type="checkbox" name="tech" value="vue" />
Vue
</label>
<label>
<input type="checkbox" name="tech" value="angular" />
Angular
</label>
</fieldset>
<!-- Radio buttons -->
<fieldset>
<legend>Preferred Learning Style</legend>
<label>
<input type="radio" name="learning" value="video" />
Video tutorials
</label>
<label>
<input type="radio" name="learning" value="reading" checked />
Written articles
</label>
<label>
<input type="radio" name="learning" value="projects" />
Hands-on projects
</label>
</fieldset>
<!-- File upload -->
<div class="form-group">
<label for="avatar">Profile Picture</label>
<input
type="file"
id="avatar"
name="avatar"
accept="image/png, image/jpeg, image/webp"
/>
</div>
<!-- Hidden input -->
<input type="hidden" name="csrf_token" value="abc123xyz" />
<!-- Buttons -->
<div class="form-actions">
<button type="submit">Create Account</button>
<button type="reset">Clear Form</button>
<button type="button" onclick="saveDraft()">Save Draft</button>
</div>
</form>The label-input connection is critical. The for attribute on <label> must match the id on the input. This creates an explicit association so:
- Clicking the label focuses the input (improves usability, especially for small checkboxes).
- Screen readers announce the label when the input receives focus.
Never use placeholder text as a substitute for a label. Placeholder text disappears when the user starts typing, leaving them with no reminder of what the field was for.
HTML Attributes Deep Dive
Attributes modify element behavior. Some are global (work on any element), some are specific to certain elements.
<!-- Global attributes -->
<div id="unique-id">Unique on the page</div>
<span class="highlight bold">Multiple classes with spaces</span>
<p hidden>This paragraph is hidden from all users</p>
<p tabindex="0">This div can receive keyboard focus</p>
<p title="Tooltip text appears on hover">Hover over me</p>
<p lang="fr">Bonjour le monde</p>
<p contenteditable="true">Users can edit this text</p>
<p data-user-id="42" data-role="admin">Custom data attributes</p>
<p spellcheck="false">No spell checking here</p>
<p draggable="true">This element can be dragged</p>Data attributes (data-*) are your way to attach custom data to HTML elements that JavaScript can then read without polluting the DOM with non-standard attributes.
<button
class="delete-btn"
data-item-id="1042"
data-confirm-message="Are you sure you want to delete this item?"
>
Delete
</button>const btn = document.querySelector('.delete-btn');
const itemId = btn.dataset.itemId; // "1042"
const message = btn.dataset.confirmMessage; // "Are you sure..."Accessibility: Building for Everyone
Accessibility (often abbreviated a11y) means ensuring your content is usable by people with disabilities. About 15% of the world population has some form of disability. The web is one of the most powerful tools for independence and participation β do not break it.
Alt Text for Images
<!-- Informative image: describe what the image communicates, not just what it shows -->
<img src="sales-chart.png" alt="Bar chart showing 40% increase in sales from Q1 to Q4 2025" />
<!-- Functional image (a logo that is also a link): describe the function -->
<a href="/"><img src="logo.png" alt="Learnixo - go to homepage" /></a>
<!-- Decorative: empty alt tells screen readers to skip it -->
<img src="decorative-wave.svg" alt="" />ARIA (Accessible Rich Internet Applications)
ARIA attributes add semantic information that HTML alone cannot express.
<!-- aria-label: provides a text alternative when visible text is absent or insufficient -->
<button aria-label="Close dialog">Γ</button>
<!-- aria-labelledby: points to an element that labels this one -->
<div role="dialog" aria-labelledby="dialog-title" aria-describedby="dialog-desc">
<h2 id="dialog-title">Confirm Deletion</h2>
<p id="dialog-desc">This action cannot be undone.</p>
</div>
<!-- aria-describedby: points to additional descriptive text -->
<input type="password" aria-describedby="pw-requirements" />
<p id="pw-requirements">Password must be at least 8 characters and include a number.</p>
<!-- aria-expanded: for collapsible content -->
<button aria-expanded="false" aria-controls="menu">Menu</button>
<ul id="menu" hidden>...</ul>
<!-- aria-live: announces dynamic content updates to screen readers -->
<div aria-live="polite" id="status-message"></div>
<!-- aria-current: marks the current item in a set -->
<nav>
<a href="/">Home</a>
<a href="/about" aria-current="page">About</a>
<a href="/contact">Contact</a>
</nav>
<!-- role: overrides or adds semantic role when HTML semantics are insufficient -->
<div role="alert">Your session will expire in 5 minutes.</div>
<div role="status">File saved successfully.</div>
<div role="progressbar" aria-valuenow="45" aria-valuemin="0" aria-valuemax="100">45%</div>The ARIA first rule: never use ARIA when you can use semantic HTML instead. <button> is better than <div role="button">. <nav> is better than <div role="navigation">.
Skip Links
Screen reader users and keyboard users navigate through every link in the header before reaching the main content. A skip link lets them jump straight to the content.
<body>
<!-- Skip link β visually hidden but becomes visible on focus -->
<a href="#main-content" class="skip-link">Skip to main content</a>
<header>
<nav><!-- lots of navigation links --></nav>
</header>
<main id="main-content">
<h1>Welcome to Learnixo</h1>
</main>
</body>.skip-link {
position: absolute;
top: -40px;
left: 0;
background: #000;
color: #fff;
padding: 8px;
z-index: 100;
}
.skip-link:focus {
top: 0;
}Complete Project: Personal Bio Page
Let's put everything together into a complete, accessible personal bio page.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta name="description" content="Asma Hafeez β Senior Software Engineer specializing in .NET, Azure, and React. View my portfolio, projects, and contact information." />
<title>Asma Hafeez β Software Engineer</title>
<link rel="stylesheet" href="styles.css" />
<!-- Canonical URL prevents duplicate content issues -->
<link rel="canonical" href="https://asmahafeez.dev" />
<!-- Open Graph for social media sharing -->
<meta property="og:title" content="Asma Hafeez β Software Engineer" />
<meta property="og:description" content="Senior Software Engineer specializing in .NET, Azure, and React." />
<meta property="og:image" content="https://asmahafeez.dev/images/profile-og.jpg" />
<meta property="og:url" content="https://asmahafeez.dev" />
</head>
<body>
<!-- Skip link for accessibility -->
<a href="#main-content" class="skip-link">Skip to main content</a>
<!-- ===== SITE HEADER ===== -->
<header class="site-header">
<div class="container">
<a href="/" class="logo" aria-label="Asma Hafeez - Go to homepage">
<span aria-hidden="true">AH</span>
</a>
<nav aria-label="Main navigation">
<ul>
<li><a href="#about" aria-current="page">About</a></li>
<li><a href="#skills">Skills</a></li>
<li><a href="#projects">Projects</a></li>
<li><a href="#experience">Experience</a></li>
<li><a href="#contact">Contact</a></li>
</ul>
</nav>
</div>
</header>
<!-- ===== MAIN CONTENT ===== -->
<main id="main-content">
<!-- Hero / About Section -->
<section id="about" aria-labelledby="about-heading">
<div class="container">
<div class="about-layout">
<div class="about-image">
<img
src="images/asma-profile.jpg"
alt="Asma Hafeez wearing a blue blazer, smiling"
width="300"
height="300"
/>
</div>
<div class="about-content">
<h1 id="about-heading">Hi, I'm Asma Hafeez</h1>
<p class="tagline">Senior Software Engineer Β· .NET Β· Azure Β· React</p>
<p>
I build scalable, secure web applications for healthcare and enterprise clients.
With over eight years of experience, I specialize in designing clean architectures
using .NET on the backend and React on the frontend, deployed on Azure.
</p>
<p>
I am passionate about <strong>developer education</strong> and currently building
<a href="https://learnixo.dev" target="_blank" rel="noopener noreferrer">Learnixo</a>,
a developer learning platform focused on production-quality skills.
</p>
<div class="about-links">
<a href="#contact" class="btn btn-primary">Get in Touch</a>
<a href="resume.pdf" download="Asma-Hafeez-Resume.pdf" class="btn btn-secondary">
Download Resume
</a>
</div>
</div>
</div>
</div>
</section>
<!-- Skills Section -->
<section id="skills" aria-labelledby="skills-heading">
<div class="container">
<h2 id="skills-heading">Technical Skills</h2>
<div class="skills-grid">
<article class="skill-category">
<h3>Backend</h3>
<ul>
<li>.NET / C#</li>
<li>ASP.NET Core Web API</li>
<li>Entity Framework Core</li>
<li>SQL Server / PostgreSQL</li>
<li>Redis</li>
</ul>
</article>
<article class="skill-category">
<h3>Frontend</h3>
<ul>
<li>React / Next.js</li>
<li>TypeScript</li>
<li>HTML5 / CSS3</li>
<li>Tailwind CSS</li>
</ul>
</article>
<article class="skill-category">
<h3>Cloud & DevOps</h3>
<ul>
<li>Microsoft Azure</li>
<li>Docker / Kubernetes</li>
<li>GitHub Actions</li>
<li>Terraform</li>
</ul>
</article>
<article class="skill-category">
<h3>Specializations</h3>
<ul>
<li>Healthcare / FHIR / HL7</li>
<li>HIPAA Compliance</li>
<li>AI Integration</li>
<li>Microservices</li>
</ul>
</article>
</div>
</div>
</section>
<!-- Projects Section -->
<section id="projects" aria-labelledby="projects-heading">
<div class="container">
<h2 id="projects-heading">Featured Projects</h2>
<div class="projects-grid">
<article class="project-card">
<figure>
<img
src="images/project-learnixo.png"
alt="Learnixo platform showing a course list and progress tracker"
width="600"
height="340"
/>
</figure>
<div class="project-content">
<h3>Learnixo</h3>
<p>
A developer education platform built with Next.js, .NET, and Azure.
Features AI-powered learning paths, interactive code editors, and
progress tracking for 200+ technical articles.
</p>
<ul class="tech-stack" aria-label="Technologies used">
<li>Next.js</li>
<li>.NET 9</li>
<li>Azure</li>
<li>PostgreSQL</li>
</ul>
<div class="project-links">
<a href="https://learnixo.dev" target="_blank" rel="noopener noreferrer">
Live Site
</a>
<a href="https://github.com/asmahafeez/learnixo" target="_blank" rel="noopener noreferrer">
GitHub
</a>
</div>
</div>
</article>
<article class="project-card">
<figure>
<img
src="images/project-fhir.png"
alt="FHIR integration dashboard showing patient data and HL7 message logs"
width="600"
height="340"
/>
</figure>
<div class="project-content">
<h3>FHIR Integration Engine</h3>
<p>
An HL7 FHIR R4 integration engine that translates legacy HL7 v2 messages
to FHIR resources in real time. Processes 50,000+ patient records daily
for a regional healthcare network.
</p>
<ul class="tech-stack" aria-label="Technologies used">
<li>.NET 8</li>
<li>HL7 FHIR R4</li>
<li>Azure Service Bus</li>
<li>SQL Server</li>
</ul>
<div class="project-links">
<a href="https://github.com/asmahafeez/fhir-engine" target="_blank" rel="noopener noreferrer">
GitHub
</a>
</div>
</div>
</article>
<article class="project-card">
<figure>
<img
src="images/project-ai-agent.png"
alt="AI agent interface showing a conversation with code generation output"
width="600"
height="340"
/>
</figure>
<div class="project-content">
<h3>SystemForge AI</h3>
<p>
An AI-powered systems engineering platform with 10 specialized agents
for architecture design, code generation, security review, and deployment
automation.
</p>
<ul class="tech-stack" aria-label="Technologies used">
<li>Next.js</li>
<li>Claude AI</li>
<li>Python</li>
<li>Azure OpenAI</li>
</ul>
<div class="project-links">
<a href="https://systemforge.ai" target="_blank" rel="noopener noreferrer">
Live Site
</a>
</div>
</div>
</article>
</div>
</div>
</section>
<!-- Experience Section -->
<section id="experience" aria-labelledby="experience-heading">
<div class="container">
<h2 id="experience-heading">Work Experience</h2>
<ol class="timeline" reversed>
<li class="timeline-item">
<div class="timeline-date">
<time datetime="2023-01">Jan 2023</time> β
<time datetime="2026-04">Present</time>
</div>
<div class="timeline-content">
<h3>Senior Software Engineer</h3>
<p class="company">Contoso Health Systems</p>
<ul>
<li>Led architecture of FHIR R4 integration platform processing 50K daily records</li>
<li>Reduced API response time by 60% through strategic caching with Redis</li>
<li>Mentored team of 4 junior developers on clean architecture patterns</li>
</ul>
</div>
</li>
<li class="timeline-item">
<div class="timeline-date">
<time datetime="2020-03">Mar 2020</time> β
<time datetime="2022-12">Dec 2022</time>
</div>
<div class="timeline-content">
<h3>Software Engineer</h3>
<p class="company">Northwind Technologies</p>
<ul>
<li>Built React frontend for enterprise resource planning application</li>
<li>Implemented OAuth 2.0 and Azure AD authentication</li>
<li>Migrated monolithic ASP.NET app to microservices architecture</li>
</ul>
</div>
</li>
</ol>
</div>
</section>
<!-- Education Section -->
<section id="education" aria-labelledby="education-heading">
<div class="container">
<h2 id="education-heading">Education & Certifications</h2>
<div class="education-grid">
<article class="education-card">
<h3>B.Sc. Computer Science</h3>
<p>University of Technology</p>
<p><time datetime="2016">2016</time> β <time datetime="2020">2020</time></p>
</article>
<article class="education-card">
<h3>Microsoft Certified: Azure Developer Associate</h3>
<p>Microsoft</p>
<p><time datetime="2022-06">June 2022</time></p>
</article>
<article class="education-card">
<h3>AWS Certified Solutions Architect</h3>
<p>Amazon Web Services</p>
<p><time datetime="2023-09">September 2023</time></p>
</article>
</div>
</div>
</section>
<!-- Contact Section -->
<section id="contact" aria-labelledby="contact-heading">
<div class="container">
<h2 id="contact-heading">Get In Touch</h2>
<p>
I'm open to interesting projects and opportunities. Send me a message
and I'll get back to you within 48 hours.
</p>
<form
action="/api/contact"
method="POST"
aria-labelledby="contact-heading"
novalidate
>
<div class="form-row">
<div class="form-group">
<label for="contact-name">
Your Name <span class="required" aria-label="required">*</span>
</label>
<input
type="text"
id="contact-name"
name="name"
required
autocomplete="name"
aria-required="true"
/>
</div>
<div class="form-group">
<label for="contact-email">
Email Address <span class="required" aria-label="required">*</span>
</label>
<input
type="email"
id="contact-email"
name="email"
required
autocomplete="email"
aria-required="true"
/>
</div>
</div>
<div class="form-group">
<label for="contact-subject">Subject</label>
<select id="contact-subject" name="subject">
<option value="">-- Choose a topic --</option>
<option value="project">Project Collaboration</option>
<option value="job">Job Opportunity</option>
<option value="speaking">Speaking Invitation</option>
<option value="other">Other</option>
</select>
</div>
<div class="form-group">
<label for="contact-message">
Message <span class="required" aria-label="required">*</span>
</label>
<textarea
id="contact-message"
name="message"
rows="6"
required
aria-required="true"
placeholder="Tell me about your project or opportunity..."
></textarea>
</div>
<!-- Status message for form submission feedback -->
<div
id="form-status"
role="status"
aria-live="polite"
class="form-status"
></div>
<button type="submit" class="btn btn-primary">Send Message</button>
</form>
</div>
</section>
</main>
<!-- ===== SITE FOOTER ===== -->
<footer class="site-footer">
<div class="container">
<div class="footer-content">
<p>© <time datetime="2026">2026</time> Asma Hafeez. All rights reserved.</p>
<nav aria-label="Social media links">
<ul>
<li>
<a
href="https://github.com/asmahafeez"
target="_blank"
rel="noopener noreferrer"
aria-label="GitHub profile (opens in new tab)"
>
GitHub
</a>
</li>
<li>
<a
href="https://linkedin.com/in/asmahafeez"
target="_blank"
rel="noopener noreferrer"
aria-label="LinkedIn profile (opens in new tab)"
>
LinkedIn
</a>
</li>
<li>
<a href="mailto:hello@asmahafeez.dev">
Email
</a>
</li>
</ul>
</nav>
</div>
</div>
</footer>
</body>
</html>Common Mistakes to Avoid
Using <div> and <span> for everything. Reach for semantic elements first. Divs and spans have no meaning β they are styling hooks, not structural building blocks.
Missing or useless alt text. alt="image" or alt="photo" is worse than no alt text. Describe what the image communicates. For decorative images, use alt="".
Skipping heading levels. If your last heading was an <h2>, the next level down is <h3>, not <h4>.
Using tables for layout. Tables are for data with row/column relationships. For page layout, use CSS Flexbox or Grid.
Labels not associated with inputs. Every form input needs an associated <label> with matching for/id values. Placeholder text is not a label.
Not specifying lang on <html>. Screen readers need this to pronounce text correctly.
Using <br> for spacing. Use CSS margin and padding. Reserve <br> for poetry, addresses, and other content where line breaks are part of the meaning.
Inline styles for everything. While valid HTML, inline styles make maintenance a nightmare. Put styles in a CSS file.
Key Takeaways
- Always start with
<!DOCTYPE html>and includelang,charset, andviewportmeta tags. - Semantic HTML communicates meaning to browsers, screen readers, and search engines β not just to human readers.
- The page heading hierarchy (
h1throughh6) must form a logical outline without skipping levels. - Every image needs an
altattribute β describe informative images, empty-string decorative ones. - Every form input needs an associated
<label>via matchingfor/idattributes. - Use ARIA attributes only when native HTML semantics are insufficient.
- Accessibility is not a feature to add later β it is a quality standard from day one.
HTML is the foundation. Get the structure right and everything built on top of it β CSS, JavaScript, SEO, accessibility β will be far easier to get right as well.
Enjoyed this article?
Explore the Frontend Engineering learning path for more.
Found this helpful?
Leave a comment
Have a question, correction, or just found this helpful? Leave a note below.