BelajarKoding Logobelajarkoding

Platform belajar web development Indonesia. Artikel, cheat sheets, roadmap, dan code challenges untuk developer Indonesia.

Navigasi

  • Artikel
  • Cheat Sheets
  • Roadmap
  • Challenges
  • Pricing
  • Search

Produk Lain

  • JagoHermes
  • KelasClaude
  • KilatKoding
  • BelajarVibeCoding
  • JualanKoding

Support

  • Privacy Policy
  • Terms of Service
  • Email

© 2026 BelajarKoding. All rights reserved.

Galih PratamaBagian dari ekosistem Galih Pratama
belajarkoding LogobyGalih Pratama
RoadmapArtikelCheat SheetsChallengesUpgrade
belajarkoding LogobyGalih Pratama
RoadmapArtikelCheat SheetsChallengesUpgrade
belajarkoding LogobyGalih Pratama
RoadmapArtikelCheat SheetsChallengesUpgrade

Daftar Isi

Meta Tags EssentialsTitle TagMeta DescriptionViewport (WAJIB untuk mobile)Robots Meta TagCanonical TagsSelf-referencing CanonicalPoint to OriginalHeading StructureProper HierarchyStructured Data (Schema)Article SchemaProduct SchemaFAQ SchemaOrganization SchemaBreadcrumb SchemaOpen Graph (Social Media)Basic Open GraphArticle-specific OG TagsImage RequirementsTwitter CardsSummary Large ImageSummary CardSemantic HTMLArticle StructureNavigationBreadcrumbsImage SEOAlt TextOptimize ImagesImage FilenameInternal LinkingDescriptive Anchor TextLink Relevancyrobots.txtBasic StructureBlock Specific BotsXML SitemapBasic Sitemap StructureNext.js Dynamic SitemapURL StructureClean URLsNext.js SEOApp Router MetadataPages Router (next-seo)React HelmetSEO ChecklistPer-Page ChecklistSite-wide ChecklistCommon Schema TypesToolsQuick Wins
SEOWeb DevelopmentMarketing

SEO Basics Cheat Sheet

Quick reference untuk SEO. Meta tags, structured data, technical SEO, dan best practices buat ranking di Google.

HTML9 min read1.761 kata
Silakan login atau daftar untuk membaca cheat sheet ini.

#Meta Tags Essentials

Tag HTML penting yang harus ada di setiap halaman untuk SEO dasar.

#Title Tag

Tag title yang muncul di hasil pencarian Google dan browser tabs.

html
<!-- Good: 50-60 characters, descriptive, keyword-rich -->
<title>React Hooks Tutorial - useState & useEffect Explained</title>
 
<!-- Bad: Too generic -->
<title>Tutorial</title>
 
<!-- Bad: Too long (akan di-truncate) -->
<title>Complete Comprehensive Ultimate Guide to Learning React Hooks from Scratch</title>

#Meta Description

Deskripsi singkat halaman yang muncul di hasil pencarian Google.

html
<!-- Good: 150-160 characters, compelling, keyword-rich -->
<meta
 name="description"
 content="Pelajari React Hooks dari nol. Tutorial useState, useEffect, dan custom hooks dengan contoh yang mudah dipahami."
>
 
<!-- Bad: Too short -->
<meta name="description" content="React tutorial">
 
<!-- Bad: Keyword stuffing -->
<meta
 name="description"
 content="React hooks react tutorial react useState react useEffect learn react"
>

#Viewport (WAJIB untuk mobile)

Meta tag yang mengatur cara browser menampilkan halaman di device mobile.

html
<meta name="viewport" content="width=device-width, initial-scale=1">

#Robots Meta Tag

Mengontrol cara search engine bots mengindeks dan mengikuti link di halaman.

html
<!-- Allow indexing and following links (default) -->
<meta name="robots" content="index, follow">
 
<!-- Prevent indexing -->
<meta name="robots" content="noindex, follow">
 
<!-- Prevent following links -->
<meta name="robots" content="index, nofollow">
 
<!-- Prevent both -->
<meta name="robots" content="noindex, nofollow">

#Canonical Tags

