Class: Publication::MetadataTranslator

Inherits:
Object
  • Object
show all
Defined in:
app/services/publication/metadata_translator.rb

Overview

Translates a publication's METADATA (the base name — the slug and display
name derive from it) into the target language, so a French variant is filed
under a French name instead of the English name with a locale suffix.

DeepL translates the PDF body; this covers what its document endpoint never
sees — the catalog record itself. A publication-specific glossary keeps brand
terms and product vocabulary stable ("towel warmer" → "chauffe-serviettes",
brand names untouched).

Non-fatal by design: any LLM failure returns nil (callers fall back to the
source-language name), so a metadata hiccup never sinks an otherwise good
document translation.

Examples:

Publication::MetadataTranslator.call('Infinity Towel Warmer Sell Sheet', lang_out: 'fr')
# => "Fiche produit du chauffe-serviettes Infinity"

Constant Summary collapse

GLOSSARY_DIR =
Rails.root.join('config/publication_translation').freeze

Class Method Summary collapse

Class Method Details

.call(text, lang_out:, lang_in: 'en') ⇒ String?

Returns the translated text, or nil when there is nothing
to translate or the translation failed.

Parameters:

  • text (String)

    source text (publication base name)

  • lang_out (String)

    target language code (e.g. 'fr')

  • lang_in (String) (defaults to: 'en')

    source language code (default 'en')

Returns:

  • (String, nil)

    the translated text, or nil when there is nothing
    to translate or the translation failed



30
31
32
33
34
35
36
37
38
39
40
41
# File 'app/services/publication/metadata_translator.rb', line 30

def call(text, lang_out:, lang_in: 'en')
  text = text.to_s.strip
  return nil if text.blank? || lang_out.to_s.blank? || lang_in.to_s == lang_out.to_s

  response = AiModelConstants.with_fallback(:translation) do |model_id|
    RubyLLM.chat(model: model_id).ask(prompt(text, lang_in:, lang_out:))
  end
  response.content.to_s.strip.gsub(/\A["']+|["']+\z/, '').presence
rescue StandardError => e
  Rails.logger.warn "[Publication::MetadataTranslator] #{lang_out} translation failed: #{e.message}"
  nil
end