c2cwsgiutils 5.2.3__py3-none-any.whl → 5.2.4__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -159,12 +159,29 @@ class Connection:
159
159
  cache_expected: CacheExpected = CacheExpected.NO,
160
160
  **kwargs: Any,
161
161
  ) -> Any:
162
- """POST the given URL (relative to the root of API)."""
162
+ """PUT the given URL (relative to the root of API)."""
163
163
  with self.session.put(self.base_url + url, headers=self._merge_headers(headers, cors), **kwargs) as r:
164
164
  check_response(r, expected_status, cache_expected)
165
165
  self._check_cors(cors, r)
166
166
  return _get_json(r)
167
167
 
168
+ def patch_json(
169
+ self,
170
+ url: str,
171
+ expected_status: int = 200,
172
+ headers: Optional[Mapping[str, str]] = None,
173
+ cors: bool = True,
174
+ cache_expected: CacheExpected = CacheExpected.NO,
175
+ **kwargs: Any,
176
+ ) -> Any:
177
+ """PATCH the given URL (relative to the root of API)."""
178
+ with self.session.patch(
179
+ self.base_url + url, headers=self._merge_headers(headers, cors), **kwargs
180
+ ) as r:
181
+ check_response(r, expected_status, cache_expected)
182
+ self._check_cors(cors, r)
183
+ return _get_json(r)
184
+
168
185
  def delete(
169
186
  self,
170
187
  url: str,
c2cwsgiutils/auth.py CHANGED
@@ -217,22 +217,26 @@ def check_access(
217
217
  return check_access_config(
218
218
  request,
219
219
  {
220
- "github_repository": env_or_settings(
221
- settings,
222
- GITHUB_REPOSITORY_ENV,
223
- GITHUB_REPOSITORY_PROP,
224
- "",
225
- )
226
- if repo is None
227
- else repo,
228
- "github_access_type": env_or_settings(
229
- settings,
230
- GITHUB_ACCESS_TYPE_ENV,
231
- GITHUB_ACCESS_TYPE_PROP,
232
- "pull",
233
- )
234
- if access_type is None
235
- else access_type,
220
+ "github_repository": (
221
+ env_or_settings(
222
+ settings,
223
+ GITHUB_REPOSITORY_ENV,
224
+ GITHUB_REPOSITORY_PROP,
225
+ "",
226
+ )
227
+ if repo is None
228
+ else repo
229
+ ),
230
+ "github_access_type": (
231
+ env_or_settings(
232
+ settings,
233
+ GITHUB_ACCESS_TYPE_ENV,
234
+ GITHUB_ACCESS_TYPE_PROP,
235
+ "pull",
236
+ )
237
+ if access_type is None
238
+ else access_type
239
+ ),
236
240
  },
237
241
  )
238
242
 
@@ -1,4 +1,5 @@
1
1
  """Broadcast messages to all the processes of Gunicorn in every containers."""
2
+
2
3
  import functools
3
4
  import logging
4
5
  import warnings
@@ -1,3 +1,4 @@
1
+ import os
1
2
  import re
2
3
  from typing import Any, Callable, Dict
3
4
 
@@ -22,6 +23,15 @@ class Filter:
22
23
  else:
23
24
  _handle_others(environ)
24
25
 
26
+ if "C2CWSGIUTILS_FORCE_PROTO" in os.environ:
27
+ environ["wsgi.url_scheme"] = os.environ["C2CWSGIUTILS_FORCE_PROTO"]
28
+ if "C2CWSGIUTILS_FORCE_HOST" in os.environ:
29
+ environ["HTTP_HOST"] = os.environ["C2CWSGIUTILS_FORCE_HOST"]
30
+ if "C2CWSGIUTILS_FORCE_SERVER_NAME" in os.environ:
31
+ environ["SERVER_NAME"] = os.environ["C2CWSGIUTILS_FORCE_SERVER_NAME"]
32
+ if "C2CWSGIUTILS_FORCE_REMOTE_ADDR" in os.environ:
33
+ environ["REMOTE_ADDR"] = os.environ["C2CWSGIUTILS_FORCE_REMOTE_ADDR"]
34
+
25
35
  return self._application(environ, start_response)
26
36
 
27
37
 
@@ -1,4 +1,5 @@
1
1
  """Private utilities."""
2
+
2
3
  import os
3
4
  from typing import Any, Callable, Mapping, Optional, cast
4
5
 
c2cwsgiutils/db.py CHANGED
@@ -1,4 +1,5 @@
1
1
  """SQLalchemy models."""
2
+
2
3
  import logging
3
4
  import re
4
5
  import warnings
c2cwsgiutils/errors.py CHANGED
@@ -1,4 +1,5 @@
1
1
  """Install exception views to have nice JSON error pages."""
2
+
2
3
  import logging
3
4
  import os
4
5
  import traceback
@@ -20,7 +21,7 @@ DEPRECATED_ENV_KEY = "ERROR_DETAILS_SECRET"
20
21
  LOG = logging.getLogger(__name__)
21
22
  STATUS_LOGGER = {
22
23
  401: LOG.debug,
23
- 500: LOG.error
24
+ 500: LOG.error,
24
25
  # The rest are warnings
25
26
  }
26
27
 
@@ -4,6 +4,7 @@ Setup an health_check API.
4
4
  To use it, create an instance of this class in your application initialization and do a few calls to its
5
5
  methods add_db_check()
6
6
  """
7
+
7
8
  import configparser
8
9
  import copy
9
10
  import logging
@@ -10,6 +10,7 @@ To add some info about requests:
10
10
 
11
11
  A pyramid event handler is installed to setup this filter for the current request.
12
12
  """
13
+
13
14
  import json
14
15
  import logging
15
16
  import logging.config
@@ -3,6 +3,7 @@ Allows to track the request_id in the logs, the DB and others.
3
3
 
4
4
  Adds a c2c_request_id attribute to the Pyramid Request class to access it.
5
5
  """
6
+
6
7
  import logging
7
8
  import urllib.parse
8
9
  import uuid
@@ -5,7 +5,7 @@ from pyramid.threadlocal import get_current_request
5
5
  from sqlalchemy.orm import Session
6
6
 
7
7
 
8
- def _add_session_id(session: Session, _transaction: Any, _connection: Any) -> None:
8
+ def _add_session_id(session: Session, _transaction: Any) -> None:
9
9
  request = get_current_request()
10
10
  if request is not None:
11
11
  session.execute(
@@ -15,4 +15,5 @@ def _add_session_id(session: Session, _transaction: Any, _connection: Any) -> No
15
15
 
16
16
  def init() -> None:
17
17
  """Initialize the SQL alchemy session selector."""
18
- sqlalchemy.event.listen(Session, "after_begin", _add_session_id)
18
+
19
+ sqlalchemy.event.listen(Session, "after_transaction_create", _add_session_id)
@@ -4,7 +4,6 @@ Used by standalone (non-wsgi) processes to setup all the bits and pieces of c2cw
4
4
  Must be imported at the very beginning of the process's life, before any other module is imported.
5
5
  """
6
6
 
7
-
8
7
  import argparse
9
8
  import warnings
10
9
  from typing import Any, Callable, Dict, Optional, TypedDict, cast
@@ -3,6 +3,7 @@ A view (URL=/sql_provider) allowing to enabled/disable a SQL spy.
3
3
 
4
4
  That runs an "EXPLAIN ANALYZE" on every SELECT query going through SQLAlchemy.
5
5
  """
6
+
6
7
  import logging
7
8
  import warnings
8
9
 
@@ -3,6 +3,7 @@ A view (URL=/sql_provider) allowing to enabled/disable a SQL spy.
3
3
 
4
4
  That runs an "EXPLAIN ANALYZE" on every SELECT query going through SQLAlchemy.
5
5
  """
6
+
6
7
  import logging
7
8
  import re
8
9
  from threading import Lock
@@ -76,7 +76,7 @@ class SQLAlchemyHandler(logging.Handler):
76
76
  try:
77
77
  self.session.bulk_save_objects(logs)
78
78
  self.session.commit()
79
- except (SQLAlchemyError):
79
+ except SQLAlchemyError:
80
80
  try:
81
81
  self.create_db()
82
82
  self.session.rollback()
@@ -101,7 +101,7 @@ class SQLAlchemyHandler(logging.Handler):
101
101
  with self.engine.begin() as connection:
102
102
  if not self.engine.dialect.has_schema(connection, self.Log.__table_args__["schema"]):
103
103
  connection.execute(
104
- sqlalchemy.schema.CreateSchema(self.Log.__table_args__["schema"]), # type: ignore
104
+ sqlalchemy.schema.CreateSchema(self.Log.__table_args__["schema"]),
105
105
  )
106
106
  Base.metadata.create_all(self.engine)
107
107
 
@@ -1,4 +1,5 @@
1
1
  """Generate statsd metrics for pyramid and SQLAlchemy events."""
2
+
2
3
  import warnings
3
4
 
4
5
  import pyramid.config
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: c2cwsgiutils
3
- Version: 5.2.3
3
+ Version: 5.2.4
4
4
  Summary: Common utilities for Camptocamp WSGI applications
5
5
  Home-page: https://github.com/camptocamp/c2cwsgiutils
6
6
  License: BSD-2-Clause
@@ -37,9 +37,11 @@ Requires-Dist: cee_syslog_handler ; extra == "standard" or extra == "all"
37
37
  Requires-Dist: certifi
38
38
  Requires-Dist: cornice ; extra == "standard" or extra == "all"
39
39
  Requires-Dist: gunicorn ; extra == "standard" or extra == "all"
40
+ Requires-Dist: idna
40
41
  Requires-Dist: lxml ; extra == "standard" or extra == "all"
41
42
  Requires-Dist: netifaces ; extra == "standard" or extra == "all"
42
43
  Requires-Dist: objgraph ; extra == "standard" or extra == "all"
44
+ Requires-Dist: pillow
43
45
  Requires-Dist: psycopg2 ; extra == "standard" or extra == "all"
44
46
  Requires-Dist: pyjwt ; extra == "oauth2" or extra == "all"
45
47
  Requires-Dist: pyramid ; extra == "standard" or extra == "all"
@@ -52,7 +54,10 @@ Requires-Dist: scikit-image ; extra == "test-images"
52
54
  Requires-Dist: scipy
53
55
  Requires-Dist: sentry-sdk ; extra == "standard" or extra == "all"
54
56
  Requires-Dist: ujson ; extra == "standard" or extra == "all"
57
+ Requires-Dist: urllib3
55
58
  Requires-Dist: waitress ; extra == "dev" or extra == "all"
59
+ Requires-Dist: webob
60
+ Requires-Dist: zipp
56
61
  Requires-Dist: zope.interface ; extra == "standard" or extra == "all"
57
62
  Requires-Dist: zope.sqlalchemy ; extra == "standard" or extra == "all"
58
63
  Project-URL: Repository, https://github.com/camptocamp/c2cwsgiutils
@@ -726,3 +731,10 @@ To make a release:
726
731
  - Add the new branch name in the `.github/workflows/rebuild.yaml` and
727
732
  `.github/workflows/audit.yaml` files.
728
733
 
734
+ ## Pserve
735
+
736
+ Pserve will not set the headers in the environment then if you are behind a reverse proxy, you will have
737
+ wrong values in client information, you can force them by using the environment variables:
738
+ `C2CWSGIUTILS_FORCE_PROTO`, `C2CWSGIUTILS_FORCE_HOST` `C2CWSGIUTILS_FORCE_SERVER_NAME` and
739
+ `C2CWSGIUTILS_FORCE_REMOTE_ADDR`.
740
+
@@ -1,27 +1,27 @@
1
1
  c2cwsgiutils/__init__.py,sha256=sPZ6-3L_gJy-NIbYdr7EcoMK2TFZMUnn-qD2BglQP8w,3997
2
2
  c2cwsgiutils/acceptance/__init__.py,sha256=vjtpPfu0kbXUOYMx15Z8713IfPFZA9XnkUKkIFtVj_M,1500
3
3
  c2cwsgiutils/acceptance/composition.py,sha256=73WT-DB3Zk_Va8bNfAQuYAOdXuJvNr-DbFJW4N_rLO8,4620
4
- c2cwsgiutils/acceptance/connection.py,sha256=62WVP8KBaEslA8tFyA3lgZIXi20i2GqJTNeCbgV7rzI,9195
4
+ c2cwsgiutils/acceptance/connection.py,sha256=fBsDlNwPUz0kl4xpVmb1_HXzl5BtmzQ2hnJGgeGG0X8,9791
5
5
  c2cwsgiutils/acceptance/image.py,sha256=x5nUxg9UItluXEeP6xWU8UhvDUWu-SwDEqoNacOu3EA,4491
6
6
  c2cwsgiutils/acceptance/print.py,sha256=DDAugcYsDAiFPzMnAQ1k4Us_x37ANEbuk5hb4d6xyKc,2329
7
7
  c2cwsgiutils/acceptance/utils.py,sha256=ixCaHzLyA744dZnfwHpp2AeFlc14WAJb4ojBbbr_R-c,2072
8
- c2cwsgiutils/auth.py,sha256=EyOH2OVG1wrXNVsQWPa5SpSkdzX96MZDir8PFE-xO9w,9314
9
- c2cwsgiutils/broadcast/__init__.py,sha256=cAODXqq2pwZp0n92QSi0ybJIQttV2CJwc1Cd1hhpEvQ,4160
8
+ c2cwsgiutils/auth.py,sha256=eFxEk5qe2UdKF_IdX6VAUjuEoI1heE253nioOY4M-Pk,9434
9
+ c2cwsgiutils/broadcast/__init__.py,sha256=ag2MHwEZ0vXjnWYKhOJxOEL1Nj7Xyt6NkYPc0zNPZjQ,4161
10
10
  c2cwsgiutils/broadcast/interface.py,sha256=M2NMNCXky05xA_jVlnkEcRG-3SE0TEA2uXTz0oR4zKs,615
11
11
  c2cwsgiutils/broadcast/local.py,sha256=iJxv9IjzKjKYz6ZLXRSbrqGRmNUmGoYsSbcRSdz4dbs,1062
12
12
  c2cwsgiutils/broadcast/redis.py,sha256=02EE4-FHG8cE4v_sIswiQblKN6LseorkO13a-b2qq-k,5058
13
13
  c2cwsgiutils/broadcast/utils.py,sha256=0fQZXPu3p_5LEJpGenJwiiMxECQjJhjZBjIkBk8h-ng,272
14
- c2cwsgiutils/client_info.py,sha256=k1jTv3_NVLeMgJURjcgUbH4tmHPjW39UuOWXPJF7DN8,3050
15
- c2cwsgiutils/config_utils.py,sha256=aN_New-YukyZ08--z2CsjTSS6YfDsI5pc_ciNewjxS0,1496
14
+ c2cwsgiutils/client_info.py,sha256=YFteIwNamIc3LIsaYv2C1MZRS6crJYoId5TgxYNvDSw,3601
15
+ c2cwsgiutils/config_utils.py,sha256=v1v4Bypfh3yZeuR_Oh1BnA7eowfbJIQa423KnzV_VFc,1497
16
16
  c2cwsgiutils/coverage_setup.py,sha256=fES0sdhFy6oaeOCuP1qjjm7PQL9l_O8rUKZhRvRBRwQ,839
17
- c2cwsgiutils/db.py,sha256=5P6hylpAOiN-bx_YKcIYLAB3Cz8_unNsGW36iKIOF1U,16140
17
+ c2cwsgiutils/db.py,sha256=gq4BRaPLP7BM6bbRdkTwbb1hWC-onQQyW3WpmJk5o58,16141
18
18
  c2cwsgiutils/db_maintenance_view.py,sha256=Br9EnG4wfFCh5-vWGY86be9iCQmS8Z3dg-n0F0Qp_wc,3049
19
19
  c2cwsgiutils/debug/__init__.py,sha256=80zdAZnE9cwgQW1odE2aOauIxYsG5CQpWvHPcslRue8,1239
20
20
  c2cwsgiutils/debug/_listeners.py,sha256=atiDbQaWYSSbLRcAuI53Rq_8jvwSN8U6e40Qzc6gePU,4364
21
21
  c2cwsgiutils/debug/_views.py,sha256=OxFHGglT6QVGAoZqsgREtK3sZ4aSAoxd4Je0CmP5eAc,7507
22
22
  c2cwsgiutils/debug/utils.py,sha256=1vtfXND_hzs6PH8ohnRGcPYaW2_qKRJ6VxDvEdG0hdU,2328
23
- c2cwsgiutils/errors.py,sha256=LUhZF3BW1i-v20x3EE-rZbT-TpdugpxiW7p5iCAu73Q,6723
24
- c2cwsgiutils/health_check.py,sha256=jpat1OyklKS4W_UwNOBpoqhF_jXJcmGbbB_ndkx2myc,20766
23
+ c2cwsgiutils/errors.py,sha256=xAJghvSBRH_KOQFcYrItGrCLIFVri60ohq_z1dyG63I,6725
24
+ c2cwsgiutils/health_check.py,sha256=cT1vgBwzb9D0KimV8GH96rslXcUnCOPFMIjMJqIhNKo,20767
25
25
  c2cwsgiutils/index.py,sha256=hXrkHNMuTQnNlG-pTe19teNWHX_gjBF4W1WmBAHiUBw,17356
26
26
  c2cwsgiutils/loader.py,sha256=hFIB30saYkyj8brmL07AKE_PFAb2Bny_kWlSOg-xp1E,628
27
27
  c2cwsgiutils/logging_view.py,sha256=zVvZiNvJDdMwclm3KiqsfK8Ra2JSKPSSQt5VYGGpQ2k,3337
@@ -32,11 +32,11 @@ c2cwsgiutils/profiler.py,sha256=3tIwoDSzOKQ06ug_U6j5VDR1BQ9auUOqdJRRLRhDoHw,739
32
32
  c2cwsgiutils/prometheus.py,sha256=03DcJqwEj_UaDjVb5rzSbMAqJ6930ZycvNWm-lKB3c4,2062
33
33
  c2cwsgiutils/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
34
34
  c2cwsgiutils/pyramid.py,sha256=VmrAMFpC636WTToNNaI9hWQOYJAk5hn__K43mBvUFtw,1346
35
- c2cwsgiutils/pyramid_logging.py,sha256=BfxYbpF7mxjMY_08TGp3I9101e6s8tUSJ5yKN7tAt9o,3703
35
+ c2cwsgiutils/pyramid_logging.py,sha256=u-z1LI-Mm_I3ihZr8Ymtospc3YFWMLPV2FMt4SUvnHw,3704
36
36
  c2cwsgiutils/redis_stats.py,sha256=2Y0xj7_yK_A6PRhu8jSK8TF0fsboMiB88BWuEO-qv90,1478
37
37
  c2cwsgiutils/redis_utils.py,sha256=_S9yYngK3owFAjaGhT82V5e-h1dGEwl77RV7hQh09dM,4513
38
- c2cwsgiutils/request_tracking/__init__.py,sha256=cArGa8BLPCEvgDrxEgJIKJoaQEhNxr5WPtBT5Gcmt0o,3823
39
- c2cwsgiutils/request_tracking/_sql.py,sha256=ME13tdXV2Vvhvscon9DbDUqehNWcn4uL75uqzcN5-Mg,577
38
+ c2cwsgiutils/request_tracking/__init__.py,sha256=uLb9IuqgM7i_QXinQ97MRImnTAIxyRbV1jXJA7tifz4,3824
39
+ c2cwsgiutils/request_tracking/_sql.py,sha256=47OtVn3g5QpCCWyl8w6V1xVjbf0ahrw4r9ijjRKXDz4,573
40
40
  c2cwsgiutils/scripts/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
41
41
  c2cwsgiutils/scripts/check_es.py,sha256=dXF1FpyyIUMRlDxA-OY4RjOdnNqxYq2F6IhoNM7nRPg,4147
42
42
  c2cwsgiutils/scripts/genversion.py,sha256=A5jE3E-yNMd3IW4jRFJmvLHphrvko4rA-is43sFKoxw,1998
@@ -44,23 +44,23 @@ c2cwsgiutils/scripts/stats_db.py,sha256=f_VY-JMYvCvZX4vGZHL17ZOQRVust6_3L4eeOgDe
44
44
  c2cwsgiutils/scripts/test_print.py,sha256=UeOZa7jTazgEq5BRJD6lq-u9K6G4movf-sOVKTEs1cQ,2096
45
45
  c2cwsgiutils/sentry.py,sha256=SpqCADxHvYVR89mFRMQDA7IbUVHh6iwKS06keWXtZSQ,5002
46
46
  c2cwsgiutils/services.py,sha256=qz51oCZOC0Lj2_ig4UuHIm0ZZO3FfpFTxrXBWZ_oaNo,1567
47
- c2cwsgiutils/setup_process.py,sha256=FDaHWxzBJwuyq2T7YdILyCyQw2T_NjhPK62ldEBcRa4,3494
48
- c2cwsgiutils/sql_profiler/__init__.py,sha256=lZYq83LYlm_P4uNMv0WU_B9Obl90YaNzkqWtteUHadg,876
49
- c2cwsgiutils/sql_profiler/_impl.py,sha256=wKv9zE6Eh7vna_Ft4bX-b16Y-sE7fiy79jlhn1SSSRM,3680
47
+ c2cwsgiutils/setup_process.py,sha256=s4_3DfKFCp54SUUDh4qS4M-C7n8LVw-XLKsEhCmk6jQ,3493
48
+ c2cwsgiutils/sql_profiler/__init__.py,sha256=_Zw5BO-0sN2tVbSwtyHwi8gkmhCtGW-F6agkENhYILM,877
49
+ c2cwsgiutils/sql_profiler/_impl.py,sha256=zRNrFfUSPGjNHNluExpCpDkxvGna24w7Ny7LnuJsge0,3681
50
50
  c2cwsgiutils/sqlalchemylogger/README.md,sha256=WEyJSrBjedtX1FFrYiq4oMaWMt1fNxRkJYmJWnAoz3g,1552
51
51
  c2cwsgiutils/sqlalchemylogger/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
52
52
  c2cwsgiutils/sqlalchemylogger/_filters.py,sha256=OJQ9_WA-fd9fMZ7TUNFzHHTPI6msw2NVBl5RoeYFnGw,752
53
53
  c2cwsgiutils/sqlalchemylogger/_models.py,sha256=gCCP_AfGl8unVtV1mQW8l2vk8ltDMWl5UJj3-tJ94Pk,1477
54
54
  c2cwsgiutils/sqlalchemylogger/examples/example.py,sha256=n48dJdUi1FH1hfBMAbfHLGPSb1bOVD8pXMxXB57PnpQ,460
55
- c2cwsgiutils/sqlalchemylogger/handlers.py,sha256=mteP0ahLj7UIKHFDHuCy3k-Qs48Z7oTWPotBbTn90Rk,4809
55
+ c2cwsgiutils/sqlalchemylogger/handlers.py,sha256=Bdmsv-C8ElM1U5C7_SWh6ZowyC4yzTQUXfKy5r0QC_k,4791
56
56
  c2cwsgiutils/stats.py,sha256=A32rL2EZ0XlZGJzfZ2uF7cgzdBb4QtFiPnq77WmFhj4,11480
57
- c2cwsgiutils/stats_pyramid/__init__.py,sha256=Vxncq4iRCIlrPjiugQVARqg3VjAMK5H3iMXpWO3NISo,971
57
+ c2cwsgiutils/stats_pyramid/__init__.py,sha256=NGVcqiLbk83HyFhl3IUKoXKNbYw4n8SrVpuYaKJjS1w,972
58
58
  c2cwsgiutils/stats_pyramid/_db_spy.py,sha256=9dpOmx3uoJo8H6NGshDo9IqY97_JQ1Ywu_1dZc4fj08,2840
59
59
  c2cwsgiutils/stats_pyramid/_pyramid_spy.py,sha256=K6Vd-nNAsstF0-2L51Qdo9xDt0RFB6-N5oBiLx5ZJms,2943
60
60
  c2cwsgiutils/stats_pyramid/_views.py,sha256=c3PfyrXzG6I184-bWUrHpR1bt3xyIMgs5mfcZ6NjEwU,527
61
61
  c2cwsgiutils/version.py,sha256=NPWGTOIOMbF2H6S0lmyOHw3r7UXh-1IkrY4ySJx7_Vk,1817
62
- c2cwsgiutils-5.2.3.dist-info/LICENSE,sha256=rM6IWxociA3daRkXnNLYOxGndT5fbs3BfVZCA2Xgt-g,1304
63
- c2cwsgiutils-5.2.3.dist-info/METADATA,sha256=6OJHnHbotmW8XeWzW1zgiDNv-L8hEpfNruGZb4_l_Yc,31462
64
- c2cwsgiutils-5.2.3.dist-info/WHEEL,sha256=WGfLGfLX43Ei_YORXSnT54hxFygu34kMpcQdmgmEwCQ,88
65
- c2cwsgiutils-5.2.3.dist-info/entry_points.txt,sha256=ujgqMTL1awN9qDg8WXmrF7m0fgR-hslUM6zKH86pvy0,703
66
- c2cwsgiutils-5.2.3.dist-info/RECORD,,
62
+ c2cwsgiutils-5.2.4.dist-info/LICENSE,sha256=rM6IWxociA3daRkXnNLYOxGndT5fbs3BfVZCA2Xgt-g,1304
63
+ c2cwsgiutils-5.2.4.dist-info/METADATA,sha256=GqWk2CBhG0kiJim8zT1VnbtPGIMU2BOPcTh5ashWfVo,31901
64
+ c2cwsgiutils-5.2.4.dist-info/WHEEL,sha256=WGfLGfLX43Ei_YORXSnT54hxFygu34kMpcQdmgmEwCQ,88
65
+ c2cwsgiutils-5.2.4.dist-info/entry_points.txt,sha256=ujgqMTL1awN9qDg8WXmrF7m0fgR-hslUM6zKH86pvy0,703
66
+ c2cwsgiutils-5.2.4.dist-info/RECORD,,