Skip to main content

Overview

The inventory management system can automatically send Excel reports via email using Gmail’s SMTP server. This guide covers the complete setup process.

Prerequisites

  • Gmail account
  • 2-Factor Authentication enabled on your Gmail account
  • Access to Google Account settings
Gmail requires 2-Factor Authentication (2FA) to be enabled before you can generate app passwords. Regular Gmail passwords will not work with SMTP.

Gmail Configuration

Step 1: Enable 2-Factor Authentication

If you haven’t already enabled 2FA:
1

Go to Google Account Security

2

Enable 2-Step Verification

Under “Signing in to Google”, click on “2-Step Verification” and follow the setup wizard
3

Complete verification

Add a phone number and verify it to complete 2FA setup

Step 2: Generate App Password

1

Access App Passwords page

Visit https://myaccount.google.com/apppasswordsOr navigate: Google Account → Security → 2-Step Verification → App passwords
2

Create new app password

  • Select app: Mail
  • Select device: Other (Custom name)
  • Enter name: Inventory System or similar
  • Click Generate
3

Copy the password

A 16-character password will be displayed (format: xxxx xxxx xxxx xxxx)Copy this password immediately - you won’t be able to see it again!
Store the app password securely. If you lose it, you’ll need to generate a new one.

Environment File Configuration

Create .env File

Create a file named .env in the project root directory:
touch .env

Add Email Credentials

Open .env and add your configuration:
EMAIL_REMITENTE=[email protected]
EMAIL_PASSWORD=xxxx xxxx xxxx xxxx
EMAIL_DESTINATARIO=[email protected]
Example:
EMAIL_REMITENTE=[email protected]
EMAIL_PASSWORD=abcd efgh ijkl mnop
EMAIL_DESTINATARIO=[email protected]
  • EMAIL_REMITENTE: Your Gmail address
  • EMAIL_PASSWORD: The 16-character app password (spaces are optional)
  • EMAIL_DESTINATARIO: Where reports should be sent

Verify Configuration

The system validates credentials before sending (from src/main.py:23-40):
if (
    EMAIL_REMITENTE
    and EMAIL_PASSWORD
    and EMAIL_DESTINATARIO
    and EMAIL_PASSWORD != "la_contraseña_generada"
    and EMAIL_REMITENTE != "[email protected]"
    and EMAIL_DESTINATARIO != "[email protected]"
):
    enviar_reporte(...)
else:
    print("⚠️ Envío de correo omitido (credenciales no configuradas)")

SMTP Settings

The system uses Gmail’s SMTP server with the following configuration (from src/emailer.py:30):
with smtplib.SMTP_SSL("smtp.gmail.com", 465) as smtp:
    smtp.login(remitente, password)
    smtp.send_message(mensaje)
SettingValue
Serversmtp.gmail.com
Port465
EncryptionSSL/TLS
AuthenticationRequired
These settings are hardcoded for Gmail. Other email providers require code modifications.

Email Content

The system sends emails with the following structure (from src/emailer.py:6-28):

Email Headers

mensaje["Subject"] = "📦 Reporte Automático de Inventario"
mensaje["From"] = remitente
mensaje["To"] = destinatario

Email Body

mensaje.set_content(
    "Este correo fue generado automáticamente.\n"
    "Se adjunta el reporte actualizado de inventario con alertas y recomendaciones."
)

Attachment

The Excel report is attached:
with open(ruta_excel, "rb") as f:
    mensaje.add_attachment(
        f.read(),
        maintype="application",
        subtype="octet-stream",
        filename=os.path.basename(ruta_excel),
    )
Attachment Details:
  • Type: Excel file (.xlsx)
  • Name: reporte_inventario.xlsx
  • Content: Multi-sheet report with complete inventory analysis

Testing Email Delivery

Quick Test

Run the system to test email delivery:
python src/main.py
Expected output if successful:
✅ Inventario cargado correctamente
✅ Clasificación ABC aplicada
✅ Riesgo evaluado y reposición recomendada
✅ Reporte Excel generado en output/reporte_inventario.xlsx
✅ Gráficos generados correctamente
✅ Reporte enviado por correo
Check your recipient inbox (including spam folder) to verify the email was received.

