canceraiddev / elm-pages / Head

This module contains low-level functions for building up values that will be rendered into the page's <head> tag when you run elm-pages build. Most likely the Head.Seo module will do everything you need out of the box, and you will just need to import Head so you can use the Tag type in your type annotations.

But this module might be useful if you have a special use case, or if you are writing a plugin package to extend elm-pages.


type Tag

Values that can be passed to the generated Pages.application config through the head function.

metaName : String -> AttributeValue -> Tag

Example:

Head.metaName "twitter:card" (Head.raw "summary_large_image")

Results in <meta name="twitter:card" content="summary_large_image" />

metaProperty : String -> AttributeValue -> Tag

Example:

Head.metaProperty "fb:app_id" (Head.raw "123456789")

Results in <meta property="fb:app_id" content="123456789" />

metaRedirect : AttributeValue -> Tag

Example:

metaRedirect (Raw "0; url=google.com")

Results in <meta http-equiv="refresh" content="0; url=google.com" />

rssLink : String -> Tag

Add a link to the site's RSS feed.

Example:

rssLink "/feed.xml"
<link rel="alternate" type="application/rss+xml" href="/rss.xml">

sitemapLink : String -> Tag

Add a link to the site's RSS feed.

Example:

sitemapLink "/feed.xml"
<link rel="sitemap" type="application/xml" href="/sitemap.xml">

rootLanguage : LanguageTag -> Tag

Set the language for a page.

https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes/lang

import Head
import LanguageTag
import LanguageTag.Language

LanguageTag.Language.de -- sets the page's language to German
    |> LanguageTag.build LanguageTag.emptySubtags
    |> Head.rootLanguage

This results pre-rendered HTML with a global lang tag set.

<html lang="no">
...
</html>

Structured Data

structuredData : Json.Encode.Value -> Tag

You can learn more about structured data in Google's intro to structured data.

When you add a structuredData item to one of your pages in elm-pages, it will add json-ld data to your document that looks like this:

<script type="application/ld+json">
{
   "@context":"http://schema.org/",
   "@type":"Article",
   "headline":"Extensible Markdown Parsing in Pure Elm",
   "description":"Introducing a new parser that extends your palette with no additional syntax",
   "image":"https://elm-pages.com/images/article-covers/extensible-markdown-parsing.jpg",
   "author":{
      "@type":"Person",
      "name":"Dillon Kearns"
   },
   "publisher":{
      "@type":"Person",
      "name":"Dillon Kearns"
   },
   "url":"https://elm-pages.com/blog/extensible-markdown-parsing-in-elm",
   "datePublished":"2019-10-08",
   "mainEntityOfPage":{
      "@type":"SoftwareSourceCode",
      "codeRepository":"https://github.com/dillonkearns/elm-pages",
      "description":"A statically typed site generator for Elm.",
      "author":"Dillon Kearns",
      "programmingLanguage":{
         "@type":"ComputerLanguage",
         "url":"http://elm-lang.org/",
         "name":"Elm",
         "image":"http://elm-lang.org/",
         "identifier":"http://elm-lang.org/"
      }
   }
}
</script>

To get that data, you would write this in your elm-pages head tags:

import Json.Encode as Encode

{-| <https://schema.org/Article>
-}
encodeArticle :
    { title : String
    , description : String
    , author : StructuredDataHelper { authorMemberOf | personOrOrganization : () } authorPossibleFields
    , publisher : StructuredDataHelper { publisherMemberOf | personOrOrganization : () } publisherPossibleFields
    , url : String
    , imageUrl : String
    , datePublished : String
    , mainEntityOfPage : Encode.Value
    }
    -> Head.Tag
encodeArticle info =
    Encode.object
        [ ( "@context", Encode.string "http://schema.org/" )
        , ( "@type", Encode.string "Article" )
        , ( "headline", Encode.string info.title )
        , ( "description", Encode.string info.description )
        , ( "image", Encode.string info.imageUrl )
        , ( "author", encode info.author )
        , ( "publisher", encode info.publisher )
        , ( "url", Encode.string info.url )
        , ( "datePublished", Encode.string info.datePublished )
        , ( "mainEntityOfPage", info.mainEntityOfPage )
        ]
        |> Head.structuredData

Take a look at this Google Search Gallery to see some examples of how structured data can be used by search engines to give rich search results. It can help boost your rankings, get better engagement for your content, and also make your content more accessible. For example, voice assistant devices can make use of structured data. If you're hosting a conference and want to make the event date and location easy for attendees to find, this can make that information more accessible.

For the current version of API, you'll need to make sure that the format is correct and contains the required and recommended structure.

Check out https://schema.org for a comprehensive listing of possible data types and fields. And take a look at Google's Structured Data Testing Tool too make sure that your structured data is valid and includes the recommended values.

In the future, elm-pages will likely support a typed API, but schema.org is a massive spec, and changes frequently. And there are multiple sources of information on the possible and recommended structure. So it will take some time for the right API design to evolve. In the meantime, this allows you to make use of this for SEO purposes.

AttributeValues


type AttributeValue

Values, such as between the <>'s here:

<meta name="<THIS IS A VALUE>" content="<THIS IS A VALUE>" />

currentPageFullUrl : AttributeValue

Create an AttributeValue representing the current page's full url.

urlAttribute : Pages.Url.Url -> AttributeValue

Create an AttributeValue from an ImagePath.

raw : String -> AttributeValue

Create a raw AttributeValue (as opposed to some kind of absolute URL).

Icons

appleTouchIcon : Maybe Basics.Int -> Pages.Url.Url -> Tag

Note: the type must be png. See https://developer.apple.com/library/archive/documentation/AppleApplications/Reference/SafariWebContent/ConfiguringWebApplications/ConfiguringWebApplications.html.

If a size is provided, it will be turned into square dimensions as per the recommendations here: https://developers.google.com/web/fundamentals/design-and-ux/browser-customization/#safari

Images must be png's, and non-transparent images are recommended. Current recommended dimensions are 180px and 192px.

icon : List ( Basics.Int, Basics.Int ) -> MimeType.MimeImage -> Pages.Url.Url -> Tag

Functions for use by generated code

toJson : String -> String -> Tag -> Json.Encode.Value

Feel free to use this, but in 99% of cases you won't need it. The generated code will run this for you to generate your manifest.json file automatically!

canonicalLink : Maybe String -> Tag

It's recommended that you use the Seo module helpers, which will provide this for you, rather than directly using this.

Example:

Head.canonicalLink "https://elm-pages.com"