udata 10.8.2.dev36872__py2.py3-none-any.whl → 10.8.2.dev36938__py2.py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of udata might be problematic. Click here for more details.
- udata/harvest/actions.py +24 -28
- udata/harvest/api.py +25 -33
- udata/harvest/commands.py +7 -7
- udata/harvest/tasks.py +1 -1
- udata/harvest/tests/ckan/test_ckan_backend.py +5 -5
- udata/harvest/tests/ckan/test_ckan_backend_errors.py +6 -6
- udata/harvest/tests/ckan/test_ckan_backend_filters.py +5 -5
- udata/harvest/tests/ckan/test_dkan_backend.py +1 -1
- udata/harvest/tests/test_actions.py +27 -32
- udata/harvest/tests/test_api.py +23 -18
- udata/harvest/tests/test_dcat_backend.py +29 -29
- udata/routing.py +6 -0
- udata/static/chunks/{11.55ab79044cda0271b595.js → 11.822f6ccb39c92c796d13.js} +3 -3
- udata/static/chunks/{11.55ab79044cda0271b595.js.map → 11.822f6ccb39c92c796d13.js.map} +1 -1
- udata/static/chunks/{13.2d06442dd9a05d9777b5.js → 13.d9c1735d14038b94c17e.js} +2 -2
- udata/static/chunks/{13.2d06442dd9a05d9777b5.js.map → 13.d9c1735d14038b94c17e.js.map} +1 -1
- udata/static/chunks/{17.e8e4caaad5cb0cc0bacc.js → 17.81c57c0dedf812e43013.js} +2 -2
- udata/static/chunks/{17.e8e4caaad5cb0cc0bacc.js.map → 17.81c57c0dedf812e43013.js.map} +1 -1
- udata/static/chunks/{19.f03a102365af4315f9db.js → 19.8d03c06efcac6884bebe.js} +3 -3
- udata/static/chunks/{19.f03a102365af4315f9db.js.map → 19.8d03c06efcac6884bebe.js.map} +1 -1
- udata/static/chunks/{5.5660483641193b7f8295.js → 5.343ca020a2d38cec1a14.js} +3 -3
- udata/static/chunks/{5.5660483641193b7f8295.js.map → 5.343ca020a2d38cec1a14.js.map} +1 -1
- udata/static/chunks/{6.30dce49d17db07600b06.js → 6.a3b07de9dd2ca2d24e85.js} +3 -3
- udata/static/chunks/{6.30dce49d17db07600b06.js.map → 6.a3b07de9dd2ca2d24e85.js.map} +1 -1
- udata/static/chunks/{8.b58fcd977fcaf3415571.js → 8.462bb3029de008497675.js} +2 -2
- udata/static/chunks/{8.b58fcd977fcaf3415571.js.map → 8.462bb3029de008497675.js.map} +1 -1
- udata/static/common.js +1 -1
- udata/static/common.js.map +1 -1
- {udata-10.8.2.dev36872.dist-info → udata-10.8.2.dev36938.dist-info}/METADATA +2 -1
- {udata-10.8.2.dev36872.dist-info → udata-10.8.2.dev36938.dist-info}/RECORD +34 -34
- {udata-10.8.2.dev36872.dist-info → udata-10.8.2.dev36938.dist-info}/LICENSE +0 -0
- {udata-10.8.2.dev36872.dist-info → udata-10.8.2.dev36938.dist-info}/WHEEL +0 -0
- {udata-10.8.2.dev36872.dist-info → udata-10.8.2.dev36938.dist-info}/entry_points.txt +0 -0
- {udata-10.8.2.dev36872.dist-info → udata-10.8.2.dev36938.dist-info}/top_level.txt +0 -0
udata/harvest/actions.py
CHANGED
|
@@ -29,6 +29,11 @@ log = logging.getLogger(__name__)
|
|
|
29
29
|
DEFAULT_PAGE_SIZE = 10
|
|
30
30
|
|
|
31
31
|
|
|
32
|
+
def get_source(ident):
|
|
33
|
+
"""Get an harvest source given its ID or its slug"""
|
|
34
|
+
return HarvestSource.get(ident)
|
|
35
|
+
|
|
36
|
+
|
|
32
37
|
def list_backends():
|
|
33
38
|
"""List all available backends"""
|
|
34
39
|
return backends.get_all(current_app).values()
|
|
@@ -44,11 +49,6 @@ def list_sources(owner=None, deleted=False):
|
|
|
44
49
|
return list(sources)
|
|
45
50
|
|
|
46
51
|
|
|
47
|
-
def get_source(ident):
|
|
48
|
-
"""Get an harvest source given its ID or its slug"""
|
|
49
|
-
return HarvestSource.get(ident)
|
|
50
|
-
|
|
51
|
-
|
|
52
52
|
def get_job(ident):
|
|
53
53
|
"""Get an harvest job given its ID"""
|
|
54
54
|
return HarvestJob.objects.get(id=ident)
|
|
@@ -89,31 +89,28 @@ def create_source(
|
|
|
89
89
|
return source
|
|
90
90
|
|
|
91
91
|
|
|
92
|
-
def update_source(
|
|
92
|
+
def update_source(source: HarvestSource, data):
|
|
93
93
|
"""Update an harvest source"""
|
|
94
|
-
source = get_source(ident)
|
|
95
94
|
source.modify(**data)
|
|
96
95
|
signals.harvest_source_updated.send(source)
|
|
97
96
|
return source
|
|
98
97
|
|
|
99
98
|
|
|
100
|
-
def validate_source(
|
|
99
|
+
def validate_source(source: HarvestSource, comment=None):
|
|
101
100
|
"""Validate a source for automatic harvesting"""
|
|
102
|
-
source = get_source(ident)
|
|
103
101
|
source.validation.on = datetime.utcnow()
|
|
104
102
|
source.validation.comment = comment
|
|
105
103
|
source.validation.state = VALIDATION_ACCEPTED
|
|
106
104
|
if current_user.is_authenticated:
|
|
107
105
|
source.validation.by = current_user._get_current_object()
|
|
108
106
|
source.save()
|
|
109
|
-
schedule(
|
|
110
|
-
launch(
|
|
107
|
+
schedule(source, cron=current_app.config["HARVEST_DEFAULT_SCHEDULE"])
|
|
108
|
+
launch(source)
|
|
111
109
|
return source
|
|
112
110
|
|
|
113
111
|
|
|
114
|
-
def reject_source(
|
|
112
|
+
def reject_source(source: HarvestSource, comment):
|
|
115
113
|
"""Reject a source for automatic harvesting"""
|
|
116
|
-
source = get_source(ident)
|
|
117
114
|
source.validation.on = datetime.utcnow()
|
|
118
115
|
source.validation.comment = comment
|
|
119
116
|
source.validation.state = VALIDATION_REFUSED
|
|
@@ -123,18 +120,16 @@ def reject_source(ident, comment):
|
|
|
123
120
|
return source
|
|
124
121
|
|
|
125
122
|
|
|
126
|
-
def delete_source(
|
|
123
|
+
def delete_source(source: HarvestSource):
|
|
127
124
|
"""Delete an harvest source"""
|
|
128
|
-
source = get_source(ident)
|
|
129
125
|
source.deleted = datetime.utcnow()
|
|
130
126
|
source.save()
|
|
131
127
|
signals.harvest_source_deleted.send(source)
|
|
132
128
|
return source
|
|
133
129
|
|
|
134
130
|
|
|
135
|
-
def clean_source(
|
|
131
|
+
def clean_source(source: HarvestSource):
|
|
136
132
|
"""Deletes all datasets linked to a harvest source"""
|
|
137
|
-
source = get_source(ident)
|
|
138
133
|
datasets = Dataset.objects.filter(harvest__source_id=str(source.id))
|
|
139
134
|
for dataset in datasets:
|
|
140
135
|
dataset.deleted = datetime.utcnow()
|
|
@@ -180,22 +175,20 @@ def purge_jobs():
|
|
|
180
175
|
return HarvestJob.objects(created__lt=expiration).delete()
|
|
181
176
|
|
|
182
177
|
|
|
183
|
-
def run(
|
|
178
|
+
def run(source: HarvestSource):
|
|
184
179
|
"""Launch or resume an harvesting for a given source if none is running"""
|
|
185
|
-
source = get_source(ident)
|
|
186
180
|
cls = backends.get(current_app, source.backend)
|
|
187
181
|
backend = cls(source)
|
|
188
182
|
backend.harvest()
|
|
189
183
|
|
|
190
184
|
|
|
191
|
-
def launch(
|
|
185
|
+
def launch(source: HarvestSource):
|
|
192
186
|
"""Launch or resume an harvesting for a given source if none is running"""
|
|
193
|
-
return harvest.delay(
|
|
187
|
+
return harvest.delay(source.id)
|
|
194
188
|
|
|
195
189
|
|
|
196
|
-
def preview(
|
|
190
|
+
def preview(source: HarvestSource):
|
|
197
191
|
"""Preview an harvesting for a given source"""
|
|
198
|
-
source = get_source(ident)
|
|
199
192
|
cls = backends.get(current_app, source.backend)
|
|
200
193
|
max_items = current_app.config["HARVEST_PREVIEW_MAX_ITEMS"]
|
|
201
194
|
backend = cls(source, dryrun=True, max_items=max_items)
|
|
@@ -240,11 +233,15 @@ def preview_from_config(
|
|
|
240
233
|
|
|
241
234
|
|
|
242
235
|
def schedule(
|
|
243
|
-
|
|
236
|
+
source: HarvestSource,
|
|
237
|
+
cron=None,
|
|
238
|
+
minute="*",
|
|
239
|
+
hour="*",
|
|
240
|
+
day_of_week="*",
|
|
241
|
+
day_of_month="*",
|
|
242
|
+
month_of_year="*",
|
|
244
243
|
):
|
|
245
244
|
"""Schedule an harvesting on a source given a crontab"""
|
|
246
|
-
source = get_source(ident)
|
|
247
|
-
|
|
248
245
|
if cron:
|
|
249
246
|
minute, hour, day_of_month, month_of_year, day_of_week = cron.split()
|
|
250
247
|
|
|
@@ -273,9 +270,8 @@ def schedule(
|
|
|
273
270
|
return source
|
|
274
271
|
|
|
275
272
|
|
|
276
|
-
def unschedule(
|
|
273
|
+
def unschedule(source: HarvestSource):
|
|
277
274
|
"""Unschedule an harvesting on a source"""
|
|
278
|
-
source = get_source(ident)
|
|
279
275
|
if not source.periodic_task:
|
|
280
276
|
msg = "Harvesting on source {0} is ot scheduled".format(source.name)
|
|
281
277
|
raise ValueError(msg)
|
udata/harvest/api.py
CHANGED
|
@@ -300,59 +300,54 @@ class SourcesAPI(API):
|
|
|
300
300
|
return source, 201
|
|
301
301
|
|
|
302
302
|
|
|
303
|
-
@ns.route("/source/<
|
|
304
|
-
@api.param("ident", "A source ID or slug")
|
|
303
|
+
@ns.route("/source/<harvest_source:source>/", endpoint="harvest_source")
|
|
305
304
|
class SourceAPI(API):
|
|
306
305
|
@api.doc("get_harvest_source")
|
|
307
306
|
@api.marshal_with(source_fields)
|
|
308
|
-
def get(self,
|
|
307
|
+
def get(self, source: HarvestSource):
|
|
309
308
|
"""Get a single source given an ID or a slug"""
|
|
310
|
-
return
|
|
309
|
+
return source
|
|
311
310
|
|
|
312
311
|
@api.secure
|
|
313
312
|
@api.doc("update_harvest_source")
|
|
314
313
|
@api.expect(source_fields)
|
|
315
314
|
@api.marshal_with(source_fields)
|
|
316
|
-
def put(self,
|
|
315
|
+
def put(self, source: HarvestSource):
|
|
317
316
|
"""Update a harvest source"""
|
|
318
|
-
source = actions.get_source(ident)
|
|
319
317
|
OwnablePermission(source).test()
|
|
320
318
|
form = api.validate(HarvestSourceForm, source)
|
|
321
|
-
source = actions.update_source(
|
|
319
|
+
source = actions.update_source(source, form.data)
|
|
322
320
|
return source
|
|
323
321
|
|
|
324
322
|
@api.secure
|
|
325
323
|
@api.doc("delete_harvest_source")
|
|
326
324
|
@api.marshal_with(source_fields)
|
|
327
|
-
def delete(self,
|
|
328
|
-
source: HarvestSource = actions.get_source(ident)
|
|
325
|
+
def delete(self, source: HarvestSource):
|
|
329
326
|
OwnablePermission(source).test()
|
|
330
|
-
return actions.delete_source(
|
|
327
|
+
return actions.delete_source(source), 204
|
|
331
328
|
|
|
332
329
|
|
|
333
|
-
@ns.route("/source/<
|
|
334
|
-
@api.param("ident", "A source ID or slug")
|
|
330
|
+
@ns.route("/source/<harvest_source:source>/validate/", endpoint="validate_harvest_source")
|
|
335
331
|
class ValidateSourceAPI(API):
|
|
336
332
|
@api.doc("validate_harvest_source")
|
|
337
333
|
@api.secure(admin_permission)
|
|
338
334
|
@api.expect(validation_fields)
|
|
339
335
|
@api.marshal_with(source_fields)
|
|
340
|
-
def post(self,
|
|
336
|
+
def post(self, source: HarvestSource):
|
|
341
337
|
"""Validate or reject an harvest source"""
|
|
342
338
|
form = api.validate(HarvestSourceValidationForm)
|
|
343
339
|
if form.state.data == VALIDATION_ACCEPTED:
|
|
344
|
-
return actions.validate_source(
|
|
340
|
+
return actions.validate_source(source, form.comment.data)
|
|
345
341
|
else:
|
|
346
|
-
return actions.reject_source(
|
|
342
|
+
return actions.reject_source(source, form.comment.data)
|
|
347
343
|
|
|
348
344
|
|
|
349
|
-
@ns.route("/source/<
|
|
350
|
-
@api.param("ident", "A source ID or slug")
|
|
345
|
+
@ns.route("/source/<harvest_source:source>/run/", endpoint="run_harvest_source")
|
|
351
346
|
class RunSourceAPI(API):
|
|
352
347
|
@api.doc("run_harvest_source")
|
|
353
348
|
@api.secure
|
|
354
349
|
@api.marshal_with(source_fields)
|
|
355
|
-
def post(self,
|
|
350
|
+
def post(self, source: HarvestSource):
|
|
356
351
|
enabled = current_app.config.get("HARVEST_ENABLE_MANUAL_RUN")
|
|
357
352
|
if not enabled and not current_user.sysadmin:
|
|
358
353
|
api.abort(
|
|
@@ -360,39 +355,37 @@ class RunSourceAPI(API):
|
|
|
360
355
|
"Cannot run source manually. Please contact the platform if you need to reschedule the harvester.",
|
|
361
356
|
)
|
|
362
357
|
|
|
363
|
-
source: HarvestSource = actions.get_source(ident)
|
|
364
358
|
OwnablePermission(source).test()
|
|
365
359
|
|
|
366
360
|
if source.validation.state != VALIDATION_ACCEPTED:
|
|
367
361
|
api.abort(400, "Source is not validated. Please validate the source before running.")
|
|
368
362
|
|
|
369
|
-
actions.launch(
|
|
363
|
+
actions.launch(source)
|
|
370
364
|
|
|
371
365
|
return source
|
|
372
366
|
|
|
373
367
|
|
|
374
|
-
@ns.route("/source/<
|
|
375
|
-
@api.param("ident", "A source ID or slug")
|
|
368
|
+
@ns.route("/source/<harvest_source:source>/schedule/", endpoint="schedule_harvest_source")
|
|
376
369
|
class ScheduleSourceAPI(API):
|
|
377
370
|
@api.doc("schedule_harvest_source")
|
|
378
371
|
@api.secure(admin_permission)
|
|
379
372
|
@api.expect((str, "A cron expression"))
|
|
380
373
|
@api.marshal_with(source_fields)
|
|
381
|
-
def post(self,
|
|
374
|
+
def post(self, source: HarvestSource):
|
|
382
375
|
"""Schedule an harvest source"""
|
|
383
376
|
# Handle both syntax: quoted and unquoted
|
|
384
377
|
try:
|
|
385
378
|
data = request.json
|
|
386
379
|
except BadRequest:
|
|
387
380
|
data = request.data.decode("utf-8")
|
|
388
|
-
return actions.schedule(
|
|
381
|
+
return actions.schedule(source, data)
|
|
389
382
|
|
|
390
383
|
@api.doc("unschedule_harvest_source")
|
|
391
384
|
@api.secure(admin_permission)
|
|
392
385
|
@api.marshal_with(source_fields)
|
|
393
|
-
def delete(self,
|
|
386
|
+
def delete(self, source: HarvestSource):
|
|
394
387
|
"""Unschedule an harvest source"""
|
|
395
|
-
return actions.unschedule(
|
|
388
|
+
return actions.unschedule(source), 204
|
|
396
389
|
|
|
397
390
|
|
|
398
391
|
@ns.route("/source/preview/", endpoint="preview_harvest_source_config")
|
|
@@ -409,15 +402,14 @@ class PreviewSourceConfigAPI(API):
|
|
|
409
402
|
return actions.preview_from_config(**form.data)
|
|
410
403
|
|
|
411
404
|
|
|
412
|
-
@ns.route("/source/<
|
|
413
|
-
@api.param("ident", "A source ID or slug")
|
|
405
|
+
@ns.route("/source/<harvest_source:source>/preview/", endpoint="preview_harvest_source")
|
|
414
406
|
class PreviewSourceAPI(API):
|
|
415
407
|
@api.secure
|
|
416
408
|
@api.doc("preview_harvest_source")
|
|
417
409
|
@api.marshal_with(preview_job_fields)
|
|
418
|
-
def get(self,
|
|
410
|
+
def get(self, source: HarvestSource):
|
|
419
411
|
"""Preview a single harvest source given an ID or a slug"""
|
|
420
|
-
return actions.preview(
|
|
412
|
+
return actions.preview(source)
|
|
421
413
|
|
|
422
414
|
|
|
423
415
|
parser = api.parser()
|
|
@@ -427,15 +419,15 @@ parser.add_argument(
|
|
|
427
419
|
)
|
|
428
420
|
|
|
429
421
|
|
|
430
|
-
@ns.route("/source/<
|
|
422
|
+
@ns.route("/source/<harvest_source:source>/jobs/", endpoint="harvest_jobs")
|
|
431
423
|
class JobsAPI(API):
|
|
432
424
|
@api.doc("list_harvest_jobs")
|
|
433
425
|
@api.expect(parser)
|
|
434
426
|
@api.marshal_with(job_page_fields)
|
|
435
|
-
def get(self,
|
|
427
|
+
def get(self, source: HarvestSource):
|
|
436
428
|
"""List all jobs for a given source"""
|
|
437
429
|
args = parser.parse_args()
|
|
438
|
-
qs = HarvestJob.objects(source=
|
|
430
|
+
qs = HarvestJob.objects(source=source)
|
|
439
431
|
qs = qs.order_by("-created")
|
|
440
432
|
return qs.paginate(args["page"], args["page_size"])
|
|
441
433
|
|
udata/harvest/commands.py
CHANGED
|
@@ -44,7 +44,7 @@ def create(name, url, backend, frequency=None, owner=None, org=None):
|
|
|
44
44
|
@click.argument("identifier")
|
|
45
45
|
def validate(identifier):
|
|
46
46
|
"""Validate a source given its identifier"""
|
|
47
|
-
source = actions.validate_source(identifier)
|
|
47
|
+
source = actions.validate_source(actions.get_source(identifier))
|
|
48
48
|
log.info("Source %s (%s) has been validated", source.slug, str(source.id))
|
|
49
49
|
|
|
50
50
|
|
|
@@ -52,7 +52,7 @@ def validate(identifier):
|
|
|
52
52
|
def delete(identifier):
|
|
53
53
|
"""Delete a harvest source"""
|
|
54
54
|
log.info('Deleting source "%s"', identifier)
|
|
55
|
-
actions.delete_source(identifier)
|
|
55
|
+
actions.delete_source(actions.get_source(identifier))
|
|
56
56
|
log.info('Deleted source "%s"', identifier)
|
|
57
57
|
|
|
58
58
|
|
|
@@ -61,7 +61,7 @@ def delete(identifier):
|
|
|
61
61
|
def clean(identifier):
|
|
62
62
|
"""Delete all datasets linked to a harvest source"""
|
|
63
63
|
log.info(f'Cleaning source "{identifier}"')
|
|
64
|
-
num_of_datasets = actions.clean_source(identifier)
|
|
64
|
+
num_of_datasets = actions.clean_source(actions.get_source(identifier))
|
|
65
65
|
log.info(f'Cleaned source "{identifier}" - deleted {num_of_datasets} dataset(s)')
|
|
66
66
|
|
|
67
67
|
|
|
@@ -99,7 +99,7 @@ def backends():
|
|
|
99
99
|
def launch(identifier):
|
|
100
100
|
"""Launch a source harvesting on the workers"""
|
|
101
101
|
log.info('Launching harvest job for source "%s"', identifier)
|
|
102
|
-
actions.launch(identifier)
|
|
102
|
+
actions.launch(actions.get_source(identifier))
|
|
103
103
|
|
|
104
104
|
|
|
105
105
|
@grp.command()
|
|
@@ -107,7 +107,7 @@ def launch(identifier):
|
|
|
107
107
|
def run(identifier):
|
|
108
108
|
"""Run a harvester synchronously"""
|
|
109
109
|
log.info('Harvesting source "%s"', identifier)
|
|
110
|
-
actions.run(identifier)
|
|
110
|
+
actions.run(actions.get_source(identifier))
|
|
111
111
|
|
|
112
112
|
|
|
113
113
|
@grp.command()
|
|
@@ -121,7 +121,7 @@ def run(identifier):
|
|
|
121
121
|
@click.option("-M", "--month-of-year", default="*", help="The crontab expression for month of year")
|
|
122
122
|
def schedule(identifier, **kwargs):
|
|
123
123
|
"""Schedule a harvest job to run periodically"""
|
|
124
|
-
source = actions.schedule(identifier, **kwargs)
|
|
124
|
+
source = actions.schedule(actions.get_source(identifier), **kwargs)
|
|
125
125
|
msg = "Scheduled {source.name} with the following crontab: {cron}"
|
|
126
126
|
log.info(msg.format(source=source, cron=source.periodic_task.crontab))
|
|
127
127
|
|
|
@@ -130,7 +130,7 @@ def schedule(identifier, **kwargs):
|
|
|
130
130
|
@click.argument("identifier")
|
|
131
131
|
def unschedule(identifier):
|
|
132
132
|
"""Unschedule a periodical harvest job"""
|
|
133
|
-
source = actions.unschedule(identifier)
|
|
133
|
+
source = actions.unschedule(actions.get_source(identifier))
|
|
134
134
|
log.info('Unscheduled harvest source "%s"', source.name)
|
|
135
135
|
|
|
136
136
|
|
udata/harvest/tasks.py
CHANGED
|
@@ -14,7 +14,7 @@ def harvest(self, ident):
|
|
|
14
14
|
|
|
15
15
|
source = HarvestSource.get(ident)
|
|
16
16
|
if source.deleted or not source.active:
|
|
17
|
-
log.info('Ignoring inactive or deleted source "%s"',
|
|
17
|
+
log.info('Ignoring inactive or deleted source "%s"', source.id)
|
|
18
18
|
return # Ignore deleted and inactive sources
|
|
19
19
|
Backend = backends.get(current_app, source.backend)
|
|
20
20
|
backend = Backend(source)
|
|
@@ -96,7 +96,7 @@ def harvest_ckan(request, source, ckan, app, rmock):
|
|
|
96
96
|
)
|
|
97
97
|
|
|
98
98
|
with app.app_context():
|
|
99
|
-
actions.run(source
|
|
99
|
+
actions.run(source)
|
|
100
100
|
source.reload()
|
|
101
101
|
job = source.get_last_job()
|
|
102
102
|
assert len(job.items) == 1
|
|
@@ -565,7 +565,7 @@ def test_minimal_ckan_response(app, rmock):
|
|
|
565
565
|
status_code=200,
|
|
566
566
|
headers={"Content-Type": "application/json"},
|
|
567
567
|
)
|
|
568
|
-
actions.run(source
|
|
568
|
+
actions.run(source)
|
|
569
569
|
source.reload()
|
|
570
570
|
assert source.get_last_job().status == "done"
|
|
571
571
|
|
|
@@ -600,7 +600,7 @@ def test_flawed_ckan_response(app, rmock):
|
|
|
600
600
|
status_code=200,
|
|
601
601
|
headers={"Content-Type": "application/json"},
|
|
602
602
|
)
|
|
603
|
-
actions.run(source
|
|
603
|
+
actions.run(source)
|
|
604
604
|
source.reload()
|
|
605
605
|
assert source.get_last_job().status == "done-errors"
|
|
606
606
|
assert source.get_last_job().items[0].remote_id == _id
|
|
@@ -617,7 +617,7 @@ def test_flawed_ckan_response(app, rmock):
|
|
|
617
617
|
status_code=200,
|
|
618
618
|
headers={"Content-Type": "application/json"},
|
|
619
619
|
)
|
|
620
|
-
actions.run(source
|
|
620
|
+
actions.run(source)
|
|
621
621
|
source.reload()
|
|
622
622
|
assert source.get_last_job().status == "done-errors"
|
|
623
623
|
assert source.get_last_job().items[0].remote_id == name
|
|
@@ -662,7 +662,7 @@ def test_max_items(app, rmock):
|
|
|
662
662
|
status_code=200,
|
|
663
663
|
headers={"Content-Type": "application/json"},
|
|
664
664
|
)
|
|
665
|
-
actions.run(source
|
|
665
|
+
actions.run(source)
|
|
666
666
|
source.reload()
|
|
667
667
|
assert source.get_last_job().status == "done"
|
|
668
668
|
assert len(source.get_last_job().items) == 1
|
|
@@ -25,7 +25,7 @@ def test_html_error(rmock, code):
|
|
|
25
25
|
|
|
26
26
|
rmock.get(API_URL, text=html, status_code=code, headers={"Content-Type": "text/html"})
|
|
27
27
|
|
|
28
|
-
actions.run(source
|
|
28
|
+
actions.run(source)
|
|
29
29
|
|
|
30
30
|
source.reload()
|
|
31
31
|
|
|
@@ -45,7 +45,7 @@ def test_plain_text_error(rmock, code):
|
|
|
45
45
|
API_URL, text='"Some error"', status_code=code, headers={"Content-Type": "text/plain"}
|
|
46
46
|
)
|
|
47
47
|
|
|
48
|
-
actions.run(source
|
|
48
|
+
actions.run(source)
|
|
49
49
|
|
|
50
50
|
source.reload()
|
|
51
51
|
|
|
@@ -66,7 +66,7 @@ def test_200_plain_text_error(rmock):
|
|
|
66
66
|
|
|
67
67
|
rmock.get(API_URL, text='"Some error"', status_code=200, headers={"Content-Type": "text/plain"})
|
|
68
68
|
|
|
69
|
-
actions.run(source
|
|
69
|
+
actions.run(source)
|
|
70
70
|
|
|
71
71
|
source.reload()
|
|
72
72
|
|
|
@@ -84,7 +84,7 @@ def test_standard_api_json_error(rmock):
|
|
|
84
84
|
|
|
85
85
|
rmock.get(API_URL, json=json, status_code=200, headers={"Content-Type": "application/json"})
|
|
86
86
|
|
|
87
|
-
actions.run(source
|
|
87
|
+
actions.run(source)
|
|
88
88
|
|
|
89
89
|
source.reload()
|
|
90
90
|
|
|
@@ -106,7 +106,7 @@ def test_standard_api_json_error_with_details(rmock):
|
|
|
106
106
|
|
|
107
107
|
rmock.get(API_URL, json=json, status_code=200, headers={"Content-Type": "application/json"})
|
|
108
108
|
|
|
109
|
-
actions.run(source
|
|
109
|
+
actions.run(source)
|
|
110
110
|
|
|
111
111
|
source.reload()
|
|
112
112
|
|
|
@@ -129,7 +129,7 @@ def test_standard_api_json_error_with_details_and_type(rmock):
|
|
|
129
129
|
|
|
130
130
|
rmock.get(API_URL, json=json, status_code=200, headers={"Content-Type": "application/json"})
|
|
131
131
|
|
|
132
|
-
actions.run(source
|
|
132
|
+
actions.run(source)
|
|
133
133
|
|
|
134
134
|
source.reload()
|
|
135
135
|
|
|
@@ -26,7 +26,7 @@ def test_include_org_filter(ckan, rmock):
|
|
|
26
26
|
headers={"Content-Type": "application/json"},
|
|
27
27
|
)
|
|
28
28
|
|
|
29
|
-
actions.run(source
|
|
29
|
+
actions.run(source)
|
|
30
30
|
source.reload()
|
|
31
31
|
|
|
32
32
|
assert rmock.call_count == 1
|
|
@@ -50,7 +50,7 @@ def test_exclude_org_filter(ckan, rmock):
|
|
|
50
50
|
headers={"Content-Type": "application/json"},
|
|
51
51
|
)
|
|
52
52
|
|
|
53
|
-
actions.run(source
|
|
53
|
+
actions.run(source)
|
|
54
54
|
source.reload()
|
|
55
55
|
|
|
56
56
|
assert rmock.call_count == 1
|
|
@@ -72,7 +72,7 @@ def test_tag_filter(ckan, rmock):
|
|
|
72
72
|
headers={"Content-Type": "application/json"},
|
|
73
73
|
)
|
|
74
74
|
|
|
75
|
-
actions.run(source
|
|
75
|
+
actions.run(source)
|
|
76
76
|
source.reload()
|
|
77
77
|
|
|
78
78
|
assert rmock.call_count == 1
|
|
@@ -95,7 +95,7 @@ def test_exclude_tag_filter(ckan, rmock):
|
|
|
95
95
|
headers={"Content-Type": "application/json"},
|
|
96
96
|
)
|
|
97
97
|
|
|
98
|
-
actions.run(source
|
|
98
|
+
actions.run(source)
|
|
99
99
|
source.reload()
|
|
100
100
|
|
|
101
101
|
assert rmock.call_count == 1
|
|
@@ -122,7 +122,7 @@ def test_can_have_multiple_filters(ckan, rmock):
|
|
|
122
122
|
headers={"Content-Type": "application/json"},
|
|
123
123
|
)
|
|
124
124
|
|
|
125
|
-
actions.run(source
|
|
125
|
+
actions.run(source)
|
|
126
126
|
source.reload()
|
|
127
127
|
|
|
128
128
|
assert rmock.call_count == 1
|
|
@@ -54,7 +54,7 @@ def test_dkan_french_w_license(app, rmock):
|
|
|
54
54
|
rmock.get(
|
|
55
55
|
PACKAGE_SHOW_URL, json=data, status_code=200, headers={"Content-Type": "application/json"}
|
|
56
56
|
)
|
|
57
|
-
actions.run(source
|
|
57
|
+
actions.run(source)
|
|
58
58
|
source.reload()
|
|
59
59
|
assert source.get_last_job().status == "done"
|
|
60
60
|
|