Merge branch 'master' into training

# Conflicts:
#	RIGS/templates/risk_assessment_form.html
#	templates/base.html
This commit is contained in:
2021-10-08 18:40:39 +01:00
36 changed files with 592 additions and 437 deletions

View File

@@ -23,7 +23,6 @@ Django = "~=3.1.12"
django-debug-toolbar = "~=3.2"
django-filter = "~=2.4.0"
django-ical = "~=1.7.1"
django-recaptcha = "~=2.0.6"
django-recurrence = "~=1.10.3"
django-registration-redux = "~=2.9"
django-reversion = "~=3.0.9"
@@ -39,7 +38,7 @@ lxml = "~=4.6.3"
Markdown = "~=3.3.3"
msgpack = "~=1.0.2"
pep517 = "~=0.9.1"
Pillow = "~=8.2.0"
Pillow = "~=8.3.2"
premailer = "~=3.7.0"
progress = "~=1.5"
psutil = "~=5.8.0"
@@ -57,7 +56,7 @@ retrying = "~=1.3.3"
simplejson = "~=3.17.2"
six = "~=1.15.0"
soupsieve = "~=2.1"
sqlparse = "~=0.4.1"
sqlparse = "~=0.4.2"
static3 = "~=0.7.0"
svg2rlg = "~=0.3"
tini = "~=3.0.1"
@@ -77,6 +76,8 @@ zipp = "~=3.4.0"
"zope.schema" = "~=6.0.1"
sentry-sdk = "*"
diff-match-patch = "*"
python-barcode = "*"
django-hCaptcha = "*"
[dev-packages]
selenium = "~=3.141.0"

499
Pipfile.lock generated
View File

