Mano, tu tá insistindo em atribuir concorrência à assincronia. Isso está errado.
Você pode até achar que seja melhor que a função assíncrona funcione em paralelo, ou concorrentemente. Mas isso é só a sua opinião. Isso não faz parte do conceito de assíncronia e jamais fará. São conceitos e utilidades diferentes.
Pegue qualquer linguagem que você considere "realmente assíncrona" e coloque para rodar em um processador com um único núcleo de processamento (ou limite o acesso do programa a apenas um núcleo). Você já não consegue mais que o programa seja "realmente concorrente", porque o processador vai executar uma instrução por vez, uma atrás da outra, mesmo que a linguagem simule uma concorrência. Mas ainda assim você pode ter a assincronia, independentemente de quantos núcleos o programa tenha acesso. Porque a assincronia só depende da instrução ser executada (ou resolver) fora da ordem que foi deflagrada.
Segundo a sua definição, um programa "realmente assíncrono" deixaria de sê-lo se ficar limitado a um único núcleo de processamento, mas isso não é verdade, pelo contrário, a única coisa que acontece é que o programa deixa de ser "realmente concorrente".
Veja bem esse exemplo:
let someCounter = 0;
const asyncFunction = async () => await new Promise(resolve => setTimeout( ()=>resolve(someCounter++), 500) );
const theValues =
{
async: asyncFunction().then( value => theValues.async = value ),
sync: someCounter++,
get counter () { return someCounter },
}
setTimeout( () => console.log(theValues), 500 );
A propriedade async
é claramente definida antes da propriedade sync
, porém esta última recebe 0
do contador enquanto a primeira recebe 1
do contador.
Por que isso acontece? Porque a propriedade async
resolve seu valor somente 500ms depois da propriedade sync
.
Por mais que o JavaScript tenha uma pilha de execução que ocorre em ordem, isso não impede a assincronia. Faz parte do design da linguagem para manter a ordem. Se você tem dois timers de 1ms definidos imediatamente um após o outro, porque diabos seria interessante que o timer definido por último execute antes do que foi definido primeiro? Na minha opinião, o JavaScript faz muito bem em manter as coisas em ordem.