Tag yang menunjukkan versi asli dari halaman untuk menghindari duplicate content.

#Self-referencing Canonical

Canonical yang mengarah ke halaman itu sendiri.

html
<!-- WAJIB di setiap page -->
<link rel="canonical" href="https://example.com/artikel/react-hooks">

#Point to Original

html
<!-- Untuk duplicate content -->
<link rel="canonical" href="https://example.com/original-article">

Penting:

  • Use absolute URLs
  • One canonical per page
  • Canonical should point to accessible page

#Heading Structure

#Proper Hierarchy

html
<!-- Good: Clear hierarchy -->
<h1>Web Performance Optimization</h1>
 
<h2>Core Web Vitals</h2>
<h3>Largest Contentful Paint</h3>
<h3>Interaction to Next Paint</h3>
 
<h2>Optimization Techniques</h2>
<h3>Lazy Loading</h3>
<h3>Code Splitting</h3>
 
<!-- Bad: Skipping levels -->
<h1>Title</h1>
<h4>Subtitle</h4> <!-- Don't skip h2 and h3 -->

Rules:

  • One H1 per page
  • Don't skip heading levels
  • Descriptive, not generic
  • Include keywords naturally

#Structured Data (Schema)

#Article Schema

html
<script type="application/ld+json">
{
 "@context": "https://schema.org",
 "@type": "Article",
 "headline": "React Hooks Tutorial",
 "description": "Panduan lengkap React Hooks",
 "image": "https://example.com/image.jpg",
 "author": {
  "@type": "Person",
  "name": "Galih Pratama",
  "url": "https://galihpratama.com"
 },
 "publisher": {
  "@type": "Organization",
  "name": "Belajar Koding",
  "logo": {
   "@type": "ImageObject",
   "url": "https://example.com/logo.png"
  }
 },
 "datePublished": "2025-11-20",
 "dateModified": "2025-11-20"
}
</script>

#Product Schema

html
<script type="application/ld+json">
{
 "@context": "https://schema.org",
 "@type": "Product",
 "name": "Product Name",
 "image": "https://example.com/product.jpg",
 "description": "Product description",
 "brand": {
  "@type": "Brand",
  "name": "Brand Name"
 },
 "offers": {
  "@type": "Offer",
  "price": "299000",
  "priceCurrency": "IDR",
  "availability": "https://schema.org/InStock",
  "url": "https://example.com/product"
 },
 "aggregateRating": {
  "@type": "AggregateRating",
  "ratingValue": "4.5",
  "reviewCount": "127"
 }
}
</script>

#FAQ Schema

html
<script type="application/ld+json">
{
 "@context": "https://schema.org",
 "@type": "FAQPage",
 "mainEntity": [
  {
   "@type": "Question",
   "name": "Apa itu React Hooks?",
   "acceptedAnswer": {
    "@type": "Answer",
    "text": "React Hooks adalah fitur yang memungkinkan kamu menggunakan state dan lifecycle di functional components."
   }
  },
  {
   "@type": "Question",
   "name": "Kapan harus pakai useEffect?",
   "acceptedAnswer": {
    "@type": "Answer",
    "text": "useEffect digunakan untuk side effects seperti fetch data, subscriptions, atau DOM manipulation."
   }
  }
 ]
}
</script>

#Organization Schema

html
<script type="application/ld+json">
{
 "@context": "https://schema.org",
 "@type": "Organization",
 "name": "Belajar Koding",
 "url": "https://example.com",
 "logo": "https://example.com/logo.png",
 "sameAs": [
  "https://x.com/belajarkoding",
  "https://github.com/belajarkoding",
  "https://linkedin.com/company/belajarkoding"
 ],
 "contactPoint": {
  "@type": "ContactPoint",
  "email": "hi@example.com",
  "contactType": "Customer Support"
 }
}
</script>

#Breadcrumb Schema

html
<script type="application/ld+json">
{
 "@context": "https://schema.org",
 "@type": "BreadcrumbList",
 "itemListElement": [
  {
   "@type": "ListItem",
   "position": 1,
   "name": "Home",
   "item": "https://example.com"
  },
  {
   "@type": "ListItem",
   "position": 2,
   "name": "Artikel",
   "item": "https://example.com/artikel"
  },
  {
   "@type": "ListItem",
   "position": 3,
   "name": "React Hooks",
   "item": "https://example.com/artikel/react-hooks"
  }
 ]
}
</script>

