diff --git a/changelog.xml b/changelog.xml
index 3c2379bd..7fb54be3 100644
--- a/changelog.xml
+++ b/changelog.xml
@@ -22,6 +22,9 @@
Add non-server batch mode via `--input-documents`
+
+ Add support for rule-dependent diagnostic severities in [`ltex.diagnosticSeverity`](https://valentjn.github.io/vscode-ltex/docs/settings.html#ltexdiagnosticseverity)
+
Add support for vowel dummies in LaTeX (`"vowelDummy"` in [`ltex.latex.commands`](https://valentjn.github.io/vscode-ltex/docs/settings.html#ltexlatexcommands)) and Markdown (`"vowelDummy"` in [`ltex.markdown.nodes`](https://valentjn.github.io/vscode-ltex/docs/settings.html#ltexmarkdownnodes))
diff --git a/src/main/kotlin/org/bsplines/ltexls/server/CodeActionGenerator.kt b/src/main/kotlin/org/bsplines/ltexls/server/CodeActionGenerator.kt
index f7aaf2cc..40b97f45 100644
--- a/src/main/kotlin/org/bsplines/ltexls/server/CodeActionGenerator.kt
+++ b/src/main/kotlin/org/bsplines/ltexls/server/CodeActionGenerator.kt
@@ -21,6 +21,7 @@ import org.eclipse.lsp4j.CodeActionKind
import org.eclipse.lsp4j.CodeActionParams
import org.eclipse.lsp4j.Command
import org.eclipse.lsp4j.Diagnostic
+import org.eclipse.lsp4j.DiagnosticSeverity
import org.eclipse.lsp4j.Range
import org.eclipse.lsp4j.ResourceOperation
import org.eclipse.lsp4j.TextDocumentEdit
@@ -36,7 +37,14 @@ class CodeActionGenerator(
val diagnostic = Diagnostic()
diagnostic.range = Range(document.convertPosition(match.fromPos),
document.convertPosition(match.toPos))
- diagnostic.severity = this.settingsManager.settings.diagnosticSeverity
+
+ val diagnosticSeverityMap: Map =
+ this.settingsManager.settings.diagnosticSeverity
+ var diagnosticSeverity: DiagnosticSeverity? = diagnosticSeverityMap[match.ruleId]
+ if (diagnosticSeverity == null) diagnosticSeverity = diagnosticSeverityMap["default"]
+ if (diagnosticSeverity == null) diagnosticSeverity = DiagnosticSeverity.Information
+ diagnostic.severity = diagnosticSeverity
+
diagnostic.source = "LTeX"
diagnostic.message = match.message.replace(SUGGESTION_REGEX, "'$1'") + " \u2013 " + match.ruleId
return diagnostic
diff --git a/src/main/kotlin/org/bsplines/ltexls/settings/Settings.kt b/src/main/kotlin/org/bsplines/ltexls/settings/Settings.kt
index 62e6e116..fed2d1ea 100644
--- a/src/main/kotlin/org/bsplines/ltexls/settings/Settings.kt
+++ b/src/main/kotlin/org/bsplines/ltexls/settings/Settings.kt
@@ -34,7 +34,7 @@ data class Settings(
private val _languageToolHttpServerUri: String? = null,
private val _logLevel: Level? = null,
private val _sentenceCacheSize: Long? = null,
- private val _diagnosticSeverity: DiagnosticSeverity? = null,
+ private val _diagnosticSeverity: Map? = null,
private val _checkFrequency: CheckFrequency? = null,
private val _clearDiagnosticsWhenClosingFile: Boolean? = null,
) {
@@ -74,8 +74,8 @@ data class Settings(
get() = (this._logLevel ?: Level.FINE)
val sentenceCacheSize: Long
get() = (this._sentenceCacheSize ?: DEFAULT_SENTENCE_CACHE_SIZE)
- val diagnosticSeverity: DiagnosticSeverity
- get() = (this._diagnosticSeverity ?: DiagnosticSeverity.Information)
+ val diagnosticSeverity: Map
+ get() = (this._diagnosticSeverity ?: DEFAULT_DIAGNOSTIC_SEVERITY)
val checkFrequency: CheckFrequency
get() = (this._checkFrequency ?: CheckFrequency.Edit)
val clearDiagnosticsWhenClosingFile: Boolean
@@ -174,6 +174,8 @@ data class Settings(
val DEFAULT_ENABLED = setOf(
"bibtex", "latex", "html", "markdown", "org", "restructuredtext", "rsweave")
private const val DEFAULT_SENTENCE_CACHE_SIZE = 2000L
+ private val DEFAULT_DIAGNOSTIC_SEVERITY: Map =
+ mapOf(Pair("default", DiagnosticSeverity.Information))
@Suppress("LongMethod")
fun fromJson(
@@ -229,11 +231,8 @@ data class Settings(
),
)
val sentenceCacheSize: Long? = getSettingFromJsonAsLong(jsonSettings, "sentenceCacheSize")
- val diagnosticSeverity: DiagnosticSeverity? = getSettingFromJsonAsEnum(
- jsonSettings,
- "diagnosticSeverity",
- DiagnosticSeverity::class.java.enumConstants,
- )
+ val diagnosticSeverity: Map? =
+ getDiagnosticSeverityFromJson(jsonSettings)
val checkFrequency: CheckFrequency? = getSettingFromJsonAsEnum(
jsonSettings,
"checkFrequency",
@@ -320,18 +319,43 @@ data class Settings(
}
}
+ private fun getDiagnosticSeverityFromJson(
+ jsonSettings: JsonElement,
+ ): Map? {
+ val jsonElement: JsonElement? =
+ getSettingFromJsonAsJsonElement(jsonSettings, "diagnosticSeverity")
+
+ return if (jsonElement == null) {
+ null
+ } else if (jsonElement.isJsonObject) {
+ convertJsonObjectToMapOfEnums(
+ jsonElement.asJsonObject,
+ DiagnosticSeverity::class.java.enumConstants,
+ )
+ } else if (jsonElement.isJsonPrimitive) {
+ val jsonPrimitive: JsonPrimitive = jsonElement.asJsonPrimitive
+
+ if (jsonPrimitive.isString) {
+ val enumValue: DiagnosticSeverity? = convertStringToEnum(
+ jsonPrimitive.asString,
+ DiagnosticSeverity::class.java.enumConstants,
+ )
+ if (enumValue != null) mapOf(Pair("default", enumValue)) else null
+ } else {
+ null
+ }
+ } else {
+ null
+ }
+ }
+
private fun getSettingFromJsonAsEnum(
jsonSettings: JsonElement,
name: String,
enumValues: Array,
): T? {
val enumString: String = getSettingFromJsonAsString(jsonSettings, name) ?: return null
-
- for (enumValue: T in enumValues) {
- if (enumValue.toString().equals(enumString, ignoreCase = true)) return enumValue
- }
-
- return null
+ return convertStringToEnum(enumString, enumValues)
}
private fun getSettingFromJsonAsJsonElement(
@@ -506,6 +530,43 @@ data class Settings(
return map
}
+ private fun convertJsonObjectToMapOfEnums(
+ obj: JsonObject?,
+ enumValues: Array,
+ ): Map? {
+ if (obj == null) return null
+ val map = HashMap()
+
+ for (entry: Map.Entry in obj.entrySet()) {
+ val enumValue: T? = convertJsonElementToEnum(entry.value, enumValues)
+ if (enumValue != null) map[entry.key] = enumValue
+ }
+
+ return map
+ }
+
+ private fun convertJsonElementToEnum(jsonElement: JsonElement, enumValues: Array): T? {
+ return if (jsonElement.isJsonPrimitive) {
+ val jsonPrimitive: JsonPrimitive = jsonElement.asJsonPrimitive
+
+ if (jsonPrimitive.isString) {
+ convertStringToEnum(jsonPrimitive.asString, enumValues)
+ } else {
+ null
+ }
+ } else {
+ null
+ }
+ }
+
+ private fun convertStringToEnum(enumString: String, enumValues: Array): T? {
+ for (enumValue: T in enumValues) {
+ if (enumValue.toString().equals(enumString, ignoreCase = true)) return enumValue
+ }
+
+ return null
+ }
+
private fun mergeMapOfListsIntoMapOfSets(
mapOfLists: Map>?,
): Map>? {
diff --git a/src/test/kotlin/org/bsplines/ltexls/settings/SettingsTest.kt b/src/test/kotlin/org/bsplines/ltexls/settings/SettingsTest.kt
index 612ef436..d0712c05 100644
--- a/src/test/kotlin/org/bsplines/ltexls/settings/SettingsTest.kt
+++ b/src/test/kotlin/org/bsplines/ltexls/settings/SettingsTest.kt
@@ -115,8 +115,8 @@ class SettingsTest {
assertEquals(1337, settings.sentenceCacheSize)
settings2 = compareSettings(settings, settings2, true)
- settings = settings.copy(_diagnosticSeverity = DiagnosticSeverity.Error)
- assertEquals(DiagnosticSeverity.Error, settings.diagnosticSeverity)
+ settings = settings.copy(_diagnosticSeverity = mapOf(Pair("ruleId", DiagnosticSeverity.Error)))
+ assertEquals(mapOf(Pair("ruleId", DiagnosticSeverity.Error)), settings.diagnosticSeverity)
settings2 = compareSettings(settings, settings2, false)
settings = settings.copy(_checkFrequency = Settings.CheckFrequency.Manual)
@@ -270,19 +270,33 @@ class SettingsTest {
jsonSettings.addProperty("diagnosticSeverity", "error")
settings = Settings.fromJson(jsonSettings, jsonWorkspaceSpecificSettings)
- assertEquals(DiagnosticSeverity.Error, settings.diagnosticSeverity)
+ assertEquals(mapOf(Pair("default", DiagnosticSeverity.Error)), settings.diagnosticSeverity)
jsonSettings.addProperty("diagnosticSeverity", "warning")
settings = Settings.fromJson(jsonSettings, jsonWorkspaceSpecificSettings)
- assertEquals(DiagnosticSeverity.Warning, settings.diagnosticSeverity)
+ assertEquals(mapOf(Pair("default", DiagnosticSeverity.Warning)), settings.diagnosticSeverity)
jsonSettings.addProperty("diagnosticSeverity", "information")
settings = Settings.fromJson(jsonSettings, jsonWorkspaceSpecificSettings)
- assertEquals(DiagnosticSeverity.Information, settings.diagnosticSeverity)
+ assertEquals(
+ mapOf(Pair("default", DiagnosticSeverity.Information)),
+ settings.diagnosticSeverity,
+ )
jsonSettings.addProperty("diagnosticSeverity", "hint")
settings = Settings.fromJson(jsonSettings, jsonWorkspaceSpecificSettings)
- assertEquals(DiagnosticSeverity.Hint, settings.diagnosticSeverity)
+ assertEquals(mapOf(Pair("default", DiagnosticSeverity.Hint)), settings.diagnosticSeverity)
+
+ val diagnosticSeverity = JsonObject()
+ diagnosticSeverity.addProperty("ruleId", "warning")
+ diagnosticSeverity.addProperty("default", "error")
+
+ jsonSettings.add("diagnosticSeverity", diagnosticSeverity)
+ settings = Settings.fromJson(jsonSettings, jsonWorkspaceSpecificSettings)
+ assertEquals(
+ mapOf(Pair("ruleId", DiagnosticSeverity.Warning), Pair("default", DiagnosticSeverity.Error)),
+ settings.diagnosticSeverity,
+ )
jsonSettings.addProperty("checkFrequency", "edit")
settings = Settings.fromJson(jsonSettings, jsonWorkspaceSpecificSettings)