Interview Question 2

by Arnaud Buchholz

HTML

<h1>
Interview Question 2
</h1>
<blockquote>
  We have an HTTP client (here <code>http</code>) to fetch resources from our API.
  Knowing the server is stateless and :
  <ul>
    <li id="/api/v1/books"><code>/api/v1/books</code> usually takes
      <select class="secs"><option selected>1</option><option>2</option><option>3</option></select>seconds
      to <select class="status"><option selected>succeed</option><option>fail</option></select>
    </li>
    <li id="/api/v1/authors"><code>/api/v1/authors</code> usually takes
      <select class="secs"><option>1</option><option>2</option><option selected>3</option></select>seconds
      to <select class="status"><option selected>succeed</option><option>fail</option></select>
    </li>
    <li id="/api/v1/libraries"><code>/api/v1/libraries</code> usually takes
      <select class="secs"><option>1</option><option selected>2</option><option>3</option></select>seconds
      to <select class="status"><option selected>succeed</option><option>fail</option></select>
    </li>
  </ul>
  Focus on the <code>request</code> function and answer the following questions :
  <ol>
    <li>How much time does the <code>request</code> function need to complete ?</li>
    <li>Can we improve the <code>request</code> function ?</li>
    <li>Can you explain the error handling, can it be improved ?</li>
  </ol>
  Feel free to express your thoughts openly and elaborate on your reasoning.
</blockquote>
<script>
const el = document.createElement.bind(document)
const tx = document.createTextNode.bind(document)
function output (msg) {
	const line = el('div')
  const timestamp = line.appendChild(el('span'))
  timestamp.className = 'timestamp'
  const now = new Date()
  const z = n => n.toString().padStart(2, '0')
  timestamp.appendChild(tx(`${z(now.getHours())}:${z(now.getMinutes())}:${z(now.getSeconds())}`))
  const message = line.appendChild(el('span'))
  message.className = 'message'
 ...

CSS

.timestamp {
  color: gray;
  margin-right: 4px;
}

blockquote {
  padding: 0.5rem;
  margin: 1rem;
  background-color: lightgray;
}

.spinner {
  display: inline-block;
  border: 2px solid #f3f3f3; /* Light grey */
  border-top: 2px solid #3498db; /* Blue */
  border-radius: 50%;
  width: 8px;
  height: 8px;
  animation: spin 1s linear infinite;
}

@keyframes spin {
  0% { transform: rotate(0deg); }
  100% { transform: rotate(360deg); }
}

select {
  border: none;
  background-color: lightgray;
}

TypeScript

const request = async () => {
  const [books, authors, libraries] = Promise.all([
    http.get('/api/v1/books'),
    http.get('/api/v1/authors'),
    http.get('/api/v1/libraries')
  ]);
  return { books, authors, libraries };
}

const click = async () => {
  try {
    const { books, authors, libraries } = await request();
    output('books : ' + books.join(','));
    output('authors : ' + authors.join(','));
    output('libraries : ' + libraries.join(','));
  } catch (e) {
    output('⚠️' + e.message);
  }
}