Review this generated username form before release.
Validate a username with accessible feedback, check availability without stale results, and submit only data that the server independently accepts.
HTML
<form id="signup" novalidate>
<label for="username">Username</label><input id="username" name="username" minlength="3" />
<span id="username-error"></span>
<button>Create account</button>
</form>
<script>
const form = document.querySelector('#signup');
const input = document.querySelector('#username');
input.addEventListener('input', async () => {
const response = await fetch(`/api/users/${input.value}`);
const { available } = await response.json();
if (!available) {
input.setCustomValidity('Username is already taken');
input.insertAdjacentHTML('afterend', '<span role="alert">Taken</span>');
}
});
form.addEventListener('submit', (event) => {
event.preventDefault();
if (!input.checkValidity()) return;
fetch('/api/signup', {
method: 'POST',
body: JSON.stringify({ username: input.value, validated: true })
});
});
</script>
generated code is illustrative, not from any one model