AJAX(Asynchronous Javascript And XML)翻譯成中文就是「異步Javascript和XML」。即便用Javascript語言與服務器進行異步交互,傳輸的數據爲XML(固然,傳輸的數據不僅是XML,如今更多使用json數據)。html
AJAX除了異步的特色外,還有一個就是:瀏覽器頁面局部刷新;(這一特色給用戶的感覺是在不知不覺中完成請求和響應過程)前端
優勢: AJAX使用Javascript技術向服務器發送異步請求 AJAX無須刷新整個頁面ajax
ajax基本語法:chrome
1 $.ajax({ 2 url:'/index/', 3 type:'get', 4 date:{"name":"shy","pwd":123}, 5 success:function(response){ 6 console.log(response) 7 } 8 })
應用案例:判斷用戶名是否已經被註冊json
後端
1 POST http://www.example.com HTTP/1.1 2 Content-Type:multipart/form-data; boundary=----WebKitFormBoundaryrGKCBY7qhFd3TrwA 3 4 ------WebKitFormBoundaryrGKCBY7qhFd3TrwA 5 Content-Disposition: form-data; name="user" 6 7 yuan 8 ------WebKitFormBoundaryrGKCBY7qhFd3TrwA 9 Content-Disposition: form-data; name="file"; filename="chrome.png" 10 Content-Type: image/png 11 12 PNG ... content of chrome.png ... 13 ------WebKitFormBoundaryrGKCBY7qhFd3TrwA--
瀏覽器
服務器
1 <form action="/text/" method="post"> 2 {% csrf_token %} 3 姓名<input name="name" type="text"> 4 年齡<input name="age" type="text"> 5 <button>提交</button> 6 </form>
後端對應一個相應的處理函數:cookie
1 def text(request): 2 print(request.POST) 3 return HttpResponse('ok')
運行成功後,咱們能夠從瀏覽器的請求頭中看到:app
1 Content-Type: application/x-www-form-urlencoded
在模板中:
1 <form action="/byform/" method="post" enctype="multipart/form-data"> 2 {% csrf_token %} 3 姓名<input name="user" type="text"><br> 4 請選擇文件 <input name="file" type="file"><br> 5 <button>提交</button> 6 </form>
在視圖中:
1 def byform(request): 2 print(request.POST) 3 # < QueryDict: {'csrfmiddlewaretoken': ['9BxiKXnDy4xobLQ9m4QZDHQsOJeiWcCCE0uETorZjgCRZB01oL9evgqBULX2ERY2'],'user': ['alex']} > 4 5 print(request.FILES) 6 # < MultiValueDict: {'file': [ < InMemoryUploadedFile: IMG20181030152136.jpg(image / jpeg) >]} > 7 8 # 文件對象 9 file_obj=request.FILES.get('file') 10 11 # 文件對象的name屬性,獲取文件名稱 12 file_name=file_obj.name 13 # IMG20181030152136.jpg 14 15 path=os.path.join(BASE_DIR,'media','img',file_name) 16 with open(path,'wb') as f: 17 for line in file_obj: 18 f.write(line) 19 return HttpResponse('上傳成功')
在模板中
1 <h4>基於ajax的文件上傳</h4> 2 <form > 3 姓名 <input class="num3" name="user" type="text"><br> 4 文件 <input class="num4" type="file"> 5 <input type="button" class="btn1" value="提交"> 6 </form> 7 8 $('.btn1').click(function(){ 9 var formdata=new FormData(); 10 formdata.append("num3",$('.num3').val()); 11 formdata.append("num4",$('.num4')[0].files[0]); 12 13 $.ajax({ 14 url:'/byform/', 15 type:'post', 16 processData: false , // 不處理數據 17 contentType: false, 18 data:formdata, 19 headers:{"X-CSRFToken":$.cookie('csrftoken')}, 20 success:function(response){ 21 console.log(response) 22 }, 23 }) 24 })
在視圖中
1 def byform(request): 2 print(request.POST) 3 # < QueryDict: {'csrfmiddlewaretoken': ['9BxiKXnDy4xobLQ9m4QZDHQsOJeiWcCCE0uETorZjgCRZB01oL9evgqBULX2ERY2'],'user': ['alex']} > 4 print(request.FILES) 5 # < MultiValueDict: {'file': [ < InMemoryUploadedFile: IMG20181030152136.jpg(image / jpeg) >]} > 6 # 文件對象 7 file_obj=request.FILES.get('num4') 8 # 文件對象的name屬性,獲取文件名稱 9 10 file_name=file_obj.name 11 # IMG20181030152136.jpg 12 13 path=os.path.join(BASE_DIR,'media','img',file_name) 14 with open(path,'wb') as f: 15 for line in file_obj: 16 f.write(line) 17 return HttpResponse('上傳成功')
1 for i in range(100): 2 book=Book(title="悼念金庸-%s"%i,price=i*i,pub_date='2012-12-12',publish_id=1 ) 3 list.append(book) 4 Book.objects.bulk_create(list)
1 paginator=Paginator(book_list,20) 2 print(paginator.count) #一共有多少頁 3 print(paginator.num_pages) #分了多少頁 4 print(paginator.page_range) #每一頁的頁碼 5 page=paginator.page(5) #第n頁的數據 6 # for i in page: 7 # print(i) 8 print(page.has_next()) #是否有上一頁 9 print(page.has_previous()) #是否有下一頁 10 print(page.next_page_number()) #上一頁的頁碼 11 print(page.previous_page_number()) #下一頁的頁碼
在模板中
1 <div class="col-md-8 col-md-offset-2"> 2 <nav aria-label="Page navigation"> 3 <ul class="pagination"> 4 {% if page.has_previous %} 5 <li><a href="?page={{ page.previous_page_number }}">上一頁</a></li> 6 {% else %} 7 <li class="disabled"><span href="">上一頁</span></li> 8 {% endif %} 9 10 {% for num in paginator.page_range %} 11 12 {% if num == page_num %} 13 <li class="active"><a href="?page={{ num }}">{{ num }}</a></li> 14 {% else %} 15 <li><a href="?page={{ num }}">{{ num }}</a></li> 16 {% endif %} 17 18 {% endfor %} 19 20 {% if page.has_next %} 21 <li><a href="?page={{ page.next_page_number }}">下一頁</a></li> 22 {% else %} 23 <li class="disabled"><span href="">下一頁</span></li> 24 {% endif %} 25 </ul> 26 </nav> 27 </div>
在視圖中
1 paginator = Paginator(book_list, 20) 2 page_num=int(request.GET.get("page",1) ) #若是取不到,就用1 3 page=paginator.page(page_num) 4 return render(request,'index.html',{"book_list":book_list,"paginator":paginator,"page":page,"page_num":page_num})
功能實現的函數:
1 class Pagination(): 2 def __init__(self, current_page_num, all_count, request, per_page_num=5, pager_count=11): 3 """ 4 封裝分頁相關數據 5 :param current_page_num: 當前訪問頁的數字 6 :param all_count: 分頁數據中的數據總條數 7 :param per_page_num: 每頁顯示的數據條數 8 :param pager_count: 最多顯示的頁碼個數 9 """ 10 try: 11 current_page_num = int(current_page_num) 12 except Exception as e: 13 current_page_num = 1 14 if current_page_num < 1: 15 current_page_num = 1 16 self.current_page_num = current_page_num 17 self.all_count = all_count 18 self.per_page_num = per_page_num 19 all_pager, tmp = divmod(all_count, per_page_num) 20 if tmp: 21 all_pager += 1 22 self.all_pager = all_pager 23 self.pager_count = pager_count 24 self.page_count_half = int((pager_count - 1) / 2) 25 import copy 26 self.params = copy.deepcopy(request.GET) 27 28 @property 29 def start(self): 30 return int((self.current_page_num - 1) * self.per_page_num) 31 32 @property 33 34 def end(self): 35 return int(self.current_page_num * self.per_page_num) 36 37 def page_html(self): 38 if self.all_pager<=self.pager_count: 39 page_start=1 40 page_end=self.all_pager+1 41 else: 42 if self.current_page_num<=self.page_count_half: 43 page_start=1 44 page_end=self.pager_count+1 45 else: 46 if self.current_page_num >(self.all_pager-self.page_count_half): 47 page_start=self.all_pager-self.pager_count+1 48 page_end=self.all_pager+1 49 else: 50 page_start=self.current_page_num-self.page_count_half 51 page_end=self.current_page_num+self.page_count_half+1 52 page_html_list=[] 53 first_page='<li><a href="?page=%s">首頁</li>' % 1 54 page_html_list.append(first_page) 55 if self.current_page_num<=1: 56 prev_page="<li class='disabled'><a href='#'>上一頁</a></li>" 57 else: 58 prev_page = "<li ><a href='?page=%s'>上一頁</a></li>" % (self.current_page_num-1) 59 page_html_list.append(prev_page) 60 for i in range(page_start,page_end): 61 self.params["page"]=i 62 if i==self.current_page_num: 63 temp="<li class='active'><a href='?%s'>%s</a></li>" % (self.params.urlencode(),i) 64 else: 65 temp = "<li><a href='?%s'>%s</a></li>" % (self.params.urlencode(), i) 66 page_html_list.append(temp) 67 if self.current_page_num>=self.all_pager: 68 next_page="<li class='disabled'><a href='#'>下一頁</a></li>" 69 else: 70 next_page = "<li ><a href='?page=%s'>下一頁</a></li>" % (self.current_page_num+1) 71 page_html_list.append(next_page) 72 last_page = '<li><a href="?page=%s">尾頁</li>' % (self.all_pager) 73 page_html_list.append(last_page) 74 return "".join(page_html_list)