Create new .json file in specific directory

Good Morning every one, 

I would like to know, if there is a way to create a JSON file and insert it in a specific directory, like using template files to create java classes? 

and another point is the fact that, how can I create it in a specific directory like (res/raw/test.json)

thank you in advance

18 comments

Good morning. You can create file templates for any kind of file you want using File -> Settings -> Editor -> File and Code Templates. There already exist several samples of JSON file templates:

As about creating them in a specific directory, could you please clarify a bit what do you need exactly - to show corresponding file templates only under particular directories, or to create the full hierarchy of nested directories containing this file, or to automatically generate the file in some certain scenario?

Thanks in advance for any further info.

0

Thanks for your hints. 

In particular, I started to develop an android studio plugin to automatically generate some implementation code and add it to the developer application. the work that I need to do in one part of this plugin is to create a JSON file like the following:

{
"User_name":"test",
"https_required": true,
....
}

so, I would like to know, How can I create this programmatically, and then I need to put this file in a resource directory of the application as the one you can see in the attached image (res\raw)

Indeed, I need to create the JSON file programmatically and then create a sub-directory inside res directory with the name of i.e test and insert the JSON file there. 

thanks in advance for your help 

0

If you want to add a file template from your plugin, you can register a template in your plugin.xml:

<internalFileTemplate name="my_json"/>

You place your template under "fileTemplates\internal" in your resources directory, with name like "my_json.json.ft". (And add one more file "my_json.json.html" if you want to provide a description.)

And then you may use com.intellij.ide.actions.CreateFileFromTemplateAction#createFileFromTemplate() in your action invocation. Use FileTemplateManager.getInstance(project).getInternalTemplate to get the template object.

 

Now it depends only on how you want to invoke your template.

Do you want to have an action in some context menu, or to expand it when the project is being created?

0

Actually, I have an action that in some context menu. so, I would like this functionality as well, in the aforementioned part. so, How can I inject it into the specified directory by using the aforementioned method? 

Regards. 

0

>Actually, I have an action that in some context menu.

In this case, just invoke CreateFileFromTemplateAction#createFileFromTemplate inside you action, it allows to specify the directory where your file is to be created.

You may also override isAvailable for your action, if you want it to be shown only in specific contexts.

0

thank you very much for your help. I will try that. 

 

0

Dear Anton, as you suggest, I take a look at this part "CreateFileFromTemplateAction#createFileFromTemplate" but the method take a PsiDirectory as an variable, so my question is that, how can I achieve this? 

Best Regards


0

I would like to ask another question, if I want to add an XML file can I follow the same procedure by using this class as well? 

thank you in advance

0

com.intellij.psi.PsiManager#findDirectory, com.intellij.openapi.vfs.VirtualFileManager#refreshAndFindFileByUrl, com.intellij.openapi.util.io.FileUtil#toSystemIndependentName, com.intellij.openapi.vfs.VirtualFileManager#constructUrl, com.intellij.openapi.vfs.VirtualFileSystem#getProtocol for LocalFileSystem

Our platform has many levels of abstraction, sorry. :) These APIs should be enough for getting PsiDirectory having its file system path. In case of any further questions - don't hesitate to ask.

 

Yes, the same can be done for any kind of files, including XML files.

0

I am sorry to disturb you again with my questions. 

String pathToFile = "/Users/amirsharif/AndroidStudioProjects/test2/app/src/main/res/layout/activity_main.xml";
VirtualFile virtualFile = LocalFileSystem.getInstance().findFileByPath(pathToFile);
FileTemplate fileTemplate = FileTemplateManager.getInstance(myProject).getInternalTemplate("TokenActivity");
resourceDirectory = psiManager.findDirectory(virtualFile);
CreateFileFromTemplateAction.createFileFromTemplate(fileTemplate, resourceDirectory);

I tried to add the xml file by using the upper code, but I got an error that is said " can not resolve method createFileFromTemplate.
0

No problem, feel free to ask your questions any time you need.

There exists no such method signature as you tried to use, that's correct.

IntelliJ community is an open-source product, so you may always consult source code in case of doubt. For instance, here you see all the available overloads for `createFileFromTemplate`:

https://github.com/JetBrains/intellij-community/blob/master/platform/lang-impl/src/com/intellij/ide/actions/CreateFileFromTemplateAction.java

We have stable branches numbered with the last two digits of year + one digit for minor update number, in case you want to see code corresponding to a particular release. So, if you want to browse source code for stable release 2018.2, for example, you should switch to branch '182'. For 2018.3, switch to branch '183', etc.

0

Actually, I did the same and I used one of the overload in the aforementioned class

protected PsiFile createFileFromTemplate(final String name, final FileTemplate template, final PsiDirectory dir). 

 

so, I don't know what is the problem, and actually the first value can be null (final string name). 

0

The method you're trying to invoke in static context is not static. :) Please use a static overload.

0

Good Morning, 

I solved the problem with thanks to your hints. now, I got an error here, when I try to get the PsiDirectory by using the following code:

psiManager = psiManager.getInstance(myProject);

String pathToFile = "/Users/amirsharif/IdeaProjects/MyApplication/app/src/main/res/layout/activity_main.xml";

VirtualFile virtualFile = LocalFileSystem.getInstance().findFileByPath(pathToFile);

resourceDirectory = psiManager.findDirectory(virtualFile);

when I tried to debug, I understand that it returns null. 

0

Good morning.

That's true that it returns null. This happens because you pass there a VirtualFile that is not a directory.

VirtualFile is an abstraction that encompasses both files and directories. So, when you have a VirtualFile for your file, just get its parent VirtualFile (`getParent` method) which is a directory, and then pass it to psiManager.findDirectory.

So, findDirectory doesn't find a parent directory for a file. It finds a PsiDirectory for a VirtualFile representing a directory.

(As for getting the project path, and handling project opening you may take a look at ProjectUtils.kt.)

0

oh, I see. I am so careless. now, it works. Thanks for the hint. I will take a look to the other class in order to understand how to take the project path. 

thanks

0

Hello, 
I tried to use "com.org.jetbrains.android" packages inside the plugin to be able to edit manifest file and some other purposes, but I got an error that Error:(18, 42) java: package org.jetbrains.android.dom.manifest does not exist. 

So, should I change the plugin.xml <depends> part?

Thanks in advance

0

Yes, you're right. You should add a dependency, <depends> with the ID of the referenced plugin. We have an article covering that.

0

Please sign in to leave a comment.