Je pense que y a pas mal de mauvaises pratiques dans ton code :
Déjà tu devrais utiliser les queryParams dans ton fetch en lui passant une query (ton searchText) et ensuite selon les queryParams tu fais ta logique. https://stackoverflow.com/questions/9870512/how-to-obtain-the-query-string-from-the-current-url-with-javascript
J'ai l'impression que la déclaration de matches est un peu problématique vu que tout est asynchrone, j'imagine que tu vas peut être rencontrer des bugs, peut-être utiliser .then ce serait mieux
Ta fonction doit avoir un return matches
Le regex est vraiment bourrin, tu pourrais juste faire states.filter(({title}) => title.toLocaleString().includes(search.toLocaleString()))
Dans ton addEventListener, tu devrais juste appeler la fonction comme ça : search.addEventListener('input', searchStates); et aller chercher la value dans la fonction, je te conseille de prendre tout de suite cette habitude, lorsque tu voudras enlever un eventListener ce sera beaucoup plus simple.
Sinon VDD a tout dit pour le côté pratique dans l'html
Bon courage 