From b0ba003d8cb2f13d1814cb86d5dc3c30fc324e66 Mon Sep 17 00:00:00 2001 From: siosio Date: Sat, 6 Jan 2018 07:07:34 +0900 Subject: [PATCH] =?UTF-8?q?=E6=A4=9C=E7=B4=A2=E6=96=B9=E6=B3=95=E3=82=92?= =?UTF-8?q?=E8=A6=8B=E7=9B=B4=E3=81=97?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/main/java/siosio/CentralSearcher.kt | 10 +++ src/main/java/siosio/Client.kt | 17 ++++ src/main/java/siosio/DependencyText.kt | 24 ++++++ ...GradleDependenciesCompletionContributor.kt | 78 ++++--------------- src/main/java/siosio/MavenFinder.kt | 66 ---------------- src/main/java/siosio/SearchParam.kt | 23 ------ .../java/siosio/searcher/ArtifactSearcher.kt | 32 ++++++++ .../java/siosio/searcher/DefaultSearcher.kt | 31 ++++++++ .../java/siosio/searcher/VersionSearcher.kt | 39 ++++++++++ src/main/resources/META-INF/plugin.xml | 8 +- 10 files changed, 173 insertions(+), 155 deletions(-) create mode 100644 src/main/java/siosio/CentralSearcher.kt create mode 100644 src/main/java/siosio/Client.kt create mode 100644 src/main/java/siosio/DependencyText.kt delete mode 100644 src/main/java/siosio/MavenFinder.kt delete mode 100644 src/main/java/siosio/SearchParam.kt create mode 100644 src/main/java/siosio/searcher/ArtifactSearcher.kt create mode 100644 src/main/java/siosio/searcher/DefaultSearcher.kt create mode 100644 src/main/java/siosio/searcher/VersionSearcher.kt diff --git a/src/main/java/siosio/CentralSearcher.kt b/src/main/java/siosio/CentralSearcher.kt new file mode 100644 index 0000000..1b71c80 --- /dev/null +++ b/src/main/java/siosio/CentralSearcher.kt @@ -0,0 +1,10 @@ +package siosio + +import com.intellij.codeInsight.completion.* + +interface CentralSearcher { + + val dependencyText: DependencyText + + fun find(resultSet: CompletionResultSet) +} \ No newline at end of file diff --git a/src/main/java/siosio/Client.kt b/src/main/java/siosio/Client.kt new file mode 100644 index 0000000..e2f481f --- /dev/null +++ b/src/main/java/siosio/Client.kt @@ -0,0 +1,17 @@ +package siosio + +import org.apache.http.client.methods.* +import org.apache.http.impl.client.* + +object Client { + + fun get(uri: String): String { + val response = HttpClients.createDefault() + .execute(HttpGet(uri)) + + return when (response.statusLine.statusCode) { + 200 -> response.entity.content.reader().readText() + else -> "" + } + } +} \ No newline at end of file diff --git a/src/main/java/siosio/DependencyText.kt b/src/main/java/siosio/DependencyText.kt new file mode 100644 index 0000000..6efb1e6 --- /dev/null +++ b/src/main/java/siosio/DependencyText.kt @@ -0,0 +1,24 @@ +package siosio + +import com.intellij.codeInsight.completion.* +import siosio.searcher.* + +class DependencyText(val text: String?) { + + val isShort: Boolean = text?.length ?: 0 < 2 + + private val splitText = text?.split(":") ?: emptyList() + + fun getGroupId() = splitText.getOrElse(0) { "" } + fun getArtifactId() = splitText.getOrElse(1) { "" } + + fun addCompletions(resultSet: CompletionResultSet) { + when (splitText.size) { + 3 -> VersionSearcher(this) + 2 -> ArtifactSearcher(this) + else -> DefaultSearcher(this) + }.find(resultSet) + + } + +} \ No newline at end of file diff --git a/src/main/java/siosio/GradleDependenciesCompletionContributor.kt b/src/main/java/siosio/GradleDependenciesCompletionContributor.kt index f97f3d7..922b6bd 100644 --- a/src/main/java/siosio/GradleDependenciesCompletionContributor.kt +++ b/src/main/java/siosio/GradleDependenciesCompletionContributor.kt @@ -14,72 +14,28 @@ import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.path.* class GradleDependenciesCompletionContributor : AbstractGradleCompletionContributor() { - init { - extend(CompletionType.SMART, - psiElement(PsiElement::class.java) - .and(psiElement().inFile(PlatformPatterns.psiFile().withName(StandardPatterns.string().endsWith(".gradle")))) - .withParent(GrLiteral::class.java) - .withSuperParent(5, psiElement(GrMethodCallExpression::class.java) - .withText(string().contains("dependencies"))), CompletionParametersCompletionProvider()) - } - - private class CompletionParametersCompletionProvider : CompletionProvider() { - - val mavenFinder = MavenFinder() - - override fun addCompletions( - parameters: CompletionParameters, - context: ProcessingContext, - resultSet: CompletionResultSet) { - - val position = parameters.originalPosition + init { + extend(CompletionType.SMART, + psiElement(PsiElement::class.java) + .and(psiElement().inFile(PlatformPatterns.psiFile().withName(StandardPatterns.string().endsWith(".gradle")))) + .withParent(GrLiteral::class.java) + .withSuperParent(5, psiElement(GrMethodCallExpression::class.java) + .withText(string().contains("dependencies"))), CompletionParametersCompletionProvider()) + } - position?.let { - val text = trimQuote(it.text) - if (isShortText(text)) { - return - } + private class CompletionParametersCompletionProvider : CompletionProvider() { - val searchParam = SearchParam(text) + override fun addCompletions( + parameters: CompletionParameters, + context: ProcessingContext, + resultSet: CompletionResultSet) { - val searchResult = mavenFinder.find(searchParam) - val completionResultSet = if (searchParam.isFindVersion()) { - resultSet.restartCompletionOnPrefixChange(text) - resultSet.withRelevanceSorter( - CompletionSorter.emptySorter().weigh(object : LookupElementWeigher("gradleDependencyWeigher") { - override fun weigh(element: LookupElement): Comparable<*> { - return DependencyComparable(searchResult, element) - } - }) - ) - } else { - resultSet.withRelevanceSorter( - CompletionSorter.emptySorter().weigh(PreferStartMatching()) - ) - } + val position = parameters.originalPosition ?: return - searchResult.forEach { - completionResultSet.addElement(LookupElementBuilder.create(it)) + DependencyText(trimQuote(position.text)) + .takeUnless { it.isShort } + ?.addCompletions(resultSet) } - } } - } - - class DependencyComparable( - versions: Set, - private val element: LookupElement) : Comparable { - - private val index: Int; - - init { - index = versions.indexOf(element.lookupString) - } - - override fun compareTo(other: DependencyComparable): Int = this.index - other.index - } - - companion object { - fun isShortText(text: String?) = (text?.length ?: 0) < 2 - } } diff --git a/src/main/java/siosio/MavenFinder.kt b/src/main/java/siosio/MavenFinder.kt deleted file mode 100644 index 045a390..0000000 --- a/src/main/java/siosio/MavenFinder.kt +++ /dev/null @@ -1,66 +0,0 @@ -package siosio - -import java.io.* -import java.net.* -import java.util.* -import kotlin.text.* - -class MavenFinder { - - companion object { - - /** mavenのアクセス結果からライブラリ名と最新バージョンを抽出する正規表現 */ - private val PATTERN = Regex("\\{\"id\":\"((?:[^:]+:){2})[^\"]+\"") - - /** バージョン番号を抽出する正規表現 */ - private val VERSION_PATTERN = Regex("\\{\"id\":\"([^\"]+)\"") - - private const val FIND_URL = "http://search.maven.org/solrsearch/select?q=a:%s&core=gav&rows=50&wt=json" - - /** バージョ番号を取得するURL */ - private const val FIND_VERSION_URL = - "http://search.maven.org/solrsearch/select?q=g:%s+AND+a:%s&rows=20&core=gav&wt=json" - - fun MatchResult.group(index: Int) = this.groups.get(index)!!.value - - private fun getConnection(spec: String): HttpURLConnection { - val url = URL(spec) - return url.openConnection() as HttpURLConnection - } - - private fun getResponse(connection: HttpURLConnection): InputStream { - if (connection.responseCode != 200) { - throw IOException("response is abnormal end.") - } - return connection.inputStream - } - } - - fun contains(searchParam: SearchParam): Boolean { - return !search(FIND_VERSION_URL.format(searchParam.group, searchParam.name), VERSION_PATTERN).isEmpty() - } - - fun find(searchParam: SearchParam): Set { - return if (searchParam.isFindVersion()) { - search( - FIND_VERSION_URL.format(searchParam.group, searchParam.name), VERSION_PATTERN) - } else { - search(FIND_URL.format(searchParam.text), PATTERN) - } - } - - private fun search(url: String, pattern: Regex): Set { - val result = LinkedHashSet() - val connection = getConnection(url) - val stream = getResponse(connection) - stream.use { - val reader = BufferedReader(it.bufferedReader()) - val text = reader.readText() - pattern.findAll(text).forEach { - result.add(it.group(1)) - } - } - return result - } -} - diff --git a/src/main/java/siosio/SearchParam.kt b/src/main/java/siosio/SearchParam.kt deleted file mode 100644 index a22882a..0000000 --- a/src/main/java/siosio/SearchParam.kt +++ /dev/null @@ -1,23 +0,0 @@ -package siosio - -class SearchParam(text: String) { - val group: String - val name: String - val text: String - - init { - val list = split(text) - if (list.size in (2..3)) { - this.group = list[0] - this.name = list[1] - this.text = "" - } else { - this.group = "" - this.name = "" - this.text = text - } - } - - fun isFindVersion() = text.isEmpty() -} - diff --git a/src/main/java/siosio/searcher/ArtifactSearcher.kt b/src/main/java/siosio/searcher/ArtifactSearcher.kt new file mode 100644 index 0000000..263cbd3 --- /dev/null +++ b/src/main/java/siosio/searcher/ArtifactSearcher.kt @@ -0,0 +1,32 @@ +package siosio.searcher + +import com.intellij.codeInsight.completion.* +import com.intellij.codeInsight.completion.impl.* +import com.intellij.codeInsight.lookup.* +import siosio.* + +class ArtifactSearcher(override val dependencyText: DependencyText) : CentralSearcher { + + override fun find(resultSet: CompletionResultSet) { + val text = Client.get( + "https://search.maven.org/solrsearch/select?q=g:${dependencyText.getGroupId()}" + + "&rows=200&wt=json") + + resultSet.restartCompletionOnPrefixChange(dependencyText.text) + resultSet.withRelevanceSorter( + CompletionSorter.emptySorter().weigh(PreferStartMatching()) + ).addAllElements(ARTIFACT_PATTERN.findAll(text) + .map { + it.groups[1]!!.value + } + .distinct() + .map { + LookupElementBuilder.create("${dependencyText.getGroupId()}:$it") + }.toList()) + } + + + companion object { + private val ARTIFACT_PATTERN = Regex(",\"a\":\"([^\"]+)\"") + } +} \ No newline at end of file diff --git a/src/main/java/siosio/searcher/DefaultSearcher.kt b/src/main/java/siosio/searcher/DefaultSearcher.kt new file mode 100644 index 0000000..cc7f2f0 --- /dev/null +++ b/src/main/java/siosio/searcher/DefaultSearcher.kt @@ -0,0 +1,31 @@ +package siosio.searcher + +import com.intellij.codeInsight.completion.* +import com.intellij.codeInsight.completion.impl.* +import com.intellij.codeInsight.lookup.* +import siosio.* +import java.awt.SystemColor.* + +class DefaultSearcher(override val dependencyText: DependencyText) : CentralSearcher { + override fun find(resultSet: CompletionResultSet) { + val result = Client.get("https://search.maven.org/solrsearch/select?q=${dependencyText.text}&rows=100&wt=json") + + resultSet.withRelevanceSorter( + CompletionSorter.emptySorter().weigh(PreferStartMatching()) + ).addAllElements(ID_PATTERN.findAll(result) + .mapNotNull { + it.groups[1]?.value + } + .map { + LookupElementBuilder.create(it) + } + .toList() + ) + } + + + companion object { + private val ID_PATTERN = Regex("\\{\"id\":\"([^\"]+)\"") + + } +} \ No newline at end of file diff --git a/src/main/java/siosio/searcher/VersionSearcher.kt b/src/main/java/siosio/searcher/VersionSearcher.kt new file mode 100644 index 0000000..bfe2917 --- /dev/null +++ b/src/main/java/siosio/searcher/VersionSearcher.kt @@ -0,0 +1,39 @@ +package siosio.searcher + +import com.intellij.codeInsight.completion.* +import com.intellij.codeInsight.lookup.* +import siosio.* + +class VersionSearcher(override val dependencyText: DependencyText) : CentralSearcher { + + override fun find(resultSet: CompletionResultSet) { + val text = Client.get( + "https://search.maven.org/solrsearch/select?q=g:${dependencyText.getGroupId()}+AND+a:${dependencyText.getArtifactId()}" + + "&rows=100&core=gav&wt=json") + + + val versions = VERSION_PATTERN.findAll(text).mapNotNull { + it.groups[1]?.value + }.distinct().toList() + + resultSet.restartCompletionOnPrefixChange(dependencyText.text) + val withRelevanceSorter = resultSet.withRelevanceSorter( + CompletionSorter.emptySorter().weigh(object : LookupElementWeigher("gradleDependencyWeigher") { + override fun weigh(element: LookupElement): Comparable { + return VersionComparable(versions.indexOf(element.lookupString)) + } + }) + ) + withRelevanceSorter.addAllElements(versions.map { + LookupElementBuilder.create(it) + }) + } + + companion object { + private val VERSION_PATTERN = Regex("\\{\"id\":\"([^\"]+)\"") + + class VersionComparable(private val index: Int) : Comparable { + override fun compareTo(other: VersionComparable): Int = this.index - other.index + } + } +} \ No newline at end of file diff --git a/src/main/resources/META-INF/plugin.xml b/src/main/resources/META-INF/plugin.xml index bc38221..28c5dd2 100644 --- a/src/main/resources/META-INF/plugin.xml +++ b/src/main/resources/META-INF/plugin.xml @@ -1,7 +1,7 @@ GradleDependenciesHelper Gradle Dependencies Helper - 1.9 + 1.10 siosio org.jetbrains.plugins.gradle org.intellij.groovy @@ -34,12 +34,10 @@ ]]> - + - - +