Hugo’s data files adalah fitur powerful yang memungkinkan Anda menyimpan data secara eksternal dan mengaksesnya di templates. Ini sangat useful untuk membuat konten yang driven oleh data seperti price lists, team members, FAQ sections, dan berbagai data yang perlu terpisah dari konten utama. Panduan ini akan membahas cara menggunakan data files di Hugo secara efektif.
Data files di Hugo adalah files yang disimpan di folder data/ dan dapat diakses melalui .Site.Data di templates. Hugo mendukung berbagai formats termasuk JSON, YAML, TOML, dan CSV. Dengan data files, Anda dapat maintain data secara terpisah dari content, memungkinkan updates yang lebih mudah tanpa harus modify content files.
Struktur Data Files
Lokasi dan Organisasi
Data files disimpan di folder data/ di root proyek Hugo:
data/
βββ authors.yaml
βββ team.yaml
βββ products.json
βββ prices.csv
βββ locations/
β βββ jakarta.yaml
β βββ surabaya.yaml
β βββ bandung.yaml
βββ navigation.yaml
Format yang Didukung
Hugo mendukung empat format data files: JSON untuk data terstruktur modern, YAML untuk human-readable configuration, TOML untuk configuration files, dan CSV untuk tabular data.
Menggunakan JSON Data
Struktur JSON Data
// data/products.json
{
"products": [
{
"id": 1,
"name": "Laptop Pro",
"price": 15000000,
"currency": "IDR",
"category": "electronics",
"inStock": true,
"features": ["16GB RAM", "512GB SSD", "Intel i7"],
"specifications": {
"processor": "Intel Core i7-1165G7",
"memory": "16GB DDR4",
"storage": "512GB NVMe SSD",
"display": "14 inch FHD"
}
},
{
"id": 2,
"name": "Wireless Mouse",
"price": 350000,
"currency": "IDR",
"category": "accessories",
"inStock": true,
"features": ["Ergonomic", "Long battery life"]
}
]
}
Mengakses JSON di Templates
{{/* layouts/_default/single.html */}}
{{ range .Site.Data.products.products }}
<div class="product">
<h3>{{ .name }}</h3>
<p class="price">{{ .price | lang.NumFmt 0 }} {{ .currency }}</p>
<ul class="features">
{{ range .features }}
<li>{{ . }}</li>
{{ end }}
</ul>
</div>
{{ end }}
Nested JSON
// data/company.json
{
"name": "Tech Solutions",
"established": 2020,
"locations": {
"headquarters": {
"city": "Jakarta",
"address": "Jl. Sudirman No. 1"
},
"branches": ["Surabaya", "Bandung", "Medan"]
},
"stats": {
"employees": 150,
"revenue": 50000000000
}
}
{{ with .Site.Data.company }}
<h2>{{ .name }}</h2>
<p>Headquarters: {{ .locations.headquarters.city }}</p>
<p>Revenue: {{ .stats.revenue | lang.NumFmt 0 }}</p>
{{ end }}
Menggunakan YAML Data
Struktur YAML Data
# data/authors.yaml
- id: 1
name: "John Doe"
email: "[email protected]"
bio: "Full-stack developer dengan 10 tahun pengalaman."
avatar: "/images/authors/john.jpg"
social:
twitter: "johndoe"
github: "johndoe"
linkedin: "johndoe"
role: "Senior Developer"
- id: 2
name: "Jane Smith"
email: "[email protected]"
bio: "UI/UX Designer passionate about accessibility."
avatar: "/images/authors/jane.jpg"
social:
twitter: "janesmith"
dribbble: "janesmith"
role: "Lead Designer"
Mengakses YAML di Templates
{{ range .Site.Data.authors }}
<div class="author-card">
<img src="{{ .avatar }}" alt="{{ .name }}">
<h3>{{ .name }}</h3>
<p>{{ .bio }}</p>
{{ with .social }}
<div class="social-links">
{{ with .twitter }}
<a href="https://twitter.com/{{ . }}">Twitter</a>
{{ end }}
{{ with .github }}
<a href="https://github.com/{{ . }}">GitHub</a>
{{ end }}
</div>
{{ end }}
</div>
{{ end }}
Multi-Language Data
# data/navigation.id.yaml
- title: "Beranda"
url: "/"
- title: "Produk"
url: "/products/"
children:
- title: "Elektronik"
url: "/products/electronics/"
- title: "Aksesori"
url: "/products/accessories/"
data/navigation.en.yaml
- title: "Home"
url: "/"
- title: "Products"
url: "/products/"
{{ $navData := index .Site.Data (printf "navigation.%s" .Site.Language.Lang) }}
{{ range $navData }}
<a href="{{ .url }}">{{ .title }}</a>
{{ end }}
Menggunakan CSV Data
Struktur CSV Data
# data/prices.csv
product,category,price,currency,discount
Laptop Pro,electronics,15000000,IDR,10
Wireless Mouse,accessories,350000,IDR,5
USB-C Hub,accessories,750000,IDR,0
Monitor 27inch,electronics,4500000,IDR,15
Keyboard Mechanical,accessories,1200000,IDR,10
Mengakses CSV di Templates
{{ range .Site.Data.prices }}
<tr>
<td>{{ .product }}</td>
<td>{{ .category }}</td>
{{- $price := div .price 1000 }}
<td>{{ lang.NumFmt 0 $price }} {{ .currency }}</td>
{{- if gt .discount 0 -}}
<td>{{ .discount }}%</td>
{{- else -}}
<td>-</td>
{{- end -}}
</tr>
{{ end }}
CSV dengan Header
Hugo automatically treats first row sebagai header. Akses dengan .header:
{{ with .Site.Data.prices }}
<thead>
<tr>
{{ range .headers }}
<th>{{ . }}</th>
{{ end }}
</tr>
</thead>
<tbody>
{{ range .data }}
<tr>
{{ range $i, $v := . }}
<td>{{ $v }}</td>
{{ end }}
</tr>
{{ end }}
</tbody>
{{ end }}
Menggunakan TOML Data
Struktur TOML Data
# data/config.toml
[site]
name = "Tech Blog"
description = "Blog tentang teknologi dan programming"
logo = "/images/logo.png"
[social]
twitter = "techblog"
github = "techblog"
linkedin = "techblog"
[[authors]]
name = "John Doe"
role = "Editor"
[[authors]]
name = "Jane Smith"
role = "Contributor"
[features]
comments = true
search = true
dark_mode = true
Mengakses TOML di Templates
{{ with .Site.Data.config }} <h1>{{ .site.name }}</h1> <p>{{ .site.description }}</p>{{ with .features }} <p>Features: {{ if .dark_mode }}Dark Mode{{ end }}</p> {{ end }}{{ end }}
Data-driven Components
FAQ Section
# data/faq.yaml - question: "Apa itu Hugo?" answer: "Hugo adalah static site generator yang ditulis dalam Go." category: "General"
- question: "Bagaimana cara install Hugo?" answer: "Hugo dapat diinstall melalui package manager atau download binary." category: "Installation"
- question: "Apakah Hugo gratis?" answer: "Ya, Hugo adalah software open-source di bawah lisensi Apache 2.0." category: "General"
{{/* layouts/shortcodes/faq.html */}} {{- $category := .Get "category" -}} <div class="faq-section"> {{- range where $.Site.Data.faq "category" $category -}} <details class="faq-item"> <summary>{{ .question }}</summary> <div class="answer">{{ .answer | markdownify }}</div> </details> {{- end -}} </div>Team Members Grid
# data/team.yaml - name: "John Doe" role: "CEO" bio: "Visionary leader dengan 15 tahun pengalaman di tech industry." image: "/images/team/john.jpg" email: "[email protected]"
- name: "Jane Smith" role: "CTO" bio: "Tech enthusiast dan open source contributor." image: "/images/team/jane.jpg" email: "[email protected]"
{{/* layouts/partials/team-grid.html */}} <div class="team-grid"> {{ range .Site.Data.team }} <div class="team-card"> <img src="{{ .image }}" alt="{{ .name }}"> <h3>{{ .name }}</h3> <p class="role">{{ .role }}</p> <p class="bio">{{ .bio }}</p> <a href="mailto:{{ .email }}">{{ .email }}</a> </div> {{ end }} </div>Product Catalog
// data/products.json { "categories": [ { "name": "Electronics", "slug": "electronics", "products": [ {"name": "Laptop", "price": 15000000}, {"name": "Monitor", "price": 4500000} ] } ] }{{/* layouts/partials/product-catalog.html */}} {{ range .Site.Data.products.categories }} <section class="category"> <h2>{{ .name }}</h2> <div class="products-grid"> {{ range .products }} <div class="product-card"> <h3>{{ .name }}</h3> <p class="price">{{ .price | lang.NumFmt 0 }} IDR</p> </div> {{ end }} </div> </section> {{ end }}Data Transformations
Filtering Data
{{/* Filter products by category */}} {{ range where .Site.Data.products.products "category" "electronics" }} <div>{{ .name }} - {{ .price }}</div> {{ end }}{{/ Filter dengan multiple conditions /}} {{ range where .Site.Data.products.products "inStock" true }} <div>{{ .name }} (In Stock)</div> {{ end }}
Sorting Data
{{/* Sort by price ascending */}} {{ range sort .Site.Data.products.products "price" "asc" }} <div>{{ .name }} - {{ .price }}</div> {{ end }}{{/ Sort by name descending /}} {{ range sort .Site.Data.products.products "name" "desc" }} <div>{{ .name }}</div> {{ end }}
Grouping Data
{{/* Group products by category */}} {{ range group .Site.Data.products.products "category" }} <h2>{{ .Key }}</h2> {{ range .Pages }} <div>{{ .name }}</div> {{ end }} {{ end }}Data Math Operations
{{/* Calculate total */}} {{ $total := 0 }} {{ range .Site.Data.products.products }} {{ $total = add $total .price }} {{ end }} <p>Total Value: {{ $total | lang.NumFmt 0 }}</p>Dynamic Content dari External APIs
Fetch External Data
Buat script untuk fetch data dari external API:
// scripts/fetch-data.js const fs = require('fs'); const fetch = require('node-fetch');async function fetchProducts() { const response = await fetch('https://api.example.com/products'); const products = await response.json();
fs.writeFileSync('data/products.json', JSON.stringify(products, null, 2)); console.log('Products data updated');}
fetchProducts().catch(console.error);
Integrate dengan CI/CD
// package.json { "scripts": { "prebuild": "node scripts/fetch-data.js", "fetch:data": "node scripts/fetch-data.js" } }Best Practices
Data Organization
Gunakan struktur folder untuk organize data-related files:
data/ βββ products/ β βββ electronics.yaml β βββ accessories.yaml β βββ services.yaml βββ team/ β βββ core.yaml β βββ advisors.yaml βββ locations/ β βββ indonesia.yaml β βββ singapore.yaml βββ content.yamlValidation
Validasi data files dengan schema:
# data/validation-schema.yaml type: object properties: products: type: array items: type: object required: - name - price properties: name: type: string price: type: numberDocumentation
Dokumentasikan data structures:
# data/README.md # Team Data StructureFormat
Array of author objects dengan fields:
name(string): Full namerole(string): Job titlebio(string): Short biographyavatar(string): Path ke imagesocial(object): Social media linksExample
- name: "John Doe" role: "CEO" bio: "Tech leader" avatar: "/images/team/john.jpg" social: twitter: "johndoe" </code></pre> <p>```</p> <h2>Kesimpulan</h2> <p>Data files di Hugo menyediakan powerful mechanism untuk membuat content yang driven oleh data. Dengan memahami cara menggunakan JSON, YAML, CSV, dan TOML, Anda dapat create dynamic dan maintainable content structures yang separate dari main content.</p> <h2>Artikel Terkait</h2> <ul> <li><a href="/hugo-headless-cms/">Hugo dengan Headless CMS: Strapi, Contentful, dan Sanity</a></li> <li><a href="/hugo-taxonomy-menu/">Hugo Taxonomy dan Menu: Struktur Navigasi dan Kategorisasi Konten</a></li> <li><a href="/tutorial-hugo-templating-layouts-templates-partial/">Tutorial Hugo Templating: Memahami Layouts, Templates, dan Partial</a></li> <li><a href="/hugo-custom-output-formats/">Hugo Custom Output Formats: JSON, AMP, dan Custom Output</a></li> </ul>
Ditulis oleh
Hendra Wijaya