diff --git a/Makefile b/Makefile index a6b8dc5972cf14e7a4f9dfeeefbc2de73c120336..8a0dc77d8ec252c8ccb6d4c08081ac130dd664b1 100644 --- a/Makefile +++ b/Makefile @@ -28,6 +28,16 @@ release: require-version worker: celery worker -A arkindex.project -l INFO --purge +test-fixtures: + export PGPASSWORD=devdata + psql -h 127.0.0.1 -p 9100 -U devuser -c 'ALTER DATABASE arkindex_dev RENAME TO arkindex_tmp_fixtures' template1 + psql -h 127.0.0.1 -p 9100 -U devuser -c 'CREATE DATABASE arkindex_dev' template1 + arkindex/manage.py migrate + arkindex/manage.py build_fixtures + arkindex/manage.py dumpdata --indent 4 documents images users > arkindex/documents/fixtures/data.json + psql -h 127.0.0.1 -p 9100 -U devuser -c 'DROP DATABASE arkindex_dev' template1 + psql -h 127.0.0.1 -p 9100 -U devuser -c 'ALTER DATABASE arkindex_tmp_fixtures RENAME TO arkindex_dev' template1 + require-docker-auth: @grep registry.gitlab.com ~/.docker/config.json > /dev/null || (echo "Docker Login on registry.gitlab.com"; docker login registry.gitlab.com) diff --git a/arkindex/documents/fixtures/data.json b/arkindex/documents/fixtures/data.json new file mode 100644 index 0000000000000000000000000000000000000000..3bfd00dbe35da109af7f60928d53d9f086fd8621 --- /dev/null +++ b/arkindex/documents/fixtures/data.json @@ -0,0 +1,1135 @@ +[ +{ + "model": "documents.corpus", + "pk": "himanis", + "fields": { + "name": "Himanis" + } +}, +{ + "model": "documents.corpus", + "pk": "test", + "fields": { + "name": "Unit Tests" + } +}, +{ + "model": "documents.elementpath", + "pk": "06592ee7-fc2d-4477-aa47-1ce06268dd8e", + "fields": { + "element": "ba22e17c-b93f-4683-b869-40588b483558", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\"]", + "ordering": 2 + } +}, +{ + "model": "documents.elementpath", + "pk": "09586b91-fed7-4a91-a4be-00a12d6b9b83", + "fields": { + "element": "cfd4952d-41ff-45f0-abe4-a904acf5350b", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "11eb3635-8c5a-4dc4-97d9-906467d92cb9", + "fields": { + "element": "c6b3f72f-1373-45c7-a218-c9b0bcf1c70f", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "157cfbab-6a6f-49cf-8dd3-212f5f277e68", + "fields": { + "element": "bc9f1cbd-0202-4075-9150-7e256bdbd485", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"a83083ae-6db0-4d3f-9dcb-c49e2a232696\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "4391ca9f-fa02-4540-aacd-8eb81dc19b29", + "fields": { + "element": "a83083ae-6db0-4d3f-9dcb-c49e2a232696", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\"]", + "ordering": 4 + } +}, +{ + "model": "documents.elementpath", + "pk": "4daddfe1-b994-4609-a7df-3119980c1b66", + "fields": { + "element": "f52d8907-aeac-45b1-b584-99c76a31f77b", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"ca3fa6e6-838b-4683-8cf9-f6ff75fa8e36\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "5039aafb-c74e-4658-9527-08f474fa1dd8", + "fields": { + "element": "bb32de06-561c-4c0d-94e0-c43720079cc3", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"ba22e17c-b93f-4683-b869-40588b483558\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "59e8a09c-865c-4846-af27-665c7501d74c", + "fields": { + "element": "6bf20744-97fa-4372-bcc0-5458bb5de3ce", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"c21ff1e2-694d-4310-97b6-d4a31cf0bfa3\"]", + "ordering": 2 + } +}, +{ + "model": "documents.elementpath", + "pk": "613d75de-cdf0-4303-90d0-98552d2fa2c6", + "fields": { + "element": "ca3fa6e6-838b-4683-8cf9-f6ff75fa8e36", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\"]", + "ordering": 2 + } +}, +{ + "model": "documents.elementpath", + "pk": "6373dce1-99c2-4405-8335-d5badae67780", + "fields": { + "element": "c31fa532-b498-4b22-9b81-5110ef02971d", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"c21ff1e2-694d-4310-97b6-d4a31cf0bfa3\"]", + "ordering": 1 + } +}, +{ + "model": "documents.elementpath", + "pk": "671a39a9-a6c8-491b-a5fa-6ccec6b78358", + "fields": { + "element": "59741867-4b09-4874-afab-86f931d2e223", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"c21ff1e2-694d-4310-97b6-d4a31cf0bfa3\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "7426e036-a6f5-462e-bb3b-52a8d6750a56", + "fields": { + "element": "4d9be55f-e873-4e21-81e8-144414dc4668", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"3901fbac-ab69-4fa5-9e8e-e973ec684873\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "83f8aa10-f2df-446e-8c79-a185f08ad499", + "fields": { + "element": "c6d1ae4d-5bf1-4167-ae28-6518c1b572c2", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"ab6fa45a-f1fc-4b95-a0fb-db59b5edd717\"]", + "ordering": 2 + } +}, +{ + "model": "documents.elementpath", + "pk": "978cc83e-2a8e-4416-9db1-8d820007795e", + "fields": { + "element": "8069f69b-3f46-47bf-9492-4aeaca1d3a50", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"ba22e17c-b93f-4683-b869-40588b483558\"]", + "ordering": 1 + } +}, +{ + "model": "documents.elementpath", + "pk": "9d6e58d9-b44c-4764-ba98-f7b592c03a35", + "fields": { + "element": "3901fbac-ab69-4fa5-9e8e-e973ec684873", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\"]", + "ordering": 3 + } +}, +{ + "model": "documents.elementpath", + "pk": "a5416544-7779-4e08-973e-67f7f241b8a5", + "fields": { + "element": "280577a2-37ea-4283-bb8a-5a41bd4158be", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"fd3ee4b9-edd2-4f82-9216-a1160bf890d4\"]", + "ordering": 1 + } +}, +{ + "model": "documents.elementpath", + "pk": "ae129f4d-44cd-4521-a366-f1e6308c2c0e", + "fields": { + "element": "6c17e8e6-71af-4a7d-8bdb-f21532fc024d", + "path": "[\"1b2ea32f-6009-4a4f-aa78-fafebbbcbacb\", \"0a47d859-a5ac-41c6-97d8-878da5fefbf1\"]", + "ordering": 1 + } +}, +{ + "model": "documents.elementpath", + "pk": "b493410b-c0fa-4a80-87b0-5ba50bff6440", + "fields": { + "element": "c21ff1e2-694d-4310-97b6-d4a31cf0bfa3", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "b92d349a-df0b-4451-8e28-8d6790af5e46", + "fields": { + "element": "fd3ee4b9-edd2-4f82-9216-a1160bf890d4", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\"]", + "ordering": 1 + } +}, +{ + "model": "documents.elementpath", + "pk": "ba4f90af-9d39-45f9-b2ba-6ac06780563e", + "fields": { + "element": "9b857bbf-c8b6-4e8c-8783-18bf1f033290", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"fd3ee4b9-edd2-4f82-9216-a1160bf890d4\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "c256c25c-16d0-4ce1-9967-e95799b2c3c8", + "fields": { + "element": "478a271b-a93b-4730-89fc-8b486fd7b0f2", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"cfd4952d-41ff-45f0-abe4-a904acf5350b\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "c8176f15-12da-4fbf-a643-6b9b97ff3b3d", + "fields": { + "element": "0a47d859-a5ac-41c6-97d8-878da5fefbf1", + "path": "[\"1b2ea32f-6009-4a4f-aa78-fafebbbcbacb\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "ce847918-cffc-4665-bb5c-df93ee05aff5", + "fields": { + "element": "87f549c2-581d-4290-b641-75e73926968e", + "path": "[\"1b2ea32f-6009-4a4f-aa78-fafebbbcbacb\", \"0a47d859-a5ac-41c6-97d8-878da5fefbf1\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "d0d0e0c9-4712-420f-8026-c5994c476dd1", + "fields": { + "element": "ce80f464-5f47-4155-b596-bafe3465c102", + "path": "[\"1b2ea32f-6009-4a4f-aa78-fafebbbcbacb\", \"0a47d859-a5ac-41c6-97d8-878da5fefbf1\"]", + "ordering": 2 + } +}, +{ + "model": "documents.elementpath", + "pk": "eb6d5273-ee51-4ffe-8a07-7d4e92b41368", + "fields": { + "element": "1327dc18-e5c7-44b0-91e6-9dfee3417ce9", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"ab6fa45a-f1fc-4b95-a0fb-db59b5edd717\"]", + "ordering": 0 + } +}, +{ + "model": "documents.elementpath", + "pk": "f00c6557-0585-4535-88fa-34a5262dc9c6", + "fields": { + "element": "58343ea9-176f-434c-a9ed-22f975b79968", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"ba22e17c-b93f-4683-b869-40588b483558\"]", + "ordering": 2 + } +}, +{ + "model": "documents.elementpath", + "pk": "f230e413-de34-4d2b-9698-5816bc72eea5", + "fields": { + "element": "ab6fa45a-f1fc-4b95-a0fb-db59b5edd717", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\"]", + "ordering": 1 + } +}, +{ + "model": "documents.elementpath", + "pk": "f81727f5-1f9f-4d9b-b945-fd4b696bb1e1", + "fields": { + "element": "9ef69659-7f7c-4204-9ceb-dbdc2d8daec3", + "path": "[\"fa275cab-d830-4f08-a227-6dd4b70ee377\", \"c6b3f72f-1373-45c7-a218-c9b0bcf1c70f\", \"ab6fa45a-f1fc-4b95-a0fb-db59b5edd717\"]", + "ordering": 1 + } +}, +{ + "model": "documents.element", + "pk": "0a47d859-a5ac-41c6-97d8-878da5fefbf1", + "fields": { + "created": "2018-07-24T08:18:54.839Z", + "updated": "2018-07-24T08:18:54.839Z", + "corpus": "test", + "type": "register", + "name": "Register 2", + "zone": null + } +}, +{ + "model": "documents.element", + "pk": "1327dc18-e5c7-44b0-91e6-9dfee3417ce9", + "fields": { + "created": "2018-07-24T08:18:54.980Z", + "updated": "2018-07-24T08:18:54.980Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "d94e1f63-584d-423f-9d66-966362e413a5" + } +}, +{ + "model": "documents.element", + "pk": "1b2ea32f-6009-4a4f-aa78-fafebbbcbacb", + "fields": { + "created": "2018-07-24T08:18:54.831Z", + "updated": "2018-07-24T08:18:54.831Z", + "corpus": "test", + "type": "volume", + "name": "Volume 2", + "zone": null + } +}, +{ + "model": "documents.element", + "pk": "280577a2-37ea-4283-bb8a-5a41bd4158be", + "fields": { + "created": "2018-07-24T08:18:55.109Z", + "updated": "2018-07-24T08:18:55.109Z", + "corpus": "test", + "type": "surface", + "name": "Surface C", + "zone": "ee7b9b2b-ee1d-49fc-8192-a03c16a03364" + } +}, +{ + "model": "documents.element", + "pk": "3901fbac-ab69-4fa5-9e8e-e973ec684873", + "fields": { + "created": "2018-07-24T08:18:55.059Z", + "updated": "2018-07-24T08:18:55.059Z", + "corpus": "test", + "type": "act", + "name": "Act 4", + "zone": null + } +}, +{ + "model": "documents.element", + "pk": "478a271b-a93b-4730-89fc-8b486fd7b0f2", + "fields": { + "created": "2018-07-24T08:18:55.103Z", + "updated": "2018-07-24T08:18:55.103Z", + "corpus": "test", + "type": "surface", + "name": "Surface A", + "zone": "b968bc1a-2c25-47e3-b49b-d6a05dc6d245" + } +}, +{ + "model": "documents.element", + "pk": "4d9be55f-e873-4e21-81e8-144414dc4668", + "fields": { + "created": "2018-07-24T08:18:55.114Z", + "updated": "2018-07-24T08:18:55.114Z", + "corpus": "test", + "type": "surface", + "name": "Surface E", + "zone": "8b777c07-2cf5-4b47-b407-a19dfc27fcc9" + } +}, +{ + "model": "documents.element", + "pk": "58343ea9-176f-434c-a9ed-22f975b79968", + "fields": { + "created": "2018-07-24T08:18:55.041Z", + "updated": "2018-07-24T08:18:55.041Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "c58b425e-1bdf-4c0d-860c-28e6793db75f" + } +}, +{ + "model": "documents.element", + "pk": "59741867-4b09-4874-afab-86f931d2e223", + "fields": { + "created": "2018-07-24T08:18:54.945Z", + "updated": "2018-07-24T08:18:54.945Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "cc592547-529e-4289-8351-53fe6a5cc55c" + } +}, +{ + "model": "documents.element", + "pk": "6bf20744-97fa-4372-bcc0-5458bb5de3ce", + "fields": { + "created": "2018-07-24T08:18:54.968Z", + "updated": "2018-07-24T08:18:54.968Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "af98c80b-e1b5-4b05-9771-d28e9e543c85" + } +}, +{ + "model": "documents.element", + "pk": "6c17e8e6-71af-4a7d-8bdb-f21532fc024d", + "fields": { + "created": "2018-07-24T08:18:54.916Z", + "updated": "2018-07-24T08:18:54.916Z", + "corpus": "test", + "type": "page", + "name": "Volume 2, page 1v", + "zone": "1542f839-401b-4cf7-8ef1-afc02f6f3cc1" + } +}, +{ + "model": "documents.element", + "pk": "8069f69b-3f46-47bf-9492-4aeaca1d3a50", + "fields": { + "created": "2018-07-24T08:18:55.029Z", + "updated": "2018-07-24T08:18:55.029Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "c50126f5-682d-42ed-ab2d-f359717b81ad" + } +}, +{ + "model": "documents.element", + "pk": "87f549c2-581d-4290-b641-75e73926968e", + "fields": { + "created": "2018-07-24T08:18:54.913Z", + "updated": "2018-07-24T08:18:54.913Z", + "corpus": "test", + "type": "page", + "name": "Volume 2, page 1r", + "zone": "0554b559-3f85-40d7-b531-9c4a159e06e2" + } +}, +{ + "model": "documents.element", + "pk": "9b857bbf-c8b6-4e8c-8783-18bf1f033290", + "fields": { + "created": "2018-07-24T08:18:55.106Z", + "updated": "2018-07-24T08:18:55.106Z", + "corpus": "test", + "type": "surface", + "name": "Surface B", + "zone": "26eb4783-b8c9-4768-b55f-0f61f3512659" + } +}, +{ + "model": "documents.element", + "pk": "9ef69659-7f7c-4204-9ceb-dbdc2d8daec3", + "fields": { + "created": "2018-07-24T08:18:54.992Z", + "updated": "2018-07-24T08:18:54.992Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "2f0c6b20-89dc-45fe-9ce7-4b4cd6b3dd03" + } +}, +{ + "model": "documents.element", + "pk": "a83083ae-6db0-4d3f-9dcb-c49e2a232696", + "fields": { + "created": "2018-07-24T08:18:55.062Z", + "updated": "2018-07-24T08:18:55.062Z", + "corpus": "test", + "type": "act", + "name": "Act 5", + "zone": null + } +}, +{ + "model": "documents.element", + "pk": "ab6fa45a-f1fc-4b95-a0fb-db59b5edd717", + "fields": { + "created": "2018-07-24T08:18:54.883Z", + "updated": "2018-07-24T08:18:54.883Z", + "corpus": "test", + "type": "page", + "name": "Volume 1, page 1v", + "zone": "1dff74fb-a607-4118-a8d3-e1137d4fe122" + } +}, +{ + "model": "documents.element", + "pk": "ba22e17c-b93f-4683-b869-40588b483558", + "fields": { + "created": "2018-07-24T08:18:54.886Z", + "updated": "2018-07-24T08:18:54.886Z", + "corpus": "test", + "type": "page", + "name": "Volume 1, page 2r", + "zone": "a8159284-10b7-423b-a199-8fe2abe949c8" + } +}, +{ + "model": "documents.element", + "pk": "bb32de06-561c-4c0d-94e0-c43720079cc3", + "fields": { + "created": "2018-07-24T08:18:55.017Z", + "updated": "2018-07-24T08:18:55.017Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "b01704a9-23ec-4a79-8ec3-476042697bb9" + } +}, +{ + "model": "documents.element", + "pk": "bc9f1cbd-0202-4075-9150-7e256bdbd485", + "fields": { + "created": "2018-07-24T08:18:55.117Z", + "updated": "2018-07-24T08:18:55.117Z", + "corpus": "test", + "type": "surface", + "name": "Surface F", + "zone": "e5b7b231-2071-4521-a413-5cda61dcf909" + } +}, +{ + "model": "documents.element", + "pk": "c21ff1e2-694d-4310-97b6-d4a31cf0bfa3", + "fields": { + "created": "2018-07-24T08:18:54.879Z", + "updated": "2018-07-24T08:18:54.879Z", + "corpus": "test", + "type": "page", + "name": "Volume 1, page 1r", + "zone": "26be1b53-bd37-4c2c-9cba-47c2c82403ea" + } +}, +{ + "model": "documents.element", + "pk": "c31fa532-b498-4b22-9b81-5110ef02971d", + "fields": { + "created": "2018-07-24T08:18:54.957Z", + "updated": "2018-07-24T08:18:54.957Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "286f8048-7b6e-4e4e-9664-22296303d47d" + } +}, +{ + "model": "documents.element", + "pk": "c6b3f72f-1373-45c7-a218-c9b0bcf1c70f", + "fields": { + "created": "2018-07-24T08:18:54.835Z", + "updated": "2018-07-24T08:18:54.835Z", + "corpus": "test", + "type": "register", + "name": "Register 1", + "zone": null + } +}, +{ + "model": "documents.element", + "pk": "c6d1ae4d-5bf1-4167-ae28-6518c1b572c2", + "fields": { + "created": "2018-07-24T08:18:55.004Z", + "updated": "2018-07-24T08:18:55.004Z", + "corpus": "test", + "type": "word", + "name": "", + "zone": "9833b904-5e2f-4642-a399-9c862068c734" + } +}, +{ + "model": "documents.element", + "pk": "ca3fa6e6-838b-4683-8cf9-f6ff75fa8e36", + "fields": { + "created": "2018-07-24T08:18:55.057Z", + "updated": "2018-07-24T08:18:55.057Z", + "corpus": "test", + "type": "act", + "name": "Act 3", + "zone": null + } +}, +{ + "model": "documents.element", + "pk": "ce80f464-5f47-4155-b596-bafe3465c102", + "fields": { + "created": "2018-07-24T08:18:54.919Z", + "updated": "2018-07-24T08:18:54.919Z", + "corpus": "test", + "type": "page", + "name": "Volume 2, page 2r", + "zone": "699eed11-e91a-448e-bd3e-4216765aa80e" + } +}, +{ + "model": "documents.element", + "pk": "cfd4952d-41ff-45f0-abe4-a904acf5350b", + "fields": { + "created": "2018-07-24T08:18:55.051Z", + "updated": "2018-07-24T08:18:55.051Z", + "corpus": "test", + "type": "act", + "name": "Act 1", + "zone": null + } +}, +{ + "model": "documents.element", + "pk": "f52d8907-aeac-45b1-b584-99c76a31f77b", + "fields": { + "created": "2018-07-24T08:18:55.112Z", + "updated": "2018-07-24T08:18:55.112Z", + "corpus": "test", + "type": "surface", + "name": "Surface D", + "zone": "87869157-a183-4015-839b-9fce89cce4f0" + } +}, +{ + "model": "documents.element", + "pk": "fa275cab-d830-4f08-a227-6dd4b70ee377", + "fields": { + "created": "2018-07-24T08:18:54.826Z", + "updated": "2018-07-24T08:18:54.826Z", + "corpus": "test", + "type": "volume", + "name": "Volume 1", + "zone": null + } +}, +{ + "model": "documents.element", + "pk": "fd3ee4b9-edd2-4f82-9216-a1160bf890d4", + "fields": { + "created": "2018-07-24T08:18:55.054Z", + "updated": "2018-07-24T08:18:55.054Z", + "corpus": "test", + "type": "act", + "name": "Act 2", + "zone": null + } +}, +{ + "model": "documents.page", + "pk": "6c17e8e6-71af-4a7d-8bdb-f21532fc024d", + "fields": { + "folio": "1v", + "page_type": "page", + "nb": 1, + "direction": "verso", + "complement": null + } +}, +{ + "model": "documents.page", + "pk": "87f549c2-581d-4290-b641-75e73926968e", + "fields": { + "folio": "1r", + "page_type": "page", + "nb": 1, + "direction": "recto", + "complement": null + } +}, +{ + "model": "documents.page", + "pk": "ab6fa45a-f1fc-4b95-a0fb-db59b5edd717", + "fields": { + "folio": "1v", + "page_type": "page", + "nb": 1, + "direction": "verso", + "complement": null + } +}, +{ + "model": "documents.page", + "pk": "ba22e17c-b93f-4683-b869-40588b483558", + "fields": { + "folio": "2r", + "page_type": "page", + "nb": 2, + "direction": "recto", + "complement": null + } +}, +{ + "model": "documents.page", + "pk": "c21ff1e2-694d-4310-97b6-d4a31cf0bfa3", + "fields": { + "folio": "1r", + "page_type": "page", + "nb": 1, + "direction": "recto", + "complement": null + } +}, +{ + "model": "documents.page", + "pk": "ce80f464-5f47-4155-b596-bafe3465c102", + "fields": { + "folio": "2r", + "page_type": "page", + "nb": 2, + "direction": "recto", + "complement": null + } +}, +{ + "model": "documents.act", + "pk": "3901fbac-ab69-4fa5-9e8e-e973ec684873", + "fields": { + "number": "4", + "folio": "2r" + } +}, +{ + "model": "documents.act", + "pk": "a83083ae-6db0-4d3f-9dcb-c49e2a232696", + "fields": { + "number": "5", + "folio": "2r" + } +}, +{ + "model": "documents.act", + "pk": "ca3fa6e6-838b-4683-8cf9-f6ff75fa8e36", + "fields": { + "number": "3", + "folio": "2r" + } +}, +{ + "model": "documents.act", + "pk": "cfd4952d-41ff-45f0-abe4-a904acf5350b", + "fields": { + "number": "1", + "folio": "1r" + } +}, +{ + "model": "documents.act", + "pk": "fd3ee4b9-edd2-4f82-9216-a1160bf890d4", + "fields": { + "number": "2", + "folio": "1r-1v" + } +}, +{ + "model": "documents.transcription", + "pk": "1327dc18-e5c7-44b0-91e6-9dfee3417ce9", + "fields": { + "line": null, + "text": "PARIS", + "score": 1.0 + } +}, +{ + "model": "documents.transcription", + "pk": "58343ea9-176f-434c-a9ed-22f975b79968", + "fields": { + "line": null, + "text": "DATUM", + "score": 1.0 + } +}, +{ + "model": "documents.transcription", + "pk": "59741867-4b09-4874-afab-86f931d2e223", + "fields": { + "line": null, + "text": "PARIS", + "score": 1.0 + } +}, +{ + "model": "documents.transcription", + "pk": "6bf20744-97fa-4372-bcc0-5458bb5de3ce", + "fields": { + "line": null, + "text": "DATUM", + "score": 1.0 + } +}, +{ + "model": "documents.transcription", + "pk": "8069f69b-3f46-47bf-9492-4aeaca1d3a50", + "fields": { + "line": null, + "text": "ROY", + "score": 1.0 + } +}, +{ + "model": "documents.transcription", + "pk": "9ef69659-7f7c-4204-9ceb-dbdc2d8daec3", + "fields": { + "line": null, + "text": "ROY", + "score": 1.0 + } +}, +{ + "model": "documents.transcription", + "pk": "bb32de06-561c-4c0d-94e0-c43720079cc3", + "fields": { + "line": null, + "text": "PARIS", + "score": 1.0 + } +}, +{ + "model": "documents.transcription", + "pk": "c31fa532-b498-4b22-9b81-5110ef02971d", + "fields": { + "line": null, + "text": "ROY", + "score": 1.0 + } +}, +{ + "model": "documents.transcription", + "pk": "c6d1ae4d-5bf1-4167-ae28-6518c1b572c2", + "fields": { + "line": null, + "text": "DATUM", + "score": 1.0 + } +}, +{ + "model": "images.imageserver", + "pk": 1, + "fields": { + "name": "Test Server", + "url": "http://server", + "created": "2018-07-24T08:18:54.795Z", + "updated": "2018-07-24T08:18:54.795Z" + } +}, +{ + "model": "images.image", + "pk": "195299b4-da0c-4499-a67c-7f926e63116f", + "fields": { + "created": "2018-07-24T08:18:54.800Z", + "updated": "2018-07-24T08:18:54.800Z", + "server": 1, + "path": "img2", + "width": 1000, + "height": 1000, + "status": "unchecked" + } +}, +{ + "model": "images.image", + "pk": "2feedc50-07d5-41bd-b720-ba2a2ce85bb2", + "fields": { + "created": "2018-07-24T08:18:54.806Z", + "updated": "2018-07-24T08:18:54.806Z", + "server": 1, + "path": "img5", + "width": 1000, + "height": 1000, + "status": "unchecked" + } +}, +{ + "model": "images.image", + "pk": "37762fff-fc51-4880-b1e0-5c7470e4a54b", + "fields": { + "created": "2018-07-24T08:18:54.804Z", + "updated": "2018-07-24T08:18:54.804Z", + "server": 1, + "path": "img4", + "width": 1000, + "height": 1000, + "status": "unchecked" + } +}, +{ + "model": "images.image", + "pk": "42d18a7a-65d9-4b52-b42a-ed0b6c07bceb", + "fields": { + "created": "2018-07-24T08:18:54.798Z", + "updated": "2018-07-24T08:18:54.798Z", + "server": 1, + "path": "img1", + "width": 1000, + "height": 1000, + "status": "unchecked" + } +}, +{ + "model": "images.image", + "pk": "c01f2ae6-abea-4a21-847f-6de9919cb91d", + "fields": { + "created": "2018-07-24T08:18:54.802Z", + "updated": "2018-07-24T08:18:54.802Z", + "server": 1, + "path": "img3", + "width": 1000, + "height": 1000, + "status": "unchecked" + } +}, +{ + "model": "images.image", + "pk": "f298ee15-f126-44bc-ae22-459d18537e6f", + "fields": { + "created": "2018-07-24T08:18:54.808Z", + "updated": "2018-07-24T08:18:54.808Z", + "server": 1, + "path": "img6", + "width": 1000, + "height": 1000, + "status": "unchecked" + } +}, +{ + "model": "images.zone", + "pk": "0554b559-3f85-40d7-b531-9c4a159e06e2", + "fields": { + "created": "2018-07-24T08:18:54.817Z", + "updated": "2018-07-24T08:18:54.817Z", + "image": "37762fff-fc51-4880-b1e0-5c7470e4a54b", + "polygon": "Polygon((0,0), (1000,0), (1000,1000), (0,1000), (0,0))" + } +}, +{ + "model": "images.zone", + "pk": "1542f839-401b-4cf7-8ef1-afc02f6f3cc1", + "fields": { + "created": "2018-07-24T08:18:54.819Z", + "updated": "2018-07-24T08:18:54.819Z", + "image": "2feedc50-07d5-41bd-b720-ba2a2ce85bb2", + "polygon": "Polygon((0,0), (1000,0), (1000,1000), (0,1000), (0,0))" + } +}, +{ + "model": "images.zone", + "pk": "1dff74fb-a607-4118-a8d3-e1137d4fe122", + "fields": { + "created": "2018-07-24T08:18:54.813Z", + "updated": "2018-07-24T08:18:54.813Z", + "image": "195299b4-da0c-4499-a67c-7f926e63116f", + "polygon": "Polygon((0,0), (1000,0), (1000,1000), (0,1000), (0,0))" + } +}, +{ + "model": "images.zone", + "pk": "26be1b53-bd37-4c2c-9cba-47c2c82403ea", + "fields": { + "created": "2018-07-24T08:18:54.810Z", + "updated": "2018-07-24T08:18:54.810Z", + "image": "42d18a7a-65d9-4b52-b42a-ed0b6c07bceb", + "polygon": "Polygon((0,0), (1000,0), (1000,1000), (0,1000), (0,0))" + } +}, +{ + "model": "images.zone", + "pk": "26eb4783-b8c9-4768-b55f-0f61f3512659", + "fields": { + "created": "2018-07-24T08:18:55.105Z", + "updated": "2018-07-24T08:18:55.105Z", + "image": "42d18a7a-65d9-4b52-b42a-ed0b6c07bceb", + "polygon": "Polygon((600,600), (1000,600), (1000,1000), (600,1000), (600,600))" + } +}, +{ + "model": "images.zone", + "pk": "286f8048-7b6e-4e4e-9664-22296303d47d", + "fields": { + "created": "2018-07-24T08:18:54.955Z", + "updated": "2018-07-24T08:18:54.955Z", + "image": "42d18a7a-65d9-4b52-b42a-ed0b6c07bceb", + "polygon": "Polygon((400,400), (500,400), (500,500), (400,500), (400,400))" + } +}, +{ + "model": "images.zone", + "pk": "2f0c6b20-89dc-45fe-9ce7-4b4cd6b3dd03", + "fields": { + "created": "2018-07-24T08:18:54.990Z", + "updated": "2018-07-24T08:18:54.990Z", + "image": "195299b4-da0c-4499-a67c-7f926e63116f", + "polygon": "Polygon((400,400), (500,400), (500,500), (400,500), (400,400))" + } +}, +{ + "model": "images.zone", + "pk": "699eed11-e91a-448e-bd3e-4216765aa80e", + "fields": { + "created": "2018-07-24T08:18:54.821Z", + "updated": "2018-07-24T08:18:54.821Z", + "image": "f298ee15-f126-44bc-ae22-459d18537e6f", + "polygon": "Polygon((0,0), (1000,0), (1000,1000), (0,1000), (0,0))" + } +}, +{ + "model": "images.zone", + "pk": "87869157-a183-4015-839b-9fce89cce4f0", + "fields": { + "created": "2018-07-24T08:18:55.110Z", + "updated": "2018-07-24T08:18:55.110Z", + "image": "c01f2ae6-abea-4a21-847f-6de9919cb91d", + "polygon": "Polygon((0,0), (300,0), (300,300), (0,300), (0,0))" + } +}, +{ + "model": "images.zone", + "pk": "8b777c07-2cf5-4b47-b407-a19dfc27fcc9", + "fields": { + "created": "2018-07-24T08:18:55.113Z", + "updated": "2018-07-24T08:18:55.113Z", + "image": "c01f2ae6-abea-4a21-847f-6de9919cb91d", + "polygon": "Polygon((300,300), (600,300), (600,600), (300,600), (300,300))" + } +}, +{ + "model": "images.zone", + "pk": "9833b904-5e2f-4642-a399-9c862068c734", + "fields": { + "created": "2018-07-24T08:18:55.001Z", + "updated": "2018-07-24T08:18:55.002Z", + "image": "195299b4-da0c-4499-a67c-7f926e63116f", + "polygon": "Polygon((700,700), (800,700), (800,800), (700,800), (700,700))" + } +}, +{ + "model": "images.zone", + "pk": "a8159284-10b7-423b-a199-8fe2abe949c8", + "fields": { + "created": "2018-07-24T08:18:54.815Z", + "updated": "2018-07-24T08:18:54.815Z", + "image": "c01f2ae6-abea-4a21-847f-6de9919cb91d", + "polygon": "Polygon((0,0), (1000,0), (1000,1000), (0,1000), (0,0))" + } +}, +{ + "model": "images.zone", + "pk": "af98c80b-e1b5-4b05-9771-d28e9e543c85", + "fields": { + "created": "2018-07-24T08:18:54.966Z", + "updated": "2018-07-24T08:18:54.966Z", + "image": "42d18a7a-65d9-4b52-b42a-ed0b6c07bceb", + "polygon": "Polygon((700,700), (800,700), (800,800), (700,800), (700,700))" + } +}, +{ + "model": "images.zone", + "pk": "b01704a9-23ec-4a79-8ec3-476042697bb9", + "fields": { + "created": "2018-07-24T08:18:55.014Z", + "updated": "2018-07-24T08:18:55.014Z", + "image": "c01f2ae6-abea-4a21-847f-6de9919cb91d", + "polygon": "Polygon((100,100), (200,100), (200,200), (100,200), (100,100))" + } +}, +{ + "model": "images.zone", + "pk": "b968bc1a-2c25-47e3-b49b-d6a05dc6d245", + "fields": { + "created": "2018-07-24T08:18:55.101Z", + "updated": "2018-07-24T08:18:55.101Z", + "image": "42d18a7a-65d9-4b52-b42a-ed0b6c07bceb", + "polygon": "Polygon((0,0), (600,0), (600,600), (0,600), (0,0))" + } +}, +{ + "model": "images.zone", + "pk": "c50126f5-682d-42ed-ab2d-f359717b81ad", + "fields": { + "created": "2018-07-24T08:18:55.027Z", + "updated": "2018-07-24T08:18:55.027Z", + "image": "c01f2ae6-abea-4a21-847f-6de9919cb91d", + "polygon": "Polygon((400,400), (500,400), (500,500), (400,500), (400,400))" + } +}, +{ + "model": "images.zone", + "pk": "c58b425e-1bdf-4c0d-860c-28e6793db75f", + "fields": { + "created": "2018-07-24T08:18:55.038Z", + "updated": "2018-07-24T08:18:55.038Z", + "image": "c01f2ae6-abea-4a21-847f-6de9919cb91d", + "polygon": "Polygon((700,700), (800,700), (800,800), (700,800), (700,700))" + } +}, +{ + "model": "images.zone", + "pk": "cc592547-529e-4289-8351-53fe6a5cc55c", + "fields": { + "created": "2018-07-24T08:18:54.943Z", + "updated": "2018-07-24T08:18:54.943Z", + "image": "42d18a7a-65d9-4b52-b42a-ed0b6c07bceb", + "polygon": "Polygon((100,100), (200,100), (200,200), (100,200), (100,100))" + } +}, +{ + "model": "images.zone", + "pk": "d94e1f63-584d-423f-9d66-966362e413a5", + "fields": { + "created": "2018-07-24T08:18:54.978Z", + "updated": "2018-07-24T08:18:54.978Z", + "image": "195299b4-da0c-4499-a67c-7f926e63116f", + "polygon": "Polygon((100,100), (200,100), (200,200), (100,200), (100,100))" + } +}, +{ + "model": "images.zone", + "pk": "e5b7b231-2071-4521-a413-5cda61dcf909", + "fields": { + "created": "2018-07-24T08:18:55.116Z", + "updated": "2018-07-24T08:18:55.116Z", + "image": "c01f2ae6-abea-4a21-847f-6de9919cb91d", + "polygon": "Polygon((600,600), (1000,600), (1000,1000), (600,1000), (600,600))" + } +}, +{ + "model": "images.zone", + "pk": "ee7b9b2b-ee1d-49fc-8192-a03c16a03364", + "fields": { + "created": "2018-07-24T08:18:55.107Z", + "updated": "2018-07-24T08:18:55.107Z", + "image": "195299b4-da0c-4499-a67c-7f926e63116f", + "polygon": "Polygon((0,0), (1000,0), (1000,1000), (0,1000), (0,0))" + } +}, +{ + "model": "users.user", + "pk": 1, + "fields": { + "password": "pbkdf2_sha256$100000$DcHO7CYPnlU5$gFLvCPAoUpyDhb785RnLm/VsgHhB523vxLvxsbF7W6k=", + "last_login": null, + "email": "root@root.fr", + "is_active": true, + "is_admin": true + } +}, +{ + "model": "users.user", + "pk": 2, + "fields": { + "password": "pbkdf2_sha256$100000$shjhRsQTakNR$Zbsbhx//3bR0juLcxyJF0+jbUC1+1+U6DN6HznIqTBc=", + "last_login": null, + "email": "user@user.fr", + "is_active": true, + "is_admin": false + } +} +] diff --git a/arkindex/documents/management/commands/build_fixtures.py b/arkindex/documents/management/commands/build_fixtures.py new file mode 100644 index 0000000000000000000000000000000000000000..fc4251c5773452915b9910b58701143a8a8db898 --- /dev/null +++ b/arkindex/documents/management/commands/build_fixtures.py @@ -0,0 +1,125 @@ +#!/usr/bin/env python3 +from django.core.management.base import BaseCommand +from arkindex.documents.models import Corpus, Element, ElementType, Page, PageDirection, PageType, Act, Transcription +from arkindex.images.models import ImageServer, Image, Zone +from arkindex.users.models import User + + +def makezone(img, x1, x2): + """ + Shortcut to create a square zone on an image + """ + return Zone.objects.create(polygon=[(x1, x1), (x2, x1), (x2, x2), (x1, x2), (x1, x1)], image=img) + + +class Command(BaseCommand): + help = 'Create test objects in the database' + + def handle(self, *args, **options): + # Create 1 image server + imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") + + # Create 6 images + img1 = Image.objects.create(path='img1', width=1000, height=1000, server=imgsrv) + img2 = Image.objects.create(path='img2', width=1000, height=1000, server=imgsrv) + img3 = Image.objects.create(path='img3', width=1000, height=1000, server=imgsrv) + img4 = Image.objects.create(path='img4', width=1000, height=1000, server=imgsrv) + img5 = Image.objects.create(path='img5', width=1000, height=1000, server=imgsrv) + img6 = Image.objects.create(path='img6', width=1000, height=1000, server=imgsrv) + + # Create 6 zones on the images for pages + z1 = makezone(img1, 0, 1000) + z2 = makezone(img2, 0, 1000) + z3 = makezone(img3, 0, 1000) + z4 = makezone(img4, 0, 1000) + z5 = makezone(img5, 0, 1000) + z6 = makezone(img6, 0, 1000) + + # Create 1 corpus + corpus = Corpus.objects.create(id='test', name='Unit Tests') + + # Create 2 volumes + vol1 = Element.objects.create(corpus=corpus, type=ElementType.Volume, name="Volume 1") + vol2 = Element.objects.create(corpus=corpus, type=ElementType.Volume, name="Volume 2") + + # Create registers for each volume + reg1 = Element.objects.create(corpus=corpus, type=ElementType.Register, name="Register 1") + reg2 = Element.objects.create(corpus=corpus, type=ElementType.Register, name="Register 2") + reg1.add_parent(vol1) + reg2.add_parent(vol2) + + # Create 3 pages in each volume + p1_1 = Page.objects.create( + corpus=corpus, name="Volume 1, page 1r", folio="1r", page_type=PageType.Page, + nb=1, direction=PageDirection.Recto, zone=z1) + p1_2 = Page.objects.create( + corpus=corpus, name="Volume 1, page 1v", folio="1v", page_type=PageType.Page, + nb=1, direction=PageDirection.Verso, zone=z2) + p1_3 = Page.objects.create( + corpus=corpus, name="Volume 1, page 2r", folio="2r", page_type=PageType.Page, + nb=2, direction=PageDirection.Recto, zone=z3) + p1_1.add_parent(reg1) + p1_2.add_parent(reg1) + p1_3.add_parent(reg1) + + p2_1 = Page.objects.create( + corpus=corpus, name="Volume 2, page 1r", folio="1r", page_type=PageType.Page, + nb=1, direction=PageDirection.Recto, zone=z4) + p2_2 = Page.objects.create( + corpus=corpus, name="Volume 2, page 1v", folio="1v", page_type=PageType.Page, + nb=1, direction=PageDirection.Verso, zone=z5) + p2_3 = Page.objects.create( + corpus=corpus, name="Volume 2, page 2r", folio="2r", page_type=PageType.Page, + nb=2, direction=PageDirection.Recto, zone=z6) + p2_1.add_parent(reg2) + p2_2.add_parent(reg2) + p2_3.add_parent(reg2) + + # Create transcriptions on images of volume 1 + for page in (p1_1, p1_2, p1_3): + for word, pos in [("PARIS", 100), ("ROY", 400), ("DATUM", 700)]: + Transcription.objects.create( + corpus=corpus, + text=word, + type=ElementType.Word, + zone=makezone(page.zone.image, pos, pos + 100), + score=1.0, + ).add_parent(page) + + # Create 5 acts on volume 1 + act1 = Act.objects.create(corpus=corpus, name="Act 1", number="1", folio="1r") + act2 = Act.objects.create(corpus=corpus, name="Act 2", number="2", folio="1r-1v") + act3 = Act.objects.create(corpus=corpus, name="Act 3", number="3", folio="2r") + act4 = Act.objects.create(corpus=corpus, name="Act 4", number="4", folio="2r") + act5 = Act.objects.create(corpus=corpus, name="Act 5", number="5", folio="2r") + act1.add_parent(reg1) + act2.add_parent(reg1) + act3.add_parent(reg1) + act4.add_parent(reg1) + act5.add_parent(reg1) + + # Create surfaces on the 3 pages of volume 1 + # Page 1 [A B] Page 2 [C] Page 3 [D E F] + sa = Element.objects.create(corpus=corpus, type=ElementType.Surface, + name="Surface A", zone=makezone(img1, 0, 600)) + sb = Element.objects.create(corpus=corpus, type=ElementType.Surface, + name="Surface B", zone=makezone(img1, 600, 1000)) + sc = Element.objects.create(corpus=corpus, type=ElementType.Surface, + name="Surface C", zone=makezone(img2, 0, 1000)) + sd = Element.objects.create(corpus=corpus, type=ElementType.Surface, + name="Surface D", zone=makezone(img3, 0, 300)) + se = Element.objects.create(corpus=corpus, type=ElementType.Surface, + name="Surface E", zone=makezone(img3, 300, 600)) + sf = Element.objects.create(corpus=corpus, type=ElementType.Surface, + name="Surface F", zone=makezone(img3, 600, 1000)) + # Act 1 [A] Act 2 [B C] Act 3 [D] Act 4 [E] Act 5 [F] + sa.add_parent(act1) + sb.add_parent(act2) + sc.add_parent(act2) + sd.add_parent(act3) + se.add_parent(act4) + sf.add_parent(act5) + + # Create an admin and a user + User.objects.create_superuser('root@root.fr', 'Pa$$w0rd') + User.objects.create_user('user@user.fr', 'Pa$$w0rd') diff --git a/arkindex/documents/tests/test_act.py b/arkindex/documents/tests/test_act.py index 3956b319cc3df99e073eb462501ebe5e4cc0ddb2..d8cdfaece938a497280c50ce1d869e955d0e4604 100644 --- a/arkindex/documents/tests/test_act.py +++ b/arkindex/documents/tests/test_act.py @@ -1,17 +1,15 @@ from django.urls import reverse -from rest_framework.test import APITestCase +from arkindex.project.tests import FixtureAPITestCase from rest_framework import status -from arkindex.documents.models import Corpus, Element, Act, ElementType, MetaData, MetaType -from arkindex.images.models import ImageServer, Image, Zone +from arkindex.documents.models import Element, Act, ElementType, MetaData, MetaType +from arkindex.images.models import Image, Zone -class TestAct(APITestCase): +class TestAct(FixtureAPITestCase): def setUp(self): # Create an act with some surfaces - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img = Image.objects.create(path='img', width=1337, height=42, server=self.imgsrv) + self.img = Image.objects.get(path='img6', server=self.imgsrv) self.act = Act.objects.create( corpus=self.corpus, name='sister act', diff --git a/arkindex/documents/tests/test_annotation_list.py b/arkindex/documents/tests/test_annotation_list.py index e1e47a62e99e537e7f3bf76b186a169044e641f0..9311410003493ffc60bae6783a993f22a13dd430 100644 --- a/arkindex/documents/tests/test_annotation_list.py +++ b/arkindex/documents/tests/test_annotation_list.py @@ -1,30 +1,14 @@ from django.urls import reverse -from rest_framework.test import APITestCase +from arkindex.project.tests import FixtureAPITestCase from rest_framework import status -from arkindex.documents.models import Corpus, Element, Page, Transcription, Act, ElementType -from arkindex.images.models import ImageServer, Image, Zone - - -class TestPageAnnotationListSerializer(APITestCase): - - def setUp(self): - # Create a page and an image with some transcriptions - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img = Image.objects.create(path='img', width=1337, height=42, server=self.imgsrv) - pagezone = Zone.objects.create(polygon=[(0, 0), (1337, 0), (1337, 42), (42, 0), (0, 0)], image=self.img) - self.page = Page.objects.create(corpus=self.corpus, name="page", folio="page", zone=pagezone) - self.z1 = Zone.objects.create( - polygon=[(100, 200), (100, 300), (300, 300), (300, 200), (100, 200)], image=self.img) - self.z2 = Zone.objects.create( - polygon=[(50, 100), (50, 150), (150, 150), (150, 100), (50, 100)], image=self.img) - self.t1 = Transcription.objects.create(type=ElementType.Word, corpus=self.corpus, text="AAA", zone=self.z1) - self.t2 = Transcription.objects.create(type=ElementType.Word, corpus=self.corpus, text="BBB", zone=self.z2) - self.t1.add_parent(self.page) - self.t2.add_parent(self.page) +from arkindex.documents.models import Page + + +class TestPageAnnotationListSerializer(FixtureAPITestCase): def test_normal_list(self): - response = self.client.get(reverse('api:page-transcription-manifest', kwargs={'pk': self.page.id})) + page = Page.objects.get(corpus=self.corpus, zone__image__path='img1') + response = self.client.get(reverse('api:page-transcription-manifest', kwargs={'pk': page.id})) self.assertEqual(response.status_code, status.HTTP_200_OK) annotation_list = response.json() @@ -35,7 +19,7 @@ class TestPageAnnotationListSerializer(APITestCase): self.assertEqual(annotation_list['@type'], 'sc:AnnotationList') self.assertEqual(annotation_list['@context'], 'http://iiif.io/api/presentation/2/context.json') - self.assertEqual(len(annotation_list['resources']), 2) + self.assertEqual(len(annotation_list['resources']), 3) for annotation in annotation_list['resources']: self.assertIn('@type', annotation) @@ -55,12 +39,12 @@ class TestPageAnnotationListSerializer(APITestCase): self.assertEqual(resource['format'], 'text/plain') self.assertEqual(resource['@type'], 'cnt:ContentAsText') - self.assertIn(resource['chars'], ['AAA', 'BBB']) + self.assertIn(resource['chars'], ['PARIS', 'ROY', 'DATUM']) def test_empty_list(self): # An annotation list with nothing in it response = self.client.get(reverse('api:page-transcription-manifest', kwargs={ - 'pk': Page.objects.create(corpus=self.corpus, name="Empty Page").id + 'pk': Page.objects.get(corpus=self.corpus, zone__image__path='img6').id })) self.assertEqual(response.status_code, status.HTTP_200_OK) annotation_list = response.json() @@ -68,26 +52,11 @@ class TestPageAnnotationListSerializer(APITestCase): self.assertEqual(len(annotation_list['resources']), 0) -class TestPageActAnnotationListSerializer(APITestCase): - - def setUp(self): - # Create a page and an image with some transcriptions - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - img = Image.objects.create(path='img', width=1337, height=42, server=imgsrv) - pagezone = Zone.objects.create(polygon=[(0, 0), (1337, 0), (1337, 42), (42, 0), (0, 0)], image=img) - self.page = Page.objects.create(corpus=self.corpus, name="page", folio="page", zone=pagezone) - z1 = Zone.objects.create(polygon=[(100, 200), (100, 300), (300, 300), (300, 200), (100, 200)], image=img) - z2 = Zone.objects.create(polygon=[(50, 100), (50, 150), (150, 150), (150, 100), (50, 100)], image=img) - a1 = Act.objects.create(corpus=self.corpus, name="a1", number="123") - a2 = Act.objects.create(corpus=self.corpus, name="a2", number="456") - s1 = Element.objects.create(corpus=self.corpus, type=ElementType.Surface, name="s1", zone=z1) - s2 = Element.objects.create(corpus=self.corpus, type=ElementType.Surface, name="s2", zone=z2) - s1.add_parent(a1) - s2.add_parent(a2) +class TestPageActAnnotationListSerializer(FixtureAPITestCase): def test_normal_list(self): - response = self.client.get(reverse('api:page-act-manifest', kwargs={'pk': self.page.id})) + page = Page.objects.get(corpus=self.corpus, zone__image__path='img1') + response = self.client.get(reverse('api:page-act-manifest', kwargs={'pk': page.id})) self.assertEqual(response.status_code, status.HTTP_200_OK) annotation_list = response.json() @@ -118,12 +87,12 @@ class TestPageActAnnotationListSerializer(APITestCase): self.assertEqual(resource['format'], 'text/plain') self.assertEqual(resource['@type'], 'cnt:ContentAsText') - self.assertIn(resource['chars'], ['Act 123', 'Act 456']) + self.assertIn(resource['chars'], ['Act 1', 'Act 2']) def test_empty_list(self): # An annotation list with nothing in it response = self.client.get(reverse('api:page-act-manifest', kwargs={ - 'pk': Page.objects.create(corpus=self.corpus, name="Empty Page").id + 'pk': Page.objects.get(corpus=self.corpus, zone__image__path='img6').id })) self.assertEqual(response.status_code, status.HTTP_200_OK) annotation_list = response.json() diff --git a/arkindex/documents/tests/test_edit_elementpath.py b/arkindex/documents/tests/test_edit_elementpath.py index b5329bc697cf44f55ef0ece5c0dee6a329adc8d5..b43b171151d5dcd11c9b6b542120c4c9333e1fb2 100644 --- a/arkindex/documents/tests/test_edit_elementpath.py +++ b/arkindex/documents/tests/test_edit_elementpath.py @@ -1,14 +1,12 @@ -from django.test import TestCase -from arkindex.documents.models import Corpus, Element, ElementPath, ElementType +from arkindex.project.tests import FixtureTestCase +from arkindex.documents.models import Element, ElementPath, ElementType import itertools -class TestEditElementPath(TestCase): +class TestEditElementPath(FixtureTestCase): """ Test ElementPath editing algorithms """ - def setUp(self): - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') def build_tree(self, tree, element_type=ElementType.Volume): """ diff --git a/arkindex/documents/tests/test_element_manager.py b/arkindex/documents/tests/test_element_manager.py index 534d6854fb7e719e1a5ebe25a291a8bbf7024e58..07c049319ab1dc148d907ff94f6590d7e663c1a1 100644 --- a/arkindex/documents/tests/test_element_manager.py +++ b/arkindex/documents/tests/test_element_manager.py @@ -1,21 +1,17 @@ -from django.test import TestCase -from arkindex.documents.models import Corpus, Element, ElementType +from arkindex.project.tests import FixtureTestCase +from arkindex.documents.models import Element, ElementType -class TestElementManager(TestCase): +class TestElementManager(FixtureTestCase): """Tests for ElementManager class""" def setUp(self): - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.reg = Element.objects.create(corpus=self.corpus, name="Register", type=ElementType.Register) - self.vol = Element.objects.create(corpus=self.corpus, name="Volume", type=ElementType.Volume) - self.p1 = Element.objects.create(corpus=self.corpus, name="Page1", type=ElementType.Page) - self.p2 = Element.objects.create(corpus=self.corpus, name="Page2", type=ElementType.Page) + self.vol = Element.objects.get(name="Volume 2") + self.reg = Element.objects.get(name="Register 2") + self.p1 = Element.objects.get(name="Volume 2, page 1r") + self.p2 = Element.objects.get(name="Volume 2, page 1v") + self.p3 = Element.objects.get(name="Volume 2, page 2r") self.act = Element.objects.create(corpus=self.corpus, name="Act", type=ElementType.Act) - # Register --> Volume --> [Page1 --> Act, Page2] - self.vol.add_parent(self.reg) - self.p1.add_parent(self.vol) - self.p2.add_parent(self.vol) self.act.add_parent(self.p1) def test_get_ascending(self): @@ -25,33 +21,35 @@ class TestElementManager(TestCase): def test_get_ascending_empty(self): # Use Register, expect empty list - ids = Element.objects.get_ascending(self.reg.id) + ids = Element.objects.get_ascending(self.vol.id) self.assertCountEqual(ids, []) def test_get_ascendings(self): - # Use Page1 and Page2, expect Register and Volume twice - ids = Element.objects.get_ascendings(self.p1.id, self.p2.id) + # Use all three pages, expect Register and Volume thrice + ids = Element.objects.get_ascendings(self.p1.id, self.p2.id, self.p3.id) self.assertCountEqual(ids[self.p1.id], [self.reg, self.vol]) self.assertCountEqual(ids[self.p2.id], [self.reg, self.vol]) + self.assertCountEqual(ids[self.p3.id], [self.reg, self.vol]) def test_get_descending(self): - # Use Volume, expect Page1, Page2 and Act - ids = Element.objects.get_descending(self.vol.id) - self.assertCountEqual(ids, [self.p1, self.p2, self.act]) + # Use register, expect all three pages and the act + ids = Element.objects.get_descending(self.reg.id) + self.assertCountEqual(ids, [self.p1, self.p2, self.p3, self.act]) def test_get_descending_empty(self): - # Use Page2, expect empty list + # Use page 2, expect empty list ids = Element.objects.get_descending(self.p2.id) self.assertCountEqual(ids, []) def test_get_descendings(self): - # Use Page1 and Page2, expect Act and nothing else - ids = Element.objects.get_descendings([self.p1.id, self.p2.id]) + # Use all pages, expect Act and nothing else + ids = Element.objects.get_descendings([self.p1.id, self.p2.id, self.p3.id]) self.assertCountEqual(ids[self.p1.id], [self.act]) self.assertCountEqual(ids[self.p2.id], []) + self.assertCountEqual(ids[self.p3.id], []) def test_get_related(self): - # Use Page1, expect Register, Volume and Act + # Use page 1, expect Register, Volume and Act ids = Element.objects.get_related(self.p1.id) self.assertCountEqual(ids, [self.reg, self.vol, self.act]) @@ -64,4 +62,4 @@ class TestElementManager(TestCase): def test_get_ascending_paths(self): paths = Element.objects.get_ascending_paths(self.act.id) self.assertEqual(len(paths), 1) - self.assertSequenceEqual(list(paths[0]), [self.reg, self.vol, self.p1]) + self.assertSequenceEqual(list(paths[0]), [self.vol, self.reg, self.p1]) diff --git a/arkindex/documents/tests/test_search_post.py b/arkindex/documents/tests/test_search_post.py index 0ce776b835dcc8e112846e6a38c7d7149535ab22..56f16d44b66047ffe2d40fa6af943a4ea4c0725e 100644 --- a/arkindex/documents/tests/test_search_post.py +++ b/arkindex/documents/tests/test_search_post.py @@ -1,95 +1,11 @@ -from django.test import TestCase -from arkindex.documents.models import Corpus, Element, ElementType, Transcription, Act, Page -from arkindex.images.models import ImageServer, Image, Zone +from arkindex.project.tests import FixtureTestCase +from arkindex.documents.models import Transcription, Act, Element from arkindex.documents.search import search_transcriptions_post, search_acts_post, search_transcriptions_filter_post -class TestSearchPostProcess(TestCase): +class TestSearchPostProcess(FixtureTestCase): """Test ElasticSearch post-processing functions""" - def setUp(self): - # Create a server with three images - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img1 = Image.objects.create(path='img1', width=1000, height=1000, server=self.imgsrv) - self.img2 = Image.objects.create(path='img2', width=1000, height=1000, server=self.imgsrv) - self.img3 = Image.objects.create(path='img3', width=1000, height=1000, server=self.imgsrv) - self.z1 = Zone.objects.create(polygon=[(0, 0), (1000, 0), (1000, 1000), (1000, 0), (0, 0)], image=self.img1) - self.z2 = Zone.objects.create(polygon=[(0, 0), (1000, 0), (1000, 1000), (1000, 0), (0, 0)], image=self.img2) - self.z3 = Zone.objects.create(polygon=[(0, 0), (1000, 0), (1000, 1000), (1000, 0), (0, 0)], image=self.img3) - - # Create a volume with two pages and another with one page - self.vol1 = Element.objects.create(corpus=self.corpus, name="Volume 1", type=ElementType.Volume) - self.vol2 = Element.objects.create(corpus=self.corpus, name="Volume 2", type=ElementType.Volume) - self.p1 = Page.objects.create(corpus=self.corpus, name="p1", folio="p1", zone=self.z1) - self.p2 = Page.objects.create(corpus=self.corpus, name="p2", folio="p2", zone=self.z2) - self.p3 = Page.objects.create(corpus=self.corpus, name="p3", folio="p3", zone=self.z3) - self.p1.add_parent(self.vol1) - self.p2.add_parent(self.vol1) - self.p3.add_parent(self.vol2) - - # Create a bunch of transcriptions - self.t1 = Transcription.objects.create( - corpus=self.corpus, - text="word", - type=ElementType.Word, - zone=Zone.objects.create( - polygon=[(10, 10), (20, 10), (20, 20), (10, 20), (10, 10)], - image=self.img1, - ) - ) - self.t2 = Transcription.objects.create( - corpus=self.corpus, - text="word", - type=ElementType.Word, - zone=Zone.objects.create( - polygon=[(110, 110), (120, 110), (120, 120), (110, 120), (110, 110)], - image=self.img1, - ) - ) - self.t3 = Transcription.objects.create( - corpus=self.corpus, - text="word", - type=ElementType.Word, - zone=Zone.objects.create( - polygon=[(210, 210), (220, 210), (220, 220), (210, 220), (210, 210)], - image=self.img2, - ) - ) - self.t4 = Transcription.objects.create( - corpus=self.corpus, - text="word", - type=ElementType.Word, - zone=Zone.objects.create( - polygon=[(310, 210), (320, 310), (320, 320), (310, 320), (310, 310)], - image=self.img3, - ) - ) - self.t1.add_parent(self.p1) - self.t2.add_parent(self.p1) - self.t3.add_parent(self.p2) - self.t4.add_parent(self.p3) - - # Create an act with surfaces on the first volume - self.act = Act.objects.create(corpus=self.corpus, name="Act 42", number="42") - self.sz1 = Zone.objects.create(polygon=[(0, 0), (500, 0), (500, 500), (0, 500), (0, 0)], image=self.img1) - self.sz2 = Zone.objects.create(polygon=[(0, 0), (500, 0), (500, 500), (0, 500), (0, 0)], image=self.img2) - self.surf1 = Element.objects.create( - corpus=self.corpus, - type=ElementType.Surface, - name="Surface 1", - zone=self.sz1, - ) - self.surf2 = Element.objects.create( - corpus=self.corpus, - type=ElementType.Surface, - name="Surface 2", - zone=self.sz2, - ) - self.act.add_parent(self.vol1) - self.surf1.add_parent(self.act) - self.surf2.add_parent(self.act) - def build_es_response(self, hits): return { "hits": { @@ -148,7 +64,7 @@ class TestSearchPostProcess(TestCase): "transcriptions": { "hits": { "total": len(ts), - "hits": [self.make_nested_transcription_hit(t) for t in ts], + "hits": list(map(self.make_nested_transcription_hit, ts)), "max_score": 1337, } } @@ -156,28 +72,31 @@ class TestSearchPostProcess(TestCase): } def test_search_transcriptions_post(self): - expected = (self.t1, self.t2, self.t3) + expected = Transcription.objects.filter(text="PARIS") results = search_transcriptions_post(self.build_es_response( - [self.make_transcription_hit(ts) for ts in expected] + list(map(self.make_transcription_hit, expected)) )) self.assertCountEqual(results, expected) def test_search_acts_post(self): + act = Act.objects.get(number="1") + ts = Transcription.objects.filter(text__in=["PARIS", "ROY"], zone__image__path='img1') + surf = Element.objects.get(name="Surface A").zone results = search_acts_post(self.build_es_response( - [self.make_act_hit(self.act, (self.t1, self.t2, self.t3)), ] + [self.make_act_hit(act, ts), ] )) - self.assertCountEqual(results, [self.act]) + self.assertCountEqual(results, [act]) self.assertTrue(hasattr(results[0], 'transcriptions')) self.assertTrue(hasattr(results[0], 'surfaces')) - self.assertCountEqual(results[0].transcriptions, [self.t1, self.t2, self.t3]) - self.assertCountEqual(results[0].surfaces, [self.sz1, self.sz2]) + self.assertCountEqual(results[0].transcriptions, ts) + self.assertCountEqual(results[0].surfaces, [surf]) def test_search_transcriptions_filter_post(self): # Filter to only get transcriptions from volume 1 - unfiltered = (self.t1, self.t2, self.t3, self.t4) - expected = (self.t1, self.t2, self.t3) + unfiltered = Transcription.objects.filter(text="PARIS") + expected = Transcription.objects.filter(text="PARIS", zone__image__path__in=['img1', 'img2', 'img3']) results = search_transcriptions_filter_post(self.build_es_response( - [self.make_transcription_hit(ts) for ts in unfiltered] - ), self.vol1.id) + list(map(self.make_transcription_hit, unfiltered)) + ), Element.objects.get(name="Volume 1").id) self.assertCountEqual(results, expected) diff --git a/arkindex/documents/tests/test_surface_importer.py b/arkindex/documents/tests/test_surface_importer.py index 51d05bf5b1da86e85afc0a64a5822cdaa3bcf75a..79711f2d6a7e4426e727777bdabb0f9ce3346151 100644 --- a/arkindex/documents/tests/test_surface_importer.py +++ b/arkindex/documents/tests/test_surface_importer.py @@ -1,14 +1,11 @@ -from django.test import TestCase +from arkindex.project.tests import FixtureTestCase from arkindex.documents.surface import parse_himanis_volume_name, parse_act_folio -from arkindex.documents.models import Corpus, Element, ElementType, Page, PageType, PageDirection +from arkindex.documents.models import Element, ElementType, Page, PageType, PageDirection -class TestSurfaceImporterFunctions(TestCase): +class TestSurfaceImporterFunctions(FixtureTestCase): """Test surface importing helper functions.""" - def setUp(self): - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - def test_parse_himanis_volume_name(self): v42 = Element.objects.create(corpus=self.corpus, type=ElementType.Volume, name="Volume JJ 042") v43 = Element.objects.create(corpus=self.corpus, type=ElementType.Volume, name="Volume JJ043") diff --git a/arkindex/documents/tests/test_surface_linker.py b/arkindex/documents/tests/test_surface_linker.py index 6563ca118011354955889fcf912251977d74bb92..a47aa793f2b40457e4a4abf32be135c21a139ba7 100644 --- a/arkindex/documents/tests/test_surface_linker.py +++ b/arkindex/documents/tests/test_surface_linker.py @@ -1,212 +1,20 @@ from unittest.mock import patch -from django.test import TestCase -from arkindex.project.polygon import Polygon -from arkindex.documents.surface_link import parse_folios, ParsedFolio, SurfaceLinker -from arkindex.documents.models import Corpus, Element, ElementType, \ - Page, PageDirection, PageComplement, PageType -from arkindex.images.models import ImageServer, Image, Zone +from arkindex.project.tests import FixtureTestCase +from arkindex.documents.surface_link import ParsedFolio, SurfaceLinker +from arkindex.documents.models import Element, ElementType -class TestSurfaceLinkerFunctions(TestCase): - """Test SurfaceLinker helper functions.""" - - def setUp(self): - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - vol = Element.objects.create(corpus=self.corpus, type=ElementType.Volume, name="Volume") - self.p1r = Page.objects.create(corpus=self.corpus, name="1r", folio="1r", nb=1, direction=PageDirection.Recto) - self.p1v = Page.objects.create(corpus=self.corpus, name="1v", folio="1v", nb=1, direction=PageDirection.Verso) - self.p2r = Page.objects.create(corpus=self.corpus, name="2r", folio="2r", nb=2, direction=PageDirection.Recto) - self.p2bisr = Page.objects.create( - corpus=self.corpus, - name="2bisr", - folio="2bisr", - nb=2, - direction=PageDirection.Recto, - complement=PageComplement.Bis, - ) - self.p2v = Page.objects.create(corpus=self.corpus, name="2v", folio="2v", nb=2, direction=PageDirection.Verso) - for page in (self.p1r, self.p1v, self.p2r, self.p2bisr, self.p2v): - page.add_parent(vol) - self.pages = list(Page.objects.get_descending(vol.id)) - - def test_page_order(self): - self.assertTrue(self.p1r < self.p1v) - self.assertTrue(self.p1v < self.p2r) - self.assertTrue(self.p1r < self.p2r) - self.assertTrue(self.p1r < self.p2v) - self.assertTrue(self.p2r < self.p2v) - self.assertTrue(self.p1r < self.p2bisr) - self.assertTrue(self.p1v < self.p2bisr) - self.assertTrue(self.p2r < self.p2bisr) - self.assertTrue(self.p2bisr < self.p2v) - self.assertTrue(self.p2v == self.p2v) - - def test_parse_folios_no_check(self): - "Test parse_folios without a page queryset" - - folios = parse_folios('14r') - self.assertEqual(len(folios), 1) - self.assertIsInstance(folios[0], ParsedFolio) - self.assertEqual(folios[0].number, 14) - self.assertEqual(folios[0].complement, None) - self.assertEqual(folios[0].direction, PageDirection.Recto) - - folios = parse_folios('17bisv-019quat') - self.assertEqual(len(folios), 2) - self.assertIsInstance(folios[0], ParsedFolio) - self.assertEqual(folios[0].number, 17) - self.assertEqual(folios[0].complement, PageComplement.Bis) - self.assertEqual(folios[0].direction, PageDirection.Verso) - self.assertIsInstance(folios[1], ParsedFolio) - self.assertEqual(folios[1].number, 19) - self.assertEqual(folios[1].complement, PageComplement.Quat) - self.assertEqual(folios[1].direction, PageDirection.Recto) - - with self.assertRaisesMessage(ValueError, 'Improperly formatted folio string'): - parse_folios('this is not a folio') - - def test_parse_folios_ignore_check(self): - "Test parse_folios with a page queryset: ignore if there is only one folio" - - folios = parse_folios('14r', pages=self.pages) - self.assertEqual(len(folios), 1) - self.assertIsInstance(folios[0], ParsedFolio) - self.assertEqual(folios[0].number, 14) - self.assertEqual(folios[0].complement, None) - self.assertEqual(folios[0].direction, PageDirection.Recto) - - def test_parse_folios_check_success(self): - "Test parse_folios with a page queryset and a valid folio" - - folios = parse_folios('2r-2v', pages=self.pages) - self.assertEqual(len(folios), 3) - self.assertIsInstance(folios[0], ParsedFolio) - self.assertEqual(folios[0].number, 2) - self.assertEqual(folios[0].complement, None) - self.assertEqual(folios[0].direction, PageDirection.Recto) - self.assertIsInstance(folios[1], ParsedFolio) - self.assertEqual(folios[1].number, 2) - self.assertEqual(folios[1].complement, PageComplement.Bis) - self.assertEqual(folios[1].direction, PageDirection.Recto) - self.assertIsInstance(folios[2], ParsedFolio) - self.assertEqual(folios[2].number, 2) - self.assertEqual(folios[2].complement, None) - self.assertEqual(folios[2].direction, PageDirection.Verso) - - def test_parse_folios_wrong_order(self): - "Test parse_folios with a page queryset and a folio in a wrong order" - - with self.assertRaisesMessage(ValueError, 'Folio seems to be in reverse order'): - parse_folios('1v-1r', pages=self.pages) - - -class TestSurfaceLinker(TestCase): +class TestSurfaceLinker(FixtureTestCase): """Test surface-act linking process.""" def setUp(self): - # Create a server with three images - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img1 = Image.objects.create(path='img1', width=1337, height=42, server=self.imgsrv) - self.img2 = Image.objects.create(path='img2', width=255, height=420, server=self.imgsrv) - self.img3 = Image.objects.create(path='img3', width=418, height=404, server=self.imgsrv) - - # Create zones for pages - self.z1 = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 1337, 42), image=self.img1) - self.z2 = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 255, 420), image=self.img2) - self.z3 = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 418, 404), image=self.img3) - - # Create zones for 6 surfaces, two per page - self.z1a = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 1337, 22), image=self.img1) - self.z1b = Zone.objects.create(polygon=Polygon.from_coords(0, 22, 1337, 200), image=self.img1) - self.z2a = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 255, 210), image=self.img2) - self.z2b = Zone.objects.create(polygon=Polygon.from_coords(0, 210, 255, 420), image=self.img2) - self.z3a = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 418, 202), image=self.img3) - self.z3b = Zone.objects.create(polygon=Polygon.from_coords(0, 202, 1337, 42), image=self.img3) - - # Create a volume and 3 pages - self.vol = Element.objects.create(corpus=self.corpus, name="Volume Name", type=ElementType.Volume) - self.p1 = Page.objects.create( - corpus=self.corpus, - name="p1", - folio="p1", - zone=self.z1, - nb=1, - direction=PageDirection.Verso, - page_type=PageType.Page, - ) - self.p2 = Page.objects.create( - corpus=self.corpus, - name="p2", - folio="p2", - zone=self.z2, - nb=2, - complement=PageComplement.Ter, - direction=PageDirection.Recto, - page_type=PageType.Page, - ) - self.p3 = Page.objects.create( - corpus=self.corpus, - name="p3", - folio="p3", - zone=self.z3, - nb=3, - direction=PageDirection.Verso, - page_type=PageType.Page, - ) - - # Create 6 surfaces - self.s1a = Element.objects.create( - corpus=self.corpus, - name="Surface P1 #1", - type=ElementType.Surface, - zone=self.z1a, - ) - self.s1b = Element.objects.create( - corpus=self.corpus, - name="Surface P1 #2", - type=ElementType.Surface, - zone=self.z1b, - ) - self.s2a = Element.objects.create( - corpus=self.corpus, - name="Surface P2 #1", - type=ElementType.Surface, - zone=self.z2a, - ) - self.s2b = Element.objects.create( - corpus=self.corpus, - name="Surface P2 #2", - type=ElementType.Surface, - zone=self.z2b, - ) - self.s3a = Element.objects.create( - corpus=self.corpus, - name="Surface P3 #1", - type=ElementType.Surface, - zone=self.z3a, - ) - self.s3b = Element.objects.create( - corpus=self.corpus, - name="Surface P3 #2", - type=ElementType.Surface, - zone=self.z3b, - ) - - # Link surfaces to pages - links = { - self.p1: [self.s1a, self.s1b], - self.p2: [self.s2a, self.s2b], - self.p3: [self.s3a, self.s3b], - } - for page, surfaces in links.items(): - for surface in surfaces: - surface.add_parent(page) - - # Link pages to vol - self.p1.add_parent(self.vol) - self.p2.add_parent(self.vol) - self.p3.add_parent(self.vol) + self.vol = Element.objects.get(name="Volume 1") + self.sa = Element.objects.get(name="Surface A") + self.sb = Element.objects.get(name="Surface B") + self.sc = Element.objects.get(name="Surface C") + self.sd = Element.objects.get(name="Surface D") + self.se = Element.objects.get(name="Surface E") + self.sf = Element.objects.get(name="Surface F") def test_init(self): "Test SurfaceLinker performs checks on its inputs" @@ -240,15 +48,15 @@ class TestSurfaceLinker(TestCase): s.find_surfaces() self.assertEqual(s.surfaces_count, 6) - folio = ParsedFolio.from_raw('1', None, 'v') + folio = ParsedFolio.from_raw('1', None, 'r') surfaces = s._pop_surfaces(folio) - self.assertListEqual(surfaces, [self.s1a, self.s1b]) + self.assertListEqual(surfaces, [self.sa, self.sb]) self.assertEqual(len(s.surfaces[folio]), 0) - folio = ParsedFolio.from_raw('3', None, 'v') + folio = ParsedFolio.from_raw('2', None, 'r') surfaces = s._pop_surfaces(folio, index=0) - self.assertListEqual(surfaces, [self.s3a]) - self.assertEqual(len(s.surfaces[folio]), 1) + self.assertListEqual(surfaces, [self.sd]) + self.assertEqual(len(s.surfaces[folio]), 2) @patch('arkindex.documents.surface_link.logger') def test_pop_surfaces_warning(self, mock_logger): @@ -284,8 +92,8 @@ class TestSurfaceLinker(TestCase): Test surface matching for an act with 2 folios on same page Greedy test case """ - self.assertTrue(self.z1a.polygon.center.y < self.z1b.polygon.center.y) - s = SurfaceLinker(self.vol, [('1', '001v'), ('2', '001v')]) + self.assertTrue(self.sa.zone.polygon.center.y < self.sb.zone.polygon.center.y) + s = SurfaceLinker(self.vol, [('1', '001r'), ('2', '001r')]) s.find_pages() self.assertEqual(len(s.pages), 3) s.find_surfaces() @@ -297,16 +105,16 @@ class TestSurfaceLinker(TestCase): self.assertEqual(s.parsed_acts, 2) self.assertEqual(s.linked_surfaces, 2) self.assertIn('1', s.acts_surfaces) - self.assertListEqual(s.acts_surfaces['1'], [self.s1a]) + self.assertListEqual(s.acts_surfaces['1'], [self.sa]) self.assertIn('2', s.acts_surfaces) - self.assertListEqual(s.acts_surfaces['2'], [self.s1b]) + self.assertListEqual(s.acts_surfaces['2'], [self.sb]) def test_two_folios(self): """ Test surface matching for an act with two folios End of page 1 + start of page 2 """ - s = SurfaceLinker(self.vol, [('2', '1v-2terr')]) + s = SurfaceLinker(self.vol, [('2', '1r-1v')]) s.find_pages() self.assertEqual(len(s.pages), 3) s.find_surfaces() @@ -318,14 +126,14 @@ class TestSurfaceLinker(TestCase): self.assertEqual(s.parsed_acts, 1) self.assertEqual(s.linked_surfaces, 2) self.assertIn('2', s.acts_surfaces) - self.assertListEqual(s.acts_surfaces['2'], [self.s1b, self.s2a]) + self.assertListEqual(s.acts_surfaces['2'], [self.sb, self.sc]) def test_three_folios(self): """ Test surface matching for an act with three folios End of page 1 + full pages 2 + start of page 3 """ - s = SurfaceLinker(self.vol, [('3', '1v-3v')]) + s = SurfaceLinker(self.vol, [('3', '1r-2r')]) s.find_pages() self.assertEqual(len(s.pages), 3) s.find_surfaces() @@ -336,9 +144,9 @@ class TestSurfaceLinker(TestCase): s.resolve_conflicts() s.link_surfaces() self.assertEqual(s.parsed_acts, 1) - self.assertEqual(s.linked_surfaces, 4) + self.assertEqual(s.linked_surfaces, 3) self.assertIn('3', s.acts_surfaces) - self.assertListEqual(s.acts_surfaces['3'], [self.s1b, self.s2a, self.s2b, self.s3a]) + self.assertListEqual(s.acts_surfaces['3'], [self.sb, self.sc, self.sd]) def test_wrong_folio(self): """ @@ -361,113 +169,9 @@ class TestSurfaceLinker(TestCase): """ Test automatic detection of missing acts """ - s = SurfaceLinker(self.vol, [('2', '1v'), ('4', '2terr')]) + s = SurfaceLinker(self.vol, [('2', '1v'), ('4', '2r')]) s.find_missing_acts() - self.assertListEqual(s.acts_raw, [('1', ''), ('2', '1v'), ('3', ''), ('4', '2terr')]) - - -class TestSurfaceLinkerConflict(TestCase): - """Test surface-act linking process and conflict solving.""" - - def setUp(self): - # Create a server with three images - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img1r = Image.objects.create(path='img1r', width=1000, height=1000, server=self.imgsrv) - self.img1v = Image.objects.create(path='img1v', width=1000, height=1000, server=self.imgsrv) - self.img2r = Image.objects.create(path='img2r', width=1000, height=1000, server=self.imgsrv) - - # Create zones for pages - self.z1r = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 1000, 1000), image=self.img1r) - self.z1v = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 1000, 1000), image=self.img1v) - self.z2r = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 1000, 1000), image=self.img2r) - - # Create zones for 5 surfaces - self.za = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 1000, 500), image=self.img1r) - self.zb = Zone.objects.create(polygon=Polygon.from_coords(0, 500, 1000, 1000), image=self.img1r) - self.zc = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 1000, 1000), image=self.img1v) - self.zd = Zone.objects.create(polygon=Polygon.from_coords(0, 0, 1000, 300), image=self.img2r) - self.ze = Zone.objects.create(polygon=Polygon.from_coords(0, 300, 1000, 600), image=self.img2r) - self.zf = Zone.objects.create(polygon=Polygon.from_coords(0, 600, 1000, 1000), image=self.img2r) - - # Create a volume and 3 pages - self.vol = Element.objects.create(corpus=self.corpus, name="Volume Name", type=ElementType.Volume) - self.p1r = Page.objects.create( - corpus=self.corpus, - name="p1r", - folio="p1r", - zone=self.z1r, - nb=1, - direction=PageDirection.Recto, - page_type=PageType.Page, - ) - self.p1v = Page.objects.create( - corpus=self.corpus, - name="p1v", - folio="p1v", - zone=self.z1v, - nb=1, - direction=PageDirection.Verso, - page_type=PageType.Page, - ) - self.p2r = Page.objects.create( - corpus=self.corpus, - name="p2r", - folio="p2r", - zone=self.z2r, - nb=2, - direction=PageDirection.Recto, - page_type=PageType.Page, - ) - - # Create 6 surfaces - self.sa = Element.objects.create( - corpus=self.corpus, - name="Surface A", - type=ElementType.Surface, - zone=self.za, - ) - self.sb = Element.objects.create( - corpus=self.corpus, - name="Surface B", - type=ElementType.Surface, - zone=self.zb, - ) - self.sc = Element.objects.create( - corpus=self.corpus, - name="Surface C", - type=ElementType.Surface, - zone=self.zc, - ) - self.sd = Element.objects.create( - corpus=self.corpus, - name="Surface D", - type=ElementType.Surface, - zone=self.zd, - ) - self.se = Element.objects.create( - corpus=self.corpus, - name="Surface E", - type=ElementType.Surface, - zone=self.ze, - ) - self.sf = Element.objects.create( - corpus=self.corpus, - name="Surface F", - type=ElementType.Surface, - zone=self.zf, - ) - - # Link surfaces to pages - links = { - self.vol: [self.p1r, self.p1v, self.p2r], - self.p1r: [self.sa, self.sb], - self.p1v: [self.sc], - self.p2r: [self.sd, self.se, self.sf], - } - for parent, children in links.items(): - for child in children: - child.add_parent(parent) + self.assertListEqual(s.acts_raw, [('1', ''), ('2', '1v'), ('3', ''), ('4', '2r')]) def test_conflict(self): """ diff --git a/arkindex/documents/tests/test_surface_linker_functions.py b/arkindex/documents/tests/test_surface_linker_functions.py new file mode 100644 index 0000000000000000000000000000000000000000..8948406e21551dd32937c1c618b73bbeb084e5cb --- /dev/null +++ b/arkindex/documents/tests/test_surface_linker_functions.py @@ -0,0 +1,95 @@ +from arkindex.project.tests import FixtureTestCase +from arkindex.documents.models import Element, Page, PageDirection, PageComplement +from arkindex.documents.surface_link import parse_folios, ParsedFolio + + +class TestSurfaceLinkerFunctions(FixtureTestCase): + """Test SurfaceLinker helper functions.""" + + def setUp(self): + vol = Element.objects.get(name="Volume 1") + self.p1r = Page.objects.get(name="Volume 1, page 1r") + self.p1v = Page.objects.get(name="Volume 1, page 1v") + self.p2r = Page.objects.get(name="Volume 1, page 2r") + self.p2bisr = Page.objects.create( + corpus=self.corpus, + name="2bisr", + folio="2bisr", + nb=2, + direction=PageDirection.Recto, + complement=PageComplement.Bis, + ) + self.p2v = Page.objects.create(corpus=self.corpus, name="2v", folio="2v", nb=2, direction=PageDirection.Verso) + for page in (self.p2bisr, self.p2v): + page.add_parent(vol) + self.pages = list(Page.objects.get_descending(vol.id)) + + def test_page_order(self): + self.assertTrue(self.p1r < self.p1v) + self.assertTrue(self.p1v < self.p2r) + self.assertTrue(self.p1r < self.p2r) + self.assertTrue(self.p1r < self.p2v) + self.assertTrue(self.p2r < self.p2v) + self.assertTrue(self.p1r < self.p2bisr) + self.assertTrue(self.p1v < self.p2bisr) + self.assertTrue(self.p2r < self.p2bisr) + self.assertTrue(self.p2bisr < self.p2v) + self.assertTrue(self.p2v == self.p2v) + + def test_parse_folios_no_check(self): + "Test parse_folios without a page queryset" + + folios = parse_folios('14r') + self.assertEqual(len(folios), 1) + self.assertIsInstance(folios[0], ParsedFolio) + self.assertEqual(folios[0].number, 14) + self.assertEqual(folios[0].complement, None) + self.assertEqual(folios[0].direction, PageDirection.Recto) + + folios = parse_folios('17bisv-019quat') + self.assertEqual(len(folios), 2) + self.assertIsInstance(folios[0], ParsedFolio) + self.assertEqual(folios[0].number, 17) + self.assertEqual(folios[0].complement, PageComplement.Bis) + self.assertEqual(folios[0].direction, PageDirection.Verso) + self.assertIsInstance(folios[1], ParsedFolio) + self.assertEqual(folios[1].number, 19) + self.assertEqual(folios[1].complement, PageComplement.Quat) + self.assertEqual(folios[1].direction, PageDirection.Recto) + + with self.assertRaisesMessage(ValueError, 'Improperly formatted folio string'): + parse_folios('this is not a folio') + + def test_parse_folios_ignore_check(self): + "Test parse_folios with a page queryset: ignore if there is only one folio" + + folios = parse_folios('14r', pages=self.pages) + self.assertEqual(len(folios), 1) + self.assertIsInstance(folios[0], ParsedFolio) + self.assertEqual(folios[0].number, 14) + self.assertEqual(folios[0].complement, None) + self.assertEqual(folios[0].direction, PageDirection.Recto) + + def test_parse_folios_check_success(self): + "Test parse_folios with a page queryset and a valid folio" + + folios = parse_folios('2r-2v', pages=self.pages) + self.assertEqual(len(folios), 3) + self.assertIsInstance(folios[0], ParsedFolio) + self.assertEqual(folios[0].number, 2) + self.assertEqual(folios[0].complement, None) + self.assertEqual(folios[0].direction, PageDirection.Recto) + self.assertIsInstance(folios[1], ParsedFolio) + self.assertEqual(folios[1].number, 2) + self.assertEqual(folios[1].complement, PageComplement.Bis) + self.assertEqual(folios[1].direction, PageDirection.Recto) + self.assertIsInstance(folios[2], ParsedFolio) + self.assertEqual(folios[2].number, 2) + self.assertEqual(folios[2].complement, None) + self.assertEqual(folios[2].direction, PageDirection.Verso) + + def test_parse_folios_wrong_order(self): + "Test parse_folios with a page queryset and a folio in a wrong order" + + with self.assertRaisesMessage(ValueError, 'Folio seems to be in reverse order'): + parse_folios('1v-1r', pages=self.pages) diff --git a/arkindex/documents/tests/test_surface_parser.py b/arkindex/documents/tests/test_surface_parser.py index 98c3a0ca2eec5c43c25489c9dd2551ee5feec5fa..8bcf8f6fcc7d6992598445c933673e679825f320 100644 --- a/arkindex/documents/tests/test_surface_parser.py +++ b/arkindex/documents/tests/test_surface_parser.py @@ -1,4 +1,4 @@ -from django.test import TestCase +from unittest import TestCase from arkindex.documents.surface import SurfaceParser import os.path diff --git a/arkindex/documents/tests/test_tasks.py b/arkindex/documents/tests/test_tasks.py index 344320fc3291464500b5f01cd9d83aecdb8e9219..054f4b7d76937bd15aea560da6775cbac9e84e43 100644 --- a/arkindex/documents/tests/test_tasks.py +++ b/arkindex/documents/tests/test_tasks.py @@ -1,5 +1,5 @@ -from django.test import TestCase from fakeredis import FakeStrictRedis +from unittest import TestCase from unittest.mock import patch from arkindex.documents.tasks import reindex_acts, reindex_transcriptions diff --git a/arkindex/documents/tests/test_transcription_create.py b/arkindex/documents/tests/test_transcription_create.py index 602fff86f0986e80d1e42995c5b88ad5a0b7b93b..b9b2c59d41b0abc7d4f73a3dfda7579dfb20eddf 100644 --- a/arkindex/documents/tests/test_transcription_create.py +++ b/arkindex/documents/tests/test_transcription_create.py @@ -1,39 +1,19 @@ from django.urls import reverse from unittest.mock import patch -from rest_framework.test import APITestCase from rest_framework import status -from arkindex.documents.models import Corpus, Page, Transcription, ElementPath, ElementType -from arkindex.images.models import ImageServer, Image, Zone -from arkindex.users.models import User +from arkindex.project.tests import FixtureAPITestCase from arkindex.project.polygon import Polygon +from arkindex.documents.models import Page, Transcription, ElementPath, ElementType import uuid -class TestTranscriptionCreate(APITestCase): +class TestTranscriptionCreate(FixtureAPITestCase): """ Tests for text element creation view """ def setUp(self): - """ - Create a page and an image with one already included transcription - """ - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img = Image.objects.create(path='img', width=1337, height=1337, server=self.imgsrv) - pagezone = Zone.objects.create(polygon=[(0, 0), (1337, 0), (1337, 1337), (1337, 0), (0, 0)], image=self.img) - self.page = Page.objects.create(corpus=self.corpus, name="page", folio="page", zone=pagezone) - self.ts_zone = Zone.objects.create( - polygon=[(100, 200), (100, 300), (300, 300), (300, 200), (100, 200)], image=self.img) - self.ts = Transcription.objects.create( - corpus=self.corpus, - text="PAAMAYIM", - score=0.5, - zone=self.ts_zone, - type=ElementType.Word, - ) - self.ts.add_parent(self.page) - self.user = User.objects.create_user(email='user@user.com', password='P45$w0rD') + self.page = Page.objects.get(corpus=self.corpus, zone__image__path='img1') def test_require_login(self): response = self.client.post(reverse('api:transcription-create'), format='json') @@ -57,7 +37,7 @@ class TestTranscriptionCreate(APITestCase): self.assertEqual(new_ts.zone.polygon, Polygon.from_coords(0, 0, 100, 100)) self.assertEqual(new_ts.score, 0.83) self.assertEqual(ElementPath.objects.filter(element_id=new_ts.id).count(), 1) - self.assertListEqual(ElementPath.objects.get(element=new_ts).path, [self.page.id]) + self.assertIn(self.page.id, ElementPath.objects.get(element=new_ts).path) self.assertTrue(indexer.return_value.run_index.called) def test_check_element_type(self): @@ -79,32 +59,36 @@ class TestTranscriptionCreate(APITestCase): Checks the view reuses zones when available """ self.client.force_login(self.user) + ts = Transcription.objects.get(zone__image__path='img1', text="PARIS") response = self.client.post(reverse('api:transcription-create'), format='json', data={ "type": "word", "element": str(self.page.id), - "polygon": self.ts_zone.polygon, + "polygon": ts.zone.polygon.serialize(), "text": "GLOUBIBOULGA", "score": 0.8, }) self.assertEqual(response.status_code, status.HTTP_201_CREATED) - self.assertEqual(Transcription.objects.get(text="GLOUBIBOULGA").zone.id, self.ts_zone.id) + self.assertEqual( + Transcription.objects.get(text="GLOUBIBOULGA").zone.id, ts.zone.id) def test_update_transcription(self): """ Checks the view updates transcriptions when they already exist """ self.client.force_login(self.user) + ts = Transcription.objects.get(zone__image__path='img1', text="PARIS") + self.assertNotEqual(ts.score, 0.99) response = self.client.post(reverse('api:transcription-create'), format='json', data={ "type": "word", "element": str(self.page.id), - "polygon": self.ts.zone.polygon, - "text": self.ts.text, + "polygon": ts.zone.polygon.serialize(), + "text": ts.text, "score": 0.99, }) self.assertEqual(response.status_code, status.HTTP_201_CREATED) - self.assertEqual(Transcription.objects.filter(text=self.ts.text).count(), 1) - self.ts.refresh_from_db() - self.assertEqual(self.ts.score, 0.99) + self.assertEqual(Transcription.objects.filter(zone__image__path='img1', text=ts.text).count(), 1) + ts.refresh_from_db() + self.assertEqual(ts.score, 0.99) def test_invalid_data(self): """ @@ -151,7 +135,7 @@ class TestTranscriptionCreate(APITestCase): self.client.force_login(self.user) response = self.client.post(reverse('api:transcription-bulk'), format='json', data={ "parent": str(self.page.id), - "image": str(self.img.id), + "image": str(self.page.zone.image.id), "transcriptions": [ { "type": "word", @@ -172,7 +156,7 @@ class TestTranscriptionCreate(APITestCase): self.assertEqual(new_ts.zone.polygon, Polygon.from_coords(0, 0, 100, 100)) self.assertEqual(new_ts.score, 0.83) self.assertEqual(ElementPath.objects.filter(element_id=new_ts.id).count(), 1) - self.assertListEqual(ElementPath.objects.get(element=new_ts).path, [self.page.id]) + self.assertIn(self.page.id, ElementPath.objects.get(element=new_ts).path) # indexer called self.assertTrue(indexer.return_value.run_index.called) diff --git a/arkindex/documents/tests/test_volume_manifest.py b/arkindex/documents/tests/test_volume_manifest.py index 603e6e4bd235b924174188a209265b74f9ec5bd1..b7fcfb3fe58719c54f113ce2e6474753d26c8ce9 100644 --- a/arkindex/documents/tests/test_volume_manifest.py +++ b/arkindex/documents/tests/test_volume_manifest.py @@ -1,31 +1,17 @@ from django.urls import reverse -from rest_framework.test import APITestCase +from arkindex.project.tests import FixtureAPITestCase from rest_framework import status from tripoli import IIIFValidator -from arkindex.documents.models import Corpus, Element, ElementType, Page -from arkindex.images.models import ImageServer, Image, Zone +from arkindex.documents.models import Element, ElementType -class TestVolumeManifestSerializer(APITestCase): +class TestVolumeManifestSerializer(FixtureAPITestCase): """Tests for VolumeManifestSerializer class""" - def setUp(self): - # Create a volume with two pages and a server with two images - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img1 = Image.objects.create(path='img1', width=1337, height=42, server=self.imgsrv) - self.img2 = Image.objects.create(path='img2', width=255, height=420, server=self.imgsrv) - self.z1 = Zone.objects.create(polygon=[(0, 0), (1337, 0), (1337, 42), (42, 0), (0, 0)], image=self.img1) - self.z2 = Zone.objects.create(polygon=[(0, 0), (255, 0), (255, 420), (0, 420), (0, 0)], image=self.img2) - self.vol = Element.objects.create(corpus=self.corpus, name="Volume Name", type=ElementType.Volume) - self.p1 = Page.objects.create(corpus=self.corpus, name="p1", folio="p1", zone=self.z1) - self.p2 = Page.objects.create(corpus=self.corpus, name="p2", folio="p2", zone=self.z2) - self.p1.add_parent(self.vol) - self.p2.add_parent(self.vol) - def test_normal_manifest(self): # Just a normal situation. - response = self.client.get(reverse('api:volume-manifest', kwargs={'pk': self.vol.id})) + vol = Element.objects.get(type=ElementType.Volume, name="Volume 1") + response = self.client.get(reverse('api:volume-manifest', kwargs={'pk': vol.id})) self.assertEqual(response.status_code, status.HTTP_200_OK) manifest = response.json() @@ -40,25 +26,25 @@ class TestVolumeManifestSerializer(APITestCase): self.assertEqual(manifest['@type'], "sc:Manifest") self.assertEqual(manifest['@context'], "http://iiif.io/api/presentation/2/context.json") - self.assertEqual(manifest['label'], self.vol.name) + self.assertEqual(manifest['label'], vol.name) self.assertEqual(manifest['thumbnail']['service']['@context'], "http://iiif.io/api/image/2/context.json") self.assertEqual(manifest['thumbnail']['service']['profile'], "http://iiif.io/api/image/2/level2.json") self.assertIn('server/img', manifest['thumbnail']['service']['@id']) - self.assertEqual(len(manifest['structures']), 3) + self.assertEqual(len(manifest['structures']), 4) topstruct = next(s for s in manifest['structures'] if s['viewingHint'] == "top") self.assertIsNotNone(topstruct) - self.assertEqual(topstruct['label'], self.vol.name) + self.assertEqual(topstruct['label'], vol.name) self.assertEqual(topstruct['@type'], 'sc:Range') - self.assertEqual(len(topstruct['ranges']), 2) + self.assertEqual(len(topstruct['ranges']), 3) self.assertEqual(manifest['@id'], topstruct['@id']) self.assertEqual(len(manifest['sequences']), 1) self.assertEqual(manifest['sequences'][0]['@type'], 'sc:Sequence') canvases = manifest['sequences'][0]['canvases'] - self.assertEqual(len(canvases), 2) + self.assertEqual(len(canvases), 3) for canvas in canvases: self.assertIn('@type', canvas) self.assertIn('@id', canvas) @@ -103,7 +89,8 @@ class TestVolumeManifestSerializer(APITestCase): self.assertEqual(len(manifest['sequences'][0]['canvases']), 0) def test_normal_manifest_iiif_validation(self): - response = self.client.get(reverse('api:volume-manifest', kwargs={'pk': self.vol.id})) + vol = Element.objects.get(type=ElementType.Volume, name="Volume 1") + response = self.client.get(reverse('api:volume-manifest', kwargs={'pk': vol.id})) self.assertEqual(response.status_code, status.HTTP_200_OK) manifest = response.json() iv = IIIFValidator() diff --git a/arkindex/images/tests.py b/arkindex/images/tests.py index 3d66dc9ce8e57017f74f277928d8117f80b4e8fa..377508318d03d75010e20b2b42989dc88c40b44f 100644 --- a/arkindex/images/tests.py +++ b/arkindex/images/tests.py @@ -1,20 +1,18 @@ -from django.test import TestCase -from arkindex.documents.models import Corpus, Page, Transcription, Element, ElementType +from arkindex.project.tests import FixtureTestCase from arkindex.project.polygon import Polygon -from arkindex.images.models import ImageServer, Image, Zone +from arkindex.documents.models import Transcription, Element, ElementType +from arkindex.images.models import Image from arkindex.images.importer import bulk_transcriptions -class TestBulkTranscriptions(TestCase): +class TestBulkTranscriptions(FixtureTestCase): """Tests for bulk transcription and zone importing""" def setUp(self): # Create a page and an image - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') - self.imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img = Image.objects.create(path='img', width=1337, height=42, server=self.imgsrv) - pagezone = Zone.objects.create(polygon=[(0, 0), (1337, 0), (1337, 42), (42, 0), (0, 0)], image=self.img) - self.page = Page.objects.create(corpus=self.corpus, name="page", folio="page", zone=pagezone) + self.img = Image.objects.get(path='img6', server=self.imgsrv) + pagezone = self.img.zones.first() + self.page = pagezone.elements.first() def test_bulk_transcriptions(self): items = [ @@ -38,7 +36,7 @@ class TestBulkTranscriptions(TestCase): }, ] bulk_transcriptions(self.img, self.page, items) - out = Transcription.objects.all().order_by('line') + out = Transcription.objects.filter(zone__image=self.img).order_by('line') self.assertEqual(len(out), 2) self.assertIsInstance(out[0], Transcription) @@ -112,7 +110,7 @@ class TestBulkTranscriptions(TestCase): out = bulk_transcriptions(self.img, self.page, items) self.assertEqual(len(out), 2) - trs = Transcription.objects.all().order_by('line') + trs = Transcription.objects.filter(zone__image=self.img).order_by('line') self.assertEqual(trs.count(), 2) self.assertIsInstance(trs[0], Transcription) diff --git a/arkindex/project/polygon.py b/arkindex/project/polygon.py index d19fa8b575dd574e84c7c3277405e34f99286d1a..9b126aa88809fa336d34302c049bc86497e9ec58 100644 --- a/arkindex/project/polygon.py +++ b/arkindex/project/polygon.py @@ -24,6 +24,8 @@ class Point(object): return '({0.x},{0.y})'.format(self) def __eq__(self, other): + if isinstance(other, collections.abc.Sequence): + return (self.x, self.y) == other return (isinstance(other, self.__class__) and self.x == other.x and self.y == other.y) @@ -37,7 +39,7 @@ class Point(object): self.y <= other.y) -class Polygon(object): +class Polygon(collections.abc.MutableSequence): ''' A hashable Polygon in-memory ''' @@ -95,16 +97,35 @@ class Polygon(object): return "Polygon({})".format(', '.join(map(str, self.points))) def __eq__(self, other): - if len(self.points) != len(other.points): + other_points = other.points if hasattr(other, 'points') else other + if len(self.points) != len(other_points): return False return all( x == y - for x, y in zip(self.points, other.points) + for x, y in zip(self.points, other_points) + ) or all( + x == y + for x, y in zip(self.points, reversed(other_points)) ) def __hash__(self): return hash(tuple(self.points)) + def __getitem__(self, i): + return self.points[i] + + def __setitem__(self, i, value): + self.points[i] = value + + def __delitem__(self, i): + del self.points[i] + + def __len__(self): + return len(self.points) + + def insert(self, i, value): + self.points.insert(i, value) + def serialize(self): ''' Used to save data in DB diff --git a/arkindex/project/tests/__init__.py b/arkindex/project/tests/__init__.py index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..ffc6bf62c5f02b8f520d5a97ef916887c3f5e984 100644 --- a/arkindex/project/tests/__init__.py +++ b/arkindex/project/tests/__init__.py @@ -0,0 +1,24 @@ +from django.test import TestCase +from rest_framework.test import APITestCase +from arkindex.documents.models import Corpus +from arkindex.images.models import ImageServer +from arkindex.users.models import User + + +class FixtureMixin(object): + fixtures = ['data.json', ] + + @classmethod + def setUpTestData(cls): + cls.corpus = Corpus.objects.get(id='test') + cls.user = User.objects.get(email='user@user.fr') + cls.superuser = User.objects.get(email='root@root.fr') + cls.imgsrv = ImageServer.objects.get(url='http://server') + + +class FixtureTestCase(FixtureMixin, TestCase): + pass + + +class FixtureAPITestCase(FixtureMixin, APITestCase): + pass diff --git a/arkindex/project/tests/test_fields.py b/arkindex/project/tests/test_fields.py index 80514df0a0de117f99fb7419bf1715097242de42..86cd0060e2967208a7e5ae733c5264497e694b0c 100644 --- a/arkindex/project/tests/test_fields.py +++ b/arkindex/project/tests/test_fields.py @@ -1,8 +1,8 @@ -from arkindex.documents.models import Element, ElementPath, Corpus, ElementType -from django.test import TestCase +from arkindex.documents.models import Element, ElementPath, ElementType +from arkindex.project.tests import FixtureTestCase -class TestArrayField(TestCase): +class TestArrayField(FixtureTestCase): """ Test the enhanced ArrayField """ @@ -11,7 +11,6 @@ class TestArrayField(TestCase): """ D -> C -> B -> A """ - self.corpus = Corpus.objects.create(id='test', name='Unit Tests') self.a, self.b, self.c, self.d = ( Element.objects.create(corpus=self.corpus, name=str(i), type=ElementType.Volume) for i in range(4) diff --git a/arkindex/project/tests/test_polygon.py b/arkindex/project/tests/test_polygon.py index d26a8f7818420e99b401d57e1cd7e8b756bd2b8d..bd5d55dd42efe39f937cb1880a83da6899eb9350 100644 --- a/arkindex/project/tests/test_polygon.py +++ b/arkindex/project/tests/test_polygon.py @@ -1,4 +1,4 @@ -from django.test import TestCase +from unittest import TestCase from arkindex.project.polygon import Polygon diff --git a/arkindex/project/tests/test_polygonfield.py b/arkindex/project/tests/test_polygonfield.py index b6282237e2cdd5b611a4c5549fe6f0591eebc9c4..e10ebae4c0550f32abe21f6f50e72b828ec4bff6 100644 --- a/arkindex/project/tests/test_polygonfield.py +++ b/arkindex/project/tests/test_polygonfield.py @@ -1,26 +1,31 @@ -from django.test import TestCase -from arkindex.images.models import ImageServer, Image, Zone +from arkindex.project.tests import FixtureTestCase +from arkindex.images.models import Image, Zone -class TestPolygonField(TestCase): +class TestPolygonField(FixtureTestCase): ''' Test the DB field & usage ''' def setUp(self): - imgsrv = ImageServer.objects.create(name="Test Server", url="http://server") - self.img = Image.objects.create(path='img', width=1000, height=1000, server=imgsrv) - self.z1 = Zone.objects.create( + self.img = Image.objects.get(path='img3', server=self.imgsrv) + self.z1 = Zone.objects.get( image=self.img, polygon=[(0, 0), (0, 1000), (1000, 1000), (1000, 0), (0, 0)]) - self.z2 = Zone.objects.create( - image=self.img, polygon=[(200, 200), (200, 300), (300, 300), (300, 200), (200, 200)]) - self.z3 = Zone.objects.create( - image=self.img, polygon=[(500, 500), (500, 600), (600, 600), (600, 500), (500, 500)]) + self.z2 = Zone.objects.get( + image=self.img, polygon=[(0, 0), (0, 300), (300, 300), (300, 0), (0, 0)]) + self.z3 = Zone.objects.get( + image=self.img, polygon=[(300, 300), (300, 600), (600, 600), (600, 300), (300, 300)]) def test_field(self): - self.assertListEqual(self.z1.polygon, [(0, 0), (0, 1000), (1000, 1000), (1000, 0), (0, 0)]) + self.assertSequenceEqual(self.z1.polygon, [(0, 0), (0, 1000), (1000, 1000), (1000, 0), (0, 0)]) def test_contains(self): - self.assertSequenceEqual(Zone.objects.filter(polygon__contains=self.z2.polygon), [self.z1, self.z2]) - self.assertSequenceEqual(Zone.objects.filter(polygon__contains=self.z3.polygon), [self.z1, self.z3]) - self.assertSequenceEqual(Zone.objects.filter(polygon__contains=self.z1.polygon), [self.z1]) + self.assertCountEqual( + Zone.objects.filter(image=self.img, polygon__contains=self.z2.polygon), + [self.z1, self.z2]) + self.assertCountEqual( + Zone.objects.filter(image=self.img, polygon__contains=self.z3.polygon), + [self.z1, self.z3]) + self.assertCountEqual( + Zone.objects.filter(image=self.img, polygon__contains=self.z1.polygon), + [self.z1]) diff --git a/arkindex/project/tests/test_tools.py b/arkindex/project/tests/test_tools.py index ea245978e2af2313ac3110814e3f1448cd303683..b9c1cffd7612ff581b44755d1c5af62a4a0c8e57 100644 --- a/arkindex/project/tests/test_tools.py +++ b/arkindex/project/tests/test_tools.py @@ -1,4 +1,4 @@ -from django.test import TestCase +from unittest import TestCase from arkindex.project.tools import elasticsearch_escape diff --git a/requirements.txt b/requirements.txt index 0cfe25a62188e46aabc6d34070464967869fd135..f723301e560f4813a50734a637e68f8ac3686fce 100644 --- a/requirements.txt +++ b/requirements.txt @@ -3,7 +3,7 @@ celery_once==2.0.0 certifi==2017.7.27.1 chardet==3.0.4 Django==2.0 -django-enumfields==0.9.0 +django-enumfields==0.10.0 djangorestframework==3.7.1 django-webpack-loader==0.5.0 elasticsearch==6.2.0