From f99723c1f7dea60d37b06b8282d8ce25fc3dad49 Mon Sep 17 00:00:00 2001 From: Jeremy Lecour Date: Wed, 20 Jan 2021 13:46:45 +0100 Subject: [PATCH] =?UTF-8?q?Extraction=20du=20mapping=20des=20metadonn?= =?UTF-8?q?=C3=A9es=20dans=20EmailAction::MetedataMapping?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/models/email.rb | 8 +++ app/services/email_action/issue_mapping.rb | 17 +++++ app/services/email_action/metadata_mapping.rb | 63 ++++++++++++++++ app/services/email_importer.rb | 71 +------------------ 4 files changed, 89 insertions(+), 70 deletions(-) create mode 100644 app/services/email_action/issue_mapping.rb create mode 100644 app/services/email_action/metadata_mapping.rb diff --git a/app/models/email.rb b/app/models/email.rb index 8663f8f..7d91860 100644 --- a/app/models/email.rb +++ b/app/models/email.rb @@ -46,6 +46,14 @@ class Email mailing_list end + def header_values(header_name) + headers.select { |header| + header["name"] == header_name + }.filter_map { |header| + header["value"] + } + end + def self.find(id) EmailRepository.new.find(id) end diff --git a/app/services/email_action/issue_mapping.rb b/app/services/email_action/issue_mapping.rb new file mode 100644 index 0000000..410eac9 --- /dev/null +++ b/app/services/email_action/issue_mapping.rb @@ -0,0 +1,17 @@ +# frozen_string_literal: true + +module EmailAction + class IssueMapping < Base + + def process(email) + values = ["X-Ticket-Id", "X-Issue-Id"].filter_map { |header_name| + email.header_values(header_name) + }.flatten.uniq + + email.tickets = values + + email + end + + end +end diff --git a/app/services/email_action/metadata_mapping.rb b/app/services/email_action/metadata_mapping.rb new file mode 100644 index 0000000..c3b3d50 --- /dev/null +++ b/app/services/email_action/metadata_mapping.rb @@ -0,0 +1,63 @@ +# frozen_string_literal: true + +module EmailAction + class MetadataMapping < Base + + attr_accessor :metadata_mapping_class + + def initialize( + metadata_mapping_class: ::MetadataMapping) + + @metadata_mapping_class = metadata_mapping_class + end + + def process(email) + metadata_inputs = metadata_inputs(email) + metadata = metadata_mapping_class.where(input: metadata_inputs).all + + email.clients = metadata.filter_map(&:entity).uniq + email.servers = metadata.filter_map(&:server).uniq + + email + rescue => ex + binding.pry + end + + def metadata_inputs(email) + inputs = [] + # add mail addresses and hostnames from headers + inputs << ["To", "Delivered-To", "X-Original-To", "From", "Subject"].filter_map { |header_name| + email.header_values(header_name) + }.flatten.filter_map() { |header_value| + keep_email_and_hostnames(header_value) + }.flatten.filter_map() { |value| + clean_subdomains(value) + }.flatten + # add other values from headers + inputs << email.header_values("X-Client-Id") + + inputs.flatten.uniq + end + + def keep_email_and_hostnames(string) + pattern = /\b((?:([-a-zA-Z0-9\._]+)@)?((?:[-a-zA-Z0-9\._]*)(?:\.[a-z]{2,})))\b/ + results = string.scan(pattern) + if results.present? + results.map(&:first) + end + end + + def clean_subdomains(value) + [ + [/[-a-zA-Z0-9\._]+@([-a-zA-Z0-9]+).evolix.net/, '@\1'] + ].filter_map { |item| + if value.match?(item[0]) + value.gsub!(item[0], item[1]) + else + value + end + } + end + + end +end diff --git a/app/services/email_importer.rb b/app/services/email_importer.rb index 2ab9714..47c20d9 100644 --- a/app/services/email_importer.rb +++ b/app/services/email_importer.rb @@ -2,16 +2,13 @@ class EmailImporter attr_accessor :email_class - attr_accessor :metadata_mapping_class attr_accessor :html_to_text_class def initialize( email_class: Email, - metadata_mapping_class: MetadataMapping, html_to_text_class: Rails.configuration.html_to_text_class) @email_class = email_class - @metadata_mapping_class = metadata_mapping_class @html_to_text_class = html_to_text_class end @@ -24,12 +21,7 @@ class EmailImporter delivered_to: delivered_to(mail), from: mail.from, plain_body: text_plain_body(mail), - headers: hashed_headers(mail), - cron: sent_by_cron?(mail), - mailing_list: mailing_list?(mail), - clients: clients(mail), - servers: servers(mail), - tickets: tickets(mail) + headers: hashed_headers(mail) ) rescue => ex binding.pry @@ -70,27 +62,6 @@ class EmailImporter } end - def sent_by_cron?(mail) - (mail.subject.present? && mail.subject.match?(/cron/i)) \ - || mail.header["X-Cron-Env"].present? - end - - def mailing_list?(mail) - mail.header["List-Unsubscribe"].present? - end - - def clients(mail) - metadata(mail).filter_map(&:entity).uniq - end - - def servers(mail) - metadata(mail).filter_map(&:server).uniq - end - - def tickets(mail) - values_from_header(header: mail.header["X-Ticket-Id"]) - end - def values_from_header(header:, default: []) if header.respond_to?(:map) header.map(&:value) @@ -102,44 +73,4 @@ class EmailImporter default end end - - def metadata(mail) - @metadata ||= metadata_mapping_class.where(input: metadata_inputs(mail)).all - end - - def metadata_inputs(mail) - inputs = [] - # add mail addresses and hostnames from headers - inputs << ["To", "Delivered-To", "X-Original-To", "From", "Subject"].filter_map { |header_name| - mail.header[header_name] - }.flatten.map(&:value).filter_map() { |header_value| - keep_email_and_hostnames(header_value) - }.flatten.filter_map() { |value| - clean_subdomains(value) - }.flatten - # add other values from headers - inputs << mail.header["X-Client-Id"] - - inputs.uniq - end - - def keep_email_and_hostnames(string) - pattern = /\b((?:([-a-zA-Z0-9\._]+)@)?((?:[-a-zA-Z0-9\._]*)(?:\.[a-z]{2,})))\b/ - results = string.scan(pattern) - if results.present? - results.map(&:first) - end - end - - def clean_subdomains(value) - [ - [/[-a-zA-Z0-9\._]+@([-a-zA-Z0-9]+).evolix.net/, '@\1'] - ].filter_map { |item| - if value.match?(item[0]) - value.gsub!(item[0], item[1]) - else - value - end - } - end end