You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Django调用send_mail触发WinError 10060超时错误求助

Django发送Gmail验证邮件时出现WinError 10060连接超时问题

错误日志

运行Daphne服务器调用send_mail()发送邮箱验证邮件时触发500错误,核心为连接超时:

PS> daphne -p 8000 Server.asgi:application
2024-06-26 11:36:00,313 INFO     Starting server at tcp:port=8000:interface=127.0.0.1
2024-06-26 11:36:00,313 INFO     HTTP/2 support not enabled (install the http2 and tls Twisted extras)
2024-06-26 11:36:00,313 INFO     Configuring endpoint tcp:port=8000:interface=127.0.0.1
2024-06-26 11:36:00,314 INFO     Listening on TCP address 127.0.0.1:8000








xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx









Internal Server Error: /Http/createUser
Traceback (most recent call last):
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\asgiref\sync.py", line 534, in thread_handler
    raise exc_info[1]
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\django\core\handlers\exception.py", line 42, in inner
    response = await get_response(request)
               ^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\asgiref\sync.py", line 534, in thread_handler
    raise exc_info[1]
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\django\core\handlers\base.py", line 253, in _get_response_async
    response = await wrapped_callback(
               ^^^^^^^^^^^^^^^^^^^^^^^
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\asgiref\sync.py", line 479, in __call__
    ret: _R = await loop.run_in_executor(
              ^^^^^^^^^^^^^^^^^^^^^^^^^^^
TimeoutError: [WinError 10060] 连接方在一段时间后没有正确答复或连接的主机没有反应,连接尝试失败
2024-06-26 11:37:01,353 ERROR    Internal Server Error: /Http/createUser
Traceback (most recent call last):
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\asgiref\sync.py", line 534, in thread_handler
    raise exc_info[1]
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\django\core\handlers\exception.py", line 42, in inner
    response = await get_response(request)
               ^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\asgiref\sync.py", line 534, in thread_handler
    raise exc_info[1]
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\django\core\handlers\base.py", line 253, in _get_response_async
    response = await wrapped_callback(
               ^^^^^^^^^^^^^^^^^^^^^^^
  File "C:\Users\Lenovo\AppData\Local\Programs\Python\Python311\Lib\site-packages\asgiref\sync.py", line 479, in __call__
    ret: _R = await loop.run_in_executor(
              ^^^^^^^^^^^^^^^^^^^^^^^^^^^
TimeoutError: [WinError 10060] 连接方在一段时间后没有正确答复或连接的主机没有反应,连接尝试失败
127.0.0.1:60554 - - [26/Jun/2024:11:37:01] "POST /Http/createUser" 500 50886

项目配置文件

Settings.py

INSTALLED_APPS = [
    #'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',

    'corsheaders',
    'channels',
    'rest_framework',

    'Http',
    'WebSocket',
]
EMAIL_BACKEND = 'django.core.mail.backends.smtp.EmailBackend'
EMAIL_HOST = 'smtp.gmail.com'
EMAIL_PORT = 587
EMAIL_USE_TLS = True
EMAIL_HOST_USER = 'myEmail'
EMAIL_HOST_PASSWORD = 'myPassword'
#DEFAULT_FROM_EMAIL = 'myEmail' # no-reply

CORS_ALLOW_ALL_ORIGINS = True

CORS_ALLOW_METHODS = [
    'DELETE',
    'GET',
    'OPTIONS',
    'PATCH',
    'POST',
    'PUT',
]

CORS_ALLOW_HEADERS = [
    'accept',
    'accept-encoding',
    'authorization',
    'content-type',
    'dnt',
    'origin',
    'user-agent',
    'x-csrftoken',
    'x-requested-with',
]


# Is Gonna Change Manually 
FRONTEND_URL = '127.0.0.1:8000'

urls.py

from django.urls import path

from . import views

app_name = "Http"
urlpatterns = [
    path('createUser', views.create_user, name='CreateUser'),
    path('verifyEmail/', views.verify_email, name='VerifyEmail'),
]

views.py

from django.shortcuts import render, get_object_or_404
from django.views.decorators.csrf import csrf_exempt # No Csrf Prot
from rest_framework.decorators import api_view
from django.http import JsonResponse
from . import models as DataBase


from rest_framework import status # type: ignore
from rest_framework.response import Response # type: ignore
from rest_framework.views import APIView # type: ignore
from .serializers import UserSerializer
from .token_generator import emailVerificationToken

@csrf_exempt
@api_view(['POST'])
def create_user(request):
    serializer = UserSerializer(data=request.data)
    if serializer.is_valid():

        user = serializer.save()

        return Response({
            'message': 'User created successfully. Check your email for verification.',
            'user_id': user.id
        }, status=status.HTTP_201_CREATED)
    return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)


@api_view(['GET'])
def verify_email(request):
    token = request.GET.get('token')
    email = request.GET.get('email')
    user = get_object_or_404(DataBase.User, email=email)

    if emailVerificationToken.check_token(user, token):
        user.is_active = True
        user.save()
        return JsonResponse({'message': 'Email verified successfully.'})
    else:
        return JsonResponse({'error': 'Invalid token or email.'}, status=400)

serializers.py

# serializers.py
from rest_framework import serializers # type: ignore
from django.contrib.auth import get_user_model
from .models import ExtraClasses_EmailVerification
from .token_generator import emailVerificationToken

User = get_user_model()

from django.core.mail import send_mail
from django.urls import reverse
from django.conf import settings

class UserSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = ('id', 'name', 'email', 'password', 'phoneNumber')

    def create(self, validated_data):
        user = User.objects.create_user(**validated_data)
        user.is_active = False
        user.save()
        
        token = emailVerificationToken.make_token(user)
        verification_record = ExtraClasses_EmailVerification.objects.create(user=user, token=token)

        verification_url = f"{settings.FRONTEND_URL}/Http/verifyEmail?token={token}&email={user.email}"

        print("\n\n\n\n\n\n\n\nxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx\n\n\n\n\n\n\n\n")
        send_mail(
            'Verify your email',
            f'Click the link to verify your email: {verification_url}',
            settings.EMAIL_HOST_USER,
            [user.email],
            fail_silently=False,
        )
        print("\n\n\n\n\n\n\n\nxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx\n\n\n\n\n\n\n\n")
        return user

models.py

from django.db import models
from phonenumber_field.modelfields import PhoneNumberField # type: ignore
from django.contrib.auth.models import AbstractBaseUser, PermissionsMixin, BaseUserManager


class ExtraClasses_CustomUserManager(BaseUserManager):
    def create_user(self, name, email, password=None, **extra_fields):
        if not email:
            raise ValueError('The Email field must be set')
        email = self.normalize_email(email)
        user = self.model(name=name, email=email, **extra_fields)
        user.set_password(password)
        user.save(using=self._db)
        return user

    def create_superuser(self, name, email, password=None, **extra_fields):
        extra_fields.setdefault('is_staff', True)
        extra_fields.setdefault('is_superuser', True)
        return self.create_user(name, email, password, **extra_fields)


class User(AbstractBaseUser, PermissionsMixin):
    """
    Users That Use The Program
    """
    profilePhoto = models.ImageField(upload_to='profileImages/', default='defaultImages/profileImage.png')
    name = models.CharField(max_length=32)
    
    friends = models.ManyToManyField('self')
    explanation = models.CharField(max_length=48)

    email = models.EmailField(unique=True)
    password = models.CharField(max_length=32)
    phoneNumber = PhoneNumberField(unique=True)
    
    date_joined = models.DateTimeField(auto_now_add=True)


    """
    Django Authentication Parts
    """

    is_staff = models.BooleanField(default=False)
    is_active = models.BooleanField(default=True)

    objects = ExtraClasses_CustomUserManager()
    
    USERNAME_FIELD = 'id'
    EMAIL_FIELD = 'email'

    def __str__(self) -> str:
        return self.name


class ExtraClasses_EmailVerification(models.Model):
    user = models.OneToOneField(User, on_delete=models.CASCADE)
    token = models.CharField(max_length=200)
    created_at = models.DateTimeField(auto_now_add=True)
    edited_at = models.DateTimeField(auto_now=True)

已排查内容

  • 网络连接:使用Test-NetConnection测试smtp.gmail.com 587端口成功,输出如下:
    Test-NetConnection -ComputerName smtp.gmail.com -Port 587
    ComputerName     : smtp.gmail.com
    RemoteAddress    : --------------
    RemotePort       : 587
    InterfaceAlias   : Wi-Fi
    SourceAddress    : --------------
    TcpTestSucceeded : True  
    
  • 排除路由器问题:其他电脑可正常解析smtp.gmail.com
  • 关闭防火墙后问题仍存在

请求协助

需要排查并解决该邮件发送超时问题。

内容的提问来源于stack exchange,提问作者Omegames

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.22 00:53:10