Troubleshooting

Cause: Email configuration validation failedSolutions:
  • Verify .env file exists in project root
  • Check all three variables are defined: EMAIL_REMITENTE, EMAIL_PASSWORD, EMAIL_DESTINATARIO
  • Ensure variables don’t contain placeholder values
  • Remove any quotes around values in .env file
Verify configuration:
cat .env
Cause: Invalid Gmail credentials or app passwordSolutions:
  • Verify you’re using an app password, not your regular Gmail password
  • Check that 2-Factor Authentication is enabled on your Gmail account
  • Generate a new app password and update .env
  • Ensure there are no extra spaces in the password
  • Verify the email address is correct
Cause: Network or firewall issuesSolutions:
  • Check internet connection
  • Verify firewall allows outbound connections on port 465
  • Try again - this can be a temporary Gmail server issue
  • Check if your organization blocks SMTP traffic
Cause: Report file doesn’t existSolutions:
  • This should not happen as the email is sent AFTER report generation
  • Check console output for errors in report generation step
  • Verify the output/ directory exists and is writable
Cause: Emails caught by spam filters or delivery delaysSolutions:
  • Check spam/junk folder in recipient email
  • Wait a few minutes - Gmail can have delays
  • Verify recipient email address is correct in .env
  • Check Gmail’s “Sent” folder to confirm it was sent
  • Add sender email to recipient’s contacts/safe senders
Cause: Attempting to use regular password instead of app passwordSolution: Google has disabled “less secure app access”. You must use app passwords with 2FA enabled. Regular passwords no longer work for SMTP.

Using Different Email Providers

To use a different email provider (not Gmail), modify src/emailer.py:30:

Outlook/Office 365

with smtplib.SMTP_SSL("smtp.office365.com", 587) as smtp:
    smtp.starttls()
    smtp.login(remitente, password)
    smtp.send_message(mensaje)

Yahoo Mail

with smtplib.SMTP_SSL("smtp.mail.yahoo.com", 465) as smtp:
    smtp.login(remitente, password)
    smtp.send_message(mensaje)

Custom SMTP Server

with smtplib.SMTP_SSL("your.smtp.server", 465) as smtp:
    smtp.login(remitente, password)
    smtp.send_message(mensaje)
Different providers may have different authentication requirements. Consult your email provider’s documentation for SMTP settings.

Security Best Practices

1

Never commit .env file

Add .env to your .gitignore file:
echo ".env" >> .gitignore
2

Use dedicated email account

Consider creating a separate Gmail account specifically for automated reporting
3

Limit app password scope

Generate separate app passwords for different applications to maintain granular control
4

Rotate passwords regularly

Periodically revoke old app passwords and generate new ones
5

Restrict file permissions

Set appropriate permissions on .env file:
chmod 600 .env

Revoking App Passwords

If you need to revoke an app password:
1

Visit App Passwords page

2

Find the password

Locate the app password you want to revoke (e.g., “Inventory System”)
3

Remove access

Click the delete/remove icon next to the password
4

Update configuration

If still needed, generate a new app password and update .env file

Automated Scheduling Considerations

When scheduling automated execution:
  • Cron jobs: Ensure the .env file path is accessible
  • Task schedulers: Verify environment variables are loaded correctly
  • Docker containers: Mount .env file or pass variables as container environment variables
  • Cloud functions: Use platform-specific secret management (e.g., AWS Secrets Manager)
For production deployments, consider using environment variable injection rather than .env files for better security.

Email Delivery Confirmation

Success indicator (from src/emailer.py:34):
print("✅ Reporte enviado por correo")
This message appears when:
  • SMTP connection succeeded
  • Authentication passed
  • Email was accepted by Gmail’s server
  • Attachment was sent successfully
This confirms the email was sent to Gmail’s server, not that it was delivered to the recipient’s inbox. Check the recipient’s inbox (including spam) to verify delivery.

Next Steps

Running the System

Learn how to execute the system and test email delivery

Understanding Outputs

Understand the email attachment contents and reports

Build docs developers (and LLMs) love