Current section

Files

Jump to
sitemaps README.md
Raw

README.md

# Sitemaps
[![CI](https://github.com/manuel-rubio/sitemaps/actions/workflows/ci.yml/badge.svg)](https://github.com/manuel-rubio/sitemaps/actions/workflows/ci.yml)
[![Hex Package](https://img.shields.io/hexpm/v/sitemaps.svg)](https://hex.pm/packages/sitemaps)
[![Hex Docs](https://img.shields.io/badge/hex-docs-purple.svg)](https://hexdocs.pm/sitemaps/)
[![Hex.pm Total Downloads](https://img.shields.io/hexpm/dt/sitemaps.svg)](https://hex.pm/packages/sitemaps)
[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://github.com/manuel-rubio/sitemaps/blob/master/LICENSE)
[![Last Updated](https://img.shields.io/github/last-commit/manuel-rubio/sitemaps.svg)](https://github.com/manuel-rubio/sitemaps/commits/master)
**Sitemaps** is a flexible, fast Elixir library for generating standard XML and gzip-compressed (`.xml.gz`) sitemaps and sitemap index files compliant with search engine specifications (Google, Bing, etc.).
> **Origin & Attribution:**
> This library is an actively maintained fork and evolution of the original [`sitemap`](https://hex.pm/packages/sitemap) package created by [Tatsuo Ikeda (`ikeikeikeike`)](https://github.com/ikeikeikeike/sitemap). It was modernized for current Elixir and Erlang/OTP releases, featuring strict test coverage (95%+), improved documentation, type specifications, and updated dependencies.
---
## Features
- **Standard & Gzip Sitemaps:** Generates uncompressed `.xml` or gzip-compressed `.xml.gz` files out of the box.
- **Automatic Index & Segmentation:** Seamlessly rotates files and builds a `<sitemapindex>` when exceeding link count (default 10,000, up to 50,000) or file size limits (50 MB).
- **Clean Macro DSL:** Intuitive `create`, `add`, and `add_to_index` macros for structuring your sitemaps.
- **Comprehensive Metadata Extensions:**
- **Images:** Captions, titles, geo-location, and license information.
- **Videos:** Thumbnails, titles, descriptions, player locations, duration, ratings, tags, and family-friendly flags.
- **News:** Publication names, languages, publication dates, titles, genres, keywords, and stock tickers.
- **Alternate Languages:** Localized URL alternates (`hreflang`) via `xhtml:link`.
- **Mobile:** Mobile search engine tags (`<mobile:mobile/>`).
- **PageMap:** Google structured data attributes.
- **Search Engine Pings:** Built-in automatic ping notifications for Google and Bing (`Sitemaps.Generator.ping/1` or `ping/1`).
- **Flexible Configuration:** Configure globally via `config.exs`, system environment variables, or per-sitemap options.
---
## Installation
Add `sitemaps` to your list of dependencies in `mix.exs`:
```elixir
def deps do
[
{:sitemaps, "~> 0.1"}
]
end
```
---
## Quick Start
### Basic Usage
```elixir
defmodule MyApp.Sitemaps do
use Sitemaps
def generate do
create do
add "/", priority: 1.0, changefreq: "daily"
add "/about", priority: 0.8, changefreq: "weekly"
add "/contact", priority: 0.5, changefreq: "monthly"
end
# Notify search engines (Google and Bing) of the updated sitemap
ping()
end
end
```
### With Phoenix (Verified Routes)
```elixir
defmodule MyAppWeb.Schedulers.Sitemaps do
use Sitemaps
use Phoenix.VerifiedRoutes,
endpoint: MyAppWeb.Endpoint,
router: MyAppWeb.Router
def generate do
Sitemaps.Config.set(:files_path, "#{:code.priv_dir(:my_app_web)}/static/sitemaps/")
Sitemaps.Config.set(:host, "https://example.com")
create do
add ~p"/", priority: 1.0, changefreq: "daily"
add ~p"/about", priority: 0.8, changefreq: "weekly"
for post <- MyApp.Blog.list_posts() do
add ~p"/blog/#{post.slug}",
priority: 0.7,
changefreq: "monthly",
lastmod: post.updated_at
end
end
ping()
end
end
```
---
## Rich Metadata Examples
### Images
```elixir
add "/gallery",
images: [
[loc: "https://example.com/photo1.jpg", title: "Sunset", caption: "Beach sunset", geo_location: "Malaga, Spain"],
[loc: "https://example.com/photo2.jpg", title: "Mountains", license: "https://creativecommons.org/licenses/by/4.0/"]
]
```
### Videos
```elixir
add "/videos/elixir-intro",
videos: [
[
thumbnail_loc: "https://example.com/thumb.jpg",
title: "Introduction to Elixir",
description: "Learn concurrent programming with Elixir and OTP",
content_loc: "https://example.com/video.mp4",
player_loc: "https://example.com/player?id=123",
duration: 600,
family_friendly: true,
tag: ["elixir", "erlang", "otp"]
]
]
```
### News
```elixir
add "/news/release-announcement",
news: [
publication: [name: "Tech Times", language: "en"],
publication_date: ~D[2026-09-02],
title: "New Elixir Release Out Now",
genres: "PressRelease",
keywords: ["elixir", "programming", "technology"]
]
```
### Alternate Languages (hreflang)
```elixir
add "/products/book",
alternates: [
[href: "https://example.com/en/products/book", lang: "en"],
[href: "https://example.com/es/products/book", lang: "es"]
]
```
### Mobile & PageMap
```elixir
add "/mobile-page", mobile: true
add "/structured-page",
pagemap: [
dataobjects: [
[
type: "document",
id: "doc-1",
attributes: [
[name: "title", value: "Custom Title"],
[name: "rating", value: "4.8"]
]
]
]
]
```
---
## Configuration
You can configure options in `config/config.exs`, passing them to `use Sitemaps`, or at runtime:
```elixir
config :sitemaps,
host: "https://example.com",
files_path: "priv/static/sitemaps/",
public_path: "sitemaps/",
compress: true,
max_sitemap_links: 10_000
```
### Available Options
| Option | Environment Variable | Default | Description |
|---|---|---|---|
| `:host` | `SITEMAPS_HOST` | `"http://www.example.com"` | Base URL scheme and host for generated links |
| `:files_path` | `SITEMAPS_SITEMAPS_PATH` | `"sitemaps/"` | Filesystem path where sitemap files are written |
| `:public_path` | `SITEMAPS_PUBLIC_PATH` | `"sitemaps/"` | URL path where sitemaps are served from |
| `:filename` | `SITEMAPS_FILENAME` | `"sitemap"` | Base filename for the sitemaps |
| `:compress` | `SITEMAPS_COMPRESS` | `true` | When `true`, compresses files with gzip (`.xml.gz`) |
| `:max_sitemap_links` | `SITEMAPS_MAXLINKS` | `10_000` | Maximum number of URLs per sitemap file (max 50,000) |
| `:max_sitemap_files` | `SITEMAPS_MAXFILES` | `10_000` | Maximum sitemaps per index file |
| `:max_sitemap_file_size` | `SITEMAPS_MAXFILESIZE` | `5_000_000` | Maximum uncompressed byte size per file |
| `:create_index` | `SITEMAPS_CREATE_INDEX` | `"auto"` | `"auto"`, `true`, or `false` for index creation |
| `:verbose` | `SITEMAPS_VERBOSE` | `true` | Enable or disable informational console logs |
---
## Acknowledgements & Credits
- Original creator and maintainer: [Tatsuo Ikeda (`ikeikeikeike`)](https://github.com/ikeikeikeike/sitemap).
- Inspired by:
- [sitemap_generator](https://github.com/kjvarga/sitemap_generator) (Ruby)
- [go-sitemap-generator](https://github.com/ikeikeikeike/go-sitemap-generator) (Go)
---
## License
This project is licensed under the [MIT License](LICENSE).