Add public assets at build time
Hi, i'm creating a local module for my project, and I'm stuck on adding public assets with the
nitro:config hook.
I did this:
and when I start the dev server all works fine. The problem comes when I try to build, as nuxt tries to find the images/icons I use in my page routes but since they are added "after", it throws this error:
14 Replies
Hi @Alwe. I'm kapa.ai, your friendly support bot. I will try to answer your question by searching through the knowledge base. :wave:
----------------------
When adding public assets from a module using the
The knowledge sources confirm that assets referenced by static URLs must exist in the
nitro:config hook, your approach to push directories to nitroConfig.publicAssets is correct for exposing folders at runtime. However, the error you’re seeing during build—[vite]: Rollup failed to resolve import "/images/logo_brand.png"—suggests that Vite (the build tool) is trying to resolve these assets at build time, but they are not available in the expected location.
Key points from the Nuxt documentation:
- The public/ directory is for static assets that are served as-is and are available at the root URL (e.g., /images/logo_brand.png). These files are not processed by the build tool and must exist before the build starts. If you reference /images/logo_brand.png in your Vue files, Vite expects to find this file in the public/images/ directory at build time, not injected later by a module or Nitro hook Docs: public directory.
- Injecting assets via nitro:config and publicAssets works for runtime serving, but does not make those assets available to Vite during the build process. This is why it works in dev (where the server can serve them dynamically) but fails in build (where Vite needs to resolve them statically) Injecting Other Assets.
Solution:
If you want assets to be available at build time for direct references (e.g., <img src="/images/logo_brand.png" />), you must ensure those files are present in the project’s public/ directory before the build starts. Adding them via nitro:config is not sufficient for Vite’s build process.
What you can do:
- Place your images/icons in the public/ directory of the main project, or
- If you want to distribute them from your module, copy them into the consuming project’s public/ directory as part of your module’s install/setup process (e.g., using a postinstall script or a Nuxt module hook that runs before build).
Summary:The knowledge sources confirm that assets referenced by static URLs must exist in the
public/ directory at build time. Injecting them via nitro:config only affects runtime serving, not build-time resolution by Vite Docs: public directory Injecting Other Assets.
I'm sorry, but there is no built-in way in Nuxt to make Vite aware of assets injected into publicAssets via nitro:config after the build has started. You need to ensure those assets are present in the public/ directory before building.
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@174602707791904769> Kapa.ai is still learning and improving, please let me know how I did by reacting below.
@kapa.ai ok so i should add them at build time to the public folder? how can i do that within a module?
Let me check the knowledge base for you again. One moment! :books:
----------------------
Yes, if you want your assets to be available at build time (so that Vite and Nuxt can resolve them when referenced in your code), you need to ensure they are present in the project's
- Assets referenced by static URLs must be in the
public/ directory before the build starts.
How to do this within a module?
The official Nuxt documentation does not provide a built-in Nuxt module API for copying files into the consuming project's public/ directory at build time. The documented approach for exposing assets from a module is to use the nitro:config hook with publicAssets, but as you've seen, this only works at runtime and not for build-time asset resolution Injecting Other Assets.
I'm sorry, but the knowledge sources do not contain explicit instructions or examples for copying files into the public/ directory from a module during the build process. You may need to use a custom script or external tool to achieve this, but this is not covered in the official Nuxt documentation.
Summary:- Assets referenced by static URLs must be in the
public/ directory before build.
- The Nuxt module system does not provide a documented way to copy files into public/ at build time.
- You may need to handle this outside of Nuxt's documented module API.
If you need more advanced asset handling, you might consider contributing to the Nuxt documentation or opening a feature request.
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@174602707791904769> Kapa.ai is still learning and improving, please let me know how I did by reacting below.
@kapa.ai I did this:
but I don't want to show the files in the git history and I don't want to ignore them as they should be merged with the files i have in my root public folder. is there a way to add them during build in the final
.output/public folder but before the error occurs?Let me check the knowledge base for you again. One moment! :books:
----------------------
Based on the official Nuxt documentation and available knowledge sources, there is no documented or supported way to copy files into the final
You cannot merge assets into
.output/public directory during the build process in a way that makes them available to Vite for static imports before the build error occurs.
- The public/ directory is the only place Nuxt guarantees static assets will be available at both build and runtime. Assets injected into .output/public via the nitro:config hook (using publicAssets) are only available at runtime, not during the Vite build step, which is why you see errors if you reference them in your code Docs: public directory Injecting Other Assets.
- There is no hook or documented API to inject files into .output/public before Vite's build step, and the build process expects all static assets to already be present in the public/ directory at the project root.
Summary:You cannot merge assets into
.output/public during build in a way that resolves the Vite import error, according to the current Nuxt documentation. All assets needed for static imports must be present in the root public/ directory before the build starts. The knowledge sources do not provide a workaround for your use case.
If you need to avoid tracking these files in git, you will need to manage them outside of Nuxt's documented build process.
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@174602707791904769> Kapa.ai is still learning and improving, please let me know how I did by reacting below.
@kapa.ai what about
nitro:build:public-assets hook?Let me check the knowledge base for you again. One moment! :books:
----------------------
Yes, there is a
- This hook runs after the Vite build step. So, assets added here will be available at runtime, but not for static imports or references that Vite resolves during build.
- If your use case is to serve files at runtime (e.g., for direct download or API access), this hook is suitable. - If you need assets to be available for static imports in your Vue components or pages, they must still be present in the
You can use
nitro:build:public-assets hook available in Nuxt. According to the official documentation, this hook is:
Called after copying public assets. Allows modifying public assets before Nitro server is built.This means you can use the
nitro:build:public-assets hook to modify or add files to the .output/public directory after the initial copy from the public/ directory, but before the Nitro server is finalized Nuxt Hooks (build time).
However, please note:- This hook runs after the Vite build step. So, assets added here will be available at runtime, but not for static imports or references that Vite resolves during build.
- If your use case is to serve files at runtime (e.g., for direct download or API access), this hook is suitable. - If you need assets to be available for static imports in your Vue components or pages, they must still be present in the
public/ directory before the build starts.
In summary:You can use
nitro:build:public-assets to add or modify files in .output/public for runtime serving, but this will not resolve Vite build-time import errors for static asset references Nuxt Hooks (build time).
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@174602707791904769> Kapa.ai is still learning and improving, please let me know how I did by reacting below.
@kapa.ai can i use the
vite:extend to do it at build time before accessing with static imports?Let me check the knowledge base for you again. One moment! :books:
----------------------
Based on the official Nuxt documentation, the
vite:extend hook allows you to extend the Vite build context, but there is no information in the knowledge sources indicating that you can use this hook to copy or inject files into the public/ directory (or any other directory) before Vite processes static imports. The documentation describes vite:extend as a way to extend the Vite context, not to manipulate the file system or asset directories Nuxt Hooks (build time).
Therefore, I'm sorry, but there's no information in the knowledge sources that suggests you can use vite:extend to copy assets into the public directory at build time before static imports are resolved. All static assets needed for Vite imports must be present in the public/ directory before the build starts.
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@174602707791904769> Kapa.ai is still learning and improving, please let me know how I did by reacting below.