Skip to content
This repository was archived by the owner on May 5, 2023. It is now read-only.

Commit d3bc28d

Browse files
committed
feat: add country and province daily list api
1 parent a3f0709 commit d3bc28d

File tree

4 files changed

+111
-29
lines changed

4 files changed

+111
-29
lines changed

ncovapi/models.py

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -194,6 +194,11 @@ class Province(models.Model):
194194
deadCount = models.IntegerField(default=0)
195195
comment = models.CharField(max_length=200)
196196
statisticsData = models.CharField(max_length=500)
197+
dailyData = models.TextField()
198+
created = models.DateTimeField(
199+
'创建时间', auto_now_add=True, editable=False)
200+
updated = models.DateTimeField(
201+
'更新时间', auto_now=True, editable=False)
197202
crawler = models.ForeignKey(
198203
"Crawler", on_delete=models.CASCADE, related_name="provinces",
199204
db_column="crawlerId"
@@ -213,6 +218,10 @@ class City(models.Model):
213218
suspectedCount = models.IntegerField(default=0)
214219
curedCount = models.IntegerField(default=0)
215220
deadCount = models.IntegerField(default=0)
221+
created = models.DateTimeField(
222+
'创建时间', auto_now_add=True, editable=False)
223+
updated = models.DateTimeField(
224+
'更新时间', auto_now=True, editable=False)
216225
province = models.ForeignKey(
217226
"Province", on_delete=models.CASCADE, related_name="cities",
218227
db_column="provinceId"
@@ -254,8 +263,11 @@ class Country(models.Model):
254263
incrVo = models.TextField(null=True)
255264
sort = models.IntegerField(null=True)
256265
operator = models.CharField(max_length=50, null=True)
257-
modifyTime = models.IntegerField(null=True)
258-
createTime = models.IntegerField(null=True)
266+
dailyData = models.TextField()
267+
created = models.DateTimeField(
268+
'创建时间', auto_now_add=True, editable=False)
269+
updated = models.DateTimeField(
270+
'更新时间', auto_now=True, editable=False)
259271
crawler = models.ForeignKey(
260272
"Crawler", on_delete=models.CASCADE, related_name="countries",
261273
db_column="countryId"

ncovapi/urls.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,9 @@
1616
path('provinces/', views.ProvinceListView.as_view(), name='province-list'),
1717
path('provinces/<int:pk>/', views.ProvinceRetrieveView.as_view(), name='province-detail'),
1818
path('provinces/<str:provinceShortName>/', views.ProvinceRetrieveByNameView.as_view(), name='province-detail-by-name'),
19+
path('provinces/<str:provinceShortName>/daily', views.ProvinceDailyListView.as_view(), name='province-daily-list'),
1920
path('countries/', views.CountryListView.as_view(), name='country-list'),
2021
path('countries/<int:pk>/', views.CountryRetrieveView.as_view(), name='country-detail'),
2122
path('countries/<str:countryName>/', views.CountryRetrieveByNameView.as_view(), name='country-detail-by-name'),
23+
path('countries/<str:countryName>/daily', views.CountryDailyListView.as_view(), name='country-daily-list'),
2224
]

ncovapi/views.py

Lines changed: 56 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
from .filters import CityFilter, ProvinceFilter, CountryFilter
2222

2323
from collections import OrderedDict
24+
import json
2425

2526
TIMEOUT = 60 * 60
2627

@@ -29,9 +30,9 @@ class LatestStatisticsView(APIView):
2930
"""最新统计信息"""
3031

3132
def get_object(self):
32-
try:
33-
crawler = Crawler.objects.order_by('-id').first()
34-
except Crawler.DoesNotExist:
33+
crawler = Crawler.objects.exclude(
34+
modifyTime__isnull=True).order_by('-id').first()
35+
if crawler is None:
3536
raise Http404
3637
result = {}
3738
insts = Statistics.objects.filter(crawler=crawler).all()
@@ -120,7 +121,8 @@ class ProvinceListView(ListAPIView):
120121
filter_class = ProvinceFilter
121122

122123
def get_queryset(self):
123-
crawler = Crawler.objects.order_by('-id').first()
124+
crawler = Crawler.objects.exclude(
125+
modifyTime__isnull=True).order_by('-id').first()
124126
queryset = Province.objects.filter(crawler=crawler)
125127
return queryset
126128

@@ -129,14 +131,34 @@ def dispatch(self, *args, **kwargs):
129131
return super(ProvinceListView, self).dispatch(*args, **kwargs)
130132

131133

132-
class ProvinceRetrieveByNameView(APIView):
133-
"""通过省名获取数据"""
134+
class ProvinceDailyListView(APIView):
135+
136+
"""省按天返回列表"""
134137

135138
def get_object(self, provinceShortName):
139+
crawler = Crawler.objects.exclude(
140+
modifyTime__isnull=True).order_by('-id').first()
136141
try:
137-
crawler = Crawler.objects.order_by('-id').first()
138-
except Crawler.DoesNotExist:
142+
return Province.objects.filter(
143+
crawler=crawler,
144+
provinceShortName=provinceShortName).first()
145+
except Province.DoesNotExist:
139146
raise Http404
147+
148+
@method_decorator(cache_page(TIMEOUT))
149+
def get(self, request, provinceShortName):
150+
province = self.get_object(provinceShortName)
151+
result = province.dailyData
152+
result = json.loads(result)
153+
return Response(result)
154+
155+
156+
class ProvinceRetrieveByNameView(APIView):
157+
"""通过省名获取数据"""
158+
159+
def get_object(self, provinceShortName):
160+
crawler = Crawler.objects.exclude(
161+
modifyTime__isnull=True).order_by('-id').first()
140162
try:
141163
return Province.objects.filter(
142164
crawler=crawler,
@@ -172,7 +194,8 @@ class CountryListView(ListAPIView):
172194
filter_class = CountryFilter
173195

174196
def get_queryset(self):
175-
crawler = Crawler.objects.order_by('-id').first()
197+
crawler = Crawler.objects.exclude(
198+
modifyTime__isnull=True).order_by('-id').first()
176199
queryset = Country.objects.filter(crawler=crawler)
177200
return queryset.all()
178201

@@ -196,13 +219,30 @@ def get(self, request, pk):
196219
return Response(serializer.data)
197220

198221

199-
class CountryRetrieveByNameView(APIView):
222+
class CountryDailyListView(APIView):
200223

201224
def get_object(self, countryName):
225+
crawler = Crawler.objects.exclude(
226+
modifyTime__isnull=True).order_by('-id').first()
202227
try:
203-
crawler = Crawler.objects.order_by('-id').first()
204-
except Crawler.DoesNotExist:
228+
return Country.objects.filter(
229+
crawler=crawler, countryName=countryName).first()
230+
except Country.DoesNotExist:
205231
raise Http404
232+
233+
@method_decorator(cache_page(TIMEOUT))
234+
def get(self, request, countryName):
235+
country = self.get_object(countryName)
236+
result = country.dailyData
237+
result = json.loads(result)
238+
return Response(result)
239+
240+
241+
class CountryRetrieveByNameView(APIView):
242+
243+
def get_object(self, countryName):
244+
crawler = Crawler.objects.exclude(
245+
modifyTime__isnull=True).order_by('-id').first()
206246
try:
207247
return Country.objects.filter(
208248
crawler=crawler, countryName=countryName).first()
@@ -222,7 +262,8 @@ class CityListView(ListAPIView):
222262
filter_class = CityFilter
223263

224264
def get_queryset(self):
225-
crawler = Crawler.objects.order_by('-id').first()
265+
crawler = Crawler.objects.exclude(
266+
modifyTime__isnull=True).order_by('-id').first()
226267
queryset = City.objects.filter(crawler=crawler)
227268
return queryset
228269

@@ -249,10 +290,8 @@ def get(self, request, pk):
249290
class CityRetrieveByNameView(APIView):
250291

251292
def get_object(self, cityName):
252-
try:
253-
crawler = Crawler.objects.order_by('-id').first()
254-
except Crawler.DoesNotExist:
255-
raise Http404
293+
crawler = Crawler.objects.exclude(
294+
modifyTime__isnull=True).order_by('-id').first()
256295
try:
257296
return City.objects.filter(
258297
crawler=crawler, cityName=cityName).first()

spider/nCoV/spiders/dxy.py

Lines changed: 39 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
# @Author: zhanglei3
33
# @Date: 2020-04-08 09:08:13
44
# @Last Modified by: leafcoder
5-
# @Last Modified time: 2020-04-29 13:51:25
5+
# @Last Modified time: 2020-04-30 10:09:06
66

77
"""丁香园数据源"""
88

@@ -19,7 +19,7 @@
1919
class DXYSpider(scrapy.Spider):
2020

2121
name = "dxy"
22-
allowed_domains = ["ncov.dxy.cn"]
22+
allowed_domains = ["ncov.dxy.cn", "file1.dxycdn.com"]
2323
start_urls = [
2424
"http://ncov.dxy.cn/ncovh5/view/pneumonia",
2525
]
@@ -45,19 +45,22 @@ def parse(self, response):
4545
self.crawler.save()
4646

4747
# 统计信息
48-
statistics = self.parse_statistics(statistics)
48+
statistics = self.explain_statistics(statistics)
4949
for item in statistics:
5050
yield item
5151

5252
# 国内数据
5353
provinces = self.get_list(scripts, '#getAreaStat')
5454
for province in provinces:
5555
cities = province.pop('cities', [])
56-
province = items.ProvinceItem(**province)
57-
yield province
58-
for city in cities:
59-
location_id = province['locationId']
60-
yield items.CityItem(province=location_id, **city)
56+
yield scrapy.Request(
57+
province['statisticsData'],
58+
callback=self.parse_province_statistics_data,
59+
meta={
60+
'province': province,
61+
'cities': cities
62+
}
63+
)
6164

6265
# 国外数据
6366
countries = self.get_list(
@@ -71,8 +74,16 @@ def parse(self, response):
7174
country.pop('provinceId')
7275
country.pop('provinceName')
7376
country.pop('provinceShortName')
77+
country.pop('modifyTime', None)
78+
country.pop('createTime', None)
7479
country['incrVo'] = json.dumps(country['incrVo'])
75-
yield items.CountryItem(**country)
80+
yield scrapy.Request(
81+
country['statisticsData'],
82+
callback=self.parse_country_statistics_data,
83+
meta={
84+
'country': country
85+
}
86+
)
7687

7788
# 时间线事件,id=“getTimelineService2” 为英文内容
7889
timelines = self.get_list(scripts, '#getTimelineService1')
@@ -127,7 +138,25 @@ def parse(self, response):
127138
rumor[key] = item.get(key)
128139
yield items.RumorItem(**rumor)
129140

130-
def parse_statistics(self, data):
141+
def parse_province_statistics_data(self, response):
142+
result = json.loads(response.text)
143+
data = json.dumps(result['data'])
144+
meta = response.meta
145+
cities = meta['cities']
146+
province = meta['province']
147+
yield items.ProvinceItem(dailyData=data, **province)
148+
for city in cities:
149+
location_id = province['locationId']
150+
yield items.CityItem(province=location_id, **city)
151+
152+
def parse_country_statistics_data(self, response):
153+
result = json.loads(response.text)
154+
data = json.dumps(result['data'])
155+
meta = response.meta
156+
country = meta['country']
157+
yield items.CountryItem(dailyData=data, **country)
158+
159+
def explain_statistics(self, data):
131160
statistics = data['globalStatistics']
132161
item = {}
133162
for key in (

0 commit comments

Comments
 (0)