Source code for searx.search.processors.online_dictionary

# SPDX-License-Identifier: AGPL-3.0-or-later
"""Processor used for ``online_dictionary`` engines."""

import typing as t
import re

from searx.sxng_locales import sxng_locales
from .online import OnlineProcessor, OnlineParams

if t.TYPE_CHECKING:
    from searx.search.models import SearchQuery

search_syntax = re.compile(r".*?([a-z]+)-([a-z]+) (.+)$", re.I)
"""Search syntax used for from/to language (e.g. ``en-de``)"""

FromToType: t.TypeAlias = tuple[bool, str, str]
"""Type of a language descriptions in the context of a ``online_dictionary``."""


[docs] class DictParams(t.TypedDict): """Dictionary request parameters.""" from_lang: FromToType """Language from which is to be translated.""" to_lang: FromToType """Language to translate into.""" query: str """Search term, cleaned of search syntax (*from-to* has been removed)."""
[docs] class OnlineDictParams(DictParams, OnlineParams): # pylint: disable=duplicate-bases """Request parameters of a ``online_dictionary`` engine."""
[docs] class OnlineDictionaryProcessor(OnlineProcessor): """Processor class for ``online_dictionary`` engines.""" engine_type: str = "online_dictionary"
[docs] def get_params(self, search_query: "SearchQuery", engine_category: str) -> OnlineDictParams | None: """Returns a dictionary with the :ref:`request params <engine request online_dictionary>` (:py:obj:`OnlineDictParams`). ``None`` is returned if the search query does not match :py:obj:`search_syntax`.""" online_params: OnlineParams | None = super().get_params(search_query, engine_category) if online_params is None: return None m = search_syntax.match(search_query.query) if not m: return None from_lang, to_lang, query = m.groups() from_lang = _get_lang_descr(from_lang) to_lang = _get_lang_descr(to_lang) if not from_lang or not to_lang: return None params: OnlineDictParams = { **online_params, "from_lang": from_lang, "to_lang": to_lang, "query": query, } return params
def _get_lang_descr(lang: str) -> FromToType | None: """Returns language's code and language's english name if argument ``lang`` describes a language known by SearXNG, otherwise ``None``. Examples: .. code:: python >>> _get_lang_descr("zz") None >>> _get_lang_descr("uk") (True, "uk", "ukrainian") >>> _get_lang_descr(b"uk") (True, "uk", "ukrainian") >>> _get_lang_descr("en") (True, "en", "english") >>> _get_lang_descr("EspaƱol") (True, "es", "spanish") >>> _get_lang_descr("Spanish") (True, "es", "spanish") """ lang = lang.lower() is_abbr = len(lang) == 2 if is_abbr: for l in sxng_locales: if l[0][:2] == lang: return (True, l[0][:2], l[3].lower()) return None for l in sxng_locales: if l[1].lower() == lang or l[3].lower() == lang: return (True, l[0][:2], l[3].lower()) return None