#Open Graph (Social Media)

#Basic Open Graph

html
<meta property="og:title" content="React Hooks Tutorial">
<meta property="og:description" content="Panduan lengkap React Hooks untuk pemula">
<meta property="og:image" content="https://example.com/og-image.jpg">
<meta property="og:url" content="https://example.com/artikel/react-hooks">
<meta property="og:type" content="article">
<meta property="og:site_name" content="Belajar Koding">
<meta property="og:locale" content="id_ID">

#Article-specific OG Tags

html
<meta property="article:published_time" content="2025-11-20T10:00:00Z">
<meta property="article:modified_time" content="2025-11-20T15:30:00Z">
<meta property="article:author" content="https://galihpratama.com">
<meta property="article:section" content="Technology">
<meta property="article:tag" content="React">
<meta property="article:tag" content="JavaScript">

#Image Requirements

html
<!-- Recommended size: 1200x630px (1.91:1 ratio) -->
<meta property="og:image" content="https://example.com/og-image.jpg">
<meta property="og:image:width" content="1200">
<meta property="og:image:height" content="630">
<meta property="og:image:alt" content="React Hooks Tutorial Cover">

#Twitter Cards

#Summary Large Image

html
<meta name="twitter:card" content="summary_large_image">
<meta name="twitter:site" content="@belajarkoding">
<meta name="twitter:creator" content="@galpratama">
<meta name="twitter:title" content="React Hooks Tutorial">
<meta name="twitter:description" content="Panduan lengkap React Hooks untuk pemula">
<meta name="twitter:image" content="https://example.com/twitter-image.jpg">
<meta name="twitter:image:alt" content="React Hooks Tutorial Cover">

#Summary Card

html
<meta name="twitter:card" content="summary">
<meta name="twitter:title" content="React Hooks Tutorial">
<meta name="twitter:description" content="Panduan lengkap React Hooks">
<meta name="twitter:image" content="https://example.com/square-image.jpg">

#Semantic HTML

#Article Structure

html
<article>
 <header>
  <h1>Article Title</h1>
  <time datetime="2025-11-20">20 November 2025</time>
  <address>
   <a rel="author" href="/author/galih">Galih Pratama</a>
  </address>
 </header>
 
 <section>
  <h2>Section Title</h2>
  <p>Content...</p>
 </section>
 
 <footer>
  <p>Tags: <a href="/tag/react">React</a></p>
 </footer>
</article>

#Navigation

html
<nav aria-label="Main navigation">
 <ul>
  <li><a href="/">Home</a></li>
  <li><a href="/artikel">Artikel</a></li>
  <li><a href="/about">About</a></li>
 </ul>
</nav>

#Breadcrumbs

html
<nav aria-label="Breadcrumb">
 <ol>
  <li><a href="/">Home</a></li>
  <li><a href="/artikel">Artikel</a></li>
  <li aria-current="page">React Hooks</li>
 </ol>
</nav>

#Image SEO

#Alt Text

html
<!-- Good: Descriptive -->
<img
 src="macbook.jpg"
 alt="MacBook Pro 16-inch with M3 chip on wooden desk"
>
 
<!-- Bad: Keyword stuffing -->
<img
 src="macbook.jpg"
 alt="macbook macbook pro laptop computer apple"
>
 
<!-- Bad: Generic -->
<img src="macbook.jpg" alt="image">

#Optimize Images

html
<!-- Use modern formats -->
<picture>
 <source srcset="image.avif" type="image/avif">
 <source srcset="image.webp" type="image/webp">
 <img
  src="image.jpg"
  alt="Descriptive alt text"
  width="800"
  height="600"
  loading="lazy"
 >
</picture>

#Image Filename

plaintext
Good: descriptive-keywords.jpg
Bad: IMG_1234.jpg
Bad: photo.jpg

#Internal Linking

#Descriptive Anchor Text

