N
Nuxt4mo ago
Mirage

How to get asset URLs in api event handlers?

I'm trying to dynamically retrieve the URL of some assets using an api endpoint. Something similar to this:
export default defineEventHandler(async (event) => {

// ...

const coverUrl = (await import('~/assets/media/video-cover.mp4')).default;

// ...

return {
coverUrl,
}
})
export default defineEventHandler(async (event) => {

// ...

const coverUrl = (await import('~/assets/media/video-cover.mp4')).default;

// ...

return {
coverUrl,
}
})
However, that results in the following error:
Cannot find module '~/assets/media/video-cover.mp4' or its corresponding type declarations. ts(2307)
Cannot find module '~/assets/media/video-cover.mp4' or its corresponding type declarations. ts(2307)
And just to be sure that the file is referenced correctly, the following works in .vue components:
<script setup lang="ts">
// ...

const coverUrl = (await import('~/assets/skirk.info/media/video-cover.mp4')).default

// ...
</script>
<template>
</template>
<script setup lang="ts">
// ...

const coverUrl = (await import('~/assets/skirk.info/media/video-cover.mp4')).default

// ...
</script>
<template>
</template>
2 Replies
kapa.ai
kapa.ai4mo ago
Hi @Mirage. I'm kapa.ai, your friendly support bot. I will try to answer your question by searching through the knowledge base. :wave: ---------------------- In Nuxt 3, asset handling differs between client-side code (like Vue components) and server-side code (such as API event handlers). The ~/assets alias and dynamic imports for assets are processed by the build tool (Vite or Webpack) and are only available in client-side or build-time contexts. They do not work in server-side runtime code, such as API event handlers in server/api/, which is why you see the error:
Cannot find module '~/assets/media/video-cover.mp4' or its corresponding type declarations. ts(2307)
Cannot find module '~/assets/media/video-cover.mp4' or its corresponding type declarations. ts(2307)
This is a known limitation: server-side code cannot resolve ~/assets or @/assets aliases, nor can it import assets this way. This is confirmed by multiple sources, including issues and documentation: - Aliases like ~/assets are not available in the server runtime, and attempting to use them in server-side code (including API handlers) will result in errors. You should use relative paths or reference files from the public/ directory instead, which is directly accessible at runtime via a static URL (Nuxt assets documentation, GitHub issue, GitHub issue). - If you need to serve static files (like images, videos, etc.) from an API endpoint, place them in the public/ directory. You can then construct their URLs using the public path (e.g., /media/video-cover.mp4 if the file is at public/media/video-cover.mp4) and return that URL from your API handler. Example:
export default defineEventHandler(async (event) => {
// Assuming the file is in public/media/video-cover.mp4
const coverUrl = '/media/video-cover.mp4';

return {
coverUrl,
}
})
export default defineEventHandler(async (event) => {
// Assuming the file is in public/media/video-cover.mp4
const coverUrl = '/media/video-cover.mp4';

return {
coverUrl,
}
})
Summary:
You cannot use ~/assets imports in API event handlers. Move your files to the public/ directory and reference them by their public URL instead. This is the recommended and supported approach in Nuxt 3 for server-side code that needs to serve or reference static assets (Nuxt assets documentation, GitHub issue, GitHub issue). ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai4mo ago
<@1368579779309207656> Kapa.ai is still learning and improving, please let me know how I did by reacting below.

Did you find this page helpful?