2

Django 1.4 で登録ページを作ろうとしています。

これらは私のファイルです:

view.py

    mensaje = ""
        if request.method == 'POST':
                form = RegistrationForm(request.POST)
                if form.is_valid():
                        usr = User.objects.create_user(username = form.cleaned_data['username'], email = form.cleaned_data['mail'], password = form.cleaned_data['pa$

                        cli = cliente(user=usr, nombre=form.cleaned_data['nombre'], apellidos = form.cleaned_data['apellidos'], empresa = form.cleaned_data['empresa$
                        mensaje = "Cliente %s guardado exitosamente con el username %s" % (cli.nombre,cli.user)
                        cli.save()
                        ctx = {'mensaje':mensaje}
                        return HttpResponseRedirect('/')
                else:
                        mensaje = "el formulario no es valido"
                        ctx = {'form': form, 'mensaje': mensaje}
                        return render_to_response('pymes/register.html', ctx, context_instance=RequestContext(request))

        else:
                form = RegistrationForm()
                context = {'form':form}
                return render_to_response('pymes/register.html', context, context_instance=RequestContext(request))

models.py

class perfilCliente(models.base.ModelBase):
        def _prepare(self):
                super(perfilCliente, self)._prepare()
                def create_cliente_user_callback(sender, instance, created, **kwargs):
                        if created:
                                self.objects.create(user=instance)
                post_save.connect(create_cliente_user_callback, sender=User, weak=False)

class cliente(models.Model):
        __metaclass__   = perfilCliente
        user            = models.OneToOneField(User)
        nombre          = models.CharField(max_length=200)
        apellidos       = models.CharField(max_length=200)
        mail            = models.CharField(max_length=200)
        empresa         = models.CharField(max_length=200)
        status          = models.BooleanField(default=True)
        plan            = models.ForeignKey('pymes.plan',null=True,blank=True)
        def __unicode__(self):
                nombreCompleto = "%s %s"%(self.nombre,self.apellidos)
                return nombreCompleto

register.html

{% extends "base.html" %}
{% block title %} Login {% endblock %}
{% block content %}
{{ mensaje }}
<form action="" method="post">
{% csrf_token %}
{% if form.errors %}<p> Corregir los campos: </p> {% endif %}
<div class="register_div">
        {% if form.nombre.errors %}<p class="error">{{ form.nombre.errors }}</p>{% endif %}
        <p><label for="nombre"{% if form.nombre.errors %} class="error"{% endif %}>Nombre:</label>{{ form.nombre }}</p>
</div>
<div class="register_div">
        {% if form.apellido.errors %}<p class="error">{{ form.apellido.errors }}</p>{% endif %}
        <p><label for="apellido"{% if form.apellido.errors %} class="error"{% endif %}>Apellido:</label>{{ form.apellidos }}</p>
</div>
<div class="register_div">
        {% if form.empresa.errors %}<p class="error">{{ form.empresa.errors }}</p>{% endif %}
        <p><label for="empresa"{% if form.empresa.errors %} class="error"{% endif %}>Empresa:</label> {{ form.empresa }}</p>
</div>
<div class="register_div">
        {% if form.mail.errors %}<p class="error">{{ form.mail.errors }}</p>{% endif %}
        <p><label for="mail"{% if form.mail.errors %} class="error"{% endif %}>Email:</label> {{ form.mail }}</p>
</div>
<div class="register_div">
        {% if form.username.errors %} <p class="error">{{ form.username.errors }}</p>{% endif %}
        <p><label for="username"{% if form.username.errors %} class="error"{% endif %}>Username:</label> {{ form.username }}</p>
</div>
<div class="register_div">
        {% if form.password.errors %}<p class="error">{{ form.password.errors }}</p>{% endif %}
        <p><label for="password"{% if form.password.errors %} class="error"{% endif %}>Password:</label> {{ form.password }}</p>
</div>
<div class="register_div">
        {% if form.passworduno.errors %}<p class="error">{{ form.passworduno.errors }}</p>{% endif %}
        <p><label for="password1"{% if form.passworduno.errors %} class="error"{% endif %}>Verify Password:</label>{{ form.passworduno }}</p>
</div>
<p><input type="submit" alt="register" /></p>
</form>

ページは正常に動作しますが、フォームを送信すると次のエラーが表示されます。

Request Method: POST
Request URL: http://192.168.2.106:8000/register/

Django Version: 1.4.5
Python Version: 2.7.3
Installed Applications:
('django.contrib.auth',
 'django.contrib.contenttypes',
 'django.contrib.sessions',
 'django.contrib.sites',
 'django.contrib.messages',
 'django.contrib.staticfiles',
 'django.contrib.admin',
 'saas.apps.pymes',
 'django.contrib.admindocs')
Installed Middleware:
('django.middleware.common.CommonMiddleware',
 'django.contrib.sessions.middleware.SessionMiddleware',
 'django.middleware.csrf.CsrfViewMiddleware',
 'django.contrib.auth.middleware.AuthenticationMiddleware',
 'django.contrib.messages.middleware.MessageMiddleware')


Traceback:
File "/usr/local/lib/python2.7/dist-packages/django/core/handlers/base.py" in get_response
  111.                         response = callback(request, *callback_args, **callback_kwargs)
File "/root/project/saas/saas/apps/pymes/views.py" in register_view
  52.           cli.save()
File "/usr/local/lib/python2.7/dist-packages/django/db/models/base.py" in save
  463.         self.save_base(using=using, force_insert=force_insert, force_update=force_update)
File "/usr/local/lib/python2.7/dist-packages/django/db/models/base.py" in save_base
  551.                 result = manager._insert([self], fields=fields, return_id=update_pk, using=using, raw=raw)
File "/usr/local/lib/python2.7/dist-packages/django/db/models/manager.py" in _insert
  203.         return insert_query(self.model, objs, fields, **kwargs)
File "/usr/local/lib/python2.7/dist-packages/django/db/models/query.py" in insert_query
  1593.     return query.get_compiler(using=using).execute_sql(return_id)
File "/usr/local/lib/python2.7/dist-packages/django/db/models/sql/compiler.py" in execute_sql
  912.             cursor.execute(sql, params)
File "/usr/local/lib/python2.7/dist-packages/django/db/backends/util.py" in execute
  40.             return self.cursor.execute(sql, params)
File "/usr/local/lib/python2.7/dist-packages/django/db/backends/mysql/base.py" in execute
  114.             return self.cursor.execute(query, args)
File "/usr/lib/python2.7/dist-packages/MySQLdb/cursors.py" in execute
  174.             self.errorhandler(self, exc, value)
File "/usr/lib/python2.7/dist-packages/MySQLdb/connections.py" in defaulterrorhandler
  36.     raise errorclass, errorvalue

Exception Type: IntegrityError at /register/
Exception Value: (1062, "Duplicate entry '3' for key 'user_id'"

これにより、データベースにid = 3の新しいユーザーが適切に作成されます

mysql> select * from auth_user;
+----+-----------+------------+-----------+--------------------+----------+----------+-----------+--------------+---------------------+---------------------+
| id | username  | first_name | last_name | email              | password                                                                      | is_staff | is_active | is_superuser | last_login          | date_joined         |
+----+-----------+------------+-----------+--------------------+-------------------------------------------------------------------------------+----------+-----------+--------------+---------------------+---------------------+
|  1 | root      |            |           | sdfds@sdfa.com     | pass1 |        1 |         1 |            1 | 2013-04-01 07:49:58 | 2013-04-01 07:49:58 |
|  2 | oespinoza |            |           | zdssd@yahoo.es | pass2 |        0 |         1 |            0 | 2013-04-01 07:50:46 | 2013-04-01 07:50:46 |
|  3 | loco      |            |           | sdfsd              | pass3 |        0 |         1 |            0 | 2013-04-01 08:03:37 | 2013-04-01 08:03:37 |
+----+-----------+------------+-----------+--------------------+---------+----------+-----------+--------------+---------------------+---------------------+

そして、リアリティもうまく機能します。しかし、テーブル「cliente」にはこれだけが表示されます:

mysql> select * from pymes_cliente;
+----+---------+--------+-----------+------+---------+--------+---------+
| id | user_id | nombre | apellidos | mail | empresa | status | plan_id |
+----+---------+--------+-----------+------+---------+--------+---------+
|  1 |       1 |        |           |      |         |      1 |    NULL |
|  2 |       2 |        |           |      |         |      1 |    NULL |
|  4 |       3 |        |           |      |         |      1 |    NULL |
+----+---------+--------+-----------+------+---------+--------+---------+

お願い助けて。

4

1 に答える 1

3

Profile登録ごとにオブジェクトの 2 つのインスタンスを作成しているようです。1 つ目はビューで、2 つ目はシグナルを介して作成しています。

# Create & save User object
usr = User.objects.create_user(...)
...
# Create profile
cli = cliente(user=usr, ...)
# Save profile & fire your signal
cli.save()

あなたの信号で

# Creates second profile with same user object, causing error
self.objects.create(user=instance)

信号 (および ) を削除する_prepareと、問題は解消されます。

Sidenote:メソッドにシグナルを登録している理由がわかりません_prepare。通常、モデル ファイルの最後に信号を登録するのが最善です。

class Client(models.Model):
    ...

def create_cliente_user_callback(sender, instance, created, **kwargs):
    ...
post_save.connect(create_cliente_user_callback, sender=User, weak=False)
于 2013-04-01T09:57:20.450 に答える