urls.py
from django.urls import path
from .views import (product_list, product_detail, manufacturer_list, manufacturer_detail) #ProductDetailview, ProductListView
urlpatterns = [
path('products/', product_list, name="product-list"),
#path('url', 呼び出す関数, name="name") nameとurlはvuerouterの{name: 'products'}ような関係。
path('products/<int:pk>/', product_detail, name="product-detail"),
path('manufacturers/', manufacturer_list, name="manufacturer-list"),
path('manufacturers/<int:pk>/', manufacturer_detail, name="manufacturer-detail")
]
views.py
from django.http import JsonResponse
from .models import Product, Manufacturer
def product_list(request):
products = Product.objects.all()#productモデルから全て取得
data = {"products": list(products.values())}
#data = {"products": list(products.values("pk", "name", "quantity"))} #pk(primarykey)をidに変えることも可能
response = JsonResponse(data)
#pythonの辞書型をJsonResponse()の引数に入れることで、JSONに変換してくれる
return response
def product_detail(request, pk):
try:
product = Product.objects.get(pk=pk)
data = {"product": {
"name": product.name,
"manufacturer": product.manufacturer.name, #this is pk of manufacturer
"description": product.description,
"photo": product.photo.url, #photoはurlを追加
"price": product.price,
"shipping_cost": product.shipping_cost,
"quantity": product.quantity,
}}
response = JsonResponse(data)
except Product.DoesNotExist:
response = JsonResponse({"error": {
"code": 404,
"message": "product not found!"
}},
status=404)
return response
def manufacturer_list(request):
manufacturers = Manufacturer.objects.filter(active=True)
data = {"manufacturers": list(manufacturers.values())}
response = JsonResponse(data)
return response
def manufacturer_detail(request, pk):
try:
manufacturer = Manufacturer.objects.get(pk=pk)
manufacturer_products = manufacturer.products.all()
data = {"manufacturer": {
"name": manufacturer.name,
"location": manufacturer.location,
"active": manufacturer.active,
"products": list(manufacturer_products.values())
}}
response = JsonResponse(data)
except Manufacturer.DoesNotExist:
response = JsonResponse({"error": {
"code": 404,
"message": "manufacturer not found!"
}},
status=404)
return response
djangoでのテーブル取得
all
model = model.objects.all()
これでまずテーブル全てを取得。
なお型は現在queryset型。(str型やint型のようにdjangoが作る型)
以下のような形で返ってきた。
queryset
<QuerySet [<Article: John>, <Article: Rio>, <Article: Rio>, <Article: Joahn>]>
これはmodels.pyで定義したタイトルだった。
models.py
def __str__(self):
return self.author
このquerysetからvalueだけを抜き取り辞書型に展開
all
value_query_set = model.values()
すると、以下のような形に変わる
<QuerySet [
{'id': 1, 'author': 'John'},
{'id': 2, 'author': 'Rio'},
{'id': 3, 'author': 'Rio'}
]>
これをリスト型に変換
data = list(value_query_set)
[
{'id': 1, 'author': 'John'},
{'id': 2, 'author': 'Rio'},
{'id': 3, 'author': 'Rio'}
]
これでJSON完成!...ではなくこれはあくまでも辞書型リスト。
なので最後にJsonResponseを使って変換してあげましょう。
from django.http import JsonResponse
response = JsonResponse(data, safe=False)
ここで大事なのは、引数のsafe=False。
普通の辞書型であれば必要はないが、辞書型リストなので、safe=Falseがない場合、
In order to allow non-dict objects to be serialized set the safe parameter to False.
と怒られる。
それゆえに下記のように辞書型にするパターンもある。
data = {'model': list(value_query_set)}
こうすることで辞書型になるのでsafe=Falseは必要なくなる。
この一連流れはlaravelでは必要ないからなにをやっているのか理解できなかった。
laravel
return Model::all();
ぶっちゃけこんだけで済んでしまう。笑
せっかくなのでlaravelでよく使っていたクエリメソッドとdjangoの場合を比較する。
laravel
$all_models = Model::all();
$model = Model::find(1);
$models = Model::where('author', 'rio')->get();
$models = Model::where('author', 'rio')->where('title', 'hello')->get();
django
all_model = model.objects.all()
model = model.objects.get(pk=1)
models = model.objects.filter(author='rio')
models = model.objects.filter(author='rio', title='hello')
get(pk=pk)で取得した場合、よくわからない型で、list(model.values())が使えない。
そのため、valueを地道に取得して、辞書型の形を作ってあげなければならない。
filter(pk=pk)を使えばall()同様queryset型なので、上記のやり方で取得可能。
参考にしたサイト。
↧