Lab 18 - WCAG Checklist

Use RegEx to convert Markdown to JSON and create an interactive accessibility checklist!

Learning Objectives

  • Write regular expressions to parse a document’s contents
  • Use capturing groups to isolate specific parts of a RegEx pattern
  • Create HTML elements dynamically based on parsed text
  • Use Git to collaborate with a large team
  • Resolve merge conflicts when using Git collaboratively

Introduction

The W3C has put together a list of Web Content Accessibility Guidelines (WCAG) for developers to follow. One way of making sure your website follows these guidelines is to perform an “audit” on it, and inspect your site to make sure it meets the specified criteria.

For instance, WebAIM has condensed these guidelines into a printable checklist you can use when auditing your site. Now, the problem is, we want an interactive, digital checklist (save the 🌳s)!

Fortunately, you’ve found a solution: the (fictitious) company Check.life has a JavaScript library that makes a web page into an interactive checklist, given that the HTML follows a specific structure.

We’ve taken the text from the accessibility checklist and put it into four separate files, in Markdown format. Your goal will be to write code to convert the text from Markdown to HTML.

Getting Started

The accessibility guidelines are split up into four sections (Perceivable, Operable, Understandable, Robust), each in its own file. For this assignment, you will be placed on a team that is responsible for one of the four sections.

First, accept the GitHub Classroom assignment provided by your instructor.

You will be placed in one giant group – everyone will be sharing the same repository for this lab.

Have all team members use the Git command-line to clone the repo to their computer.

Instructions

Your task is to read in a text file (containing Markdown-formatted text) and create HTML elements to fill in the page.

We’ve broken the problem up into multiple functions for each section, so you can split the workload across team members. They will look like the following:

  • processFormatting(String) : String
    • This function should do multiple RegEx “find-and-replaces” to convert the given Markdown text into HTML, for the formatting rules.
  • processChecklists(String) : String
    • This function should do a RegEx “find-and-replace” to convert the given Markdown text into HTML, for only the Checklists.
  • processCriteria(String) : String
    • This function should do a RegEx “find-and-replace” to convert the given Markdown text into HTML, for only the Criteria.
  • processGuidelines(String) : String
    • This function should do a RegEx “find-and-replace” to convert the given Markdown text into HTML, for only the Guidelines.

These functions will be called one after the other, so the output of one function will be the input of the next. Finally, the output of processGuidelines will be the HTML that will be inserted into the DOM.

Steps:

  1. Your team will need to code all four process functions.
    • In each function, you must only process the text that is relevant to that function. For example, processChecklists should not convert Markdown links to HTML.
    • We recommend you delegate each function to a “sub-team”
    • You may want to reference this guide on using RexExp objects in JavaScript
  2. Try to test/develop your RegEx patterns in RegExr first! Here is one with example markdown.
  3. Don’t forget to test the webpage to make sure that your function is working properly!
    • You may need to view the page’s source to see your converted output.
    • You can also log the returned string to the console for debugging.
  4. After finishing a function, Make a commit in Git with your team’s name and the method name as the commit message, like Team Kraken - processFormatting1.
  5. Synchronize (git pull from the server, then git push) your commits with the remote repository
    • You may (read: will likely) encounter merge conflicts after a pull! If you do, follow the steps here to resolve the conflict and commit the resolution.
      • You will need to make a decision on whether or not to include your code vs. the code from the remote.
      • Make sure you test the website again to make sure you didn’t accidentally break anything 😖
    • After resolving the conflict, commit it and then try to synchronize your commits again.
    • If you get an error when pulling, see if it mentions a default pull strategy or similar.
      • This means you need to set the default pull behavior. For this lab, we will want to tell it to merge. Run this command to set merge as the default:
        git config --global pull.merge true
        
      • Next, repeat the pull and push again, following the instructions above.

Tips for Success:

  • Here is an example RegEx that searches for text marked for bold and replaces it with <strong> tags:
    let text = "Some text with __boldness__ and __strength__";
    let re = new RegExp("__([^_]+?)__", "g");    OR    let re = /__([^_]+?)__/g;
    text = text.replaceAll(re, "<strong>$1</strong>"); // Called on the String
    
    • You can create a RegExp object using the constructor or a “RegExp literal”, with the slashes.
    • Pay attention to the flags (just g in this case)
      • These modify how the RegExp will work – g stands for global and will let you use methods like a String’s replaceAll() method
    • Take a look at the RegExr breakdown here for an explanation of the pattern
  • For processFormatting, you should only need the g flag, like above.
    • However, you will need to do multiple find-and-replaces in a row for the different formatting types!
  • For processChecklists, processCriteria, and processGuidelines, you may need to use three flags: g – global, m – multiline (enables use of start ^ and end $ of line), and s – dotall (makes the dot . match newlines as well)
    • Here is an example RegEx that uses all three flags:
      let re = new RegExp("^pat(.*)tern$", "gms");    OR    let re = /^pat(.*)tern$/gms;
      
      This allows the pattern to match across lines, like so:
      pat
      another line
      tern
      
  • You can make multiline strings using JavaScript template literals:
    let html = `<div class="primary">
      <a href="https://www.google.com/">Search</a>
    </div>`;
    

