JSFiddle - React, Tailwind, and code Playground

HTML

<h1 style="background-color: yellow" id="is-checking" class="result">  Checking </h1>
<h1 style="background-color: red"    id="is-connected"    class="result">  Hostname Resolved </h1>
<h1 style="background-color: green"  id="is-failed"   class="result">  Hostname Not Resolved </h1>


<form onkeydown="return event.key != 'Enter';">
  Hostname To Lookup: <br>
  <input type="text" id="hostname">
  <br>
  <input type="button" value="Query" onclick="window.checkHostname(document.getElementById('hostname').value)">
</form>

JavaScript

let answerPc = null, offerPc = null;

function hideAllResults() {
  document.querySelectorAll('.result').forEach(el  => {
    el.style.display = 'none';
  });
}
hideAllResults();

function updateForConnectionState(iceConnectionState) {
  hideAllResults();
  if ((el = document.querySelector(`#is-${iceConnectionState}`)) != null) {
    el .style.display = 'block';
  }
}

function rewriteCandidate(peerConnection, candidate, hostname) {
  if (candidate == null) {
    return;
  }

  peerConnection.addIceCandidate({
    candidate: candidate.candidate.replace(/\S+\.\S+/, hostname),
    sdpMid: candidate.sdpMid,
    sdpMLineIndex: candidate.sdpMLineIndex,
  })
}

window.checkHostname = hostname => {
  if (!hostname.endsWith('.local')) {
    hostname += '.local';
  }

  if (answerPc) {
    answerPc.close();
    offerPc.close();
  }

  updateForConnectionState('checking')

  answerPc = new RTCPeerConnection();
  offerPc = new RTCPeerConnection();
  offerPc.createDataChannel('dummyChannel');

  offerPc.oniceconnectionstatechange = () => updateForConnectionState(answerPc.iceConnectionState)
  answerPc.oniceconnectionstatechange = () => updateForConnectionState(answerPc.iceConnectionState)

  offerPc.onicecandidate = e => rewriteCandidate(answerPc, e.candidate, hostname)
  answerPc.onicecandidate = e => rewriteCandidate(offerPc, e.candidate, hostname)

  offerPc.createOffer().then(offer => {
    offerPc.setLocalDescription(offer)
    answerPc.setRemoteDescription(offer)
    return answerPc.createAnswer()
  }).then(answer => {
    answerPc.setLocalDescription(answer)
    offerPc.setRemoteDescription(answer)
  }).catch(alert)
}