Python SMTP రిలే సమర్పణ: 587లో STARTTLS లేదా 465లో TLS?
587లో STARTTLS మరియు 465లో అంతర్లీన TLS రెండూ Python సమర్పణను తీసుకువెళతాయి, కానీ మీ రిలేకు ఒకటి మాత్రమే సరిపోతుంది. హ్యాండ్షేక్ మరియు వైఫల్య విధానాలను పోల్చండి.
రెండు కనెక్షన్ పద్ధతులు ఒకే సందేశాన్ని ఒకే రిలే ఖాతాకు చేరవేస్తాయి, మరియు భేదం TLS ఎక్కడ ప్రారంభమవుతుందనేది, ఏమి పంపబడుతుందనేది కాదు. ఒకటి స్పష్ట పాఠ్యంలో తెరుచుకుని కనెక్షన్ లోపలే అప్గ్రేడ్ అవుతుంది; మరొకటి మొదటి బైట్ నుండే గుప్తీకరించబడి ఉంటుంది. ఆ ఒకే భేదం కఠినమైన రిలే విధానం ఏమి ఆమోదిస్తుంది, మధ్యంతర పరికరం ఏమి గమనించగలదు, మరియు ఏ లోప సందేశాన్ని మీరు అర్ధరోజు చదువుతారు అనేది నిర్ణయిస్తుంది. ప్రైవేట్ నెట్వర్క్లోని అప్లికేషన్ అంతర్గత సమర్పణ సేవకు సందేశాన్ని అప్పగించినప్పుడు నేను ఈ రెండింటి మధ్య ఎలా ఎంచుకుంటానో ఇది.
రెండు పద్ధతులు నిజంగా ఎక్కడ విడిపోతాయి
రెండు సందర్భాలలోనూ పని ఒకటే: ఆమోదించబడిన ఖాతాగా ప్రామాణీకరించండి, అనుమతించిన పంపినవారిని పేర్కొనండి, గ్రహీతలను జాబితా చేయండి, మరియు రిలే బాధ్యత తీసుకునే వరకు వేచి ఉండండి. మారేది కార్యకలాపాల క్రమం. పోర్ట్ 587 స్పష్ట పాఠ్య SMTP సెషన్గా ప్రారంభమవుతుంది, EHLO ప్రతిస్పందనలో STARTTLS ప్రకటిస్తుంది, మరియు క్లయింట్ అడిగితేనే అప్గ్రేడ్ అవుతుంది. పోర్ట్ 465 ఏదైనా SMTP ఆదేశం చెప్పబడకముందే TLS హ్యాండ్షేక్ను ఆశిస్తుంది.
సమర్పణ మరియు రిలే వేర్వేరు పనులు, అందుకే పోర్ట్ సంఖ్యలు పరస్పరం మార్చుకోగల అలవాట్లు కావు. RFC 6409 సందేశ సమర్పణను స్వంత సేవగా వివరిస్తుంది, మరియు RFC 8314 చాలా ఆధునిక రిలేలు 465లో అందించే అంతర్లీన-TLS రూపాన్ని కవర్ చేస్తుంది. మీ రిలే రెండింటిలో ఒకటి నమోదు చేస్తే, ఆ పత్రం మునుపటి యజమాని నుండి పొందిన ఏ ప్రాధాన్యతను మించి ఉంటుంది.
587లో STARTTLS మీకు ఏమి ఇస్తుంది
అప్గ్రేడ్ SMTP సంభాషణలోపలే జరుగుతుంది, కాబట్టి రిలే దాన్ని ప్రకటించగలదు మరియు క్లయింట్ అది లేకుండా కొనసాగడానికి నిరాకరించగలదు. Pythonలో, సర్వర్ ఆ పొడిగింపును అందించనప్పుడు starttls() మినహాయింపును విసురుతుంది, ఇది తరుగుదల ప్రయత్నాన్ని నిశ్శబ్ద స్పష్ట-పాఠ్య లాగిన్కు బదులుగా కనిపించే వైఫల్యంగా మారుస్తుంది. ఆ ప్రవర్తనే ఈ పద్ధతికి ప్రధాన వాదన, దానిపై యాదృచ్ఛికంగా కాకుండా ఉద్దేశపూర్వకంగా ఆధారపడటం విలువైనది.
బహిర్గత విండో చిన్నది కానీ నిజమైనది: ప్రారంభ EHLO మార్పిడి చదవగలిగేది, మరియు అప్గ్రేడ్కు ముందు ఏదీ ఆధారాలను మోసుకెళ్లదు. అప్లికేషన్ సబ్నెట్ మరియు అంతర్గత రిలే మధ్య ప్రైవేట్ మార్గంలో ఆ విండో సాధారణంగా ఆమోదయోగ్యం. మీరు నియంత్రించని మార్గంలో, కొన్ని జట్లు మరో పద్ధతిపై పట్టుబట్టడానికి కారణం అదే.
STARTTLS సామర్థ్యాన్ని తొలగించే ఇంటర్సెప్షన్ పరికరం విఫలమైన సమర్పణను ఉత్పత్తి చేస్తుంది, ఫాల్బ్యాక్ కాదు. అదే మీకు కావలసిన ఫలితం, మరియు మార్గంలో ఏదో SMTPను తిరిగి రాస్తోందని కనుగొనడానికి వేగవంతమైన మార్గం కూడా అదే.
465లో అంతర్లీన TLS ఏమి మారుస్తుంది
స్పష్ట పాఠ్య దశ అసలే లేదు. సాకెట్ తెరుచుకోగానే క్లయింట్ TLS హ్యాండ్షేక్ చేస్తుంది, తన విశ్వాస నిల్వకు వ్యతిరేకంగా ధృవపత్రాన్ని ధృవీకరిస్తుంది, ఆ తర్వాతే EHLO, AUTH మరియు సందేశాన్ని మార్పిడి చేస్తుంది. చర్చించడానికి స్పష్ట-పాఠ్య స్థితి లేనందున ఏదీ సెషన్ను తగ్గించలేదు, మరియు అది ఇంటర్సెప్షన్ వైఫల్యాల మొత్తం వర్గాన్ని తొలగిస్తుంది.
ఈ మార్పిడి నిర్ధారణ సామర్థ్యం. 465లో స్పష్ట-పాఠ్య SMTPతో సమాధానమిచ్చే రిలే, లేదా తప్పు ధృవపత్రం పేరుతో TLSను ముగించే లోడ్ బ్యాలెన్సర్, హ్యాండ్షేక్లో విఫలమై మెయిల్ లోపానికి బదులు మీకు SSL లోపాన్ని ఇస్తుంది. అది సంభవించినప్పుడు, సమస్య అప్లికేషన్ కింద ఉంటుంది, ఎంత సందేశ నిర్మాణం చేసినా దాన్ని సరిచేయదు.
ఒక సమర్పణ ఫంక్షన్, రెండు రవాణాలు
కోడ్ రెండు పద్ధతుల మధ్య దాదాపు భిన్నంగా ఉండదు, అందుకే ఎంపిక లైబ్రరీ సౌలభ్యం నుండి కాకుండా రిలే విధానం నుండి జరగాలి. మొదట సెట్టింగ్లను ఎగుమతి చేయండి, తర్వాత కాన్ఫిగర్ చేసిన పోర్ట్ నుండి రవాణాను ఎంచుకునే ఒక స్క్రిప్ట్ను అమలు చేయండి.
export SMTP_HOST=smtp.relay.internal export SMTP_PORT=587 export SMTP_USER=svc-notify export [email protected] export [email protected] export SMTP_PASSWORD="$(cat /run/secrets/smtp_password)"
import os, smtplib, ssl
from email.message import EmailMessage
ctx = ssl.create_default_context()
msg = EmailMessage()
msg["From"] = os.environ["MAIL_FROM"]
msg["To"] = os.environ["MAIL_TEST_TO"]
msg["Subject"] = "relay submission test"
msg.set_content("One authorized test message from the app.")
host = os.environ["SMTP_HOST"]
port = int(os.environ.get("SMTP_PORT", "587"))
if port == 465:
client = smtplib.SMTP_SSL(host, port, context=ctx, timeout=15)
else:
client = smtplib.SMTP(host, port, timeout=15)
client.ehlo()
client.starttls(context=ctx)
client.ehlo()
with client:
client.login(os.environ["SMTP_USER"], os.environ["SMTP_PASSWORD"])
refused = client.send_message(msg)
print("refused:", refused)
create_default_context() గొలుసు మరియు హోస్ట్ పేరును ధృవీకరిస్తుంది, కాబట్టి ప్రైవేట్ CA విశ్వాస నిల్వలో ఇన్స్టాల్ చేయాలి, ధృవీకరించని సందర్భంతో తప్పించుకోకూడదు. send_message() రిలే తిరస్కరించిన గ్రహీతల నిఘంటువును తిరిగి ఇస్తుంది; ఖాళీ నిఘంటువు అంటే అది అందరినీ ఆమోదించింది. పదిహేను సెకన్ల సమయ పరిమితి ప్రారంభ బిందువు, మీ నెట్వర్క్ కోసం ట్యూన్ చేసిన విలువ కాదు.
పాస్వర్డ్ను ఇమేజ్ నుండి మరియు లాగ్ల నుండి బయట ఉంచండి. రన్టైమ్లో మౌంట్ చేసి పర్యావరణంలోకి చదివే రహస్యం సరైనది; పర్యావరణాన్ని లాగ్ లైన్లో ప్రతిధ్వనించడం సరైనది కాదు, AUTH మార్పిడి డీబగ్ జాడ కూడా కాదు.
అలవాటుతో కాదు, రిలే విధానం మరియు మార్గంతో ఎంచుకోండి
మూడు షరతులు దీన్ని నిర్ణయిస్తాయి. మొదట, రిలే నిజంగా ఏమి ప్రకటిస్తుంది: 587లో STARTTLSతో మాత్రమే వినే సేవను 465లో చేరుకోలేరు, మీరెంత అంతర్లీన TLS ఇష్టపడినా. రెండవది, అప్లికేషన్ మరియు రిలే మధ్య మార్గం చదవగలిగే EHLO మార్పిడిని ఆమోదించడానికి తగినంత విశ్వసనీయమైనదా అనేది. మూడవది, మధ్యలో ఏదో SMTPను తిరిగి రాస్తుందా లేదా ప్రాక్సీ చేస్తుందా అనేది, ఎందుకంటే తరుగుదల ప్రమాదం సైద్ధాంతికమా లేదా నిజమైనదా అనేది అదే నిర్ణయిస్తుంది.
రిలే రెండింటినీ అందించినప్పుడు, పర్యవేక్షణ లేకుండా నడిచే సేవకు నేను 465 తీసుకుంటాను మరియు మొదటి ప్రచురణను ఒక వ్యక్తి గమనిస్తున్న సేవకు 587 తీసుకుంటాను, వైఫల్య సందేశాలు వేర్వేరు పొరలను సూచిస్తాయనే ఒకే కారణంతో. ఆ ప్రాధాన్యత నాది మరియు అది విధానం కాదు.
మీరు ఏది ఎంచుకున్నా, పోర్ట్, విశ్వాస పదార్థం మరియు పంపినవారి డొమైన్ను ప్రచురణతో పాటు నమోదు చేయండి. తర్వాత ఒక అధికారిక పరీక్ష సందేశాన్ని పంపి రిలే దాన్ని ఆమోదించిందని నిర్ధారించుకోండి, సమర్పణ ఫలితాన్ని మరియు తర్వాత వచ్చే ఏదైనా డెలివరీ నివేదికను వేర్వేరు రికార్డులుగా ఉంచండి. రిలేకు విజయవంతమైన అప్పగింపు అప్లికేషన్ బాధ్యత ముగింపు, సందేశం ఇన్బాక్స్కు చేరిందనే రుజువు కాదు.