Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

519
Views
How can I get $magics to support async?

A much admired feature of HTMX among beginners is it's ability to abstract away javascript and make fetch requests from the backend directly in markup.

I don't like HTMX because I think it's really limiting, I love Alpine and don't like using multiple frameworks - but I would like the ability to on occasion just do a simple request of my backend in order to populate an item in my dom from within Alpine without specifically calling a function to do that.

I have built this functionality using a simple function I have called xfetch in the below example, which is simply passed a url and returns the relevant item into the x-text, x-html or variable in x-data. It can be used in alpine as follows:

<div x-data>
    <span x-text="await xfetch("url")>
</div>

I think implementing this in a straightforward way, without getting into the details of promises, etc, would be really helpful for beginners getting started with Alpine as their first JS framework.

Ideally I would make this an Alpine magic called $fetch but I can't work out how to make magics work nicely with async and await.

My current code is as follows:

<html lang="en">
<head>
    <script defer src="https://unpkg.com/alpinejs@3.x.x/dist/cdn.min.js"></script>
</head>
<body>

<div x-data="{ time: xfetch('http://date.jsontest.com', method = 'GET', jsonItem='time') }">

    <p>
        This pulls the time from an object in x-data:
        <span x-text="await time"></span>
    </p>

    <p>
        ... but you can also pass a url right into the x-text:
        <span x-text="await xfetch('http://date.jsontest.com', method = 'GET', jsonItem='date')"> </span>
    </p>
</div>


<script>

    async function xfetch(url, method='GET', jsonItem=null) {

        return fetch(url, {
            method: method,
        })
        .then((response) => response.json())
        .then((responseJson) => {
            return responseJson[jsonItem]
        });

    }
</script>

</body>
</html>

Ideally I would add in:

document.addEventListener('alpine:init', () => {

    Alpine.magic('fetch', () => url => {
        return await xfetch(url, method='GET', jsonItem=null)
    })

})

but this doesn't work I think because the async isn't working when I put it in a $magic.

Two questions:

  1. Is it possible for a magic function to run an await the result of an async command?
  2. Is it possible to pass multiple variables to a $magic function?

Thanks

about 4 years ago · Juan Pablo Isaza
1 answers
Answer question

0

EDIT: Updating this answer as @Super and I worked through this and it seems we discovered the answers to the original questions posed.

  1. it appears while it is possible for a magic to handle async results, it seems you can only do this if there are no arguments to the async function represented by the $magic
  2. yes, multiple arguments can be passed to a $magic

HOWEVER: it appears you cannot do both at the same time. It seems you cannot have a $magic that is async and also accepts arguments.


  1. I believe what you need here is async "all of the way down". I could not definitively test your example as I got a CORS error requesting the data, but I did test with a local handler here that returns some data and I did get my result.
  2. I changed your arrow function to a standard function and added a second function arg.

I would also note that HTMX has ajax functionality that handles and resolves the async Promise results for you.

For your example, perhaps try something like this

 <script>
        async function xfetch(url, method = 'GET', jsonItem = null) {
            let response=
           await  fetch(url, {
                method: method,
            })
                .then((response) => response.json())
                .then((responseJson) => {
                    return responseJson[jsonItem]
                });
            return response;
        }
        document.addEventListener('alpine:init', async () => {

            Alpine.magic('fetch', async function(url,otherdata) {
                let response = await xfetch(url, method = 'GET', jsonItem = null)
                return await response.text();
            })

        })
    </script>
about 4 years ago · Juan Pablo Isaza Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!