@@ -1,7 +1,7 @@
{
"_meta": {
"hash": {
"sha256": "ef5cfe5505d1e3cd15d0c0690a3a1b7475364b9a42555c0d90d0ee30b11bf322"
"sha256": "ad1849939ea22858eeac17e407bacd6b5abdac3279a845ca275ea64073d71dd9"
},
"pipfile-spec": 6,
"requires": {
@@ -26,11 +26,11 @@
},
"asgiref": {
"hashes": [
"sha256:5ee950735509d04eb673bd7f7120f8fa1c9e2df495394992c73234d526907e17",
"sha256:7162a3cb30ab0609f1a4c95938fd73e8604f63bdba516a7f7d64b83ff09478f0"
"sha256:92906c611ce6c967347bbfea733f13d6313901d54dcca88195eaeb52b2a8e8ee",
"sha256:d1216dfbdfb63826470995d31caed36225dcaf34f182e0fa257a4dd9e86f1b78"
],
"index": "pypi",
"version": "==3.3.1"
"version": "==3.3.4"
},
"backports.tempfile": {
"hashes": [
@@ -61,12 +61,17 @@
"hashes": [
"sha256:160c78292e98d21e73a4cc7f76a234390e516afcd982fa17e1422f7c6a9ce9c8",
"sha256:16d528a45c2e1909c2798f27f7bf0a3feec1dc9e50948e738b961618e38b6a7b",
"sha256:19598ecddd8a212aedb1ffa15763dd52a388518c4550e615aed88dc3753c0f0c",
"sha256:1c48472a6ba3b113452355b9af0a60da5c2ae60477f8feda8346f8fd48e3e87c",
"sha256:268fe94547ba25b58ebc724680609c8ee3e5a843202e9a381f6f9c5e8bdb5c70",
"sha256:269a5743a393c65db46a7bb982644c67ecba4b8d91b392403ad8a861ba6f495f",
"sha256:26d168aac4aaec9a4394221240e8a5436b5634adc3cd1cdf637f6645cecbf181",
"sha256:29d1d350178e5225397e28ea1b7aca3648fcbab546d20e7475805437bfb0a130",
"sha256:2aad0e0baa04517741c9bb5b07586c642302e5fb3e75319cb62087bd0995ab19",
"sha256:35a3edbe18e876e596553c4007a087f8bcfd538f19bc116917b3c7522fca0429",
"sha256:3b78a24b5fd13c03ee2b7b86290ed20efdc95da75a3557cc06811764d5ad1126",
"sha256:40d15c79f42e0a2c72892bf407979febd9cf91f36f495ffb333d1d04cebb34e4",
"sha256:44bb8ff420c1d19d91d79d8c3574b8954288bdff0273bf788954064d260d7ab0",
"sha256:4d1b810aa0ed773f81dceda2cc7b403d01057458730e309856356d4ef4188438",
"sha256:503fa6af7da9f4b5780bb7e4cbe0c639b010f12be85d02c99452825dd0feef3f",
"sha256:56d027eace784738457437df7331965473f2c0da2c70e1a1f6fdbae5402e0389",
@@ -74,15 +79,24 @@
"sha256:5b6ef7d9f9c38292df3690fe3e302b5b530999fa90014853dcd0d6902fb59f26",
"sha256:5cb1e18167792d7d21e21365d7650b72d5081ed476123ff7b8cac7f45189c0c7",
"sha256:61a7ee1f13ab913897dac7da44a73c6d44d48a4adff42a5701e3239791c96e14",
"sha256:622a231b08899c864eb87e85f81c75e7b9ce05b001e59bbfbf43d4a71f5f32b2",
"sha256:68715970f16b6e92c574c30747c95cf8cf62804569647386ff032195dc89a430",
"sha256:6b2ae9f5f67f89aade1fab0f7fd8f2832501311c363a21579d02defa844d9296",
"sha256:6c772d6c0a79ac0f414a9f8947cc407e119b8598de7621f39cacadae3cf57d12",
"sha256:76ffebb907bec09ff511bb3acc077695e2c32bc2142819491579a695f77ffd4d",
"sha256:7cb81373984cc0e4682f31bc3d6be9026006d96eecd07ea49aafb06897746452",
"sha256:7ee83d3e3a024a9618e5be64648d6d11c37047ac48adff25f12fa4226cf23d1c",
"sha256:854c33dad5ba0fbd6ab69185fec8dab89e13cda6b7d191ba111987df74f38761",
"sha256:87fdccbb6bb589095f413b1e05734ba492c962b4a45a13ff3408fa44ffe6479b",
"sha256:88c63a1b55f352b02c6ffd24b15ead9fc0e8bf781dbe070213039324922a2eea",
"sha256:8a674ac10e0a87b683f4fa2b6fa41090edfd686a6524bd8dedbd6138b309175c",
"sha256:93130612b837103e15ac3f9cbacb4613f9e348b58b3aad53721d92e57f96d46a",
"sha256:9744a863b489c79a73aba014df554b0e7a0fc44ef3f8a0ef2a52919c7d155031",
"sha256:9749a124280a0ada4187a6cfd1ffd35c350fb3af79c706589d98e088c5044267",
"sha256:97f715cf371b16ac88b8c19da00029804e20e25f30d80203417255d239f228b5",
"sha256:9bf919756d25e4114ace16a8ce91eb340eb57a08e2c6950c3cebcbe3dff2a5e7",
"sha256:9d12cf2851759b8de8ca5fde36a59c08210a97ffca0eb94c532ce7b17c6a3d1d",
"sha256:a72661af47119a80d82fa583b554095308d6a4c356b2a554fdc2799bc19f2a43",
"sha256:afde17ae04d90fbe53afb628f7f2d4ca022797aa093e809de5c3cf276f61bbfa",
"sha256:b663f1e02de5d0573610756398e44c130add0eb9a3fc912a09665332942a2efb",
"sha256:c2415d9d082152460f2bd4e382a1e85aed233abc92db5a3880da2257dc7daf7b",
@@ -90,6 +104,7 @@
"sha256:cfc391f4429ee0a9370aa93d812a52e1fee0f37a81861f4fdd1f4fb28e8547c3",
"sha256:db844eb158a87ccab83e868a762ea8024ae27337fc7ddcbfcddd157f841fdfe7",
"sha256:defed7ea5f218a9f2336301e6fd379f55c655bea65ba2476346340a0ce6f74a1",
"sha256:e16eb9541f3dd1a3e92b89005e37b1257b157b7256df0e36bd7b33b50be73bcb",
"sha256:f909bbbc433048b499cb9db9e713b5d8d949e8c109a2a548502fb9aa8630f0b1"
],
"index": "pypi",
@@ -97,11 +112,11 @@
},
"cachetools": {
"hashes": [
"sha256:1d9d5f567be80f7c07d765e21b814326d78c61eb0c3a637dffc0e5d1796cb2e2",
"sha256:f469e29e7aa4cff64d8de4aad95ce76de8ea1125a16c68e0d93f65c3c3dc92e9"
"sha256:2cc0b89715337ab6dbba85b5b50effe2b0c74e035d83ee8ed637cf52f12ae001",
"sha256:61b5ed1e22a0924aed1d23b478f37e8d52549ff8a961de2909c69bf950020cff"
],
"index": "pypi",
"version": "==4.2.1"
"version": "==4.2.2"
},
"certifi": {
"hashes": [
@@ -176,19 +191,19 @@
},
"django": {
"hashes": [
"sha256:a523d62b7ab2908f551dabc32b99017a86aa7784e32b761708e52be3dce6d35d",
"sha256:dc41bf07357f1f4810c1c555b685cb51f780b41e37892d6cc92b89789f2847e1"
"sha256:9f8be75646f62204320b195062b1d696ba28aa3d45ee72fb7c888ffaebc5bdb2",
"sha256:a6e0d1ff11095b7394c079ade7094c73b2dc3df4a7a373c9b58ed73b77a97feb"
],
"index": "pypi",
"version": "==3.1.12"
"version": "==3.1.13"
},
"django-debug-toolbar": {
"hashes": [
"sha256:a5ff2a54f24bf88286f9872836081078f4baa843dc3735ee88524e89f8821e33",
"sha256:e759e63e3fe2d3110e0e519639c166816368701eab4a47fed75d7de7018467b9"
"sha256:8c5b13795d4040008ee69ba82dcdd259c49db346cf7d0de6e561a49d191f0860",
"sha256:d7bab7573fab35b0fd029163371b7182f5826c13da69734beb675c761d06a4d3"
],
"index": "pypi",
"version": "==3.2.1"
"version": "==3.2.2"
},
"django-filter": {
"hashes": [
@@ -198,6 +213,13 @@
"index": "pypi",
"version": "==2.4.0"
},
"django-hcaptcha": {
"hashes": [
"sha256:2b80197c07bb8444249bcce3758b0472d369cca309fb02d7abcd0a856431b76b"
],
"index": "pypi",
"version": "==0.1.0"
},
"django-htmlmin": {
"hashes": [
"sha256:e41b2a2157570846645cc636a9bddde8aa3e03f6834a9211e61a17f2ed42b87e"
@@ -207,18 +229,11 @@
},
"django-ical": {
"hashes": [
"sha256:42bb51020f935342fe78f0202346a0775777811a4bdbc1c9c32bb8ec068d2f95",
"sha256:645344dda9611ca77dc3609f53b6e751bd89cc7d01f77adf1fd72838992b5579"
"sha256:6df4dc61eb4abc55816bd16a949e497bea99828c7de648438ace7f1f85eeb405",
"sha256:bd5c874d2eb81329f220174cc0dde7be385f4574ce6c8a2d1579d7fd564a94f3"
],
"index": "pypi",
"version": "==1.7.1"
},
"django-recaptcha": {
"hashes": [
"sha256:567784963fd5400feaf92e8951d8dbbbdb4b4c48a76e225d4baa63a2c9d2cd8c"
],
"index": "pypi",
"version": "==2.0.6"
"version": "==1.7.3"
},
"django-recurrence": {
"hashes": [
@@ -279,7 +294,6 @@
"sha256:0d78f8fde1c230e99fe37986a60526d7049ed4bf8a9fadbad5f00e22e58e041d",
"sha256:b2e5b40261e20f354d198eae92afc10d750afb487ed5e50f9c4eaf07c184146f"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4'",
"version": "==1.1"
},
"icalendar": {
@@ -327,6 +341,7 @@
"sha256:542d454665a3e277f76954418124d67516c5f88e51a900365ed54a9806122b83",
"sha256:5a0a14e264069c03e46f926be0d8919f4105c1623d620e7ec0e612a2e9bf1c04",
"sha256:5c8c163396cc0df3fd151b927e74f6e4acd67160d6c33304e805b84293351d16",
"sha256:64812391546a18896adaa86c77c59a4998f33c24788cadc35789e55b727a37f4",
"sha256:66e575c62792c3f9ca47cb8b6fab9e35bab91360c783d1606f758761810c9791",
"sha256:6f12e1427285008fd32a6025e38e977d44d6382cf28e7201ed10d6c1698d2a9a",
"sha256:74f7d8d439b18fa4c385f3f5dfd11144bb87c1da034a466c5b5577d23a1d9b51",
@@ -341,6 +356,7 @@
"sha256:b007cbb845b28db4fb8b6a5cdcbf65bacb16a8bd328b53cbc0698688a68e1caa",
"sha256:bc4313cbeb0e7a416a488d72f9680fffffc645f8a838bd2193809881c67dd106",
"sha256:bccbfc27563652de7dc9bdc595cb25e90b59c5f8e23e806ed0fd623755b6565d",
"sha256:c1a40c06fd5ba37ad39caa0b3144eb3772e813b5fb5b084198a985431c2f1e8d",
"sha256:c47ff7e0a36d4efac9fd692cfa33fbd0636674c102e9e8d9b26e1b93a94e7617",
"sha256:c4f05c5a7c49d2fb70223d0d5bcfbe474cf928310ac9fa6a7c6dddc831d0b1d4",
"sha256:cdaf11d2bd275bf391b5308f86731e5194a21af45fbaaaf1d9e8147b9160ea92",
@@ -410,83 +426,99 @@
},
"pikepdf": {
"hashes": [
"sha256:1bc381015edd3793bd2f458b1b7fa0412550b0769f7371b4329481892cc482c8",
"sha256:2526569db97a67ea00308145fd0ed56c65fb268befba1a67f58f262be8f70262",
"sha256:2a6689fc87f3886cf6d801a5cb606e4464b71f0408557010f503cf02f3ce95d2",
"sha256:33643d8ff2339e7cef803227fdf9fe96461d38d79c9bf9fd26d910e27d3c49d1",
"sha256:394b56c095d45e9a312ced15e5f24c3d2b5f690702ff066bca5da169e66da27c",
"sha256:3bc9f6842865cfaa128802cdf15d7dcae60ba86b11af46ad65db5c3e9ecdbbb6",
"sha256:4331bbab201136b83bac6977b750477e83dbb8356080cfaf99b0eca98ec12ce4",
"sha256:502ce98b1bc3e96aee9b38f2f4dc1542452d32a98f351f198ee6e2b387257ee4",
"sha256:624e2d988627c1362bf83ff341b07ddee87809c9966da4eca48d8fca11099b0a",
"sha256:66dd2be87c0ec317f80253d50296cfcf22c81667c69894ec7d4c892b1a613fbf",
"sha256:6d665d4f1f98f8b264dbe677dd59f0c80bf3ad5c739a349186ab3f076bf7e3f0",
"sha256:7d156055a94fc0b01656afc49602311b40f0224013092ad27373826ea034aac2",
"sha256:8afb75b9933b2cb7eb4cd34af4fff2b97e45ba9b7c3ce2cc42fbd72458ad3b0b",
"sha256:8cd16afcc374cf5b122870603492e31a446285c3ef5f8389bf616cb85c504db2",
"sha256:8e3c03319013ec00406c09671413c7b47ac1dd23e67a872c2386cd0538d7e371",
"sha256:9484921319aa072f7471b823bd196879f97945e811f9d9bc0a15e52ae05a25b6",
"sha256:9c479fc03a68ad0d34d0de59d9264d0c9f4fd7d573c3173117f287123b19c244",
"sha256:a414898948ffb27ab797b41a19869e3b68a1476044a7e6cdd24e574077f1e9b3",
"sha256:a6f0774e83a72175a166ac75dd3b75320efecf506a6e5b65c007f61bb9552376",
"sha256:ae8b85cd77af424d0cc07a0aee539c5da11bd545bf72193841ad5f58bd26f979",
"sha256:b18a90b4c6abaa1bf4b2b39266fa02c833be87c219b0e7cdfdb02c43e77eefe7",
"sha256:bcfc8841d911b9c3a637ffa721ab83166876c6245ccb04fdeae1580cf2f7b3f9",
"sha256:bfe796abe75e75659c5966332e08dda1a94b2f00ffddd5547802df454def6080",
"sha256:d19b8f611d1c660d2048511921ed8ac26b2c6a694dbf96cd668c15397c857f63",
"sha256:d7426734b3f1f22637e1b3cf0cfaacbc7c9daab8ef558e1a299eebc8266ce8da",
"sha256:ed7b6f9fab3b4eef527301a0628ecc47586593d6c85fafc3d4b3e86206025e6e"
"sha256:1de8b978bbea7024576db18f0e8c58cba1092b07898e7b6350fbc1d6b51a736d",
"sha256:2b5dcb5857743c5c903270bcce0184593d81d6b771e8a18480ba0026329d45c5",
"sha256:31473ac2506fede408d43decca8bd31fdd0f8528e202b8bb6c7a3c32dff594c4",
"sha256:32f83164accd8e570fcbe0378dfe5b781e37c515d74ade55a086140d85f2439b",
"sha256:36f48a3261904f1350dbbf63d4a8d6587ecb70fccd596ad6af688a453e449900",
"sha256:3a370dec316a4dad572a2c37c8734cd543ee499e4d502cedb090011f5d7fcd7b",
"sha256:3c17937e230b22afa975e69130e89df2911dd1e2c7bbe200138684154e428843",
"sha256:3d097af6bb735fe23ca1f7386f967adffdd0e51f9bc6fb92657ad0f2a0a24e76",
"sha256:4c2114630ae4e9fc69c127f154786765a53f87df306a802f58d8622bdb06b12e",
"sha256:5f8766bfdc4fd9ce879c3e0973b6b979ec7bcf4cf693179b34c3841ee39ecaf8",
"sha256:62932d06265c821ca161d6bba6c7b8fb4804129acbb75877351403e5e8fcd27f",
"sha256:6866deb4a4fd5defe186e418be04a9540b7240c06a8752b4ba6c5d6f33fcad76",
"sha256:81c628d7eae51b7a076b88e04b66681556f4bc7373cecf80e4c1155c18e50032",
"sha256:9188295bce64648bed2364b96aa7a946de6db6cdefb77fee21b0bd63b6978561",
"sha256:b1592772761bde77be1fb6ffc2be5131f25bb38412d89e433d5fe13a8a62f8e9",
"sha256:b213b4665161f1447e82fc05c51f95bbcdb9b26c733f0ded2d6d7427bbef4b7c",
"sha256:bbded0e77da1b07a4bfde920a44514ebeecd57174c2c39c02a630250953e5553",
"sha256:c0c4d4c17f644024235263b20e766939dde1e63f1cb616f74331e7d901275f35",
"sha256:cb2b3ef8aeb69b66a5e13834671a4a040ffc116d364e0cafd8b96472d18d1403",
"sha256:cc02f01011a291e2e702884438517e6ce7eee3cafb2bc61b4fa9d73dab514111",
"sha256:d9612d1570c698b75ff4530e866a35b100cf7588345e3fc98fdc39c2baaa637d",
"sha256:dd65b9c87ff8c3a6838e50e6268407505457c1bd72037d7801828b94a6bed826",
"sha256:e94c00bc3cefda5a4d1289f486f79b56be2f564c841d3753e749d9c3a076e67a",
"sha256:f147932f1090a029c208a37a979cd8b97bdd6107c4885faeabf8c9da6cd32c43",
"sha256:f1a31fcb7f34609eca0b3330ad4fbc38ff3b30b9341a0ff69a0cd7e376ce6b91"
],
"markers": "python_version >= '3.6'",
"version": "==2.13.0"
"version": "==3.0.0"
},
"pillow": {
"hashes": [
"sha256:01425106e4e8cee195a411f729cff2a7d61813b0b11737c12bd5991f5f14bcd5",
"sha256:031a6c88c77d08aab84fecc05c3cde8414cd6f8406f4d2b16fed1e97634cc8a4",
"sha256:083781abd261bdabf090ad07bb69f8f5599943ddb539d64497ed021b2a67e5a9",
"sha256:0d19d70ee7c2ba97631bae1e7d4725cdb2ecf238178096e8c82ee481e189168a",
"sha256:0e04d61f0064b545b989126197930807c86bcbd4534d39168f4aa5fda39bb8f9",
"sha256:12e5e7471f9b637762453da74e390e56cc43e486a88289995c1f4c1dc0bfe727",
"sha256:22fd0f42ad15dfdde6c581347eaa4adb9a6fc4b865f90b23378aa7914895e120",
"sha256:238c197fc275b475e87c1453b05b467d2d02c2915fdfdd4af126145ff2e4610c",
"sha256:3b570f84a6161cf8865c4e08adf629441f56e32f180f7aa4ccbd2e0a5a02cba2",
"sha256:463822e2f0d81459e113372a168f2ff59723e78528f91f0bd25680ac185cf797",
"sha256:4d98abdd6b1e3bf1a1cbb14c3895226816e666749ac040c4e2554231068c639b",
"sha256:5afe6b237a0b81bd54b53f835a153770802f164c5570bab5e005aad693dab87f",
"sha256:5b70110acb39f3aff6b74cf09bb4169b167e2660dabc304c1e25b6555fa781ef",
"sha256:5cbf3e3b1014dddc45496e8cf38b9f099c95a326275885199f427825c6522232",
"sha256:624b977355cde8b065f6d51b98497d6cd5fbdd4f36405f7a8790e3376125e2bb",
"sha256:63728564c1410d99e6d1ae8e3b810fe012bc440952168af0a2877e8ff5ab96b9",
"sha256:66cc56579fd91f517290ab02c51e3a80f581aba45fd924fcdee01fa06e635812",
"sha256:6c32cc3145928c4305d142ebec682419a6c0a8ce9e33db900027ddca1ec39178",
"sha256:8b56553c0345ad6dcb2e9b433ae47d67f95fc23fe28a0bde15a120f25257e291",
"sha256:8bb1e155a74e1bfbacd84555ea62fa21c58e0b4e7e6b20e4447b8d07990ac78b",
"sha256:95d5ef984eff897850f3a83883363da64aae1000e79cb3c321915468e8c6add5",
"sha256:a013cbe25d20c2e0c4e85a9daf438f85121a4d0344ddc76e33fd7e3965d9af4b",
"sha256:a787ab10d7bb5494e5f76536ac460741788f1fbce851068d73a87ca7c35fc3e1",
"sha256:a7d5e9fad90eff8f6f6106d3b98b553a88b6f976e51fce287192a5d2d5363713",
"sha256:aac00e4bc94d1b7813fe882c28990c1bc2f9d0e1aa765a5f2b516e8a6a16a9e4",
"sha256:b91c36492a4bbb1ee855b7d16fe51379e5f96b85692dc8210831fbb24c43e484",
"sha256:c03c07ed32c5324939b19e36ae5f75c660c81461e312a41aea30acdd46f93a7c",
"sha256:c5236606e8570542ed424849f7852a0ff0bce2c4c8d0ba05cc202a5a9c97dee9",
"sha256:c6b39294464b03457f9064e98c124e09008b35a62e3189d3513e5148611c9388",
"sha256:cb7a09e173903541fa888ba010c345893cd9fc1b5891aaf060f6ca77b6a3722d",
"sha256:d68cb92c408261f806b15923834203f024110a2e2872ecb0bd2a110f89d3c602",
"sha256:dc38f57d8f20f06dd7c3161c59ca2c86893632623f33a42d592f097b00f720a9",
"sha256:e98eca29a05913e82177b3ba3d198b1728e164869c613d76d0de4bde6768a50e",
"sha256:f217c3954ce5fd88303fc0c317af55d5e0204106d86dea17eb8205700d47dec2"
"sha256:0412516dcc9de9b0a1e0ae25a280015809de8270f134cc2c1e32c4eeb397cf30",
"sha256:04835e68ef12904bc3e1fd002b33eea0779320d4346082bd5b24bec12ad9c3e9",
"sha256:06d1adaa284696785375fa80a6a8eb309be722cf4ef8949518beb34487a3df71",
"sha256:085a90a99404b859a4b6c3daa42afde17cb3ad3115e44a75f0d7b4a32f06a6c9",
"sha256:0b9911ec70731711c3b6ebcde26caea620cbdd9dcb73c67b0730c8817f24711b",
"sha256:10e00f7336780ca7d3653cf3ac26f068fa11b5a96894ea29a64d3dc4b810d630",
"sha256:11c27e74bab423eb3c9232d97553111cc0be81b74b47165f07ebfdd29d825875",
"sha256:11eb7f98165d56042545c9e6db3ce394ed8b45089a67124298f0473b29cb60b2",
"sha256:13654b521fb98abdecec105ea3fb5ba863d1548c9b58831dd5105bb3873569f1",
"sha256:15ccb81a6ffc57ea0137f9f3ac2737ffa1d11f786244d719639df17476d399a7",
"sha256:18a07a683805d32826c09acfce44a90bf474e6a66ce482b1c7fcd3757d588df3",
"sha256:19ec4cfe4b961edc249b0e04b5618666c23a83bc35842dea2bfd5dfa0157f81b",
"sha256:1c3ff00110835bdda2b1e2b07f4a2548a39744bb7de5946dc8e95517c4fb2ca6",
"sha256:27a330bf7014ee034046db43ccbb05c766aa9e70b8d6c5260bfc38d73103b0ba",
"sha256:2b11c9d310a3522b0fd3c35667914271f570576a0e387701f370eb39d45f08a4",
"sha256:2c661542c6f71dfd9dc82d9d29a8386287e82813b0375b3a02983feac69ef864",
"sha256:2cde7a4d3687f21cffdf5bb171172070bb95e02af448c4c8b2f223d783214056",
"sha256:2d5e9dc0bf1b5d9048a94c48d0813b6c96fccfa4ccf276d9c36308840f40c228",
"sha256:2f23b2d3079522fdf3c09de6517f625f7a964f916c956527bed805ac043799b8",
"sha256:35d27687f027ad25a8d0ef45dd5208ef044c588003cdcedf05afb00dbc5c2deb",
"sha256:35d409030bf3bd05fa66fb5fdedc39c521b397f61ad04309c90444e893d05f7d",
"sha256:4326ea1e2722f3dc00ed77c36d3b5354b8fb7399fb59230249ea6d59cbed90da",
"sha256:4abc247b31a98f29e5224f2d31ef15f86a71f79c7f4d2ac345a5d551d6393073",
"sha256:4d89a2e9219a526401015153c0e9dd48319ea6ab9fe3b066a20aa9aee23d9fd3",
"sha256:4e59e99fd680e2b8b11bbd463f3c9450ab799305d5f2bafb74fefba6ac058616",
"sha256:548794f99ff52a73a156771a0402f5e1c35285bd981046a502d7e4793e8facaa",
"sha256:56fd98c8294f57636084f4b076b75f86c57b2a63a8410c0cd172bc93695ee979",
"sha256:59697568a0455764a094585b2551fd76bfd6b959c9f92d4bdec9d0e14616303a",
"sha256:6bff50ba9891be0a004ef48828e012babaaf7da204d81ab9be37480b9020a82b",
"sha256:6cb3dd7f23b044b0737317f892d399f9e2f0b3a02b22b2c692851fb8120d82c6",
"sha256:7dbfbc0020aa1d9bc1b0b8bcf255a7d73f4ad0336f8fd2533fcc54a4ccfb9441",
"sha256:838eb85de6d9307c19c655c726f8d13b8b646f144ca6b3771fa62b711ebf7624",
"sha256:8b68f565a4175e12e68ca900af8910e8fe48aaa48fd3ca853494f384e11c8bcd",
"sha256:8f284dc1695caf71a74f24993b7c7473d77bc760be45f776a2c2f4e04c170550",
"sha256:963ebdc5365d748185fdb06daf2ac758116deecb2277ec5ae98139f93844bc09",
"sha256:a048dad5ed6ad1fad338c02c609b862dfaa921fcd065d747194a6805f91f2196",
"sha256:a1bd983c565f92779be456ece2479840ec39d386007cd4ae83382646293d681b",
"sha256:a66566f8a22561fc1a88dc87606c69b84fa9ce724f99522cf922c801ec68f5c1",
"sha256:bcb04ff12e79b28be6c9988f275e7ab69f01cc2ba319fb3114f87817bb7c74b6",
"sha256:bd24054aaf21e70a51e2a2a5ed1183560d3a69e6f9594a4bfe360a46f94eba83",
"sha256:be25cb93442c6d2f8702c599b51184bd3ccd83adebd08886b682173e09ef0c3f",
"sha256:c691b26283c3a31594683217d746f1dad59a7ae1d4cfc24626d7a064a11197d4",
"sha256:cc9d0dec711c914ed500f1d0d3822868760954dce98dfb0b7382a854aee55d19",
"sha256:ce2e5e04bb86da6187f96d7bab3f93a7877830981b37f0287dd6479e27a10341",
"sha256:ce651ca46d0202c302a535d3047c55a0131a720cf554a578fc1b8a2aff0e7d96",
"sha256:d0c8ebbfd439c37624db98f3877d9ed12c137cadd99dde2d2eae0dab0bbfc355",
"sha256:d675a876b295afa114ca8bf42d7f86b5fb1298e1b6bb9a24405a3f6c8338811c",
"sha256:dde3f3ed8d00c72631bc19cbfff8ad3b6215062a5eed402381ad365f82f0c18c",
"sha256:e5a31c07cea5edbaeb4bdba6f2b87db7d3dc0f446f379d907e51cc70ea375629",
"sha256:f514c2717012859ccb349c97862568fdc0479aad85b0270d6b5a6509dbc142e2",
"sha256:fc0db32f7223b094964e71729c0361f93db43664dd1ec86d3df217853cedda87",
"sha256:fd4fd83aa912d7b89b4b4a1580d30e2a4242f3936882a3f433586e5ab97ed0d5",
"sha256:feb5db446e96bfecfec078b943cc07744cc759893cef045aa8b8b6d6aaa8274e"
],
"index": "pypi",
"version": "==8.2.0"
"version": "==8.3.2"
},
"pluggy": {
"hashes": [
"sha256:15b2acde666561e1298d71b523007ed7364de07029219b604cf808bfa1c765b0",
"sha256:966c145cd83c96502c3c3868f50408687b38434af77734af1e9ca461a4081d2d"
"sha256:4224373bacce55f955a878bf9cfa763c1e360858e330072059e10bad68531159",
"sha256:74134bbf457f031a36d68416e1509f34bd5ccc019f0bcc952c7b909d06b37bd3"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3'",
"version": "==0.13.1"
"version": "==1.0.0"
},
"premailer": {
"hashes": [
@@ -498,10 +530,10 @@
},
"progress": {
"hashes": [
"sha256:69ecedd1d1bbe71bf6313d88d1e6c4d2957b7f1d4f71312c211257f7dae64372"
"sha256:c9c86e98b5c03fa1fe11e3b67c1feda4788b8d0fe7336c2ff7d5644ccfba34cd"
],
"index": "pypi",
"version": "==1.5"
"version": "==1.6"
},
"psutil": {
"hashes": [
@@ -589,13 +621,21 @@
"index": "pypi",
"version": "==2.2.0"
},
"python-dateutil": {
"python-barcode": {
"hashes": [
"sha256:73ebfe9dbf22e832286dafa60473e4cd239f8592f699aa5adaf10050e6e1823c",
"sha256:75bb3f31ea686f1197762692a9ee6a7550b59fc6ca3a1f4b5d7e32fb98e2da2a"
"sha256:daa32fb999a843812fbb1c75ff909638811af7c465f0a991e9e41d26d2a44a24",
"sha256:fafba4aa24e9d969777be521c294ff18f6c2b36ad63b5fc2f2108d972e23b252"
],
"index": "pypi",
"version": "==2.8.1"
"version": "==0.13.1"
},
"python-dateutil": {
"hashes": [
"sha256:0123cacc1627ae19ddf3c27a5de5bd67ee4586fbdd6440d9748f8abb483d3e86",
"sha256:961d03dc3453ebbc59dbdea9e4e11c5651520a876d0f4db161e8674aae935da9"
],
"index": "pypi",
"version": "==2.8.2"
},
"pytoml": {
"hashes": [
@@ -615,38 +655,38 @@
},
"reportlab": {
"hashes": [
"sha256:07f9d9c0360cb8fc780ca05264faa68b90583cd28dbdf2cda6bda34379b6e66c",
"sha256:27a831da0d17153e33c985bd7a88307e206c5a28778cddb755d5372598d12637",
"sha256:289539f7888239343ef7ebcd30c55e6204ef78d5f70e1547fdeb854a2da8bfa1",
"sha256:3ec70873d99c14570e2a9c44b86c8c01526871e7af5ee4b2855246db15cb0c9f",
"sha256:46745826657d35f86843487f4bc6f6f805f61260428f8ee13642bf6372f9df55",
"sha256:4a784ecdf3008f533e5a032b96c395e8592ed5e679baaf5ef4dcc136b01c72e9",
"sha256:4c42e85851f969e21fa4d6414587b7544e877ce685e2495d7d422589c70b6281",
"sha256:58bec163f727c1c60515fc4704a961b3b4ccf2c76b4e6ec1a457ea7ed0c2d756",
"sha256:6f007142f2b166f52cbb3e5d23319e3e496c429831e53b904e6db28c3370f279",
"sha256:81898de0a0be2c8318468ae0ae1590f828805e9b7fd68e5a50667dce8b942171",
"sha256:8707cc21a769150154bf4634dca6e9581ae24a05f0fb81a84fcc1143b1cbbfde",
"sha256:99aeee49a61c85f1af1087e9e418f3d0c2352c4dd0f0abbfac17ae6c467185aa",
"sha256:9ec95808b742ce70c1dab28b2c5bef9093816b92315b948419c2c6968658f9cc",
"sha256:b2c7eedb4d19db63301c27ad1076086a099fd4c8ca0a6f62f6e9ed749fa5908f",
"sha256:b2cf692ae7af995b499a31a3f58f2001d98e310e03f74812bcb97a08078239c0",
"sha256:b9494986f35d82350b0ce0c29704a49a3945421b789dff92e93fbd3de554fa34",
"sha256:ba2d10f368c9ea1e76c84b3bb6b9982eb5a8f243c434e821c505b75ca8d85852",
"sha256:bc62187181582772688d65c557ad6a40a4c3bb8d1f74de463d35ea81983e9b75",
"sha256:bdf751289efee4891f4f354ce9122da8de8258a40f328b3f11540c4888363337",
"sha256:c12432575c793b8cd8552fddc219bbf2813541c64d02854ae345a108fb875b9d",
"sha256:cdf8ff72cd6fa9303744c8409fb81ef7720da2e034c369762c2fdf496462179e",
"sha256:d810bffd4bcd50fdcb2bab0d1fe9ea4e6187ed5237687e41c6ade6c884b00c1e",
"sha256:d8fefd07072bfae2715283a821fb1acf8fc4946cf925509d5cc2af791c611809",
"sha256:d92834993bf998853a04946729266a3276965e7b13f7423212f1c1abdfc4a1c7",
"sha256:ee711804acdaf3ea7f0f2cd27f19478af993e730df8c8d923a678eb0e2572fba",
"sha256:f0634740b099b69caed081acd89692996b5504c59f86f39781b6bebc82b267f5",
"sha256:f92388e30bf6b5d2eceb3d7b05ee2df856635f74ce7d950a8f45d2b70c685a5b",
"sha256:fd6712a8a6dca12181a3a12316f97810927861e77f2a98029efd2c5cfc8546dc",
"sha256:fe5d98cdac07dd702bcd49f5723aacdd0af8c84d70fc82a5cc3781e52aedad52"
"sha256:010f86a192c397f7c8ae667953a85d913395a8a6a8da112bff1c1ea28e679bcd",
"sha256:08b53568979228b6969b790339d06a0b8db8883f92ae7339013f9878042dd9ca",
"sha256:19708801278f600d712c04ee6bfb650e45d1b2898713f7bd97b39ab89bd08c1e",
"sha256:28c72d27f21d74a7301789c7950b5e82a430ed38817ecee060fa1f2f3e959360",
"sha256:2c0c88a7cf83a20a2bb355f97a1a9d0373a6de60c3aec35d301d3cc75dc4bb72",
"sha256:2dc5ee0c5b659697cdfbc218ec9abea54dd9c5a95ea8ca95245fe94f5ef111f9",
"sha256:332f836ff4c975c92d307302e86a54d6f0e3d2ce33a35759812e7a1d17e2091f",
"sha256:45113c1c359ba314499032c891487802cccd7c4225a3e930d6cf492d62ea4f07",
"sha256:46f15f5a34a50375c332ab8eaa907a0212c88787b0885ac25a9505c0741ee9ba",
"sha256:580eed6d9e5c20870ea909bec6840f9ceb9d13c33316d448cae21eb3ca47c7fd",
"sha256:5865c4247229584408515055b5b19c7f935ae94433d6258c7a9234c4a07d6d34",
"sha256:6063466779e438375bcdd2c15fc551ebd68f16ebfb2766497234df9cfa57e5b1",
"sha256:63578cab96fc4383e71dd9fe1877bb26ab78b2a6c91139068e99d130687289ab",
"sha256:66b5a08cbeb910edee7201efa786bd1bf7027c7ec526dddf7d60fc2252e2b30f",
"sha256:6b448a1824d381d282c5ea1da1669a5fa53dac67c57a1ecad6bcc149f286d1fd",
"sha256:6f905390f5e5801b21b6027c8ffaed915e5eec1e46bbdf6a74c8838213717b44",
"sha256:70e7461aa47eff810be8c4e4a0cbc6fcf47aecaddd46de6ca4524c76065f8490",
"sha256:7e466276f1a1121dac23b703af6c22db0cedf6cec5139969f8387e8d8046f203",
"sha256:81d1958d90fccf86f62b38ecbedf9208a973d99e0747b6cd75036914ae8641c4",
"sha256:9a00feb8eafbce1283cd3edbb29735bd40c9566b3f45913110a301700c16b63a",
"sha256:a48221d4ab7de37975ad052f7e565cf13ab708def63f203a38ae9927ab5442cd",
"sha256:ad9a49890de59e8dd16fa0ce03ef607e46a5ff2f39de44f8556f796b3d4ddffb",
"sha256:b25608059558910585a9e229bae0fd3d67af49ae5e1c7a20057680c6b3d5f6f7",
"sha256:b57ebeb28f7a58a9da6f8c293acb6d31d89f634b3eba0b728a040cef08afc4ea",
"sha256:b9ae0c534c09274b80f8fd87408071c1f814d56c5f51fe450b2157f1f13e921b",
"sha256:c0612d9101f40679245e7d9edb169d8d79378a47f38cd8e6b38c55d7ff31db3f",
"sha256:ced16daf89f948eeb4e376b5d814da5d99f7205fbd42e17a96f257e35dc31bdd",
"sha256:dd3409ebabe699c98058690b7b730f93e6b0bd4ed5e49ca3b15e1530ae07b40b",
"sha256:efef6a97e3ab49f3f40037dbf9a4166668a17cc6aaba13d5ecbabdf854a9b332"
],
"index": "pypi",
"version": "==3.5.65"
"version": "==3.5.68"
},
"requests": {
"hashes": [
@@ -672,62 +712,63 @@
},
"sentry-sdk": {
"hashes": [
"sha256:71de00c9711926816f750bc0f57ef2abbcb1bfbdf5378c601df7ec978f44857a",
"sha256:9221e985f425913204989d0e0e1cbb719e8b7fa10540f1bc509f660c06a34e66"
"sha256:ebe99144fa9618d4b0e7617e7929b75acd905d258c3c779edcd34c0adfffe26c",
"sha256:f33d34c886d0ba24c75ea8885a8b3a172358853c7cbde05979fc99c29ef7bc52"
],
"index": "pypi",
"version": "==1.0.0"
"version": "==1.3.1"
},
"simplejson": {
"hashes": [
"sha256:034550078a11664d77bc1a8364c90bb7eef0e44c2dbb1fd0a4d92e3997088667",
"sha256:05b43d568300c1cd43f95ff4bfcff984bc658aa001be91efb3bb21df9d6288d3",
"sha256:0dd9d9c738cb008bfc0862c9b8fa6743495c03a0ed543884bf92fb7d30f8d043",
"sha256:10fc250c3edea4abc15d930d77274ddb8df4803453dde7ad50c2f5565a18a4bb",
"sha256:2862beabfb9097a745a961426fe7daf66e1714151da8bb9a0c430dde3d59c7c0",
"sha256:292c2e3f53be314cc59853bd20a35bf1f965f3bc121e007ab6fd526ed412a85d",
"sha256:2d3eab2c3fe52007d703a26f71cf649a8c771fcdd949a3ae73041ba6797cfcf8",
"sha256:2e7b57c2c146f8e4dadf84977a83f7ee50da17c8861fd7faf694d55e3274784f",
"sha256:311f5dc2af07361725033b13cc3d0351de3da8bede3397d45650784c3f21fbcf",
"sha256:344e2d920a7f27b4023c087ab539877a1e39ce8e3e90b867e0bfa97829824748",
"sha256:3fabde09af43e0cbdee407555383063f8b45bfb52c361bc5da83fcffdb4fd278",
"sha256:42b8b8dd0799f78e067e2aaae97e60d58a8f63582939af60abce4c48631a0aa4",
"sha256:4b3442249d5e3893b90cb9f72c7d6ce4d2ea144d2c0d9f75b9ae1e5460f3121a",
"sha256:55d65f9cc1b733d85ef95ab11f559cce55c7649a2160da2ac7a078534da676c8",
"sha256:5c659a0efc80aaaba57fcd878855c8534ecb655a28ac8508885c50648e6e659d",
"sha256:72d8a3ffca19a901002d6b068cf746be85747571c6a7ba12cbcf427bfb4ed971",
"sha256:75ecc79f26d99222a084fbdd1ce5aad3ac3a8bd535cd9059528452da38b68841",
"sha256:76ac9605bf2f6d9b56abf6f9da9047a8782574ad3531c82eae774947ae99cc3f",
"sha256:7d276f69bfc8c7ba6c717ba8deaf28f9d3c8450ff0aa8713f5a3280e232be16b",
"sha256:7f10f8ba9c1b1430addc7dd385fc322e221559d3ae49b812aebf57470ce8de45",
"sha256:8042040af86a494a23c189b5aa0ea9433769cc029707833f261a79c98e3375f9",
"sha256:813846738277729d7db71b82176204abc7fdae2f566e2d9fcf874f9b6472e3e6",
"sha256:845a14f6deb124a3bcb98a62def067a67462a000e0508f256f9c18eff5847efc",
"sha256:869a183c8e44bc03be1b2bbcc9ec4338e37fa8557fc506bf6115887c1d3bb956",
"sha256:8acf76443cfb5c949b6e781c154278c059b09ac717d2757a830c869ba000cf8d",
"sha256:8f713ea65958ef40049b6c45c40c206ab363db9591ff5a49d89b448933fa5746",
"sha256:934115642c8ba9659b402c8bdbdedb48651fb94b576e3b3efd1ccb079609b04a",
"sha256:9551f23e09300a9a528f7af20e35c9f79686d46d646152a0c8fc41d2d074d9b0",
"sha256:9a2b7543559f8a1c9ed72724b549d8cc3515da7daf3e79813a15bdc4a769de25",
"sha256:a55c76254d7cf8d4494bc508e7abb993a82a192d0db4552421e5139235604625",
"sha256:ad8f41c2357b73bc9e8606d2fa226233bf4d55d85a8982ecdfd55823a6959995",
"sha256:af4868da7dd53296cd7630687161d53a7ebe2e63814234631445697bd7c29f46",
"sha256:afebfc3dd3520d37056f641969ce320b071bc7a0800639c71877b90d053e087f",
"sha256:b59aa298137ca74a744c1e6e22cfc0bf9dca3a2f41f51bc92eb05695155d905a",
"sha256:bc00d1210567a4cdd215ac6e17dc00cb9893ee521cee701adfd0fa43f7c73139",
"sha256:c1cb29b1fced01f97e6d5631c3edc2dadb424d1f4421dad079cb13fc97acb42f",
"sha256:c94dc64b1a389a416fc4218cd4799aa3756f25940cae33530a4f7f2f54f166da",
"sha256:ceaa28a5bce8a46a130cd223e895080e258a88d51bf6e8de2fc54a6ef7e38c34",
"sha256:cff6453e25204d3369c47b97dd34783ca820611bd334779d22192da23784194b",
"sha256:d0b64409df09edb4c365d95004775c988259efe9be39697d7315c42b7a5e7e94",
"sha256:d4813b30cb62d3b63ccc60dd12f2121780c7a3068db692daeb90f989877aaf04",
"sha256:da3c55cdc66cfc3fffb607db49a42448785ea2732f055ac1549b69dcb392663b",
"sha256:e058c7656c44fb494a11443191e381355388443d543f6fc1a245d5d238544396",
"sha256:fed0f22bf1313ff79c7fc318f7199d6c2f96d4de3234b2f12a1eab350e597c06",
"sha256:ffd4e4877a78c84d693e491b223385e0271278f5f4e1476a4962dca6824ecfeb"
"sha256:065230b9659ac38c8021fa512802562d122afb0cf8d4b89e257014dcddb5730a",
"sha256:07707ba69324eaf58f0c6f59d289acc3e0ed9ec528dae5b0d4219c0d6da27dc5",
"sha256:10defa88dd10a0a4763f16c1b5504e96ae6dc68953cfe5fc572b4a8fcaf9409b",
"sha256:140eb58809f24d843736edb8080b220417e22c82ac07a3dfa473f57e78216b5f",
"sha256:188f2c78a8ac1eb7a70a4b2b7b9ad11f52181044957bf981fb3e399c719e30ee",
"sha256:1c2688365743b0f190392e674af5e313ebe9d621813d15f9332e874b7c1f2d04",
"sha256:24e413bd845bd17d4d72063d64e053898543fb7abc81afeae13e5c43cef9c171",
"sha256:2b59acd09b02da97728d0bae8ff48876d7efcbbb08e569c55e2d0c2e018324f5",
"sha256:2df15814529a4625ea6f7b354a083609b3944c269b954ece0d0e7455872e1b2a",
"sha256:352c11582aa1e49a2f0f7f7d8fd5ec5311da890d1354287e83c63ab6af857cf5",
"sha256:36b08b886027eac67e7a0e822e3a5bf419429efad7612e69501669d6252a21f2",
"sha256:376023f51edaf7290332dacfb055bc00ce864cb013c0338d0dea48731f37e42f",
"sha256:3ba82f8b421886f4a2311c43fb98faaf36c581976192349fef2a89ed0fcdbdef",
"sha256:3d72aa9e73134dacd049a2d6f9bd219f7be9c004d03d52395831611d66cedb71",
"sha256:40ece8fa730d1a947bff792bcc7824bd02d3ce6105432798e9a04a360c8c07b0",
"sha256:417b7e119d66085dc45bdd563dcb2c575ee10a3b1c492dd3502a029448d4be1c",
"sha256:42b7c7264229860fe879be961877f7466d9f7173bd6427b3ba98144a031d49fb",
"sha256:457d9cfe7ece1571770381edccdad7fc255b12cd7b5b813219441146d4f47595",
"sha256:4a6943816e10028eeed512ea03be52b54ea83108b408d1049b999f58a760089b",
"sha256:5b94df70bd34a3b946c0eb272022fb0f8a9eb27cad76e7f313fedbee2ebe4317",
"sha256:5f5051a13e7d53430a990604b532c9124253c5f348857e2d5106d45fc8533860",
"sha256:5f7f53b1edd4b23fb112b89208377480c0bcee45d43a03ffacf30f3290e0ed85",
"sha256:5fe8c6dcb9e6f7066bdc07d3c410a2fca78c0d0b4e0e72510ffd20a60a20eb8e",
"sha256:71a54815ec0212b0cba23adc1b2a731bdd2df7b9e4432718b2ed20e8aaf7f01a",
"sha256:7332f7b06d42153255f7bfeb10266141c08d48cc1a022a35473c95238ff2aebc",
"sha256:78c6f0ed72b440ebe1892d273c1e5f91e55e6861bea611d3b904e673152a7a4c",
"sha256:7c9b30a2524ae6983b708f12741a31fbc2fb8d6fecd0b6c8584a62fd59f59e09",
"sha256:86fcffc06f1125cb443e2bed812805739d64ceb78597ac3c1b2d439471a09717",
"sha256:87572213965fd8a4fb7a97f837221e01d8fddcfb558363c671b8aa93477fb6a2",
"sha256:8e595de17178dd3bbeb2c5b8ea97536341c63b7278639cb8ee2681a84c0ef037",
"sha256:917f01db71d5e720b731effa3ff4a2c702a1b6dacad9bcdc580d86a018dfc3ca",
"sha256:91cfb43fb91ff6d1e4258be04eee84b51a4ef40a28d899679b9ea2556322fb50",
"sha256:aa86cfdeb118795875855589934013e32895715ec2d9e8eb7a59be3e7e07a7e1",
"sha256:ade09aa3c284d11f39640aebdcbb748e1996f0c60504f8c4a0c5a9fec821e67a",
"sha256:b2a5688606dffbe95e1347a05b77eb90489fe337edde888e23bbb7fd81b0d93b",
"sha256:b92fbc2bc549c5045c8233d954f3260ccf99e0f3ec9edfd2372b74b350917752",
"sha256:c2d5334d935af711f6d6dfeec2d34e071cdf73ec0df8e8bd35ac435b26d8da97",
"sha256:cb0afc3bad49eb89a579103616574a54b523856d20fc539a4f7a513a0a8ba4b2",
"sha256:ce66f730031b9b3683b2fc6ad4160a18db86557c004c3d490a29bf8d450d7ab9",
"sha256:e29b9cea4216ec130df85d8c36efb9985fda1c9039e4706fb30e0fb6a67602ff",
"sha256:e2cc4b68e59319e3de778325e34fbff487bfdb2225530e89995402989898d681",
"sha256:e90d2e219c3dce1500dda95f5b893c293c4d53c4e330c968afbd4e7a90ff4a5b",
"sha256:f13c48cc4363829bdfecc0c181b6ddf28008931de54908a492dc8ccd0066cd60",
"sha256:f550730d18edec4ff9d4252784b62adfe885d4542946b6d5a54c8a6521b56afd",
"sha256:fa843ee0d34c7193f5a816e79df8142faff851549cab31e84b526f04878ac778",
"sha256:fe1c33f78d2060719d52ea9459d97d7ae3a5b707ec02548575c4fbed1d1d345b"
],
"index": "pypi",
"version": "==3.17.2"
"version": "==3.17.5"
},
"six": {
"hashes": [
@@ -739,19 +780,20 @@
},
"soupsieve": {
"hashes": [
"sha256:407fa1e8eb3458d1b5614df51d9651a1180ea5fedf07feb46e45d7e25e6d6cdd",
"sha256:d3a5ea5b350423f47d07639f74475afedad48cf41c0ad7a82ca13a3928af34f6"
"sha256:052774848f448cf19c7e959adf5566904d525f33a3f8b6ba6f6f8f26ec7de0cc",
"sha256:c2c1c2d44f158cdbddab7824a9af8c4f83c76b1e23e049479aa432feb6c4c23b"
],
"index": "pypi",
"version": "==2.2"
"markers": "python_version >= '3.0'",
"version": "==2.2.1"
},
"sqlparse": {
"hashes": [
"sha256:017cde379adbd6a1f15a61873f43e8274179378e95ef3fede90b5aa64d304ed0",
"sha256:0f91fd2e829c44362cbcfab3e9ae12e22badaa8a29ad5ff599f9ec109f0454e8"
"sha256:0c00730c74263a94e5a9919ade150dfc3b19c574389985446148402998287dae",
"sha256:48719e356bb8b42991bdbb1e8b83223757b93789c00910a616a071910ca4a64d"
],
"index": "pypi",
"version": "==0.4.1"
"version": "==0.4.2"
},
"static3": {
"hashes": [
@@ -780,7 +822,6 @@
"sha256:806143ae5bfb6a3c6e736a764057db0e6a0e05e338b5630894a5f779cabb4f9b",
"sha256:b3bda1d108d5dd99f4a20d24d9c348e91c4db7ab1b749200bded2f839ccbe68f"
],
"markers": "python_version >= '2.6' and python_version not in '3.0, 3.1, 3.2, 3.3'",
"version": "==0.10.2"
},
"tornado": {
@@ -832,11 +873,11 @@
},
"urllib3": {
"hashes": [
"sha256:753a0374df26658f99d826cfe40394a686d05985786d946fbe4165b5148f5a7c",
"sha256:a7acd0977125325f516bda9735fa7142b909a8d01e8b2e4c8108d0984e6e0098"
"sha256:39fb8672126159acb139a7718dd10806104dec1e2f0f6c88aab05d17df10c8d4",
"sha256:f57b4c16c62fa2760b7e3d97c35b255512fb6b59a259730f36ba32ce9f8e342f"
],
"index": "pypi",
"version": "==1.26.5"
"version": "==1.26.6"
},
"webencodings": {
"hashes": [
@@ -869,11 +910,11 @@
},
"zipp": {
"hashes": [
"sha256:3607921face881ba3e026887d8150cca609d517579abe052ac81fc5aeffdbd76",
"sha256:51cb66cc54621609dd593d1787f286ee42a5c0adbb4b29abea5a63edc3e03098"
"sha256:a5303f8ad20aff64720bf548256646f74fc8c167065c0d177a98a7cadceed85a",
"sha256:ce85de43ee0ead77dd0fbee3902bec1501aef59b92a2e18265396b22a1d756ab"
],
"index": "pypi",
"version": "==3.4.1"
"version": "==3.4.2"
},
"zope.component": {
"hashes": [
@@ -1072,7 +1113,6 @@
"sha256:149e90d6d8ac20db7a955ad60cf0e6881a3f20d37096140088356da6c716b0b1",
"sha256:ef6aaac3ca6cd92904cdd0d83f629a15f18053ec84e6432106f7a4d04ae4f5fb"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4'",
"version": "==21.2.0"
},
"certifi": {
@@ -1083,13 +1123,13 @@
"index": "pypi",
"version": "==2020.12.5"
},
"chardet": {
"charset-normalizer": {
"hashes": [
"sha256:0d6f53a15db4120f2b08c94f11e7d93d2c911ee118b6b30a04ec3ee8310179fa",
"sha256:f864054d66fd9118f2e67044ac8981a54775ec5b67aed0441892edb553d21da5"
"sha256:5d209c0a931f215cee683b6445e2d77677e7e75e159f78def0db09d68fafcaa6",
"sha256:5ec46d183433dcbd0ab716f2d7f29d8dee50505b3fdb40c6b985c7c4f5a3591f"
],
"index": "pypi",
"version": "==4.0.0"
"markers": "python_version >= '3'",
"version": "==2.0.6"
},
"coverage": {
"hashes": [
@@ -1146,23 +1186,22 @@
"sha256:f0b278ce10936db1a37e6954e15a3730bea96a0997c26d7fee88e6c396c2086d",
"sha256:f11642dddbb0253cc8853254301b51390ba0081750a8ac03f20ea8103f0c56b6"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4' and python_version < '4'",
"version": "==5.5"
},
"coveralls": {
"hashes": [
"sha256:7bd173b3425733661ba3063c88f180127cc2b20e9740686f86d2622b31b41385",
"sha256:cbb942ae5ef3d2b55388cb5b43e93a269544911535f1e750e1c656aef019ce60"
"sha256:15a987d9df877fff44cd81948c5806ffb6eafb757b3443f737888358e96156ee",
"sha256:aedfcc5296b788ebaf8ace8029376e5f102f67c53d1373f2e821515c15b36527"
],
"index": "pypi",
"version": "==3.0.1"
"version": "==3.2.0"
},
"django-coverage-plugin": {
"hashes": [
"sha256:d53cbf3828fd83d6b89ff7292c6805de5274e36411711692043e67bcde25ae0c"
"sha256:5a7ac412528876563a45f9b54ad9962e33e5f95b409843c4c6c92cb0247eee66"
],
"index": "pypi",
"version": "==1.8.0"
"version": "==2.0.0"
},
"docopt": {
"hashes": [
@@ -1175,7 +1214,6 @@
"sha256:8f694f3ba9cc92cab508b152dcfe322153975c29bda272e2fd7f3f00f36e47c5",
"sha256:a295f7cc774947aac58dde7fdc85f4aa00c42adf5d8f5468fc630c1acf30a142"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4'",
"version": "==1.9.0"
},
"idna": {
@@ -1195,19 +1233,17 @@
},
"packaging": {
"hashes": [
"sha256:5b327ac1320dc863dca72f4514ecc086f31186744b84a230374cc1fd776feae5",
"sha256:67714da7f7bc052e064859c05c595155bd1ee9f69f76557e21f051443c20947a"
"sha256:7dc96269f53a4ccec5c0670940a4281106dd0bb343f47b7471f779df49c2fbe7",
"sha256:c86254f9220d55e31cc94d69bade760f0847da8000def4dfe1c6b872fd14ff14"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3'",
"version": "==20.9"
"version": "==21.0"
},
"pluggy": {
"hashes": [
"sha256:15b2acde666561e1298d71b523007ed7364de07029219b604cf808bfa1c765b0",
"sha256:966c145cd83c96502c3c3868f50408687b38434af77734af1e9ca461a4081d2d"
"sha256:4224373bacce55f955a878bf9cfa763c1e360858e330072059e10bad68531159",
"sha256:74134bbf457f031a36d68416e1509f34bd5ccc019f0bcc952c7b909d06b37bd3"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3'",
"version": "==0.13.1"
"version": "==1.0.0"
},
"psutil": {
"hashes": [
@@ -1248,7 +1284,6 @@
"sha256:21b81bda15b66ef5e1a777a21c4dcd9c20ad3efd0b3f817e7a809035269e1bd3",
"sha256:3b80836aa6d1feeaa108e046da6423ab8f6ceda6468545ae8d02d9d58d18818a"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3'",
"version": "==1.10.0"
},
"pycodestyle": {
@@ -1277,34 +1312,33 @@
},
"pytest": {
"hashes": [
"sha256:9d1edf9e7d0b84d72ea3dbcdfd22b35fb543a5e8f2a60092dd578936bf63d7f9",
"sha256:b574b57423e818210672e07ca1fa90aaf194a4f63f3ab909a2c67ebb22913839"
"sha256:131b36680866a76e6781d13f101efb86cf674ebb9762eb70d3082b6f29889e89",
"sha256:7310f8d27bc79ced999e760ca304d69f6ba6c6649c0b60fb0e04a4a77cacc134"
],
"index": "pypi",
"version": "==6.2.2"
"version": "==6.2.5"
},
"pytest-cov": {
"hashes": [
"sha256:359952d9d39b9f822d9d29324483e7ba04a3a17dd7d05aa6beb7ea01e359e5f7",
"sha256:bdb9fdb0b85a7cc825269a4c56b48ccaa5c7e365054b6038772c32ddcdc969da"
"sha256:261bb9e47e65bd099c89c3edf92972865210c36813f80ede5277dceb77a4a62a",
"sha256:261ceeb8c227b726249b376b8526b600f38667ee314f910353fa318caa01f4d7"
],
"index": "pypi",
"version": "==2.11.1"
"version": "==2.12.1"
},
"pytest-django": {
"hashes": [
"sha256:10e384e6b8912ded92db64c58be8139d9ae23fb8361e5fc139d8e4f8fc601bc2",
"sha256:26f02c16d36fd4c8672390deebe3413678d89f30720c16efb8b2a6bf63b9041f"
"sha256:65783e78382456528bd9d79a35843adde9e6a47347b20464eb2c885cb0f1f606",
"sha256:b5171e3798bf7e3fc5ea7072fe87324db67a4dd9f1192b037fed4cc3c1b7f455"
],
"index": "pypi",
"version": "==4.1.0"
"version": "==4.4.0"
},
"pytest-forked": {
"hashes": [
"sha256:6aa9ac7e00ad1a539c41bec6d21011332de671e938c7637378ec9710204e37ca",
"sha256:dc4147784048e70ef5d437951728825a131b81714b398d5d52f17c7c144d8815"
],
"markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4'",
"version": "==1.3.0"
},
"pytest-splinter": {
@@ -1315,15 +1349,12 @@
"version": "==3.3.1"
},
"pytest-xdist": {
"extras": [
"psutil"
],
"hashes": [
"sha256:2447a1592ab41745955fb870ac7023026f20a5f0bfccf1b52a879bd193d46450",
"sha256:718887296892f92683f6a51f25a3ae584993b06f7076ce1e1fd482e59a8220a2"
"sha256:e8ecde2f85d88fbcadb7d28cb33da0fa29bca5cf7d5967fa89fc0e97e5299ea5",
"sha256:ed3d7da961070fce2a01818b51f6888327fb88df4379edeb6b9d990e789d9c8d"
],
"index": "pypi",
"version": "==2.2.1"
"version": "==2.3.0"
},
"requests": {
"hashes": [
@@ -1350,26 +1381,26 @@
},
"splinter": {
"hashes": [
"sha256:459e39e7a9f7572db6f1cdb5fdc5ccfc6404f021dccb969ee6287be2386a40db",
"sha256:7e5e69c5b76ada909283465cdc3636e2632f7e557932ce96ab9c0432b0b32f7f"
"sha256:18b9d992352953cdd61ca8ece9616c9f214b47caebf8893266cb46bce60f6d60",
"sha256:218f4433018f9d1710a3201de7c22284273ab8bf29e5793247844fd74aafaf89",
"sha256:3f63f946fd96b750b4fd3c49ffb17abd6dc03d094b4836753e6be33f53fcfee1"
],
"version": "==0.14.0"
"version": "==0.15.0"
},
"toml": {
"hashes": [
"sha256:806143ae5bfb6a3c6e736a764057db0e6a0e05e338b5630894a5f779cabb4f9b",
"sha256:b3bda1d108d5dd99f4a20d24d9c348e91c4db7ab1b749200bded2f839ccbe68f"
],
"markers": "python_version >= '2.6' and python_version not in '3.0, 3.1, 3.2, 3.3'",
"version": "==0.10.2"
},
"urllib3": {
"hashes": [
"sha256:753a0374df26658f99d826cfe40394a686d05985786d946fbe4165b5148f5a7c",
"sha256:a7acd0977125325f516bda9735fa7142b909a8d01e8b2e4c8108d0984e6e0098"
"sha256:39fb8672126159acb139a7718dd10806104dec1e2f0f6c88aab05d17df10c8d4",
"sha256:f57b4c16c62fa2760b7e3d97c35b255512fb6b59a259730f36ba32ce9f8e342f"
],
"index": "pypi",
"version": "==1.26.5"
"version": "==1.26.6"
},
"zope.component": {
"hashes": [

View File

@@ -66,8 +66,8 @@ INSTALLED_APPS = (
'debug_toolbar',
'registration',
'reversion',
'captcha',
'widget_tweaks',
'hcaptcha',
)
MIDDLEWARE = (
@@ -187,12 +187,13 @@ LOGOUT_URL = '/user/logout/'
ACCOUNT_ACTIVATION_DAYS = 7
# reCAPTCHA settings
RECAPTCHA_PUBLIC_KEY = env('RECAPTCHA_PUBLIC_KEY', default="6LeIxAcTAAAAAJcZVRqyHh71UMIEGNQ_MXjiZKhI") # If not set, use development key
RECAPTCHA_PRIVATE_KEY = env('RECAPTCHA_PUBLIC_KEY', default="6LeIxAcTAAAAAGG-vFI1TnRWxMZNFuojJ4WifJWe") # If not set, use development key
NOCAPTCHA = True
SILENCED_SYSTEM_CHECKS = ['captcha.recaptcha_test_key_error']
# CAPTCHA settings
if DEBUG or CI:
HCAPTCHA_SITEKEY = '10000000-ffff-ffff-ffff-000000000001'
HCAPTCHA_SECRET = '0x0000000000000000000000000000000000000000'
else:
HCAPTCHA_SITEKEY = env('HCAPTCHA_SITEKEY')
HCAPTCHA_SECRET = env('HCAPTCHA_SECRET')
# Email
EMAILER_TEST = False

View File

@@ -33,20 +33,7 @@ class InvoiceIndex(generic.ListView):
return context
def get_queryset(self):
# Manual query is the only way I have found to do this efficiently. Not ideal but needs must
sql = "SELECT * FROM " \
"(SELECT " \
"(SELECT COUNT(p.amount) FROM \"RIGS_payment\" AS p WHERE p.invoice_id=\"RIGS_invoice\".id) AS \"payment_count\", " \
"(SELECT SUM(ei.cost * ei.quantity) FROM \"RIGS_eventitem\" AS ei WHERE ei.event_id=\"RIGS_invoice\".event_id) AS \"cost\", " \
"(SELECT SUM(p.amount) FROM \"RIGS_payment\" AS p WHERE p.invoice_id=\"RIGS_invoice\".id) AS \"payments\", " \
"\"RIGS_invoice\".\"id\", \"RIGS_invoice\".\"event_id\", \"RIGS_invoice\".\"invoice_date\", \"RIGS_invoice\".\"void\" FROM \"RIGS_invoice\") " \
"AS sub " \
"WHERE (((cost > 0.0) AND (payment_count=0)) OR (cost - payments) <> 0.0) AND void = '0'" \
"ORDER BY invoice_date"
query = self.model.objects.raw(sql)
return query
return self.model.objects.outstanding_invoices()
class InvoiceDetail(generic.DetailView):

View File

@@ -70,6 +70,11 @@ class EventRiskAssessmentDetail(generic.DetailView):
model = models.RiskAssessment
template_name = 'risk_assessment_detail.html'
def get_context_data(self, **kwargs):
context = super(EventRiskAssessmentDetail, self).get_context_data(**kwargs)
context['page_title'] = "Risk Assessment for Event <a href='{}'>{} {}</a>".format(self.object.event.get_absolute_url(), self.object.event.display_id, self.object.event.name)
return context
class EventRiskAssessmentList(generic.ListView):
paginate_by = 20
@@ -107,7 +112,7 @@ class EventChecklistDetail(generic.DetailView):
def get_context_data(self, **kwargs):
context = super(EventChecklistDetail, self).get_context_data(**kwargs)
context['page_title'] = "Event Checklist for Event {} {}".format(self.object.event.display_id, self.object.event.name)
context['page_title'] = "Event Checklist for Event <a href='{}'>{} {}</a>".format(self.object.event.get_absolute_url(), self.object.event.display_id, self.object.event.name)
return context

View File

@@ -0,0 +1,34 @@
# Generated by Django 3.1.13 on 2021-10-07 22:38
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = [
('RIGS', '0041_auto_20210302_1204'),
]
operations = [
migrations.AlterField(
model_name='eventchecklist',
name='fd_earth_fault',
field=models.DecimalField(blank=True, decimal_places=2, help_text='Earth Fault Loop Impedance (Z<small>S</small>)', max_digits=5, null=True, verbose_name='Earth Fault Loop Impedance'),
),
migrations.AlterField(
model_name='eventchecklist',
name='w1_earth_fault',
field=models.DecimalField(blank=True, decimal_places=2, help_text='Earth Fault Loop Impedance (Z<small>S</small>)', max_digits=5, null=True, verbose_name='Earth Fault Loop Impedance'),
),
migrations.AlterField(
model_name='eventchecklist',
name='w2_earth_fault',
field=models.DecimalField(blank=True, decimal_places=2, help_text='Earth Fault Loop Impedance (Z<small>S</small>)', max_digits=5, null=True, verbose_name='Earth Fault Loop Impedance'),
),
migrations.AlterField(
model_name='eventchecklist',
name='w3_earth_fault',
field=models.DecimalField(blank=True, decimal_places=2, help_text='Earth Fault Loop Impedance (Z<small>S</small>)', max_digits=5, null=True, verbose_name='Earth Fault Loop Impedance'),
),
]

View File

@@ -540,6 +540,23 @@ class EventAuthorisation(models.Model, RevisionMixin):
return "{} (requested by {})".format(self.event.display_id, self.sent_by.initials)
class InvoiceManager(models.Manager):
def outstanding_invoices(self):
# Manual query is the only way I have found to do this efficiently. Not ideal but needs must
sql = "SELECT * FROM " \
"(SELECT " \
"(SELECT COUNT(p.amount) FROM \"RIGS_payment\" AS p WHERE p.invoice_id=\"RIGS_invoice\".id) AS \"payment_count\", " \
"(SELECT SUM(ei.cost * ei.quantity) FROM \"RIGS_eventitem\" AS ei WHERE ei.event_id=\"RIGS_invoice\".event_id) AS \"cost\", " \
"(SELECT SUM(p.amount) FROM \"RIGS_payment\" AS p WHERE p.invoice_id=\"RIGS_invoice\".id) AS \"payments\", " \
"\"RIGS_invoice\".\"id\", \"RIGS_invoice\".\"event_id\", \"RIGS_invoice\".\"invoice_date\", \"RIGS_invoice\".\"void\" FROM \"RIGS_invoice\") " \
"AS sub " \
"WHERE (((cost > 0.0) AND (payment_count=0)) OR (cost - payments) <> 0.0) AND void = '0'" \
"ORDER BY invoice_date"
query = self.raw(sql)
return query
@reversion.register(follow=['payment_set'])
class Invoice(models.Model, RevisionMixin):
event = models.OneToOneField('Event', on_delete=models.CASCADE)
@@ -548,6 +565,8 @@ class Invoice(models.Model, RevisionMixin):
reversion_perm = 'RIGS.view_invoice'
objects = InvoiceManager()
@property
def sum_total(self):
return self.event.sum_total
@@ -778,21 +797,21 @@ class EventChecklist(models.Model, RevisionMixin):
fd_voltage_l2 = models.IntegerField(blank=True, null=True, verbose_name="First Distro Voltage L2-N", help_text="L2 - N")
fd_voltage_l3 = models.IntegerField(blank=True, null=True, verbose_name="First Distro Voltage L3-N", help_text="L3 - N")
fd_phase_rotation = models.BooleanField(blank=True, null=True, verbose_name="Phase Rotation", help_text="Phase Rotation<br><small>(if required)</small>")
fd_earth_fault = models.IntegerField(blank=True, null=True, verbose_name="Earth Fault Loop Impedance", help_text="Earth Fault Loop Impedance (Z<small>S</small>)")
fd_earth_fault = models.DecimalField(blank=True, null=True, max_digits=5, decimal_places=2, verbose_name="Earth Fault Loop Impedance", help_text="Earth Fault Loop Impedance (Z<small>S</small>)")
fd_pssc = models.IntegerField(blank=True, null=True, verbose_name="PSCC", help_text="Prospective Short Circuit Current")
# Worst case points
w1_description = models.CharField(blank=True, default='', max_length=255, help_text="Description")
w1_polarity = models.BooleanField(blank=True, null=True, help_text="Polarity Checked?")
w1_voltage = models.IntegerField(blank=True, null=True, help_text="Voltage")
w1_earth_fault = models.IntegerField(blank=True, null=True, help_text="Earth Fault Loop Impedance (Z<small>S</small>)")
w1_earth_fault = models.DecimalField(blank=True, null=True, max_digits=5, decimal_places=2, verbose_name="Earth Fault Loop Impedance", help_text="Earth Fault Loop Impedance (Z<small>S</small>)")
w2_description = models.CharField(blank=True, default='', max_length=255, help_text="Description")
w2_polarity = models.BooleanField(blank=True, null=True, help_text="Polarity Checked?")
w2_voltage = models.IntegerField(blank=True, null=True, help_text="Voltage")
w2_earth_fault = models.IntegerField(blank=True, null=True, help_text="Earth Fault Loop Impedance (Z<small>S</small>)")
w2_earth_fault = models.DecimalField(blank=True, null=True, max_digits=5, decimal_places=2, verbose_name="Earth Fault Loop Impedance", help_text="Earth Fault Loop Impedance (Z<small>S</small>)")
w3_description = models.CharField(blank=True, default='', max_length=255, help_text="Description")
w3_polarity = models.BooleanField(blank=True, null=True, help_text="Polarity Checked?")
w3_voltage = models.IntegerField(blank=True, null=True, help_text="Voltage")
w3_earth_fault = models.IntegerField(blank=True, null=True, help_text="Earth Fault Loop Impedance (Z<small>S</small>)")
w3_earth_fault = models.DecimalField(blank=True, null=True, max_digits=5, decimal_places=2, verbose_name="Earth Fault Loop Impedance", help_text="Earth Fault Loop Impedance (Z<small>S</small>)")
all_rcds_tested = models.BooleanField(blank=True, null=True, help_text="All circuit RCDs tested?<br><small>(using test button)</small>")
public_sockets_tested = models.BooleanField(blank=True, null=True, help_text="Public/Performer accessible circuits tested?<br><small>(using socket tester)</small>")

Binary file not shown.

After

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 164 KiB

View File

@@ -2,9 +2,11 @@
{% load static %}
{% load invoices_waiting from filters %}
{% load invoices_outstanding from filters %}
{% load total_invoices_todo from filters %}
{% block titleheader %}
<a class="navbar-brand" href="/">RIGS</a>
<a class="navbar-brand" style="margin-left: auto; margin-right: auto;" href="/">RIGS</a>
{% endblock %}
{% block titleelements %}
@@ -45,14 +47,17 @@
{% endif %}
{% if perms.RIGS.view_invoice %}
<li class="nav-item dropdown">
{% total_invoices_todo as todo %}
{% invoices_waiting as waiting %}
{% invoices_outstanding as outstanding %}
<a class="nav-link dropdown-toggle" href="#" id="navbarDropdownInvoices" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
Invoices <span class="badge badge-danger badge-pill">{% invoices_waiting %}</span>
Invoices <span class="badge {% if todo == 0 %}badge-success{% else %}badge-danger{% endif %} badge-pill">{{ todo }}</span>
</a>
<div class="dropdown-menu" aria-labelledby="navbarDropdownInvoices">
{% if perms.RIGS.add_invoice %}
<a class="dropdown-item text-nowrap" href="{% url 'invoice_waiting' %}"><span class="fas fa-briefcase text-danger"></span> Waiting <span class="badge badge-danger badge-pill">{% invoices_waiting %}</span></a>
<a class="dropdown-item text-nowrap" href="{% url 'invoice_waiting' %}"><span class="fas fa-briefcase text-danger"></span> Waiting <span class="badge {% if waiting == 0 %}badge-success{% else %}badge-danger{% endif %} badge-pill">{{ waiting }}</span></a>
{% endif %}
<a class="dropdown-item" href="{% url 'invoice_list' %}"><span class="fas fa-pound-sign text-warning"></span> Outstanding</a>
<a class="dropdown-item" href="{% url 'invoice_list' %}"><span class="fas fa-pound-sign text-warning"></span> Outstanding <span class="badge {% if outstanding == 0 %}badge-success{% else %}badge-danger{% endif %} badge-pill">{{ outstanding }}</span></a>
<a class="dropdown-item" href="{% url 'invoice_archive' %}"><span class="fas fa-book"></span> Archive</a>
</div>
</li>

View File

@@ -102,6 +102,10 @@
<td>{{crew.role}}</td>
<td>{{crew.end}}</td>
</tr>
{% empty %}
<tr>
<td colspan="4" class="text-center bg-warning">Apparently this event happened by magic...</td>
</tr>
{% endfor %}
</tbody>
</table>
@@ -109,9 +113,27 @@
</div>
<div class="card mb-3">
<div class="card-header">Power {% include 'partials/event_size.html' with object=object.event.riskassessment %}</div>
{% if object.event.riskassessment.event_size != 2 %}
<div class="card-body">
{% if object.event.riskassessment.event_size == 1 %}
{% if event.riskassessment.event_size == 0 %}
<dl class="row">
<dt class="col-10">{{ object|help_text:'rcds'|safe }}</dt>
<dd class="col-2">
{{ object.rcds|yesnoi }}
</dd>
<dt class="col-10">{{ object|help_text:'supply_test'|safe }}</dt>
<dd class="col-2">
{{ object.supply_test|yesnoi }}
</dd>
<dt class="col-10">{{ object|help_text:'earthing'|safe }}</dt>
<dd class="col-2">
{{ object.earthing|yesnoi }}
</dd>
<dt class="col-10">{{ object|help_text:'pat'|safe }}</dt>
<dd class="col-2">
{{ object.pat|yesnoi }}
</dd>
</dl>
{% else %}
<dl class="row">
<dt class="col-10">{{ object|help_text:'source_rcd'|safe }}</dt>
<dd class="col-2">
@@ -216,28 +238,8 @@
</dl>
<hr>
{% include 'partials/ec_power_info.html' %}
{% else %}
<dl class="row">
<dt class="col-10">{{ object|help_text:'rcds'|safe }}</dt>
<dd class="col-2">
{{ object.rcds|yesnoi }}
</dd>
<dt class="col-10">{{ object|help_text:'supply_test'|safe }}</dt>
<dd class="col-2">
{{ object.supply_test|yesnoi }}
</dd>
<dt class="col-10">{{ object|help_text:'earthing'|safe }}</dt>
<dd class="col-2">
{{ object.earthing|yesnoi }}
</dd>
<dt class="col-10">{{ object|help_text:'pat'|safe }}</dt>
<dd class="col-2">
{{ object.pat|yesnoi }}
</dd>
</dl>
{% endif %}
</div>
{% endif %}
</div>
<div class="col-12 text-right">
{% button 'edit' url='ec_edit' pk=object.pk %}

View File

@@ -244,12 +244,19 @@
</div>
</div>
</div>
{% elif event.riskassessment.event_size == 1 %}
{% else %}
<div class="row my-3" id="size-1">
<div class="col-12">
{% if event.riskassessment.event_size == 1 %}
<div class="card border-warning">
<div class="card-header">Electrical Checks <small>for Medium TEC Events </small></div>
<div class="card-body">
{% else %}
<div class="card border-danger">
<div class="card-header">Electrical Checks <small>for Large TEC Events</small></div>
<div class="card-body">
<div class="alert alert-danger"><strong>Here be dragons. Ensure you have appeased the Power Gods before continuing... (If you didn't check with a Supervisor, <em>you cannot continue your event!</em>)</strong></div>
{% endif %}
{% include 'partials/checklist_checkbox.html' with formitem=form.source_rcd %}
{% include 'partials/checklist_checkbox.html' with formitem=form.labelling %}
{% include 'partials/checklist_checkbox.html' with formitem=form.earthing %}
@@ -339,17 +346,6 @@
</div>
</div>
</div>
{% else %}
<div class="row my-3" id="size-2">
<div class="col-12">
<div class="card border-danger">
<div class="card-header">Electrical Checks <small>for Large TEC Events</small></div>
<div class="card-body">
<p>Outside the scope of this assessment. <strong>I really hope you checked with a supervisor...</strong></p>
</div>
</div>
</div>
</div>
{% endif %}
<div class="row mt-3">
<div class="col-sm-12 text-right">

View File

@@ -5,15 +5,13 @@
<p>Hi {{ to_name|default:"there" }},</p>
<p><b>{{ request.user.get_full_name }}</b> has requested that you authorise <b>{{ object.display_id }}
| {{ object.name }}</b>{% if not to_name %} on behalf of <b>{{ object.person.name }}</b>{% endif %}.</p>
| {{ object.name }}</b>{% if not to_name %} on behalf of <b>{% if object.person %}{{ object.person.name }}{% else %}{{ object.organisation.name }}{% endif %}</b>{% endif %}.</p>
<p>
Please find the link below to complete the event booking process.
{% if object.event.organisation and object.event.organisation.union_account %}{# internal #}
Remember that only Presidents or Treasurers are allowed to sign off payments. You may need to forward
this
email on.
{% endif %}
Remember that only Presidents or Treasurers are allowed to sign off payments. You may need to forward
this
email on.
</p>

View File

@@ -1,6 +1,6 @@
Hi {{ to_name|default:"there" }},
{{ request.user.get_full_name }} has requested that you authorise N{{ object.pk|stringformat:"05d" }}| {{ object.name }}{% if not to_name %} on behalf of {{ object.person.name }}{% endif %}.
{{ request.user.get_full_name }} has requested that you authorise N{{ object.pk|stringformat:"05d" }}| {{ object.name }}{% if not to_name %} on behalf of {% if object.person %}{{ object.person.name }}{% else %}{{ object.organisation.name }}{% endif %}{% endif %}.
Please find the link below to complete the event booking process.
{% if object.event.organisation and object.event.organisation.union_account %}{# internal #}

View File

@@ -5,7 +5,7 @@
<div class="row py-4">
<div class="col-sm-12 text-right px-0">
<div class="btn-group">
<a href="{% url 'event_detail' object.pk %}" class="btn btn-primary">Open Event Page <span class="fas fa-eye"></span></a>
<a href="{% url 'event_detail' object.event.pk %}" class="btn btn-primary">Open Event Page <span class="fas fa-eye"></span></a>
<a href="{% url 'invoice_delete' object.pk %}" class="btn btn-danger" title="Delete Invoice">
<span class="fas fa-times"></span> <span
class="d-none d-sm-inline">Delete</span>

View File

@@ -1,27 +1,29 @@
<div class="col-sm-6">
{% if event.person %}
<div class="card mb-3">
<div class="card-header">Contact Details</div>
<div class="card-body">
<dl class="row">
<dt class="col-sm-5">Person</dt>
<dd class="col-sm-7">
{% if event.person %}
{{ event.person.name }}
{% endif %}
{{ event.person.name }}
</dd>
{% if event.person.email %}
<dt class="col-sm-5">Email</dt>
<dd class="col-sm-7">
<span class="overflow-ellipsis">{{ event.person.email }}</span>
</dd>
{% endif %}
{% if event.person.phone %}
<dt class="col-sm-5">Phone Number</dt>
<dd class="col-sm-7">{{ event.person.phone }}</dd>
{% endif %}
</dl>
</div>
</div>
{% endif %}
{% if event.organisation %}
<div class="card mt-3">
<div class="card">
<div class="card-header">Organisation Details</div>
<div class="card-body">
<dl class="row">
@@ -29,9 +31,10 @@
<dd class="col-sm-7">
{{ event.organisation.name }}
</dd>
{% if event.organisation.phone %}
<dt class="col-sm-5">Phone Number</dt>
<dd class="col-sm-7">{{ object.organisation.phone }}</dd>
<dd class="col-sm-7">{{ event.organisation.phone }}</dd>
{% endif %}
</dl>
</div>
</div>

View File

@@ -48,6 +48,6 @@
<span class="d-none d-sm-inline">Invoice</span></a>
{% endif %}
<a href="https://docs.google.com/forms/d/e/1FAIpQLSf-TBOuJZCTYc2L8DWdAaC3_Werq0ulsUs8-6G85I6pA9WVsg/viewform" class="btn btn-danger"><span class="fas fa-file-invoice-dollar"></span> Subhire Insurance Form</a>
<a href="https://docs.google.com/forms/d/e/1FAIpQLSf-TBOuJZCTYc2L8DWdAaC3_Werq0ulsUs8-6G85I6pA9WVsg/viewform" class="btn btn-danger"><span class="fas fa-file-invoice-dollar"></span> <span class="d-none d-sm-inline">Subhire Insurance Form</span></a>
{% endif %}
</div>

View File

@@ -6,6 +6,10 @@
<span class="badge badge-success">PO: {{ event.purchase_order }}</span>
{% elif event.authorised %}
<span class="badge badge-success">Authorisation: Complete <span class="fas fa-check"></span></span>
{% elif event.authorisation and event.authorisation.amount != event.total and event.authorisation.last_edited_at > event.auth_request_at %}
<span class="badge badge-warning"> Authorisation: Issue <span class="fas fa-exclamation-circle"></span></span>
{% elif event.auth_request_to %}
<span class="badge badge-info"> Authorisation: Sent <span class="fas fa-paper-plane"></span></span>
{% else %}
<span class="badge badge-danger">Authorisation: <span class="fas fa-times"></span></span>
{% endif %}

View File

@@ -67,9 +67,9 @@
</h4>
{% if event.is_rig and not event.cancelled %}
<h5>
{{ event.person.name }}
<a href="{{ event.person.get_absolute_url }}">{{ event.person.name }}</a>
{% if event.organisation %}
for {{ event.organisation.name }}
for <a href="{{ event.organisation.get_absolute_url }}">{{ event.organisation.name }}</a>
{% endif %}
</h5>
{% endif %}

View File

@@ -1,5 +1,4 @@
{% extends request.is_ajax|yesno:"base_ajax.html,base_rigs.html" %}
{% block title %}Risk Assessment for Event N{{ object.event.pk|stringformat:"05d" }} {{ object.event.name }}{% endblock %}
{% load help_text from filters %}
{% load yesnoi from filters %}
{% load linkornone from filters %}
@@ -7,7 +6,6 @@
{% block content %}
<div class="row py-3">
<div class="col-12">
<h3>Risk Assessment for Event N{{ object.event.pk|stringformat:"05d" }} {{ object.event.name }}</h3>
<div class="card card-default mb-3">
<div class="card-header">General</div>
<div class="card-body">
@@ -97,58 +95,64 @@
</dl>
</div>
</div>
<div class="card card-default mb-3">
<div class="card-header">Site Details</div>
<div class="card-body">
<dl class="row">
<dt class="col-sm-6">{{ object|help_text:'known_venue' }}</dt>
<dd class="col-sm-6">
{{ object.known_venue|yesnoi:'invert' }}
</dd>
<dt class="col-sm-6">{{ object|help_text:'safe_loading'|safe }}</dt>
<dd class="col-sm-6">
{{ object.safe_loading|yesnoi:'invert' }}
</dd>
<dt class="col-sm-6">{{ object|help_text:'safe_storage' }}</dt>
<dd class="col-sm-6">
{{ object.safe_storage|yesnoi:'invert' }}
</dd>
<dt class="col-sm-6">{{ object|help_text:'area_outside_of_control' }}</dt>
<dd class="col-sm-6">
{{ object.area_outside_of_control|yesnoi:'invert' }}
</dd>
<dt class="col-sm-6">{{ object|help_text:'barrier_required' }}</dt>
<dd class="col-sm-6">
{{ object.barrier_required|yesnoi:'invert' }}
</dd>
<dt class="col-sm-6">{{ object|help_text:'nonstandard_emergency_procedure' }}</dt>
<dd class="col-sm-6">
{{ object.nonstandard_emergency_procedure|yesnoi:'invert' }}
</dd>
</dl>
<div class="row">
<div class="col-lg-6 col-12">
<div class="card card-default mb-3">
<div class="card-header">Site Details</div>
<div class="card-body">
<dl class="row">
<dt class="col-10">{{ object|help_text:'known_venue' }}</dt>
<dd class="col-2">
{{ object.known_venue|yesnoi:'invert' }}
</dd>
<dt class="col-10">{{ object|help_text:'safe_loading'|safe }}</dt>
<dd class="col-2">
{{ object.safe_loading|yesnoi:'invert' }}
</dd>
<dt class="col-10">{{ object|help_text:'safe_storage' }}</dt>
<dd class="col-2">
{{ object.safe_storage|yesnoi:'invert' }}
</dd>
<dt class="col-10">{{ object|help_text:'area_outside_of_control' }}</dt>
<dd class="col-2">
{{ object.area_outside_of_control|yesnoi:'invert' }}
</dd>
<dt class="col-10">{{ object|help_text:'barrier_required' }}</dt>
<dd class="col-2">
{{ object.barrier_required|yesnoi:'invert' }}
</dd>
<dt class="col-10">{{ object|help_text:'nonstandard_emergency_procedure' }}</dt>
<dd class="col-2">
{{ object.nonstandard_emergency_procedure|yesnoi:'invert' }}
</dd>
</dl>
</div>
</div>
</div>
</div>
<div class="card card-default mb-3">
<div class="card-header">Structures</div>
<div class="card-body">
<dl class="row">
<dt class="col-sm-6">{{ object|help_text:'special_structures' }}</dt>
<dd class="col-sm-6">
{{ object.special_structures|yesnoi:'invert' }}
</dd>
<dt class="col-sm-6">{{ object|help_text:'suspended_structures' }}</dt>
<dd class="col-sm-6">
{{ object.suspended_structures|yesnoi:'invert' }}
</dd>
<dt class="col-sm-6">{{ object|help_text:'persons_responsible_structures' }}</dt>
<dd class="col-sm-6">
{{ object.persons_responsible_structures.name|default:'N/A'|linebreaks }}
</dd>
<dt class="col-6">{{ object|help_text:'rigging_plan'|safe }}</dt>
<dd class="col-6">
{{ object.rigging_plan|linkornone }}
</dd>
</dl>
<div class="col-lg-6 col-12">
<div class="card card-default mb-3">
<div class="card-header">Structures</div>
<div class="card-body">
<dl class="row">
<dt class="col-10">{{ object|help_text:'special_structures' }}</dt>
<dd class="col-2">
{{ object.special_structures|yesnoi:'invert' }}
</dd>
<dt class="col-10">{{ object|help_text:'suspended_structures' }}</dt>
<dd class="col-2">
{{ object.suspended_structures|yesnoi:'invert' }}
</dd>
<dt class="col-12">{{ object|help_text:'persons_responsible_structures' }}</dt>
<dd class="col-12">
{{ object.persons_responsible_structures.name|default:'N/A'|linebreaks }}
</dd>
<dt class="col-12">{{ object|help_text:'rigging_plan'|safe }}</dt>
<dd class="col-12">
{{ object.rigging_plan|linkornone|default:'N/A' }}
</dd>
</dl>
</div>
</div>
</div>
</div>
</div>

View File

@@ -222,3 +222,13 @@ def button(type, url=None, pk=None, clazz="", icon=None, text="", id=None, style
@register.simple_tag
def invoices_waiting():
return len(models.Event.objects.waiting_invoices())
@register.simple_tag
def invoices_outstanding():
return len(models.Invoice.objects.outstanding_invoices())
@register.simple_tag
def total_invoices_todo():
return len(models.Event.objects.waiting_invoices()) + len(models.Invoice.objects.outstanding_invoices())

View File

@@ -721,12 +721,12 @@ def test_ec_create_medium(logged_in_browser, live_server, admin_user, medium_ra)
page.fd_voltage_l2 = 235
page.fd_voltage_l3 = 0
page.fd_phase_rotation = True
page.fd_earth_fault = 666
page.fd_earth_fault = "1.21"
page.fd_pssc = 1984
page.w1_description = "In the carpark, by the bins"
page.w1_polarity = True
page.w1_voltage = 240
page.w1_earth_fault = 333
page.w1_earth_fault = "0.42"
page.submit()
assert page.success

View File

@@ -49,7 +49,7 @@ class Supplier(models.Model, RevisionMixin):
ordering = ['name']
def get_absolute_url(self):
return reverse('supplier_list')
return reverse('supplier_detail', kwargs={'pk': self.pk})
def __str__(self):
return self.name
@@ -82,6 +82,9 @@ class CableType(models.Model):
else:
return "Unknown"
def get_absolute_url(self):
return reverse('cable_type_detail', kwargs={'pk': self.pk})
def get_available_asset_id(wanted_prefix=""):
sql = """

View File

@@ -2,6 +2,9 @@
{% load widget_tweaks %}
{% block content %}
<div class="row justify-content-end">
{% include 'partials/asset_buttons.html' %}
</div>
<div class="row">
<div class="col-md-6 mb-3">
{% include 'partials/asset_detail_form.html' %}

View File

@@ -34,7 +34,7 @@
})
.ajaxSelectPicker({
ajax: {
url: '{% url 'asset_search_json' %}',
url: "{% url 'asset_search_json' %}",
type: "GET",
data: function () {
let params = {

View File

@@ -11,7 +11,10 @@
<div class="btn-group">
{% button 'edit' url='asset_update' pk=object.asset_id %}
{% button 'duplicate' url='asset_duplicate' pk=object.asset_id %}
<a type="button" class="btn btn-info" href="{% url 'asset_audit' object.asset_id %}"><i class="fas fa-certificate"></i> Audit</a>
<a type="button" class="btn btn-info" href="{% url 'asset_audit' object.asset_id %}"><span class="fas fa-certificate"></span> Audit</a>
{% if object.is_cable %}
<a type="button" class="btn btn-primary" href="{% url 'generate_label' object.asset_id %}"><span class="fas fa-barcode"></span> Generate Label</a>
{% endif %}
</div>
{% endif %}
{% if create or edit or duplicate %}

View File

@@ -17,11 +17,9 @@
{% else %}
<dl>
<dt>Cable Type</dt>
<dd>{{ object.cable_type|default_if_none:'-' }}</dd>
<dd>{% if object.cable_type %}<a href="{{object.cable_type.get_absolute_url}}">{{ object.cable_type }}</a>{%else%}-{%endif%}</dd>
<dt>Length</dt>
<dd>{{ object.length|default_if_none:'-' }}m</dd>
<dt>Cross Sectional Area</dt>
<dd>{{ object.csa|default_if_none:'-' }}mm²</dd>
</dl>

View File

@@ -28,13 +28,13 @@
<dt>Children</dt>
{% if object.asset_parent.all %}
<div style="max-height: 200px; overflow-y: auto; -webkit-overflow-scrolling: touch; ">
{% for child in object.asset_parent.all %}
<dd>
<a href="{% url 'asset_detail' child.asset_id %}">
{{ child.asset_id }} - {{ child.description }}
</a>
<a href="{% url 'asset_detail' child.asset_id %}">{{ child }}</a>
</dd>
{% endfor %}
</div>
{% else %}
<dd><span>-</span></dd>
{% endif %}

View File

@@ -1,4 +1,5 @@
{% load widget_tweaks %}
{% load linkornone from filters %}
<div class="card mb-2">
<div class="card-header">
Purchase Details
@@ -51,14 +52,11 @@
{% else %}
<dl>
<dt>Purchased From</dt>
<dd>{{ object.purchased_from|default_if_none:'-' }}</dd>
<dd>{% if object.purchased_from %}<a href="{{object.purchased_from.get_absolute_url}}">{{ object.purchased_from }}</a>{%else%}-{%endif%}</dd>
<dt>Purchase Price</dt>
<dd>£{{ object.purchase_price|default_if_none:'-' }}</dd>
<dt>Salvage Value</dt>
<dd>£{{ object.salvage_value|default_if_none:'-' }}</dd>
<dt>Date Acquired</dt>
<dd>{{ object.date_acquired|default_if_none:'-' }}</dd>
{% if object.date_sold %}

View File

@@ -16,6 +16,7 @@ urlpatterns = [
(views.AssetEdit.as_view()), name='asset_update'),
path('asset/id/<str:pk>/duplicate/', permission_required_with_403('assets.add_asset')
(views.AssetDuplicate.as_view()), name='asset_duplicate'),
path('asset/id/<str:pk>/label', login_required(views.GenerateLabel.as_view()), name='generate_label'),
path('cabletype/list/', login_required(views.CableTypeList.as_view()), name='cable_type_list'),
path('cabletype/create/', permission_required_with_403('assets.add_cable_type')(views.CableTypeCreate.as_view()), name='cable_type_create'),

View File

@@ -1,4 +1,5 @@
import simplejson
import random
from django.contrib import messages
from django.contrib.auth.mixins import LoginRequiredMixin
from django.core import serializers
@@ -9,6 +10,11 @@ from django.utils import timezone
from django.utils.decorators import method_decorator
from django.views import generic
from django.views.decorators.csrf import csrf_exempt
from django.shortcuts import get_object_or_404
from PIL import Image, ImageDraw, ImageFont
from barcode import Code39
from barcode.writer import ImageWriter
from PyRIGS.views import GenericListView, GenericDetailView, GenericUpdateView, GenericCreateView, ModalURLMixin, \
is_ajax, OEmbedView
@@ -338,3 +344,37 @@ class CableTypeUpdate(generic.UpdateView):
def get_success_url(self):
return reverse("cable_type_detail", kwargs={"pk": self.object.pk})
class GenerateLabel(generic.View):
def get(self, request, pk):
black = (0, 0, 0)
white = (255, 255, 255)
size = (700, 200)
font = ImageFont.truetype("static/fonts/OpenSans-Regular.tff", 20)
obj = get_object_or_404(models.Asset, asset_id=pk)
asset_id = "Asset: {}".format(obj.asset_id)
length = "Length: {}m".format(obj.length)
csa = "CSA: {}mm²".format(obj.csa)
image = Image.new("RGB", size, white)
logo = Image.open("static/imgs/square_logo.png")
draw = ImageDraw.Draw(image)
draw.text((210, 140), asset_id, fill=black, font=font)
draw.text((210, 170), length, fill=black, font=font)
draw.text((350, 170), csa, fill=black, font=font)
draw.multiline_text((500, 140), "TEC PA & Lighting\n(0115) 84 68720", fill=black, font=font)
barcode = Code39(str(obj.asset_id), writer=ImageWriter())
logo_size = (200, 200)
image.paste(logo.resize(logo_size, Image.ANTIALIAS))
barcode_image = barcode.render(writer_options={"quiet_zone": 0, "write_text": False})
width, height = barcode_image.size
image.paste(barcode_image.crop((0, 0, width, 135)), (int(((size[0] + logo_size[0]) - width) / 2), 0))
response = HttpResponse(content_type="image/png")
image.save(response, "PNG")
return response

View File

@@ -31,28 +31,26 @@
<a class="skip-link" href='#main'>Skip to content</a>
{% include "analytics.html" %}
{% block navbar %}
<nav class="navbar navbar-expand-lg navbar-dark bg-dark flex-nowrap text-nowrap" role="navigation">
<a class="navbar-brand" href="{% if request.user.is_authenticated %}https://members.nottinghamtec.co.uk{%else%}https://nottinghamtec.co.uk{%endif%}">
<img src="{% static 'imgs/logo.webp' %}" width="40" height="40" alt="TEC's Logo: Serif 'TEC' vertically next to a blue box with the words 'PA and Lighting', surrounded by graduated rings" id="logo">
</a>
<div class="container" style="padding-left: 0; padding-right: 0;">
<div class="row w-100 flex-nowrap">
<nav class="navbar navbar-expand-lg navbar-dark bg-dark" role="navigation">
<div class="container">
<a class="navbar-brand" style="position: absolute; left:0.5em; top: 2px;" href="{% if request.user.is_authenticated %}https://members.nottinghamtec.co.uk{%else%}https://nottinghamtec.co.uk{%endif%}">
<img src="{% static 'imgs/logo.webp' %}" width="40" height="40" alt="TEC's Logo: Serif 'TEC' vertically next to a blue box with the words 'PA and Lighting', surrounded by graduated rings" id="logo">
</a>
{% block titleheader %}
{% endblock %}
<button class="navbar-toggler ml-auto" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation" onclick="document.getElementById('logo').classList.toggle('d-none');">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="navbarSupportedContent">
<div class="collapse navbar-collapse justify-content-between" id="navbarSupportedContent">
<ul class="navbar-nav">
{% block titleelements %}
{% endblock %}
</ul>
<ul class="navbar-nav ml-auto">
<ul class="navbar-nav align-self-end">
{% block titleelements_right %}
{% endblock %}
</ul>
</div>
</div>
</div>
</nav>
{% endblock %}

View File

@@ -1,29 +1,36 @@
{% extends 'base_rigs.html' %}
{% load widget_tweaks %}
{% load static %}
{% block title %}Registration{% endblock %}
{% block content %}
<div class="col-sm-10 col-sm-offset-1">
<h3>New User Registration</h3>
{% if form.errors or supplement_form.errors %}
<div class="alert alert-danger">
{{form.errors}}
{{supplement_form.errors}}
</div>
{% endif %}
<div class="col-sm-8 col-sm-offset-2">
<form action="" method="post" class="" role="form">{% csrf_token %}
{% for field in form %}
<div class="form-group">
<label for="{{ field.id_for_label }}" class="col-form-label col-sm-4">{{ field.label }}</label>
<div class="controls col-sm-8">
{% render_field field class+="form-control" placeholder=field.label %}
</div>
</div>
{% endfor %}
<p><input type="submit" value="Register" class="btn btn-primary pull-right"></p>
</form>
<div style="background-image: linear-gradient(rgba(0, 0, 0, 0.7), rgba(0, 0, 0, 0.7)), url({% static 'imgs/wof2014-1-small.jpg' %}); background-repeat: no-repeat; background-size: cover; width: 100vw; height: 100vh; position: relative; left: 50%; right: 50%; margin-left: -50vw; margin-right: -50vw; margin-top: -24px; padding-top: 24px;">
<div class="container">
<div class="card">
<h3 class="card-header">New User Registration</h3>
<div class="card-body">
{% if form.errors or supplement_form.errors %}
<div class="alert alert-danger">
{{form.errors}}
{{supplement_form.errors}}
</div>
{% endif %}
<div class="col-sm-8 col-sm-offset-2">
<form method="post" role="form">{% csrf_token %}
{% for field in form %}
<div class="form-group form-row">
<label for="{{ field.id_for_label }}" class="col-form-label col-sm-4">{{ field.label }}</label>
<div class="controls col-sm-8">
{% render_field field class+="form-control" placeholder=field.label %}
</div>
</div>
{% endfor %}
<p><input type="submit" value="Register" class="btn btn-primary pull-right"></p>
</form>
</div>
</div>
</div>
</div>
</div>
</div>
{% endblock %}

View File

@@ -1,15 +1,24 @@
from captcha.fields import ReCaptchaField
from hcaptcha.fields import hCaptchaField
from django import forms
from django.contrib.auth.forms import (AuthenticationForm, PasswordResetForm,
UserChangeForm, UserCreationForm)
from django.conf import settings
from registration.forms import RegistrationFormUniqueEmail
from RIGS import models
class CaptchaField(hCaptchaField):
def validate(self, value):
# Skip validation if we're testing FIXME: Arona, y u so lazy
if settings.HCAPTCHA_SITEKEY != '10000000-ffff-ffff-ffff-000000000001':
super().validate(value)
# Registration
class ProfileRegistrationFormUniqueEmail(RegistrationFormUniqueEmail):
captcha = ReCaptchaField()
hcaptcha = CaptchaField()
class Meta:
model = models.Profile
@@ -41,7 +50,7 @@ class EmbeddedAuthenticationForm(CheckApprovedForm):
class PasswordReset(PasswordResetForm):
captcha = ReCaptchaField(label='Captcha')
hcaptcha = CaptchaField()
class ProfileCreationForm(UserCreationForm):

View File

@@ -1,4 +1,4 @@
<li class="nav-item dropdown" id="user">
<li class="nav-item dropdown align-self-end" id="user">
{% if user.is_authenticated %}
<a class="nav-link dropdown-toggle" href="#" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
Hi {{ user.first_name }}

View File

@@ -1,8 +1,10 @@
import os
import re
import time
from django.core import mail
from django.test import LiveServerTestCase
from django.test.utils import override_settings
from selenium.webdriver.common.keys import Keys
from PyRIGS.tests.base import create_browser
@@ -13,14 +15,12 @@ from RIGS import models
class UserRegistrationTest(LiveServerTestCase):
def setUp(self):
self.browser = create_browser()
self.browser.implicitly_wait(3) # Set implicit wait session wide
os.environ['RECAPTCHA_TESTING'] = 'True'
self.browser.implicitly_wait(5) # Set implicit wait session wide
def tearDown(self):
self.browser.quit()
os.environ['RECAPTCHA_TESTING'] = 'False'
@override_settings(DEBUG=True)
def test_registration(self):
# Navigate to the registration page
self.browser.get(self.live_server_url + '/user/register/')
@@ -61,9 +61,11 @@ class UserRegistrationTest(LiveServerTestCase):
last_name.send_keys('Smith')
initials.send_keys('JS')
# phone.send_keys('0123456789')
self.browser.execute_script(
"return function() {jQuery('#g-recaptcha-response').val('PASSED'); return 0}()")
time.sleep(1)
self.browser.switch_to.frame(self.browser.find_element_by_tag_name("iframe"))
self.browser.find_element_by_id('anchor').click()
self.browser.switch_to.default_content()
time.sleep(3)
# Submit incorrect form
submit = self.browser.find_element_by_xpath("//input[@type='submit']")
submit.click()
@@ -85,9 +87,6 @@ class UserRegistrationTest(LiveServerTestCase):
# Correct error
password1.send_keys('correcthorsebatterystaple')
password2.send_keys('correcthorsebatterystaple')
self.browser.execute_script("console.log('Hello, world!')")
self.browser.execute_script(
"return function() {jQuery('#g-recaptcha-response').val('PASSED'); return 0}()")
# Submit again
password2.send_keys(Keys.ENTER)
@@ -126,8 +125,6 @@ class UserRegistrationTest(LiveServerTestCase):
# Expected to fail as not approved
username.send_keys('TestUsername')
password.send_keys('correcthorsebatterystaple')
self.browser.execute_script(
"return function() {jQuery('#g-recaptcha-response').val('PASSED'); return 0}()")
password.send_keys(Keys.ENTER)
# Test approval
@@ -149,8 +146,6 @@ class UserRegistrationTest(LiveServerTestCase):
username.send_keys('TestUsername')
password = self.browser.find_element_by_id('id_password')
password.send_keys('correcthorsebatterystaple')
self.browser.execute_script(
"return function() {jQuery('#g-recaptcha-response').val('PASSED'); return 0}()")
password.send_keys(Keys.ENTER)
# Check we are logged in