Markdown Format Guide

Take a look at the Markdown Basic Syntax, which includes the corresponding HTML for given Markdown text. Look at the Headings, Emphasis, and Lists sections.

To simplify, we will focus on the following rules for formatting:

  • Italicized text is represented by one underscore surrounding some text (_some text_) and should use the <em> tags (<em>some text</em>)
  • Bold text is represented by two underscores on both sides (__some text__) and should use the <strong> tags (<strong>some text</strong>)
  • code text is represented by backticks surrounding some text (`some text`) and should use the <code> tags (<code>some text</code>)
  • Links are represented by a pair of square brackets followed by parentheses ([some text](URL)). The link text is in the brackets, and the URL is in the parentheses (<a href="URL">some text</a>)

Here’s a snippet from one of the checklist files:

#### Guideline 1.1: Provide text alternatives for any non-text content
* [1.1.1 Non-text Content](https://www.w3.org/TR/WCAG22/#non-text-content)
    * Images, image buttons, and image map hot spots have appropriate, equivalent [alternative text](https://webaim.org/techniques/alttext/).
    * Images that __do not__ convey content, are decorative, or contain content that is already conveyed in text are given empty _alternative text_ (`alt=""`) or implemented as CSS backgrounds. All linked images have descriptive alternative text.
    <!--END CRITERION-->

<!--END GUIDELINE-->

This should translate into the following HTML:

<div class="guideline">
  <h4>Guideline 1.1: Provide text alternatives for any non-text content</h4>
  <ul class="criteria">
    <li>
      <a href="https://www.w3.org/TR/WCAG22/#non-text-content">1.1.1 Non-text Content</a>
      <ul class="checklist">
        <li>Images, image buttons, and image map hot spots have appropriate, equivalent <a href="https://webaim.org/techniques/alttext/">alternative text</a>.</li>
        <li>Images that <strong>do not</strong> convey content, are decorative, or contain content that is already conveyed in text are given empty <em>alternative text</em> (<code>alt=""</code>) or implemented as CSS backgrounds. All linked images have descriptive alternative text.</li>
      </ul>
    </li>
  </ul>
</div>

Format: Guidelines

Guidelines start with #### (four pound signs and a space) and their title:

  • The guideline’s content consists of everything after the guideline title and before <!---END GUIDELINE--->
  • In HTML, each guideline should be represented by a <div> with the class guideline
  • The guideline title is the first element in the <div> and represented by h4-level heading
  • After the title, there should be an unordered list <ul> with the class criteria
  • All content should be put in between the <ul> tags

For example:

#### Guideline 1.1: Provide text alternatives for any non-text content
...a bunch of content, including potentially some HTML...
    <!--END CRITERION-->

<!--END GUIDELINE-->

should become:

<div class="guideline">
  <h4>Guideline 1.1: Provide text alternatives for any non-text content</h4>
  <ul class="criteria">
    ...a bunch of content, including potentially some HTML...
  </ul>
</div>

Format: Criteria

Each criterion starts with * at the beginning of a line (a star and a space) and their title:

  • The criterion’s content consists of everything after the criterion title and before <!--END CRITERION-->
  • In HTML, each criterion should be represented by a list item <li>
  • The criterion title should be inside the <li>
  • After the title, but still inside the <li>, there should be an unordered list <ul> with the class checklist
  • All content should be put in between the <ul> tags

For example:

* 1.1.1 Non-text Content
    ...a bunch of content, including potentially some HTML...
    <!--END CRITERION-->

should become:

<li>
  1.1.1 Non-text Content
  <ul class="checklist">
    ...a bunch of content, including potentially some HTML...
  </ul>
</li>

Format: Checklists

Each checklist item starts with    *  (four spaces, a star, and a space):

  • The item’s content is all on one line, after the    * 
  • In HTML, each item should be represented by a list item <li>
  • All content should be put in the <li>

For example:

    * A descriptive transcript of relevant content is provided for non-live audio-only (audio podcasts, MP3 files, etc.).

should become:

<li>A descriptive transcript of relevant content is provided for non-live audio-only (audio podcasts, MP3 files, etc.).</li>