@@ -21,6 +21,15 @@ use std::{
21use once_cell::sync::{Lazy, OnceCell};
21use once_cell::sync::{Lazy, OnceCell};
22use serde::{Deserialize, Serialize};
22use serde::{Deserialize, Serialize};
24+fn deserialize_regex<'de, D>(deserializer: D) -> Result<Option<Regex>, D::Error>
26+ D: serde::Deserializer<'de>,
28+ Option::<String>::deserialize(deserializer)?
29+ .map(|buf| Regex::new(&buf).map_err(serde::de::Error::custom))
24#[derive(Debug, Serialize, Deserialize)]
33#[derive(Debug, Serialize, Deserialize)]
25pub struct Configuration {
34pub struct Configuration {
26 pub language: Vec<LanguageConfiguration>,
35 pub language: Vec<LanguageConfiguration>,
@@ -42,7 +51,8 @@ pub struct LanguageConfiguration {
42 pub auto_format: bool,
51 pub auto_format: bool,
44 // content_regex
53 // content_regex
54+ #[serde(default, skip_serializing, deserialize_with = "deserialize_regex")]
45− // injection_regex
55+ injection_regex: Option<Regex>,
46 // first_line_regex
56 // first_line_regex
48 #[serde(skip)]
58 #[serde(skip)]
@@ -243,6 +253,30 @@ impl Loader {
243 .cloned()
253 .cloned()
256+ pub fn language_configuration_for_injection_string(
259+ ) -> Option<Arc<LanguageConfiguration>> {
260+ let mut best_match_length = 0;
261+ let mut best_match_position = None;
262+ for (i, configuration) in self.language_configs.iter().enumerate() {
263+ if let Some(injection_regex) = &configuration.injection_regex {
264+ if let Some(mat) = injection_regex.find(string) {
265+ let length = mat.end() - mat.start();
266+ if length > best_match_length {
267+ best_match_position = Some(i);
268+ best_match_length = length;
274+ if let Some(i) = best_match_position {
275+ let configuration = &self.language_configs[i];
276+ return Some(configuration.clone());
246 pub fn language_configs_iter(&self) -> impl Iterator<Item = &Arc<LanguageConfiguration>> {
280 pub fn language_configs_iter(&self) -> impl Iterator<Item = &Arc<LanguageConfiguration>> {
247 self.language_configs.iter()
281 self.language_configs.iter()