Working with $PROJECT_DIR$ in plugin configuration options

For the IvyIDEA plugin, a number of paths are saved as part of the plugin configuration settings (the facet config). Now these are stored absolute (I just save the text that comes from the TextFieldWithBrowseButton).

Is there an easy way to store these path relative to the project basedir using the $PROJECT_DIR$ placeholder and have them loaded correctly?

I saw a thread about this from 2004 here but the answer was not very clear to me.



You can try implement PersistentStateComponent<YourClass> and annotate it like this:

@State (
    name = "YourPluginConfiguration",
    storages = {
        @Storage (id = "default", file = "$PROJECT_FILE$"),
        @Storage (id = "dir", file = "$PROJECT_CONFIG_DIR$/../config.xml", scheme = StorageScheme.DIRECTORY_BASED)

then add project-component to your plugin.xml,
and in projects with ".idea" format configuration state of your class will be saved in .idea/../config.xml. For more information see
This is what you want or I don't understand you?

Thanks for your reply!

The problem is than in my PersistentStateComponent I have a String property that configures a file path. This is now stored absolute because I take it directly from user input. I was wondering on how to store that pathname relative to the $PROJECT_DIR$.


I understood you wrong. Ok, you have string '/path/to/your/file', this is absolute path. You have project in folder '/path/to/your/project'. If you want to produce path something like this '../file' you can:

VirtualFile projectDir = project.getBaseDir();
String relativePath =,"/path/to/your/file/",File.separatorChar);

If this still not what you want(my english not perfect:)), please explain clearer.

I found another solution! You can use:

PathMacroManager macroManager = PathMacroManager.getInstance(project);
String pathWithMacro = macroManager.collapsePath("/path/to/your/project/your/file");
assert pathWithMacro.equals("$PROJECT_DIR$/your/file");

It also have method expandPath(String), which do reverse.

PathMacroManager also have methods collapsePaths(Element element)/expandPaths(Element element), this mean that if you implements ProjectComponent<Element> and apply this methods to Element objects in getState()/loadState(Element element) IDEA will collapse/expand all pathes in your xml config, but when config will be loaded - it will contain normal pathes.

Maybe this is what you want.

This sounds exactly like what I need, I'll give it a try, thanks!!




Please sign in to leave a comment.