PSI文件
PSI文件
PSI (Program Structure Interface) 文件用结构化数据来表示文件内容。
PsiFile 类是所有 PSI文件的父类,其它的编程语言中的文件都是它的子类,例如,JAVA中表示为 PsiJavaFile ,XML中表示为 XmlFile
VirtualFile 和 Document 作用域是 application (即使打开了多个项目,每个文件都使用同一个 VirtualFile 实例)。PSI的作用域是 project:如果同一时间,在多个项目中打开同一个文件,这个文件会有多个PsiFile实例。
如果获取PSI文件
PSI文件能干啥
可以直接修改某个PSI元素,不需要修改整个文件。
可以使用下面代码遍历PSI文件中的PSI元素:
psiFile.accept(new PsiRecursiveElementWalkingVisitor() {
// 访问PSI元素
});
更多内容请查看文档: PSI导航
PSI文件从哪来
PSI依赖于编程语言,使用Language 实例创建的:
LanguageParserDefinitions.INSTANCE
.forLanguage(MyLanguage.INSTANCE)
.createFile(fileViewProvider);
和 Documents 一样,当访问某个文件的PSI时,就会创建对应的PSI文件
PSI 文件可以保存多长时间?
和 Documents 一样,PSI文件来自于VirtualFile的弱引用,当不被任何对象引用的时候,会被回收。
如何创建PSI文件
PsiFileFactory.createFileFromText() 可以根据指定的内容在内存中创建 PSI文件
PsiDirectory.add() 方法可以把 PSI文件保存在硬盘上。
如何监控PSI文件修改
PsiManager.getInstance(project).addPsiTreeChangeListener() 可以监控项目中PSI树的所有修改。或者在plugin.xml里注册扩展,代码如下:
<extensions defaultExtensionNs="com.intellij">
<psi.treeChangeListener implementation="com.intellij.psi.PsiTreeChangeListener 实现类" ></psi.treeChangeListener>
</extensions>
如何继承PSI
当需要支持新编程语言的时候,需要继承PSI, 具体可查看文档: Custom Language Support
PSI的工作规则
PSI文件的所有修改都会反映到 Document 上,所以和Document 的规则是一样的(读,写,命令,只读等),可以参考它的文档。