今天无意间看到 simple-todo: 一个简易的 todo 程序 - web.py 中文教程 ,然后发现竟然有好多的版本 http://simple-is-better.com/news/tag/simple-todo
然后看到django版的是个半成品,好吧,自己动手丰衣足食。
django 安装配置这里就不再介绍了,直接给之前的地址: django 简易博客开发 1 安装、创建、配置、admin使用
使用的环境: fedora 17 + django1.4 + python2.7 + sqlite3
前端使用的 bootstrap + jquery
实现添加修改删除 ajax支持 可自行添加用户控制
1、django安装 project 创建 、app 创建、安装、admin使用
看着个吧,这篇博客有详细教程
2、上代码
#!/usr/bin/python # -*- coding: utf-8 -*- from django.db import models from django_openid_auth.models import User #之前我用过openid 这里换成 from django.contrib.auth.models import User 就可以了 class Todo(models.Model): user = models.ForeignKey(User) todo = models.CharField(max_length=50) flag = models.CharField(max_length=2, default='1') priority = models.CharField(max_length=2, default='0') pubtime = models.DateTimeField(auto_now_add=True) def __unicode__(self): return u'%d %s %s' % (self.id, self.todo, self.flag) class Meta: ordering = ['priority', 'pubtime']
priority 为优先级 排序时优先级高的在前面,越小优先级越高;然后再按时间排序,越早越靠前
flag 标记是否完成 默认为1表示未完成
当然这两处改为models.IntegerField 更好一些,可以自己修改一下
创建数据库:
python manage.py syncdb
在admin查看
#!/usr/bin/python # -*- coding: utf-8 -*- from django.contrib import admin from simpleToDo.models import Todo class TodoAdmin(admin.ModelAdmin): list_display = ('user', 'todo', 'priority', 'flag', 'pubtime') list_filter = ('pubtime',) ordering = ('-pubtime',) admin.site.register(Todo, TodoAdmin)
urls.py
#!/usr/bin/python # -*- coding: utf-8 -*- from django.conf.urls import * urlpatterns = patterns(('simpleToDo.views'), url(r'^$', 'todolist', name='todo'), url(r'^addtodo/$', 'addTodo', name='add'), url(r'^todofinish/(?P<id>\d+)/$', 'todofinish', name='finish'), url(r'^todobackout/(?P<id>\d+)/$', 'todoback', name='backout'), url(r'^updatetodo/(?P<id>\d+)/$', 'updatetodo', name='update'), url(r'^tododelete/(?P<id>\d+)/$', 'tododelete', name='delete'), )
views.py
1 from django.shortcuts import render_to_response 2 from django.http import HttpResponseRedirect 3 from django.template import RequestContext 4 from django_openid_auth.models import User 5 from django.http import Http404 6 from simpleToDo.models import Todo 7 8 9 def todolist(request): 10 todolist = Todo.objects.filter(flag=1) 11 finishtodos = Todo.objects.filter(flag=0) 12 return render_to_response('simpleTodo.html', 13 {'todolist': todolist, 'finishtodos': finishtodos}, 14 context_instance=RequestContext(request)) 15 16 17 def todofinish(request, id=''): 18 todo = Todo.objects.get(id=id) 19 if todo.flag == '1': 20 todo.flag = '0' 21 todo.save() 22 return HttpResponseRedirect('/simpleTodo/') 23 todolist = Todo.objects.filter(flag=1) 24 return render_to_response('simpleTodo.html', {'todolist': todolist}, 25 context_instance=RequestContext(request)) 26 27 28 def todoback(request, id=''): 29 todo = Todo.objects.get(id=id) 30 if todo.flag == '0': 31 todo.flag = '1' 32 todo.save() 33 return HttpResponseRedirect('/simpleTodo/') 34 todolist = Todo.objects.filter(flag=1) 35 return render_to_response('simpleTodo.html', {'todolist': todolist}, 36 context_instance=RequestContext(request)) 37 38 39 def tododelete(request, id=''): 40 try: 41 todo = Todo.objects.get(id=id) 42 except Exception: 43 raise Http404 44 if todo: 45 todo.delete() 46 return HttpResponseRedirect('/simpleTodo/') 47 todolist = Todo.objects.filter(flag=1) 48 return render_to_response('simpleTodo.html', {'todolist': todolist}, 49 context_instance=RequestContext(request)) 50 51 52 def addTodo(request): 53 if request.method == 'POST': 54 atodo = request.POST['todo'] 55 priority = request.POST['priority'] 56 user = User.objects.get(id='1') 57 todo = Todo(user=user, todo=atodo, priority=priority, flag='1') 58 todo.save() 59 todolist = Todo.objects.filter(flag='1') 60 finishtodos = Todo.objects.filter(flag=0) 61 return render_to_response('showtodo.html', 62 {'todolist': todolist, 'finishtodos': finishtodos}, 63 context_instance=RequestContext(request)) 64 else: 65 todolist = Todo.objects.filter(flag=1) 66 finishtodos = Todo.objects.filter(flag=0) 67 return render_to_response('simpleTodo.html', 68 {'todolist': todolist, 'finishtodos': finishtodos}) 69 70 71 def updatetodo(request, id=''): 72 if request.method == 'POST': 73 print 'ddd' 74 atodo = request.POST['todo'] 75 priority = request.POST['priority'] 76 user = User.objects.get(id='1') 77 todo = Todo(user=user, todo=atodo, priority=priority, flag='1') 78 todo.save() 79 todolist = Todo.objects.filter(flag='1') 80 finishtodos = Todo.objects.filter(flag=0) 81 return render_to_response('simpleTodo.html', 82 {'todolist': todolist, 'finishtodos': finishtodos}, 83 context_instance=RequestContext(request)) 84 else: 85 try: 86 todo = Todo.objects.get(id=id) 87 except Exception: 88 raise Http404 89 return render_to_response('updatatodo.html', {'todo': todo}, 90 context_instance=RequestContext(request))
因为表单使用的是post方法,所以每个view 后都添加了 context_instance=RequestContext(request)
否则可能会出现这个错误
/usr/lib/python2.7/site-packages/django/template/defaulttags.py:55: UserWarning: A {% csrf_token %} was used in a template, but the context did not provide the value. This is usually caused by not using RequestContext. warnings.warn("A {% csrf_token %} was used in a template, but the context did not provide the value. This is usually caused by not using RequestContext.")
templates 代码
<!DOCTYPE html> <html lang="en"> <head> <title>{% block title %}Simple Todo{% endblock %}</title> <meta charset="UTF-8" /> <link rel="stylesheet" href="/static/css/bootstrap.min.css"> <link rel="stylesheet" href="/static/css/code.css"> <script src="/static/js/modernizr.js"></script> <script src="/static/js/jquery.js"></script> {% block extra_head %} <style> body {padding-top: 40px;} .ftodo{text-decoration : line-through ; } textarea{ width: 97%; padding: 5px; font-size: 14px; resize: vertical;} </style> <script type="text/javascript"> function sendtwitter(){ $('#myModal form').submit(function(){ $.ajax({ type: "POST", data: $('#myModal form').serialize(), url: "{% url add %}", cache: false, dataType: "html", success: function(html, textStatus) { $('#todo').replaceWith(html); $('#myModal').modal('hide'); $('#myModal form')[0].reset(); }, error: function (XMLHttpRequest, textStatus, errorThrown) { $('#comment_form form').replaceWith('Your comment was unable to be posted at this time. We apologise for the inconvenience.'); } }); return false; }); } $(document).ready(function(){ sendtwitter(); }) </script> {% endblock %} </head> <body> <div class="container"> <div class="row"> <div class="span8 offset2"> <div id="todo" class="well"> {% block todo %} <table class="table table-hover"> <thead> <tr> <td> <h3 class="text-success">待办事项</h3> </td> </tr> </thead> <tbody> {% for todo in todolist %} {% if todo.priority == '1' %} <tr class='error'> {% endif %} {% if todo.priority == '2' %} <tr class='warning'> {% endif %} {% if todo.priority == '3' %} <tr class='info'> {% endif %} <td class="todo">{{ todo.todo }}</td> <td class="te"> <div class="span2"> <a href="{% url finish todo.id %}" title="finish"><i class=" icon-ok"></i></a> <a href="{% url update todo.id %}" title="edit"><i class="icon-edit"></i></a> <a href="{% url delete todo.id %}" title="delete"><i class="icon-trash"></i></a> </div> </td> </tr> {% endfor %} {% for ftodo in finishtodos %} <tr class='success'> <td class="ftodo muted">{{ ftodo.todo }}</td> <td class="te"> <div class="span2"> <a href="{% url backout ftodo.id %}" title="finish"><i class=" icon-repeat"></i></a> <a href="{% url update ftodo.id %}" title="edit"><i class="icon-edit"></i></a> <a href="{% url delete ftodo.id %}" title="delete"><i class="icon-trash"></i></a> </div> </td> </tr> {% endfor %} </tbody> </table> <a class="btn btn-success" href="#myModal" role="button" data-toggle="modal"> <i class="icon-plus icon-white"></i><span > ADD</span> </a> {% endblock %} </div> </div> </div> </div> <div class="modal hide fade" id="myModal" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true"> <div class="modal-header"> <button type="button" class="close" data-dismiss="modal" aria-hidden="true">×</button> <h3 id="myModalLabel">Add TODO</h3> </div> <form action="" method="post">{% csrf_token %} <div class="modal-body"> <textarea name="todo" class="txtodo" id="txtodo" required="required">{{ todo.todo }}</textarea> <fieldset> <label class="radio inline" for="priority"> <span class="label label-info">Priority</span> </label> <label class="radio inline" for="priority"> <input type="radio" name="priority" value="1"/> <span class="label label-important">重要</span> </label> <label class="radio inline" for="priority"> <input type="radio" name="priority" value="2"/> <span class="label label-warning">警告</span> </label> <label class="radio inline" for="priority"> <input type="radio" name="priority" value="3"/> <span class="label label-success">成功</span> </label> </fieldset> </div> <div class="modal-footer"> <button class="btn" data-dismiss="modal" aria-hidden="true">Close</button> <button id="send" class="btn btn-success" type="submit" name="submit" >Save changes</button> </div> </form> </div> <script src="/static/js/bootstrap.min.js"></script> </body> </html>
1 <div id="todo"> 2 <table class="table table-hover"> 3 <thead> 4 <tr> 5 <td> 6 <h4>todo</h4> 7 </td> 8 <td> 9 <a class="btn btn-success" href="#myModal" role="button" data-toggle="modal"> 10 <i class="icon-plus icon-white"></i><span > ADD</span> 11 </a> 12 </td> 13 </tr> 14 </thead> 15 <tbody> 16 {% for todo in todolist %} 17 {% if todo.priority == '1' %} 18 <tr class='error'> 19 {% endif %} 20 {% if todo.priority == '2' %} 21 <tr class='warning'> 22 {% endif %} 23 {% if todo.priority == '3' %} 24 <tr class='info'> 25 {% endif %} 26 <td class="todo">{{ todo.todo }}</td> 27 <td class="te"> 28 <div class="span2"> 29 <a href="{% url finish todo.id %}" title="finish"><i class=" icon-ok"></i></a> 30 <a href="{% url updateblog todo.id %}" title="edit"><i class="icon-edit"></i></a> 31 <a href="{% url delete todo.id %}" title="delete"><i class="icon-trash"></i></a> 32 </div> 33 </td> 34 </tr> 35 {% endfor %} 36 {% for ftodo in finishtodos %} 37 <tr class='success'> 38 <td class="todo muted">{{ ftodo.todo }}</td> 39 <td class="te"> 40 <div class="span2"> 41 <a href="{% url backout ftodo.id %}" title="finish"><i class=" icon-ok"></i></a> 42 <a href="{# {% url updateblog blog.id %} #}" title="edit"><i class="icon-edit"></i></a> 43 <a href="{% url delete ftodo.id %}" title="delete"><i class="icon-trash"></i></a> 44 </div> 45 </td> 46 </tr> 47 {% endfor %} 48 </tbody> 49 </table> 50 </div>
1 {% extends 'simpleTodo.html'%} 2 3 {% block title %} update Todo {% endblock %} 4 5 {% block todo %} 6 <form action="{% url update todo.id %}" method="post">{% csrf_token %} 7 <div class="modal-body"> 8 <textarea name="todo" class="txtodo" id="txtodo" required="required">{{ todo.todo }}</textarea> 9 <fieldset> 10 <label class="radio inline" for="priority"> 11 <span class="label label-info">Priority</span> 12 </label> 13 <label class="radio inline" for="priority"> 14 <input type="radio" name="priority" value="1" {% if todo.priority == '1' %} checked{% endif %}/> 15 <span class="label label-important">重要</span> 16 </label> 17 <label class="radio inline" for="priority"> 18 <input type="radio" name="priority" value="2" {% if todo.priority == '2' %} checked{% endif %}/> 19 <span class="label label-warning">警告</span> 20 </label> 21 <label class="radio inline" for="priority"> 22 <input type="radio" name="priority" value="3" {% if todo.priority == '3' %} checked{% endif %}/> 23 <span class="label label-success">成功</span> 24 </label> 25 </fieldset> 26 </div> 27 <div class="modal-footer"> 28 <button class="btn" data-dismiss="modal" aria-hidden="true">Close</button> 29 <button id="send" class="btn btn-success" type="submit" name="submit" >Save changes</button> 30 </div> 31 </form> 32 {% endblock %}
实现效果
1、首页
2、添加事项页面
3、修改事项时页面
项目地址: https://github.com/goodspeedcheng/Django-Simple-Todo
希望大家能把错误的地方指出来,让django版todo的更好一些 谢谢