Back to Freecodecamp

Build a Travel Agency Page

curriculum/challenges/english/blocks/lab-travel-agency-page/669e2f60e83c011754f711f9.md

latest9.6 KB
Original Source

--description--

Objective: Fulfill the user stories below and get all the tests to pass to complete the lab.

User Stories:

  1. You should have a DOCTYPE declaration.
  2. You should have an html element with lang set to en.
  3. You should have a head element containing a meta void element with charset set to utf-8 and a title with the text Travel Agency Page.
  4. You should have a meta tag in your head element that contains a short description of your website for SEO.
  5. You should have an h1 element to present your travel destinations.
  6. You should have a paragraph below the h1 element introducing the travel opportunities.
  7. You should have an h2 element with the text Packages.
  8. You should have a p element introducing briefly the various packages.
  9. You should have an unordered list element with two list items. The two list items should have the text Group Travels and Private Tours, respectively. The text of each list item should be enclosed by an anchor element.
  10. You should have an h2 element with the text Top Itineraries.
  11. You should have at least three figure elements, each containing an anchor element and a figcaption element.
  12. The three anchor elements should have an img element with an appropriate alt attribute and a src attribute set to a valid image as their content. You can use https://cdn.freecodecamp.org/curriculum/labs/colosseo.jpg, https://cdn.freecodecamp.org/curriculum/labs/alps.jpg, and https://cdn.freecodecamp.org/curriculum/labs/sea.jpg if you would like.
  13. All your five anchor elements should have an href attribute with the value of https://www.freecodecamp.org/learn and a target attribute with the value of _blank.

--hints--

Your travel agency page should have a !DOCTYPE html declaration.

js
assert.match(code, /<!DOCTYPE\s+html>/i);

You should have an html element with lang set to en.

