Envoi d'e-mails via proxy SOCKS avec javax.mail en Java

Configuration d'un compte e-mail avec proxy SOCKS

Pour envoyer des e-mails via un proxy SOCKS en utilisent la bibliothèque javax.mail, il faut configurer les propriétés SMTP et ajouter les paramètres de proxy. Voici un exemple de code pour initialiser l'envoi.


public class ServiceEmailAvecProxy {
    private static final Logger journal = LoggerFactory.getLogger(ServiceEmailAvecProxy.class);

    public void envoyerEmails(Liste<objetenvoi> listeObjets) {
        if (listeObjets == null || listeObjets.isEmpty()) return;

        String adresseExpediteur = ConfigUtils.obtenirValeur("config.email.adresse");
        String hoteSMTP = ConfigUtils.obtenirValeur("config.email.hote");
        String portSMTP = ConfigUtils.obtenirValeur("config.email.port");
        String motDePasse = ConfigUtils.obtenirValeur("config.email.motDePasse");
        String activerSSL = ConfigUtils.obtenirValeur("config.email.activerSSL");
        String activerSTARTTLS = ConfigUtils.obtenirValeur("config.email.activerSTARTTLS");

        if (StrUtil.isBlank(adresseExpediteur)) {
            journal.error("Échec de l'envoi : adresse de l'expéditeur non configurée");
            return;
        }
        if (StrUtil.isBlank(hoteSMTP)) {
            journal.error("Échec de l'envoi : hôte SMTP non configuré");
            return;
        }
        if (StrUtil.isBlank(portSMTP) || !Validator.isNumber(portSMTP)) {
            journal.error("Échec de l'envoi : port SMTP invalide");
            return;
        }
        if (StrUtil.isBlank(motDePasse)) {
            journal.error("Échec de l'envoi : mot de passe non configuré");
            return;
        }

        Properties proprietes = new Properties();
        proprietes.setProperty("mail.smtp.host", hoteSMTP);
        proprietes.setProperty("mail.smtp.port", portSMTP);
        proprietes.put("mail.smtp.auth", "true");
        proprietes.put("mail.smtp.ssl.protocols", "TLSv1.2");
        proprietes.setProperty("mail.transport.protocol", "smtp");

        if ("1".equals(activerSSL)) {
            proprietes.setProperty("mail.smtp.ssl.enable", "true");
        } else {
            proprietes.setProperty("mail.smtp.ssl.enable", "false");
        }

        if ("1".equals(activerSTARTTLS)) {
            proprietes.setProperty("mail.smtp.starttls.enable", "true");
        } else {
            proprietes.setProperty("mail.smtp.starttls.enable", "false");
        }

        // Configuration du proxy SOCKS
        String proxyHote = ConfigService.obtenirParametre("reseau.proxy.hote");
        String proxyPort = ConfigService.obtenirParametre("reseau.proxy.port");
        String proxyUtilisateur = ConfigService.obtenirParametre("reseau.proxy.utilisateur");
        String proxyMotDePasse = ConfigService.obtenirParametre("reseau.proxy.motDePasse");

        if (StrUtil.isNotBlank(proxyHote) && StrUtil.isNotBlank(proxyPort)) {
            proprietes.setProperty("mail.smtp.socks.host", proxyHote);
            proprietes.setProperty("mail.smtp.socks.port", proxyPort);
            if (StrUtil.isNotBlank(proxyUtilisateur) && StrUtil.isNotBlank(proxyMotDePasse)) {
                java.net.Authenticator.setDefault(new AuthentificationProxy(proxyUtilisateur, proxyMotDePasse));
            }
        }

        Session session = Session.getDefaultInstance(proprietes);
        String motDePasseDecrypte = CryptUtils.dechiffrer(motDePasse);

        for (ObjetEnvoi objet : listeObjets) {
            String destinataire = objet.getDestinataire();
            if (StrUtil.isNotBlank(destinataire)) {
                destinataire += "," + adresseExpediteur;
            } else {
                destinataire = adresseExpediteur;
            }
            try {
                MimeMessage message = creerMessage(session, adresseExpediteur, destinataire, objet.getSujet(), objet.getContenu());
                Transport transport = session.getTransport();
                transport.connect(hoteSMTP, adresseExpediteur, motDePasseDecrypte);
                transport.sendMessage(message, message.getAllRecipients());
                transport.close();
                journal.info("E-mail envoyé à {} avec sujet {}", destinataire, objet.getSujet());
            } catch (Exception e) {
                journal.error("Échec de l'envoi à {} : {}", destinataire, e.getMessage());
                throw new ServiceException("L'envoi de l'e-mail a échoué.");
            }
        }
    }