html
<!-- Good: Descriptive -->
<a href="/artikel/react-hooks">
 Pelajari lebih lanjut tentang React Hooks
</a>
 
<!-- Bad: Generic -->
<a href="/artikel/react-hooks">Klik di sini</a>
 
<!-- Bad: URL as anchor -->
<a href="/artikel/react-hooks">
 https://example.com/artikel/react-hooks
</a>

#Link Relevancy

html
<!-- Link ke related content -->
<p>
 Untuk memahami hooks lebih baik, baca dulu
 <a href="/artikel/javascript-fundamentals">JavaScript Fundamentals</a>
 dan <a href="/artikel/react-basics">React Basics</a>.
</p>

#robots.txt

#Basic Structure

txt
# Allow all bots to crawl everything
User-agent: *
Allow: /
 
# Disallow specific paths
Disallow: /admin/
Disallow: /api/
Disallow: /private/
Disallow: /cart/
Disallow: /checkout/
 
# Disallow search result pages
Disallow: /search?
 
# Sitemap location
Sitemap: https://example.com/sitemap.xml
Sitemap: https://example.com/sitemap-news.xml

#Block Specific Bots

txt
# Block bad bots
User-agent: BadBot
Disallow: /
 
# Allow Googlebot everything
User-agent: Googlebot
Allow: /
 
# Allow others but restrict
User-agent: *
Disallow: /admin/

#XML Sitemap

#Basic Sitemap Structure

xml
<?xml version="1.0" encoding="UTF-8"?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
 <url>
  <loc>https://example.com</loc>
  <lastmod>2025-11-20</lastmod>
  <changefreq>daily</changefreq>
  <priority>1.0</priority>
 </url>
 <url>
  <loc>https://example.com/artikel/react-hooks</loc>
  <lastmod>2025-11-20</lastmod>
  <changefreq>monthly</changefreq>
  <priority>0.8</priority>
 </url>
</urlset>

#Next.js Dynamic Sitemap

javascript
// pages/sitemap.xml.js
export async function getServerSideProps({ res }) {
 const baseUrl = 'https://example.com';
 const posts = await getAllPosts();
 
 const sitemap = `<?xml version="1.0" encoding="UTF-8"?>
  <urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
   <url>
    <loc>${baseUrl}</loc>
    <lastmod>${new Date().toISOString()}</lastmod>
    <priority>1.0</priority>
   </url>
   ${posts.map((post) => `
    <url>
     <loc>${baseUrl}/artikel/${post.slug}</loc>
     <lastmod>${post.date}</lastmod>
     <priority>0.8</priority>
    </url>
   `).join('')}
  </urlset>
 `;
 
 res.setHeader('Content-Type', 'text/xml');
 res.write(sitemap);
 res.end();
 
 return { props: {} };
}
 
export default function Sitemap() {}

#URL Structure

#Clean URLs

plaintext
Good:
https://example.com/artikel/react-hooks-tutorial
https://example.com/products/nike-air-max-90
https://example.com/category/web-development
 
Bad:
https://example.com/article?id=12345&cat=4
https://example.com/p/aX9kL2mN
https://example.com/kategori/web/artikel/2025/11/20/long/path/slug

Best practices:

  • Use hyphens (not underscores)
  • Lowercase letters
  • Short and descriptive
  • Include keywords
  • Avoid parameters

#Next.js SEO

#App Router Metadata

javascript
// app/artikel/[slug]/page.js
export async function generateMetadata({ params }) {
 const post = await getPost(params.slug);
 
 return {
  title: post.title,
  description: post.description,
  openGraph: {
   title: post.title,
   description: post.description,
   images: [
    {
     url: post.image,
     width: 1200,
     height: 630,
     alt: post.title,
    }
   ],
   type: 'article',
   publishedTime: post.date,
   authors: [post.author],
  },
  twitter: {
   card: 'summary_large_image',
   title: post.title,
   description: post.description,
   images: [post.image],
   creator: '@galpratama',
  },
  alternates: {
   canonical: `https://example.com/artikel/${params.slug}`,
  },
 };
}

#Pages Router (next-seo)

javascript
import { NextSeo, ArticleJsonLd } from 'next-seo';
 