js
assert.match(code, /<html\s+lang\s*=\s*('|")en\1\s*>[\s\S]*<\/\s*html\s*>/i);

You should have a head element within the html element.

js
assert.match(
  code,
  /<html[\s\S]*>[\s\S]*<\s*head\s*>[\s\S]*<\/\s*head\s*>[\s\S]*<\/\s*html\s*>/i
);

You should have two meta elements within your head element.

js
assert.match(code, /<\s*head\s*>[\s\S]*(<\s*meta[\s\S]*>[\s\S]*){2,}<\/\s*head\s*>/i);

One meta element should have a name attribute with value of description and a non-empty content attribute.

js
assert.match(code,
 /<\s*meta\s+[^>]*name\s*=\s*["']description["'][^>]*content\s*=\s*["'][^"']+?["'][^>]*>/i,
);

One meta element should have its charset attribute set to UTF-8.

js
assert.match(code, /<\s*meta[\s\S]+?charset\s*=\s*('|")UTF-8\1/i);

You should have title element within your head element.

js
assert.match(
  code,
  /<\s*head\s*>[\s\S]*<\s*title\s*>[\s\S]*<\/\s*title\s*>[\s\S]*<\/\s*head\s*>/i
);

Your title element should have your travel agency name.

js
assert.isAbove(document.querySelector('title')?.innerText.trim().length, 0);

You should have a body element within your html element.

js
assert.match(
  code,
  /<\s*html[\s\S]*>[\s\S]*<\s*head\s*>[\s\S]*<\/\s*head\s*>[\s\S]*<\s*body\s*>[\s\S]*<\/\s*body\s*>[\s\S]*<\/\s*html\s*>/i
);

You should have an h1 element to present your travel destinations.

js
assert.isAbove(document.querySelector('h1')?.innerText.length, 0);

You should only have one h1 element.

js
assert.lengthOf(document.querySelectorAll('h1'), 1);

You should have a p element below the h1 element.

js
assert.strictEqual(
  document.querySelector('h1')?.nextElementSibling.tagName, 'P'
);

Your first p element should introduce the travel opportunities.

js
assert.isNotEmpty(document.querySelector('p')?.textContent?.trim());

Your first h2 element should have the text Packages.

js
assert.equal(document.querySelectorAll('h2')[0]?.innerText.trim(), 'Packages');

You should have a p element below your first h2 element.

js
assert.strictEqual(
    document.querySelector('h2')?.nextElementSibling.tagName, 'P'
);

Your second p element should introduce briefly the various packages.

js
assert.isNotEmpty(document.querySelectorAll('p')?.[1]?.textContent?.trim());

You should have an unordered list element below your second p element.

js
assert.strictEqual(
  document.querySelectorAll('p')?.[1]?.nextElementSibling?.tagName,
  'UL'
);

You should have two items in your unordered list.

js
assert.lengthOf(document.querySelectorAll('p + ul li'), 2);

Both your list items should contain an anchor element.

js
const listItems = document.querySelectorAll('p + ul li');
assert.isNotEmpty(listItems);
for (let e of listItems) {
  assert.strictEqual(e.children[0].tagName, 'A');
  assert.lengthOf(e.children, 1);
}

The anchor element of your first list item should wrap the text Group Travels.

js
assert.equal(document.querySelectorAll('li > a')[0]?.innerText.trim(), 'Group Travels');

The anchor element of your second list item should wrap the text Private Tours.

js
assert.equal(document.querySelectorAll('li > a')[1]?.innerText.trim(), 'Private Tours');

You should have an h2 element after your unordered list.

js
assert.strictEqual(
  document.querySelectorAll('h2')[1]?.previousElementSibling.tagName,
  'UL'
);

Your second h2 element should have the text Top Itineraries.

js
assert.equal(document.querySelectorAll('h2')[1]?.innerText.trim(), 'Top Itineraries');

You should have at least three figure elements.

js
assert.isAtLeast(document.querySelectorAll('figure').length, 3);

Each figure element should contain an anchor element as its first child.

js
const figures = document.querySelectorAll('figure');
assert.isNotEmpty(figures);
for (let figure of figures) {
  assert.equal(figure.children[0].tagName, 'A');
}

Each figure element should contain a figcaption element as its second child.

js
const figures = document.querySelectorAll('figure');
assert.isNotEmpty(figures);
for (let figure of figures) {
  assert.equal(figure.children[1]?.tagName, 'FIGCAPTION');
}

Each figcaption should contain some text.

js
const figcaptionEls = document.querySelectorAll('figcaption');
assert.isNotEmpty(figcaptionEls);
figcaptionEls.forEach((figcaption => assert.isNotEmpty(figcaption.innerText)));

Each of the a elements that are children of your figure elements should contain an image.

js
const anchors = document.querySelectorAll('figure > a');
assert.isNotEmpty(anchors);
for (let anchor of anchors) {
  assert.equal(anchor.children[0]?.tagName, 'IMG');
}

Each img element should have a valid src attribute.

js
const images = document.querySelectorAll('img');
assert.isNotEmpty(images);
for (let image of images) {
  assert.isAbove(image.src.trim().length, 0);
}

Each img element should have an alt attribute with an appropriate value.

js
const images = document.querySelectorAll('img');
assert.isNotEmpty(images);
for (let image of images) {
  assert.isAbove(image.alt.trim().length, 0);
}

Each a element should have an href attribute with the value of https://www.freecodecamp.org/learn. Don't forget the links in the list items.

js
const anchors = document.querySelectorAll('a');
assert.isNotEmpty(anchors);
for (let anchor of anchors) {
  assert.equal(anchor.href, 'https://www.freecodecamp.org/learn');
}

Each a element should have a target attribute with the value of _blank. Don't forget the links in the list items.

js
const anchors = document.querySelectorAll('a');
assert.isNotEmpty(anchors);
for (let anchor of anchors) {
  assert.equal(anchor.target, '_blank');
}

--seed--

--seed-contents--

html

--solutions--

html
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <title>Travel Agency Page</title>
    <meta name="description" content="This is an example website."/>
  </head>
  <body>
    <h1>Discover Italy</h1>
    <p>
      Art, folklore, food, nature, and more. Choose among our wide selection of
      guided tours and excursions, and live an unforgettable experience
      exploring Italy.
    </p>
    <h2>Packages</h2>
    <p>
      We offer an extensive range of holiday solutions to accommodate the needs
      of all our clients. From daily excursions in the most beautiful cities, to
      thorough tours of hidden villages and medieval towns to discover Italy's
      lesser-known sides.
    </p>
    <ul>
      <li>
        <a href="https://www.freecodecamp.org/learn" target="_blank"
          >Group Travels</a
        >
      </li>
      <li>
        <a href="https://www.freecodecamp.org/learn" target="_blank"
          >Private Tours</a
        >
      </li>
    </ul>
    <h2>Top Itineraries</h2>
    <figure>
      <a href="https://www.freecodecamp.org/learn" target="_blank">
        
      </a>
      <figcaption>Rome and Center Italy</figcaption>
    </figure>
    <figure>
      <a href="https://www.freecodecamp.org/learn" target="_blank">
        
      </a>
      <figcaption>Nature and National Parks</figcaption>
    </figure>
    <figure>
      <a href="https://www.freecodecamp.org/learn" target="_blank">
        
      </a>
      <figcaption>South Italy and Islands</figcaption>
    </figure>
  </body>
</html>