    private MimeMessage creerMessage(Session session, String de, String a, String sujet, String contenu) throws Exception {
        MimeMessage msg = new MimeMessage(session);
        msg.setFrom(new InternetAddress(de));
        msg.setRecipients(MimeMessage.RecipientType.TO, InternetAddress.parse(a));
        msg.setSubject(sujet, "UTF-8");
        msg.setContent(contenu, "text/html;charset=UTF-8");
        msg.setSentDate(new Date());
        return msg;
    }

    public String genererContenuHTML(String[] parametres) throws IOException {
        InputStream flux = getClass().getClassLoader().getResourceAsStream("modele_email.html");
        BufferedReader lecteur = new BufferedReader(new InputStreamReader(flux, "UTF-8"));
        StringBuilder constructeur = new StringBuilder();
        String ligne;
        while ((ligne = lecteur.readLine()) != null) {
            constructeur.append(ligne);
        }
        lecteur.close();
        return MessageFormat.format(constructeur.toString(), parametres);
    }

    public String lireFichierHTML(String nomFichier) throws Exception {
        InputStream fluxEntree = null;
        Reader lecteur = null;
        try {
            fluxEntree = getClass().getClassLoader().getResourceAsStream(nomFichier);
            if (fluxEntree == null) throw new Exception("Fichier modèle introuvable");
            lecteur = new InputStreamReader(fluxEntree, "UTF-8");
            StringBuilder sb = new StringBuilder();
            char[] tampon = new char[1024];
            int longueur;
            while ((longueur = lecteur.read(tampon)) != -1) {
                sb.append(tampon, 0, longueur);
            }
            return sb.toString();
        } finally {
            if (fluxEntree != null) fluxEntree.close();
            if (lecteur != null) lecteur.close();
        }
    }

    private static class AuthentificationProxy extends java.net.Authenticator {
        private final String utilisateur;
        private final String motDePasse;

        public AuthentificationProxy(String utilisateur, String motDePasse) {
            this.utilisateur = utilisateur;
            this.motDePasse = motDePasse;
        }

        protected java.net.PasswordAuthentication getPasswordAuthentication() {
            return new java.net.PasswordAuthentication(utilisateur, motDePasse.toCharArray());
        }
    }
}
</objetenvoi>

Exemple d'utilisation

Voici comment utiliser la classe pour envoyer un e-mail avec des paramètres dynamiqeus.


public void envoyerEmailUtilisateur(String email, String identifiantClient, String nomUtilisateur, String motDePasse, String titre) {
    List<objetenvoi> liste = new ArrayList<>();
    ObjetEnvoi envoi = new ObjetEnvoi();
    envoi.setDestinataire(email);
    envoi.setSujet(Messages.get(titre));
    String[] parametres = {
        Messages.get("nom.plateforme"),
        Messages.get(titre),
        Messages.get("salutation") + nomUtilisateur,
        Messages.get("remerciement"),
        Messages.get("compte"),
        Messages.get("identifiant.client"),
        identifiantClient,
        Messages.get("nom.utilisateur"),
        "admin",
        Messages.get("mot.de.passe"),
        motDePasse,
        Messages.get("conclusion"),
        Messages.get("avertissement")
    };
    try {
        envoi.setContenu(serviceEmail.genererContenuHTML(parametres));
    } catch (IOException e) {
        throw new RuntimeException("Erreur de génération du contenu", e);
    }
    liste.add(envoi);
    serviceEmail.envoyerEmails(liste);
}
</objetenvoi>

Étiquettes: javax.mail socks-proxy SMTP Java spring-boot

Publié le 17 juillet à 10h22