SlideShare a Scribd company logo
Building Books from Static Sites
Digital (and print) publishing with the JAMstack
Eric Gardner
Lead Developer, Rumors
Background
Building books from static sites: Digital (and print) publishing with the JAMstack
Digital Publishing at the Getty
• Mandate: publish the museum’s collection catalogues in a digital format
• Attempts to shoehorn academic books into a CMS didn’t work very well
• Team of 2 (developer, product manager) embedded in a larger print
publishing team
• Didn’t want to lose the beautiful design and long-term availability of printed
books
Web books on the JAM Stack
• Ancient Terracottas from South Italy and Sicily, Maria Lucia Ferruzza
• Roman Mosaics in the J. Paul Getty Museum, Alexis Belis
• Ancient Lamps in the J. Paul Getty Museum, Jean Bussiere and Birgitta Lindros Wohl
• Many more at www.getty.edu/publications/digital/
Tech Stack
• Middleman static site generator (easy to extend in Ruby)
• Plain text back-end (markdown & YAML files), stored on GitHub
• Vue.js and other javascript libraries for interactive UI elements
• PrinceXML and CSS3 for PDF generation at build-time
Features
Book-like reading experience
Building books from static sites: Digital (and print) publishing with the JAMstack
Full-text seach using Lunr.js (no server required)
Building books from static sites: Digital (and print) publishing with the JAMstack
pages = sitemap.resources.find_all { |p| p.source_file.match(/.md/) }
entries = []
pages.each_with_index do |page, index|
entry = {
:id => index,
:title => page.data.title,
:url => page.url,
:content => page.render({:layout => false }).gsub(
%r{</?[^>]+?>}, '' )
}
entries << entry
JSON Index template (content.json.erb)
// Feed data into Lunr index
function populateIndex(data) {
var index = lunr(function(){
this.field('title', { boost: 10 });
this.field('content');
this.ref('id');
});
data.forEach(function(item) {
index.add(item);
});
return index;
}
Basic Lunr setup
Deep-zoom images using Leaflet.js
Building books from static sites: Digital (and print) publishing with the JAMstack
Dynamic maps using Leaflet.js
Building books from static sites: Digital (and print) publishing with the JAMstack
Dynamic UI components using Vue.js
Building books from static sites: Digital (and print) publishing with the JAMstack
Automatic PDF & Epub generation
Building books from static sites: Digital (and print) publishing with the JAMstack
}
@page:left {
margin-bottom: $bottom-margin;
margin-left: $outer-margin;
margin-right: $inner-margin;
margin-top: $top-margin;
@bottom-left {
content: counter(page);
font-family: $base-font-family;
font-size: $page-number-size;
}
}
@page:right {
margin-bottom: $bottom-margin;
margin-left: $inner-margin;
margin-right: $outer-margin;
margin-top: $top-margin;
@bottom-right {
content: counter(page);
font-family: $base-font-family;
page: spread-bleed;
page-break-after: always;
width: $bleed-width;
}
%print-page-content {
color: $print-text-color;
column-count: 2;
column-fill: auto;
column-gap: ($print-base-spacing * 2);
font-size: $print-base-font-size;
a[href] {
color: $print-text-color;
prince-link: none;
text-decoration: none;
}
p {
margin: 0;
+ p { text-indent: $print-paragraph-indent; }
}
h2, h3, h4, h5, h6 {
CSS @page rules
Takeaways
1. Building things that last
2. Cross-disciplinary collaboration
Building books from static sites: Digital (and print) publishing with the JAMstack
Building books from static sites: Digital (and print) publishing with the JAMstack
http://blogs.getty.edu/iris/an-editors-view-of-digital-publishing/
3. Development of Quire, an open-source
digital publishing framework
https://github.com/gettypubs/quire
Acknowledgements
Open-source tools that made this project possible
Build things that last

More Related Content

PDF
Building Maps with Leaflet
PDF
Responsive Maps in WordPress
PPTX
Ankur py mongo.pptx
PDF
The Future is Static
PDF
Static site generation using Metalsmith (Node.js)
DOCX
Design & Modeling SoftwareSoftware for REBE Students.docx
DOCX
Design & Modeling SoftwareSoftware for REBE Students
PPTX
Going Mobile with HTML5
Building Maps with Leaflet
Responsive Maps in WordPress
Ankur py mongo.pptx
The Future is Static
Static site generation using Metalsmith (Node.js)
Design & Modeling SoftwareSoftware for REBE Students.docx
Design & Modeling SoftwareSoftware for REBE Students
Going Mobile with HTML5

Similar to Building books from static sites: Digital (and print) publishing with the JAMstack (20)

PDF
HTML 5 - Future of Web Browsing
PDF
2018 WebTrends - DigiPrima Technologies
PDF
Everything is Awesome - Cutting the Corners off the Web
PDF
3D ICONS: Europeana goes 3D, Daniel Pletinckx, Visual Dimension Belgium
PDF
Europeana goes 3D
PDF
Ustream Techtalks: Google Chrome Developer Tools
PDF
A Comprehensive Guide on Building Lightning-Fast Websites with React Static S...
PDF
Glass 2.0
PPTX
Mobile gotcha
PDF
Gatsby (Code.Talks) 2019
PDF
#1 - HTML5 Overview
PDF
Architecture of the Web browser
PDF
ODP
Technological processes pver the centuries
PPTX
Bing Webmaster Tools Search and Social Webinar
PPTX
CityTimes
PDF
Static is just a cache
PDF
Adaptation in Open Source Software, PyCon 2016 Keynote
PDF
Empowering the Mobile Web - Mills
PDF
Empowering the "mobile web"
HTML 5 - Future of Web Browsing
2018 WebTrends - DigiPrima Technologies
Everything is Awesome - Cutting the Corners off the Web
3D ICONS: Europeana goes 3D, Daniel Pletinckx, Visual Dimension Belgium
Europeana goes 3D
Ustream Techtalks: Google Chrome Developer Tools
A Comprehensive Guide on Building Lightning-Fast Websites with React Static S...
Glass 2.0
Mobile gotcha
Gatsby (Code.Talks) 2019
#1 - HTML5 Overview
Architecture of the Web browser
Technological processes pver the centuries
Bing Webmaster Tools Search and Social Webinar
CityTimes
Static is just a cache
Adaptation in Open Source Software, PyCon 2016 Keynote
Empowering the Mobile Web - Mills
Empowering the "mobile web"
Ad

Recently uploaded (20)

PPTX
Oracle Fusion HCM Cloud Demo for Beginners
PPTX
Computer Software and OS of computer science of grade 11.pptx
PDF
Odoo Companies in India – Driving Business Transformation.pdf
PPTX
assetexplorer- product-overview - presentation
PPTX
history of c programming in notes for students .pptx
PPTX
Operating system designcfffgfgggggggvggggggggg
PDF
EN-Survey-Report-SAP-LeanIX-EA-Insights-2025.pdf
PDF
Complete Guide to Website Development in Malaysia for SMEs
PDF
Product Update: Alluxio AI 3.7 Now with Sub-Millisecond Latency
PDF
Wondershare Filmora 15 Crack With Activation Key [2025
PDF
Designing Intelligence for the Shop Floor.pdf
PDF
How to Make Money in the Metaverse_ Top Strategies for Beginners.pdf
PDF
Design an Analysis of Algorithms II-SECS-1021-03
PDF
Cost to Outsource Software Development in 2025
PPTX
Why Generative AI is the Future of Content, Code & Creativity?
PDF
CapCut Video Editor 6.8.1 Crack for PC Latest Download (Fully Activated) 2025
PDF
Adobe Illustrator 28.6 Crack My Vision of Vector Design
PDF
CCleaner Pro 6.38.11537 Crack Final Latest Version 2025
PDF
Digital Systems & Binary Numbers (comprehensive )
DOCX
Greta — No-Code AI for Building Full-Stack Web & Mobile Apps
Oracle Fusion HCM Cloud Demo for Beginners
Computer Software and OS of computer science of grade 11.pptx
Odoo Companies in India – Driving Business Transformation.pdf
assetexplorer- product-overview - presentation
history of c programming in notes for students .pptx
Operating system designcfffgfgggggggvggggggggg
EN-Survey-Report-SAP-LeanIX-EA-Insights-2025.pdf
Complete Guide to Website Development in Malaysia for SMEs
Product Update: Alluxio AI 3.7 Now with Sub-Millisecond Latency
Wondershare Filmora 15 Crack With Activation Key [2025
Designing Intelligence for the Shop Floor.pdf
How to Make Money in the Metaverse_ Top Strategies for Beginners.pdf
Design an Analysis of Algorithms II-SECS-1021-03
Cost to Outsource Software Development in 2025
Why Generative AI is the Future of Content, Code & Creativity?
CapCut Video Editor 6.8.1 Crack for PC Latest Download (Fully Activated) 2025
Adobe Illustrator 28.6 Crack My Vision of Vector Design
CCleaner Pro 6.38.11537 Crack Final Latest Version 2025
Digital Systems & Binary Numbers (comprehensive )
Greta — No-Code AI for Building Full-Stack Web & Mobile Apps
Ad

Building books from static sites: Digital (and print) publishing with the JAMstack

  • 1. Building Books from Static Sites Digital (and print) publishing with the JAMstack Eric Gardner Lead Developer, Rumors
  • 4. Digital Publishing at the Getty • Mandate: publish the museum’s collection catalogues in a digital format • Attempts to shoehorn academic books into a CMS didn’t work very well • Team of 2 (developer, product manager) embedded in a larger print publishing team • Didn’t want to lose the beautiful design and long-term availability of printed books
  • 5. Web books on the JAM Stack • Ancient Terracottas from South Italy and Sicily, Maria Lucia Ferruzza • Roman Mosaics in the J. Paul Getty Museum, Alexis Belis • Ancient Lamps in the J. Paul Getty Museum, Jean Bussiere and Birgitta Lindros Wohl • Many more at www.getty.edu/publications/digital/
  • 6. Tech Stack • Middleman static site generator (easy to extend in Ruby) • Plain text back-end (markdown & YAML files), stored on GitHub • Vue.js and other javascript libraries for interactive UI elements • PrinceXML and CSS3 for PDF generation at build-time
  • 10. Full-text seach using Lunr.js (no server required)
  • 12. pages = sitemap.resources.find_all { |p| p.source_file.match(/.md/) } entries = [] pages.each_with_index do |page, index| entry = { :id => index, :title => page.data.title, :url => page.url, :content => page.render({:layout => false }).gsub( %r{</?[^>]+?>}, '' ) } entries << entry JSON Index template (content.json.erb)
  • 13. // Feed data into Lunr index function populateIndex(data) { var index = lunr(function(){ this.field('title', { boost: 10 }); this.field('content'); this.ref('id'); }); data.forEach(function(item) { index.add(item); }); return index; } Basic Lunr setup
  • 16. Dynamic maps using Leaflet.js
  • 18. Dynamic UI components using Vue.js
  • 20. Automatic PDF & Epub generation
  • 22. } @page:left { margin-bottom: $bottom-margin; margin-left: $outer-margin; margin-right: $inner-margin; margin-top: $top-margin; @bottom-left { content: counter(page); font-family: $base-font-family; font-size: $page-number-size; } } @page:right { margin-bottom: $bottom-margin; margin-left: $inner-margin; margin-right: $outer-margin; margin-top: $top-margin; @bottom-right { content: counter(page); font-family: $base-font-family; page: spread-bleed; page-break-after: always; width: $bleed-width; } %print-page-content { color: $print-text-color; column-count: 2; column-fill: auto; column-gap: ($print-base-spacing * 2); font-size: $print-base-font-size; a[href] { color: $print-text-color; prince-link: none; text-decoration: none; } p { margin: 0; + p { text-indent: $print-paragraph-indent; } } h2, h3, h4, h5, h6 { CSS @page rules
  • 24. 1. Building things that last
  • 29. 3. Development of Quire, an open-source digital publishing framework
  • 31. Acknowledgements Open-source tools that made this project possible

Editor's Notes

  • #2: Hi everyone! Thanks so much for being here this evening. My name is Eric Gardner. I’m a software engineer at Rumors, a design studio in Portland. I’ve been passionate about the technology of the “JAM Stack” since before that acronym existed! Tonight I’d like to talk about one application of this technology that I hope you find interesting – using static web tech as a system for digital publishing.
  • #3: First some background. Prior to joining Rumors in Portland, I worked for several years as a software developer at the Getty Museum in Los Angeles.
  • #4: This was just another day at the office. I highly recommend a visit if you’re ever in LA, the architecture alone is pretty amazing. And admission is free!
  • #5: The Getty is a world-class art museum, and it also houses a publishing department that produces dozens of art-related books each year. I worked within this department during my time there.
  • #6: We found a solution based on static site generator technology, or what you’d now call the JAM Stack. We began publishing books this way in 2016 with Ancient Terracottas from South Italy and Sicily. Since then a total of 6 major scholarly publications have been produced this way at the museum, with several more in the pipeline. I’m going to talk mostly about the first “trilogy” here. All of these are available online at www.getty.edu/publications/digital. They are also open source, and the code is available at github.com/gettypubs.
  • #7: Since this is a tech conference, here’s a quick overview of our tech stack for these projects.
  • #9: We wanted the products we were creating to feel like books.
  • #10: The simplicity of building sites on top of static generator tech allowed us to focus on things like creating a great reading experience and responsive design. You can see some examples of that design here. We were inspired by sites like Medium and wanted to deliver an elegant, distraction-free experience to the reader.
  • #11: Another key feature was making the full text of the books searchable. We used the Lunr.js library for this feature.
  • #12: Lunr is described by its creator as “a little bit like Solr but much smaller and not as bright”. We still thought it was pretty amazing. No back-end server was required - we generated a JSON index at build time which was consumed by the client at runtime.
  • #13: Building a JSON index of all text pages in Middleman is pretty straightforward, since you have all of Ruby at your disposal. The software has a “sitemap” object which can be queried and manipulated in various ways. Here we simply looped through the pages and constructed a simple data structure containing text content and basic metadata for each page, which then gets rendered as JSON.
  • #14: On the client side, the JSON data is fetched and fed into the Lunr search index; fields can be given different weights to prioritize matches found in the title for example.
  • #15: Leaflet is an open-source mapping library, but it also supports deep-zoom image display.
  • #16: I wrote a simple ruby script to split up high-resolution images from the museum into tiles at various zoom levels and uploaded them to S3. The catalogue entry pages can then display the images with a zoomable interface similar to Google Maps. We were able to display hundreds of views of dozens of artifacts, at high levels of detail – something that would simply not have been possible in a printed publication. Link out to http://www.getty.edu/publications/terracottas/catalogue/1/ if desired
  • #17: You can also use Leaflet to display actual maps, of course.
  • #18: We were able to connect artifacts with the locations where they were found or manufactured.
  • #19: These catalogues primarily were mainly composed of static HTML pages generated by Middleman. But when more interactivity was required, Vue.js proved to be a useful tool for building complex UI components. It is easy to introduce a Vue component in an otherwise standard web page.
  • #20: This example comes from the Ancient Lamps catalogue, which contained over 600 entries. Using Vue’s computed properties feature, it was easy to do things like filter and sort a large collection of data in response to multiple criteria instantaneously.
  • #21: Perhaps the “killer feature” of our web books was the fact that we could also provide EPUB, PDF, and print-on-demand versions of the same material automatically. This is one place where Middleman really shines – out of all the static site generators, it is the easiest one to add custom functionality in. The extension API lets you hook into the build process at various points and inject custom code. I wrote a small extension in Ruby that queried the sitemap during a build to find all the pages where a front matter flag had been set for inclusion in the print version – these pages were fed to the PrinceXML tool which generated a PDF from them.
  • #22: Here is an example of the kinds of layouts we were able to create using CSS.
  • #23: The little-known Paged Media module supports pretty sophisticated control over printed layouts (margins, columns, bleeds, breaks, page numbering, etc). Much of this spec is already implemented in major browsers, but the command-line Prince XML software (not open source, unfortunately), offers the best support and was instrumental to generating the print editions.
  • #25: Compared to traditional books, most websites have a laughably short lifespan. But scholarly work needs to be available for years if not decades so that future researchers can make use of it. The JAM stack is a great way to mitigate this problem. Between the human-readable text files in Git, the static web versions that require no back-end services, and the Epub, PDF, and print versions that we generated at the same time, we are confident that at least some versions of these books will still be usable decades from now.
  • #26: Another huge advantage of this approach is that the relative simplicity of the tech lowers the barriers to entry for non-specialists.
  • #27: When your data looks like this, it’s much easier for to collaborate with non-technical staff (editors, designers, etc)
  • #28: We were able to successfully train editors to use tools like GitHub and text editors. This is an example “revision” of a book after it was published.
  • #29: One of our editors (Ruth, pictured here) enjoyed the process so much that she wrote about it for the Getty blog.
  • #30: Finally, our initial work on these publications led to the development of a digital publishing framework, Quire, that is still in active development at the Getty.
  • #31: Quire builds on top of the Hugo static site generator and uses a CLI written in Node.js to add support for building additional publication formats (PDF, Epub, etc). The project is currently in alpha stages, but several museums and small publishers already have projects in production using this tool. More info at the GitHub repo here.
  • #32: Before I wrap up, I just want to acknowledge some of the amazing open-source tools that made these projects possible. Finally, I want to leave you all with a challenge, and that is:
  • #33: Thank you.