This guide explains how to integrate nextjs-htk into your Next.js project.
- New Project Setup
- Existing Project Migration
- Configuration
- Using Components
- Content Management
- Build and Deployment
# Create a new Next.js project
npx create-next-app@latest my-site --typescript --tailwind=false --app=false
cd my-site
# Install nextjs-htk packages
pnpm add @nextjs-htk/core @nextjs-htk/build-tools
# Optional: Add content adapters
pnpm add @nextjs-htk/content
# Install peer dependencies
pnpm add next@15 react@19 react-dom@19 bootstrap react-bootstrap sassSet up your project structure:
my-site/
├── src/
│ ├── pages/
│ │ ├── index.tsx
│ │ ├── about.tsx
│ │ └── _app.tsx
│ ├── components/ # Custom components
│ ├── styles/ # Custom styles
│ └── content/ # Content files (markdown, JSON)
├── public/ # Static assets
├── htk.config.ts # NextJS-HTK configuration
├── next.config.mjs # Next.js configuration
└── package.json
Create htk.config.ts:
import { defineConfig } from '@nextjs-htk/core'
export default defineConfig({
site: {
name: 'My Site',
title: 'Welcome to My Site',
description: 'A website built with NextJS-HTK',
url: 'https://mysite.com',
author: 'Your Name',
},
navigation: [
{ label: 'Home', href: '/' },
{ label: 'About', href: '/about' },
{ label: 'Contact', href: '/contact' },
],
footer: {
copyright: '© 2025 My Site. All rights reserved.',
links: [
{ label: 'Privacy', href: '/privacy' },
{ label: 'Terms', href: '/terms' },
],
},
social: {
github: 'yourusername',
twitter: 'yourhandle',
},
theme: {
colors: {
primary: '#007bff',
secondary: '#6c757d',
},
},
seo: {
defaultImage: '/og-image.png',
twitterCard: 'summary_large_image',
},
})Create next.config.mjs:
/** @type {import('next').NextConfig} */
const nextConfig = {
output: 'export',
distDir: 'docs',
trailingSlash: true,
images: {
unoptimized: true,
},
}
export default nextConfigpnpm add @nextjs-htk/core @nextjs-htk/build-tools
# Add other packages as neededUpdate next.config.js for static export:
module.exports = {
output: 'export',
distDir: 'docs',
trailingSlash: true,
images: {
unoptimized: true,
},
}Create htk.config.ts with your site settings (see example above).
Replace existing components with HTK components:
Before:
// Old header component
import Header from '../components/Header'
export default function Page() {
return (
<>
<Header />
<main>Content</main>
<Footer />
</>
)
}After:
// Using HTK BaseLayout
import { BaseLayout } from '@nextjs-htk/core'
export default function Page() {
return (
<BaseLayout title="Page Title">
<main>Content</main>
</BaseLayout>
)
}Update package.json:
{
"scripts": {
"dev": "next dev",
"build": "next build",
"deploy": "next build && git add docs && git commit -m 'Deploy' && git push"
}
}The htk.config.ts file controls all site-wide settings:
import { defineConfig } from '@nextjs-htk/core'
export default defineConfig({
// Required: Site metadata
site: {
name: string // Site name
title: string // Default page title
description: string // Default meta description
url: string // Full site URL (https://...)
author: string // Author name
},
// Required: Navigation menu
navigation: [
{
label: string // Menu label
href: string // Link URL
children?: [] // Optional submenu
}
],
// Required: Footer configuration
footer: {
copyright: string // Copyright notice
links?: [] // Optional footer links
},
// Optional: Social media links
social?: {
twitter?: string
github?: string
linkedin?: string
facebook?: string
instagram?: string
},
// Optional: Theme customization
theme?: {
colors?: {
primary?: string
secondary?: string
},
fonts?: {
body?: string
heading?: string
}
},
// Optional: SEO settings
seo?: {
defaultImage?: string
twitterCard?: 'summary' | 'summary_large_image'
},
// Optional: Analytics
analytics?: {
google?: string // Google Analytics ID
}
})Provides standard page structure with header, footer, and SEO:
import { BaseLayout } from '@nextjs-htk/core'
export default function Page() {
return (
<BaseLayout
title="About Us"
description="Learn more about our company"
showHeader={true}
showFooter={true}
>
<section>
<h1>About Us</h1>
<p>Content goes here...</p>
</section>
</BaseLayout>
)
}For custom SEO on specific pages:
import { SEO } from '@nextjs-htk/core'
export default function BlogPost({ post }) {
return (
<>
<SEO
title={post.title}
description={post.excerpt}
image={post.featuredImage}
url={`https://mysite.com/blog/${post.slug}`}
type="article"
/>
<article>
<h1>{post.title}</h1>
{/* ... */}
</article>
</>
)
}Standalone header (if not using BaseLayout):
import { Header } from '@nextjs-htk/core'
export default function CustomLayout({ children }) {
return (
<>
<Header />
{children}
</>
)
}Standalone footer:
import { Footer } from '@nextjs-htk/core'
export default function CustomLayout({ children }) {
return (
<>
{children}
<Footer />
</>
)
}Install the content adapter:
pnpm add @nextjs-htk/contentConfigure in htk.config.ts:
import { createMarkdownSource } from '@nextjs-htk/content/markdown'
export default defineConfig({
// ... site config ...
content: {
blog: createMarkdownSource({
dir: 'src/posts',
sortBy: 'date',
sortOrder: 'desc',
}),
},
})Create markdown files in src/posts/:
---
title: My First Post
date: 2025-01-15
author: Your Name
tags: [nextjs, tutorial]
---
# My First Post
Content goes here...Use in pages:
import { getPostBySlug, getAllPosts } from '@nextjs-htk/content/markdown'
export async function getStaticProps({ params }) {
const post = await getPostBySlug(params.slug)
return {
props: { post }
}
}
export default function BlogPost({ post }) {
return (
<BaseLayout title={post.title}>
<article dangerouslySetInnerHTML={{ __html: post.content }} />
</BaseLayout>
)
}For structured data (menus, team members, etc.):
import { createJSONSource } from '@nextjs-htk/content/json'
export default defineConfig({
content: {
menu: createJSONSource({
path: 'src/data/menu.json',
}),
},
})For data from external sources:
import { createGitHubSource } from '@nextjs-htk/content/api'
export default defineConfig({
content: {
projects: createGitHubSource({
org: 'myorg',
cache: 'src/data/projects.json',
}),
},
})pnpm dev
# Site runs at http://localhost:3000pnpm build
# Static files generated in docs/-
Enable GitHub Pages:
- Repository Settings → Pages
- Source: Deploy from a branch
- Branch: master, Folder: /docs
-
Add CNAME file (for custom domain):
echo "mysite.com" > docs/CNAME
git add docs/CNAME
git commit -m "Add CNAME"- Deploy:
# Build and commit
pnpm build
git add docs
git commit -m "Deploy update"
git pushCreate a Makefile for convenience:
.PHONY: install dev build deploy clean
install:
pnpm install
dev:
pnpm dev
build:
pnpm build
deploy: build
git add docs
git commit -m "Deploy $(shell date +%Y-%m-%d)"
git push
clean:
rm -rf node_modules .next docsThen use:
make dev # Development server
make build # Build site
make deploy # Build and deployCreate custom styles in src/styles/:
// src/styles/custom.module.scss
.hero {
background: var(--primary-color);
padding: 4rem 2rem;
}Use in components:
import styles from '../styles/custom.module.scss'
export default function Hero() {
return (
<div className={styles.hero}>
<h1>Welcome</h1>
</div>
)
}Override Bootstrap variables:
// src/styles/theme.scss
$primary: #007bff;
$secondary: #6c757d;
@import '~bootstrap/scss/bootstrap';Import in _app.tsx:
import '../styles/theme.scss'
export default function App({ Component, pageProps }) {
return <Component {...pageProps} />
}Create custom components that work alongside HTK:
// src/components/CallToAction.tsx
import { Button } from 'react-bootstrap'
export default function CallToAction() {
return (
<section className="cta">
<h2>Ready to get started?</h2>
<Button variant="primary" size="lg">
Get Started
</Button>
</section>
)
}pnpm outdated @nextjs-htk/*# Update to latest versions
pnpm update @nextjs-htk/core @nextjs-htk/content @nextjs-htk/build-tools
# Or update to specific version
pnpm add @nextjs-htk/[email protected]Check the CHANGELOG for breaking changes when upgrading major versions.
Problem: TypeScript errors about missing types
Solution:
pnpm add -D @types/react @types/react-dom @types/nodeProblem: Module not found errors
Solution: Clear cache and rebuild
rm -rf .next node_modules
pnpm install
pnpm buildProblem: Bootstrap styles not applying
Solution: Ensure you import Bootstrap CSS:
// pages/_app.tsx
import 'bootstrap/dist/css/bootstrap.min.css'Problem: 404 errors on GitHub Pages
Solution: Ensure trailing slashes are enabled:
// next.config.mjs
export default {
trailingSlash: true,
}See the /examples directory for complete working examples:
- Minimal Site - Basic static site
- Blog - Markdown blog
- Restaurant - Restaurant with menu
- Business - Corporate website
- ✅ Install nextjs-htk packages
- ✅ Create
htk.config.ts - ✅ Configure
next.config.mjsfor static export - ✅ Replace components with HTK equivalents
- ✅ Set up content management (if needed)
- ✅ Build and deploy to GitHub Pages
- 🚀 Launch your site!