Skip to content

Commit 6713b69

Browse files
committed
优化代码存储和 DartYamlModel 创建逻辑
1 parent 8f433c3 commit 6713b69

4 files changed

Lines changed: 71 additions & 43 deletions

File tree

.idea/dataSources.local.xml

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

.idea/workspace.xml

Lines changed: 10 additions & 6 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/main/kotlin/shop/itbug/flutterx/common/yaml/DartYamlModel.kt

Lines changed: 34 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
package shop.itbug.flutterx.common.yaml
22

33
import com.intellij.openapi.application.readAction
4+
import com.intellij.psi.PsiInvalidElementAccessException
45
import com.intellij.psi.SmartPointerManager
56
import com.intellij.psi.SmartPsiElementPointer
67
import com.intellij.psi.util.PsiTreeUtil
@@ -71,37 +72,49 @@ data class DartYamlModel(
7172

7273
companion object {
7374

74-
suspend fun create(element: YAMLKeyValueImpl): DartYamlModel? {
75-
// 在 readAction 内部进行所有 PSI 访问,避免元素在异步操作中失效
75+
suspend fun create(elementPointer: SmartPsiElementPointer<YAMLKeyValueImpl>): DartYamlModel? {
76+
// 1. 获取 project 时也要注意安全性
77+
val project = try { elementPointer.project } catch (_: Exception) { return null }
78+
7679
return readAction {
77-
// 检查元素是否仍然有效
78-
if (!element.isValid) return@readAction null
79-
val pt = PsiTreeUtil.findChildOfType(element,YAMLPlainTextImpl::class.java) ?: return@readAction null
80-
val hasBlock = PsiTreeUtil.findChildOfType(element,YAMLBlockMappingImpl::class.java) != null
81-
if (hasBlock) return@readAction null
82-
83-
val version = element.valueText.trim()
84-
if (version.isBlank()) return@readAction null
85-
val name = element.keyText.trim()
86-
val point = SmartPointerManager.getInstance(element.project).createSmartPsiElementPointer(element)
87-
val plainText = SmartPointerManager.getInstance(element.project).createSmartPsiElementPointer(pt)
88-
DartYamlModel(
89-
name, version, tryParseDartVersionType(version), point, plainText,
90-
)
80+
try {
81+
// 2. 检查 element 是否还在
82+
val element = elementPointer.element ?: return@readAction null
83+
if (!element.isValid || project.isDisposed) return@readAction null
84+
85+
// 3. 这里的 pt 指针还是需要的,因为它是 element 的子元素
86+
val pt = PsiTreeUtil.findChildOfType(element, YAMLPlainTextImpl::class.java) ?: return@readAction null
87+
88+
// 检查是否有 block (比如有些 pubspec 是 key: { version: 1.0.0 } 这种结构)
89+
val hasBlock = PsiTreeUtil.findChildOfType(element, YAMLBlockMappingImpl::class.java) != null
90+
if (hasBlock) return@readAction null
91+
92+
val version = element.valueText.trim()
93+
if (version.isBlank()) return@readAction null
94+
val name = element.keyText.trim()
95+
96+
// 创建 pt 的指针
97+
val pointerManager = SmartPointerManager.getInstance(project)
98+
val plainTextPointer = pointerManager.createSmartPsiElementPointer(pt)
99+
100+
// 直接复用传入的 elementPointer,不需要再 create 一次
101+
DartYamlModel(name, version, tryParseDartVersionType(version), elementPointer, plainTextPointer)
102+
} catch (_: PsiInvalidElementAccessException) {
103+
null
104+
}
91105
}
92106
}
93107

94108
/**
95109
* 解析model的时候同时请求pub.dev的包数据
96110
* 多了一个请求
97111
*/
98-
suspend fun fetch(element: YAMLKeyValueImpl): DartYamlModel? {
112+
suspend fun fetch(element: SmartPsiElementPointer<YAMLKeyValueImpl>): DartYamlModel? {
99113
val model = create(element) ?: return null
100-
val fileAndProject = readAction {
101-
if (!element.isValid) return@readAction null
102-
element.containingFile to element.project
114+
val (file, project) = readAction {
115+
val psi = model.element.element ?: return@readAction null
116+
psi.containingFile to psi.project
103117
} ?: return null
104-
val (file, project) = fileAndProject
105118
val isIgnored = YamlFileIgDartPackageCache.getInstance(project).state.hasItem(file, model.name)
106119
if (isIgnored) return null
107120
val data = PubService.callPluginDetails(model.name) ?: return null

src/main/kotlin/shop/itbug/flutterx/common/yaml/YamlFileTools.kt

Lines changed: 26 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,15 @@
11
package shop.itbug.flutterx.common.yaml
22

3+
import com.intellij.openapi.application.readAction
34
import com.intellij.openapi.project.Project
45
import com.intellij.openapi.project.guessProjectDir
56
import com.intellij.psi.PsiManager
7+
import com.intellij.psi.SmartPointerManager
68
import kotlinx.coroutines.async
79
import kotlinx.coroutines.awaitAll
810
import kotlinx.coroutines.coroutineScope
911
import org.jetbrains.yaml.psi.YAMLFile
1012
import org.jetbrains.yaml.psi.impl.YAMLKeyValueImpl
11-
import shop.itbug.flutterx.services.MyPackageGroup
1213

1314
// 判断项目是否为 flutter 项目
1415
suspend fun Project.isFlutterProject(): Boolean {
@@ -44,26 +45,36 @@ class PubspecYamlFileTools private constructor(yaml: YAMLFile) : YamlFileToolBas
4445
suspend fun getDependencyOverrides() = getChsWith("dependency_overrides")
4546

4647

48+
private val YAMLKeyValueImpl.point
49+
get() = SmartPointerManager.getInstance(project).createSmartPsiElementPointer(this)
50+
4751
/**
4852
* 获取全部的插件模型
4953
*/
50-
suspend fun allDependencies() =
51-
(getDependencies().map {
52-
DartYamlModel.create(it)?.copy(
53-
type = MyPackageGroup.Dependencies
54-
)
55-
} + getDevDependencies().map {
56-
DartYamlModel.create(it)?.copy(type = MyPackageGroup.DevDependencies)
57-
} + getDependencyOverrides().map {
58-
DartYamlModel.create(it)?.copy(type = MyPackageGroup.DependencyOverrides)
59-
}).filterNotNull()
54+
suspend fun allDependencies(): List<DartYamlModel> = coroutineScope {
55+
val deps = getDependencies()
56+
val devDeps = getDevDependencies()
57+
val overrideDeps = getDependencyOverrides()
58+
59+
val pointers = readAction {
60+
(deps + devDeps + overrideDeps)
61+
.filter { it.isValid }
62+
.map { SmartPointerManager.createPointer(it) }
63+
}
64+
65+
pointers.map { ptr ->
66+
async { DartYamlModel.create(ptr) }
67+
}.awaitAll().filterNotNull()
68+
}
6069

61-
/**
62-
* 获取插件列表模型
63-
*/
6470
suspend fun getDependenciesModel(list: List<YAMLKeyValueImpl>): List<DartYamlModel> {
71+
val pointers = readAction {
72+
list.filter { it.isValid }.map { SmartPointerManager.createPointer(it) }
73+
}
6574
return coroutineScope {
66-
list.map { async { DartYamlModel.fetch(it) } }.awaitAll().filterNotNull()
75+
pointers.map { ptr ->
76+
async { DartYamlModel.fetch(ptr) }
77+
}.awaitAll().filterNotNull()
6778
}
6879
}
6980

0 commit comments

Comments
 (0)