export default function ArticlePage({ article }) {
 return (
  <>
   <NextSeo
    title={article.title}
    description={article.description}
    canonical={article.url}
    openGraph={{
     type: 'article',
     url: article.url,
     title: article.title,
     description: article.description,
     images: [
      {
       url: article.image,
       width: 1200,
       height: 630,
       alt: article.title,
      }
     ],
     article: {
      publishedTime: article.publishedAt,
      modifiedTime: article.updatedAt,
      authors: [article.author],
      tags: article.tags,
     },
    }}
   />
   <ArticleJsonLd
    url={article.url}
    title={article.title}
    images={[article.image]}
    datePublished={article.publishedAt}
    dateModified={article.updatedAt}
    authorName={article.author}
    description={article.description}
   />
 
   <article>{/* Content */}</article>
  </>
 );
}

#React Helmet

javascript
import { Helmet } from 'react-helmet';
 
function ArticlePage({ article }) {
 const structuredData = {
  "@context": "https://schema.org",
  "@type": "Article",
  headline: article.title,
  description: article.description,
  image: article.image,
  datePublished: article.date,
  author: {
   "@type": "Person",
   name: article.author
  }
 };
 
 return (
  <>
   <Helmet>
    <title>{article.title}</title>
    <meta name="description" content={article.description} />
    <link rel="canonical" href={article.url} />
 
    <meta property="og:title" content={article.title} />
    <meta property="og:description" content={article.description} />
    <meta property="og:image" content={article.image} />
    <meta property="og:url" content={article.url} />
    <meta property="og:type" content="article" />
 
    <meta name="twitter:card" content="summary_large_image" />
    <meta name="twitter:title" content={article.title} />
    <meta name="twitter:description" content={article.description} />
    <meta name="twitter:image" content={article.image} />
 
    <script type="application/ld+json">
     {JSON.stringify(structuredData)}
    </script>
   </Helmet>
 
   <article>{/* Content */}</article>
  </>
 );
}

#SEO Checklist

#Per-Page Checklist

  • Unique, descriptive title (50-60 chars)
  • Compelling meta description (150-160 chars)
  • One H1 with target keyword
  • Proper heading hierarchy (H2, H3, etc)
  • Canonical tag
  • Structured data (Article/Product/etc)
  • Optimized images (alt text, WebP, lazy loading)
  • Internal links to related content
  • Clean, descriptive URL
  • Open Graph & Twitter Card tags
  • Mobile-friendly responsive
  • Fast loading (LCP < 2.5s)

#Site-wide Checklist

  • robots.txt configured
  • XML sitemap created & submitted
  • Google Search Console setup
  • Analytics installed
  • HTTPS enabled
  • 404 page exists
  • Breadcrumb navigation
  • Sitemap linked in footer

#Common Schema Types

TypeUse Case
ArticleBlog posts, news
ProductE-commerce items
OrganizationCompany info
LocalBusinessPhysical locations
PersonAuthor profiles
FAQQuestion & answers
HowToStep-by-step guides
RecipeFood recipes
ReviewProduct/service reviews
EventEvents, webinars
VideoObjectVideo content
BreadcrumbListNavigation path

#Tools

Free:

  • Google Search Console: https://search.google.com/search-console
  • Rich Results Test: https://search.google.com/test/rich-results
  • PageSpeed Insights: https://pagespeed.web.dev/
  • Mobile-Friendly Test: https://search.google.com/test/mobile-friendly

Freemium:

  • Screaming Frog SEO Spider
  • Ubersuggest
  • AnswerThePublic

Paid:

  • Ahrefs
  • SEMrush
  • Moz Pro

#Quick Wins

  1. Add missing title & meta descriptions
  2. Fix broken internal links
  3. Optimize image alt text
  4. Add canonical tags
  5. Create/submit XML sitemap
  6. Enable HTTPS
  7. Improve page speed (see Web Performance cheat sheet)
  8. Add structured data
  9. Make mobile-friendly
  10. Set up Google Search Console

Baca Cheat Sheet Lengkap

Login atau daftar akun gratis untuk membaca cheat sheet ini.

LoginDaftar Gratis
Share: