hdx-python-utilities 3.6.0__tar.gz → 3.6.2__tar.gz

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.
Files changed (124) hide show
  1. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/.github/workflows/run-python-tests.yaml +1 -0
  2. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/PKG-INFO +1 -1
  3. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/documentation/.readthedocs.yaml +1 -3
  4. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/documentation/main.md +29 -8
  5. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/documentation/pydoc-markdown.yaml +1 -1
  6. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/requirements.txt +24 -19
  7. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/_version.py +2 -2
  8. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/downloader.py +2 -2
  9. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/email.py +4 -4
  10. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/html.py +1 -1
  11. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/session.py +1 -1
  12. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/state.py +40 -1
  13. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/useragent.py +16 -11
  14. hdx_python_utilities-3.6.2/tests/fixtures/state/analysis_dates.txt +1 -0
  15. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_downloader.py +6 -6
  16. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_email.py +1 -1
  17. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_loader.py +6 -6
  18. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_saver.py +1 -1
  19. hdx_python_utilities-3.6.2/tests/hdx/utilities/test_state.py +83 -0
  20. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_useragent.py +5 -5
  21. hdx_python_utilities-3.6.0/tests/hdx/utilities/test_state.py +0 -40
  22. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/.config/black.toml +0 -0
  23. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/.config/coveragerc +0 -0
  24. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/.config/pre-commit-config.yaml +0 -0
  25. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/.config/pytest.ini +0 -0
  26. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/.config/ruff.toml +0 -0
  27. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/.github/workflows/publish.yaml +0 -0
  28. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/.gitignore +0 -0
  29. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/CONTRIBUTING.md +0 -0
  30. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/LICENSE +0 -0
  31. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/README.md +0 -0
  32. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/pyproject.toml +0 -0
  33. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/__init__.py +0 -0
  34. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/base_downloader.py +0 -0
  35. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/compare.py +0 -0
  36. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/dateparse.py +0 -0
  37. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/dictandlist.py +0 -0
  38. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/easy_logging.py +0 -0
  39. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/encoding.py +0 -0
  40. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/errors_onexit.py +0 -0
  41. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/frictionless_wrapper.py +0 -0
  42. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/loader.py +0 -0
  43. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/path.py +0 -0
  44. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/retriever.py +0 -0
  45. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/saver.py +0 -0
  46. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/text.py +0 -0
  47. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/typehint.py +0 -0
  48. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/src/hdx/utilities/uuid.py +0 -0
  49. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/compare/test_csv_processing.csv +0 -0
  50. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/compare/test_csv_processing2.csv +0 -0
  51. /hdx_python_utilities-3.6.0/tests/fixtures/config/empty.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/empty.yaml +0 -0
  52. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/config/hdx_config.json +0 -0
  53. /hdx_python_utilities-3.6.0/tests/fixtures/config/hdx_config.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/hdx_config.yaml +0 -0
  54. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/config/hdx_email_configuration.json +0 -0
  55. /hdx_python_utilities-3.6.0/tests/fixtures/config/hdx_email_configuration.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/hdx_email_configuration.yaml +0 -0
  56. /hdx_python_utilities-3.6.0/tests/fixtures/config/json_csv.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/json_csv.yaml +0 -0
  57. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/config/logging_config.json +0 -0
  58. /hdx_python_utilities-3.6.0/tests/fixtures/config/logging_config.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/logging_config.yaml +0 -0
  59. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/config/project_configuration.json +0 -0
  60. /hdx_python_utilities-3.6.0/tests/fixtures/config/project_configuration.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/project_configuration.yaml +0 -0
  61. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/config/smtp_config.json +0 -0
  62. /hdx_python_utilities-3.6.0/tests/fixtures/config/smtp_config.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/smtp_config.yaml +0 -0
  63. /hdx_python_utilities-3.6.0/tests/fixtures/config/user_agent_config.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/user_agent_config.yaml +0 -0
  64. /hdx_python_utilities-3.6.0/tests/fixtures/config/user_agent_config2.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/user_agent_config2.yaml +0 -0
  65. /hdx_python_utilities-3.6.0/tests/fixtures/config/user_agent_config3.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/user_agent_config3.yaml +0 -0
  66. /hdx_python_utilities-3.6.0/tests/fixtures/config/user_agent_config_wrong.yml → /hdx_python_utilities-3.6.2/tests/fixtures/config/user_agent_config_wrong.yaml +0 -0
  67. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/basicauth.txt +0 -0
  68. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/extra_params.json +0 -0
  69. /hdx_python_utilities-3.6.0/tests/fixtures/downloader/extra_params.yml → /hdx_python_utilities-3.6.2/tests/fixtures/downloader/extra_params.yaml +0 -0
  70. /hdx_python_utilities-3.6.0/tests/fixtures/downloader/extra_params_tree.yml → /hdx_python_utilities-3.6.2/tests/fixtures/downloader/extra_params_tree.yaml +0 -0
  71. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_csv_processing.csv +0 -0
  72. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_csv_processing_blanks.csv +0 -0
  73. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_data.csv +0 -0
  74. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_data.xlsx +0 -0
  75. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_data1.csv/empty.txt +0 -0
  76. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_data2.csv +0 -0
  77. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_json_processing.json +0 -0
  78. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_xls_processing.xls +0 -0
  79. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/downloader/test_xlsx_processing.xlsx +0 -0
  80. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/html/response.html +0 -0
  81. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/loader/empty.json +0 -0
  82. /hdx_python_utilities-3.6.0/tests/fixtures/loader/empty.yml → /hdx_python_utilities-3.6.2/tests/fixtures/loader/empty.yaml +0 -0
  83. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/fallbacks/test.csv +0 -0
  84. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/fallbacks/test.json +0 -0
  85. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/fallbacks/test.txt +0 -0
  86. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/fallbacks/test.yaml +0 -0
  87. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/retriever-test.csv +0 -0
  88. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/test.csv +0 -0
  89. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/test.json +0 -0
  90. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/test.txt +0 -0
  91. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/test.yaml +0 -0
  92. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/retriever/test_hxl.csv +0 -0
  93. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out.csv +0 -0
  94. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out.json +0 -0
  95. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out2.csv +0 -0
  96. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out2.json +0 -0
  97. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out5.json +0 -0
  98. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out6.json +0 -0
  99. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out7.json +0 -0
  100. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out8.csv +0 -0
  101. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/out8.json +0 -0
  102. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/pretty-false_sortkeys-false.json +0 -0
  103. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/pretty-false_sortkeys-false.yaml +0 -0
  104. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/pretty-false_sortkeys-true.json +0 -0
  105. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/pretty-false_sortkeys-true.yaml +0 -0
  106. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/pretty-true_sortkeys-false.json +0 -0
  107. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/pretty-true_sortkeys-false.yaml +0 -0
  108. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/pretty-true_sortkeys-true.json +0 -0
  109. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/saver/pretty-true_sortkeys-true.yaml +0 -0
  110. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/state/last_build_date.txt +0 -0
  111. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/fixtures/test_data.csv +0 -0
  112. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/conftest.py +0 -0
  113. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_compare.py +0 -0
  114. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_dateparse.py +0 -0
  115. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_dictandlist.py +0 -0
  116. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_easy_logging.py +0 -0
  117. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_encoding.py +0 -0
  118. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_errors_onexit.py +0 -0
  119. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_html.py +0 -0
  120. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_path.py +0 -0
  121. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_retriever.py +0 -0
  122. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_text.py +0 -0
  123. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/test_uuid.py +0 -0
  124. {hdx_python_utilities-3.6.0 → hdx_python_utilities-3.6.2}/tests/hdx/utilities/utils.py +0 -0
@@ -4,6 +4,7 @@
4
4
  name: Run tests
5
5
 
6
6
  on:
7
+ workflow_dispatch: # add run button in github
7
8
  push:
8
9
  branches-ignore:
9
10
  - gh-pages
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: hdx-python-utilities
3
- Version: 3.6.0
3
+ Version: 3.6.2
4
4
  Summary: HDX Python Utilities for streaming tabular data, date and time handling and other helpful functions
5
5
  Project-URL: Homepage, https://github.com/OCHA-DAP/hdx-python-utilities
6
6
  Author-email: Michael Rans <rans@email.com>
@@ -1,7 +1,7 @@
1
1
  version: 2
2
2
 
3
3
  mkdocs:
4
- configuration: mkdocs.yml
4
+ configuration: docs/mkdocs.yml
5
5
  fail_on_warning: false
6
6
 
7
7
  build:
@@ -13,5 +13,3 @@ build:
13
13
  - pip install --upgrade mkdocs
14
14
  - pip install pydoc-markdown
15
15
  - pydoc-markdown documentation/pydoc-markdown.yaml
16
- - mv docs/content/* docs
17
- - rmdir docs/content
@@ -82,7 +82,7 @@ methods that all downloaders should have: `download_file`, `download_text`,
82
82
  Note that a single `Download` object cannot be used in parallel: each download operation
83
83
  must be completed before starting the next.
84
84
 
85
- For example, given YAML file extraparams.yml:
85
+ For example, given YAML file extraparams.yaml:
86
86
 
87
87
  mykey:
88
88
  basic_auth: "XXXXXXXX"
@@ -92,7 +92,7 @@ We can create a downloader as shown below that will use the authentication defin
92
92
  `basic\_auth` and add the parameter `locale=en` to each request (eg. for get request
93
93
  <http://myurl/lala?param1=p1&locale=en>):
94
94
 
95
- with Download(user_agent="test", extra_params_yaml="extraparams.yml", extra_params_lookup="mykey") as downloader:
95
+ with Download(user_agent="test", extra_params_yaml="extraparams.yaml", extra_params_lookup="mykey") as downloader:
96
96
  response = downloader.download(url) # get requests library response
97
97
  json = response.json()
98
98
 
@@ -340,16 +340,16 @@ Examples:
340
340
  Examples:
341
341
 
342
342
  # Load YAML
343
- mydict = load_yaml("my_yaml.yml")
343
+ mydict = load_yaml("my_yaml.yaml")
344
344
 
345
345
  # Load 2 YAMLs and merge into dictionary
346
- mydict = load_and_merge_yaml("my_yaml1.yml", "my_yaml2.yml")
346
+ mydict = load_and_merge_yaml("my_yaml1.yaml", "my_yaml2.yaml")
347
347
 
348
348
  # Load YAML into existing dictionary
349
- mydict = load_yaml_into_existing_dict(existing_dict, "my_yaml.yml")
349
+ mydict = load_yaml_into_existing_dict(existing_dict, "my_yaml.yaml")
350
350
 
351
351
  # Load JSON
352
- mydict = load_json("my_json.yml")
352
+ mydict = load_json("my_json.yaml")
353
353
 
354
354
  # Load 2 JSONs and merge into dictionary
355
355
  mydict = load_and_merge_json("my_json1.json", "my_json2.json")
@@ -359,7 +359,7 @@ Examples:
359
359
 
360
360
  # Save dictionary to YAML file in pretty format
361
361
  # preserving order if it is an OrderedDict
362
- save_yaml(mydict, "mypath.yml", pretty=True, sortkeys=False)
362
+ save_yaml(mydict, "mypath.yaml", pretty=True, sortkeys=False)
363
363
 
364
364
  # Save dictionary to JSON file in compact form
365
365
  # sorting the keys
@@ -679,6 +679,27 @@ transformation outputs a string. It is used as follows:
679
679
  ) as state:
680
680
  assert state.get() == date2.replace(hour=0, minute=0)
681
681
 
682
+ with State(
683
+ statepath,
684
+ State.dates_str_to_country_date_dict,
685
+ State.country_date_dict_to_dates_str,
686
+ ) as state:
687
+ state_dict = state.get()
688
+ assert state_dict == {"DEFAULT": date1}
689
+ state_dict["AFG"] = date2
690
+ state.set(state_dict)
691
+ with State(
692
+ statepath,
693
+ State.dates_str_to_country_date_dict,
694
+ State.country_date_dict_to_dates_str,
695
+ ) as state:
696
+ state_dict = state.get()
697
+ assert state_dict == {
698
+ "DEFAULT": date1,
699
+ "AFG": date2.replace(hour=0, minute=0),
700
+ }
701
+
702
+
682
703
  If run inside a GitHub Action, the saved state file could be committed to
683
704
  GitHub so that on the next run the state is available in the repository.
684
705
 
@@ -819,5 +840,5 @@ Examples:
819
840
 
820
841
  ## Easy building and packaging
821
842
 
822
- The pyproject.toml, setup.cfg, .readthedocs.yml and GitHub Actions workflows
843
+ The pyproject.toml, setup.cfg, .readthedocs.yaml and GitHub Actions workflows
823
844
  provide a template that can be used by other projects or libraries.
@@ -9,7 +9,7 @@ renderer:
9
9
  output_directory: docs
10
10
  mkdocs_config:
11
11
  site_name: HDX Python Utilities
12
- theme: readthedocs
12
+ theme: mkdocs
13
13
  repo_url: "https://github.com/OCHA-DAP/hdx-python-utilities"
14
14
  markdown:
15
15
  source_linker:
@@ -4,6 +4,8 @@
4
4
  #
5
5
  # pip-compile --all-extras --output-file=requirements.txt --resolver=backtracking pyproject.toml
6
6
  #
7
+ annotated-types==0.5.0
8
+ # via pydantic
7
9
  attrs==23.1.0
8
10
  # via
9
11
  # frictionless
@@ -11,15 +13,15 @@ attrs==23.1.0
11
13
  # jsonschema
12
14
  beautifulsoup4==4.12.2
13
15
  # via hdx-python-utilities (pyproject.toml)
14
- certifi==2023.5.7
16
+ certifi==2023.7.22
15
17
  # via requests
16
18
  cfgv==3.3.1
17
19
  # via pre-commit
18
- chardet==5.1.0
20
+ chardet==5.2.0
19
21
  # via frictionless
20
- charset-normalizer==3.1.0
22
+ charset-normalizer==3.2.0
21
23
  # via requests
22
- click==8.1.3
24
+ click==8.1.6
23
25
  # via typer
24
26
  colorama==0.4.6
25
27
  # via typer
@@ -27,9 +29,9 @@ coverage[toml]==7.2.7
27
29
  # via pytest-cov
28
30
  decorator==5.1.1
29
31
  # via validators
30
- distlib==0.3.6
32
+ distlib==0.3.7
31
33
  # via virtualenv
32
- dnspython==2.3.0
34
+ dnspython==2.4.1
33
35
  # via email-validator
34
36
  email-validator==2.0.0.post2
35
37
  # via hdx-python-utilities (pyproject.toml)
@@ -37,19 +39,19 @@ et-xmlfile==1.1.0
37
39
  # via openpyxl
38
40
  filelock==3.12.2
39
41
  # via virtualenv
40
- frictionless==5.13.1
42
+ frictionless==5.15.10
41
43
  # via hdx-python-utilities (pyproject.toml)
42
44
  html5lib==1.1
43
45
  # via hdx-python-utilities (pyproject.toml)
44
- humanize==4.6.0
46
+ humanize==4.7.0
45
47
  # via frictionless
46
- identify==2.5.24
48
+ identify==2.5.26
47
49
  # via pre-commit
48
50
  idna==3.4
49
51
  # via
50
52
  # email-validator
51
53
  # requests
52
- ijson==3.2.2
54
+ ijson==3.2.3
53
55
  # via hdx-python-utilities (pyproject.toml)
54
56
  iniconfig==2.0.0
55
57
  # via pytest
@@ -83,19 +85,21 @@ packaging==23.1
83
85
  # via pytest
84
86
  petl==1.7.12
85
87
  # via frictionless
86
- platformdirs==3.7.0
88
+ platformdirs==3.10.0
87
89
  # via virtualenv
88
90
  pluggy==1.2.0
89
91
  # via pytest
90
92
  pre-commit==3.3.3
91
93
  # via hdx-python-utilities (pyproject.toml)
92
- pydantic==1.10.9
94
+ pydantic==2.1.1
93
95
  # via frictionless
94
- pygments==2.15.1
96
+ pydantic-core==2.4.0
97
+ # via pydantic
98
+ pygments==2.16.1
95
99
  # via rich
96
100
  pyrsistent==0.19.3
97
101
  # via jsonschema
98
- pytest==7.3.2
102
+ pytest==7.4.0
99
103
  # via
100
104
  # hdx-python-utilities (pyproject.toml)
101
105
  # pytest-cov
@@ -110,7 +114,7 @@ python-dateutil==2.8.2
110
114
  # hdx-python-utilities (pyproject.toml)
111
115
  python-slugify==8.0.1
112
116
  # via frictionless
113
- pyyaml==6.0
117
+ pyyaml==6.0.1
114
118
  # via
115
119
  # frictionless
116
120
  # pre-commit
@@ -125,7 +129,7 @@ requests-file==1.5.1
125
129
  # via hdx-python-utilities (pyproject.toml)
126
130
  rfc3986==2.0.0
127
131
  # via frictionless
128
- rich==13.4.2
132
+ rich==13.5.2
129
133
  # via typer
130
134
  ruamel-yaml==0.17.32
131
135
  # via hdx-python-utilities (pyproject.toml)
@@ -153,16 +157,17 @@ text-unidecode==1.3
153
157
  # via python-slugify
154
158
  typer[all]==0.9.0
155
159
  # via frictionless
156
- typing-extensions==4.6.3
160
+ typing-extensions==4.7.1
157
161
  # via
158
162
  # frictionless
159
163
  # pydantic
164
+ # pydantic-core
160
165
  # typer
161
- urllib3==2.0.3
166
+ urllib3==2.0.4
162
167
  # via requests
163
168
  validators==0.20.0
164
169
  # via frictionless
165
- virtualenv==20.23.1
170
+ virtualenv==20.24.2
166
171
  # via pre-commit
167
172
  webencodings==0.5.1
168
173
  # via html5lib
@@ -1,4 +1,4 @@
1
1
  # file generated by setuptools_scm
2
2
  # don't change, don't track in version control
3
- __version__ = version = '3.6.0'
4
- __version_tuple__ = version_tuple = (3, 6, 0)
3
+ __version__ = version = '3.6.2'
4
+ __version_tuple__ = version_tuple = (3, 6, 2)
@@ -31,7 +31,7 @@ class Download(BaseDownload):
31
31
 
32
32
  Args:
33
33
  user_agent (Optional[str]): User agent string. HDXPythonUtilities/X.X.X- is prefixed.
34
- user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yml.
34
+ user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yaml.
35
35
  user_agent_lookup (Optional[str]): Lookup key for YAML. Ignored if user_agent supplied.
36
36
  use_env (bool): Whether to read environment variables. Defaults to True.
37
37
  fail_on_missing_file (bool): Raise an exception if any specified configuration files are missing. Defaults to True.
@@ -1255,7 +1255,7 @@ class Download(BaseDownload):
1255
1255
  Args:
1256
1256
  custom_configs (Dict[str, Dict]): Optional dictionary of custom configurations.
1257
1257
  user_agent (Optional[str]): User agent string. HDXPythonUtilities/X.X.X- is prefixed.
1258
- user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yml.
1258
+ user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yaml.
1259
1259
  user_agent_lookup (Optional[str]): Lookup key for YAML. Ignored if user_agent supplied.
1260
1260
  use_env (bool): Whether to read environment variables. Defaults to True.
1261
1261
  fail_on_missing_file (bool): Raise an exception if any specified configuration files are missing. Defaults to True.
@@ -38,11 +38,11 @@ class Email:
38
38
  **kwargs: See below
39
39
  email_config_dict (dict): HDX configuration dictionary OR
40
40
  email_config_json (str): Path to JSON HDX configuration OR
41
- email_config_yaml (str): Path to YAML HDX configuration. Defaults to ~/hdx_email_configuration.yml.
41
+ email_config_yaml (str): Path to YAML HDX configuration. Defaults to ~/hdx_email_configuration.yaml.
42
42
  """
43
43
 
44
44
  default_email_config_yaml = join(
45
- expanduser("~"), "hdx_email_configuration.yml"
45
+ expanduser("~"), "hdx_email_configuration.yaml"
46
46
  )
47
47
 
48
48
  def __init__(self, **kwargs: Any) -> None:
@@ -171,7 +171,7 @@ class Email:
171
171
  recipient, check_deliverability=True
172
172
  ) # validate and get info
173
173
  normalised_recipients.append(
174
- v["email"]
174
+ v.normalized
175
175
  ) # replace with normalized form
176
176
  return normalised_recipients
177
177
 
@@ -209,7 +209,7 @@ class Email:
209
209
  v = validate_email(
210
210
  sender, check_deliverability=False
211
211
  ) # validate and get info
212
- sender = v["email"] # replace with normalized form
212
+ sender = v.normalized
213
213
 
214
214
  if html_body is not None:
215
215
  msg = MIMEMultipart("alternative")
@@ -31,7 +31,7 @@ if BeautifulSoup is not None:
31
31
  url (str): url to read
32
32
  downloader (Download): Download object. Defaults to creating a Download object with given user agent values.
33
33
  user_agent (Optional[str]): User agent string. HDXPythonUtilities/X.X.X- is prefixed.
34
- user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yml.
34
+ user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yaml.
35
35
  user_agent_lookup (Optional[str]): Lookup key for YAML. Ignored if user_agent supplied.
36
36
 
37
37
  Returns:
@@ -35,7 +35,7 @@ def get_session(
35
35
 
36
36
  Args:
37
37
  user_agent (Optional[str]): User agent string. HDXPythonUtilities/X.X.X- is prefixed.
38
- user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yml.
38
+ user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yaml.
39
39
  user_agent_lookup (Optional[str]): Lookup key for YAML. Ignored if user_agent supplied.
40
40
  use_env (bool): Whether to read environment variables. Defaults to True.
41
41
  fail_on_missing_file (bool): Raise an exception if any specified configuration files are missing. Defaults to True.
@@ -1,7 +1,8 @@
1
1
  """Utility to save state to a file and read it back."""
2
2
  import logging
3
- from typing import Any, Callable
3
+ from typing import Any, Callable, Dict
4
4
 
5
+ from hdx.utilities.dateparse import iso_string_from_datetime, parse_date
5
6
  from hdx.utilities.loader import load_text
6
7
  from hdx.utilities.saver import save_text
7
8
 
@@ -91,3 +92,41 @@ class State:
91
92
  None
92
93
  """
93
94
  self.state = state
95
+
96
+ @staticmethod
97
+ def dates_str_to_country_date_dict(dates_str: str) -> Dict:
98
+ """Convert a comma separated string of key=date string pairs eg.
99
+ "default=2017-01-01,afg=2019-01-01" to a dictionary of key date
100
+ mappings eg.
101
+ {"default": 2017-01-01 as datetime, "afg": 2019-01-01 as datetime}
102
+
103
+ Args:
104
+ dates_str (str): Comma separated string of key=date string pairs
105
+
106
+ Returns:
107
+ Dict: Dictionary of key date mappings
108
+ """
109
+ result = {}
110
+ for keyvalue in dates_str.split(","):
111
+ key, value = keyvalue.split("=")
112
+ result[key] = parse_date(value)
113
+ return result
114
+
115
+ @staticmethod
116
+ def country_date_dict_to_dates_str(country_date_dict: Dict) -> str:
117
+ """Convert a dictionary of key date mappings eg.
118
+ {"default": 2017-01-01 as datetime, "afg": 2019-01-01 as datetime}
119
+ to a comma separated string of key=date string pairs eg.
120
+ "default=2017-01-01,afg=2019-01-01"
121
+
122
+ Args:
123
+ country_date_dict (Dict): Dictionary of key date mappings
124
+
125
+ Returns:
126
+ str: Comma separated string of key=date string pairs
127
+ """
128
+ strlist = []
129
+ for key, value in country_date_dict.items():
130
+ valstr = iso_string_from_datetime(value)
131
+ strlist.append(f"{key}={valstr}")
132
+ return ",".join(strlist)
@@ -15,7 +15,7 @@ class UserAgentError(Exception):
15
15
 
16
16
 
17
17
  class UserAgent:
18
- default_user_agent_config_yaml = join(expanduser("~"), ".useragent.yml")
18
+ default_user_agent_config_yaml = join(expanduser("~"), ".useragent.yaml")
19
19
  user_agent = None
20
20
 
21
21
  @staticmethod
@@ -82,13 +82,18 @@ class UserAgent:
82
82
  """
83
83
  if not user_agent_config_yaml:
84
84
  user_agent_config_yaml = cls.default_user_agent_config_yaml
85
- logger.info(
86
- f"No user agent or user agent config file given. Using default user agent config file: {user_agent_config_yaml}."
87
- )
88
- if not isfile(user_agent_config_yaml):
89
- raise UserAgentError(
90
- "User_agent should be supplied in a YAML config file. It can be your project's name for example."
91
- )
85
+ if not isfile(user_agent_config_yaml):
86
+ user_agent_config_yaml = user_agent_config_yaml.replace(
87
+ ".yaml", ".yml"
88
+ )
89
+ if isfile(user_agent_config_yaml):
90
+ logger.info(
91
+ f"No user agent or user agent config file given. Using default user agent config file: {user_agent_config_yaml}."
92
+ )
93
+ else:
94
+ raise UserAgentError(
95
+ f"User_agent should be supplied in a YAML config file and no configuration file at default path: {cls.default_user_agent_config_yaml}. User agent can be your project's name for example."
96
+ )
92
97
  logger.info(
93
98
  f"Loading user agent config from: {user_agent_config_yaml}"
94
99
  )
@@ -116,7 +121,7 @@ class UserAgent:
116
121
 
117
122
  Args:
118
123
  user_agent (Optional[str]): User agent string. HDXPythonLibrary/X.X.X- is prefixed.
119
- user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yml.
124
+ user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yaml.
120
125
  user_agent_lookup (Optional[str]): Lookup key for YAML. Ignored if user_agent supplied.
121
126
 
122
127
  Returns:
@@ -154,7 +159,7 @@ class UserAgent:
154
159
 
155
160
  Args:
156
161
  user_agent (Optional[str]): User agent string. HDXPythonLibrary/X.X.X- is prefixed.
157
- user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yml.
162
+ user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yaml.
158
163
  user_agent_lookup (Optional[str]): Lookup key for YAML. Ignored if user_agent supplied.
159
164
 
160
165
  Returns:
@@ -177,7 +182,7 @@ class UserAgent:
177
182
 
178
183
  Args:
179
184
  user_agent (Optional[str]): User agent string. HDXPythonLibrary/X.X.X- is prefixed.
180
- user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yml.
185
+ user_agent_config_yaml (Optional[str]): Path to YAML user agent configuration. Ignored if user_agent supplied. Defaults to ~/.useragent.yaml.
181
186
  user_agent_lookup (Optional[str]): Lookup key for YAML. Ignored if user_agent supplied.
182
187
 
183
188
  Returns:
@@ -0,0 +1 @@
1
+ DEFAULT=2020-09-23
@@ -43,7 +43,7 @@ class TestDownloader:
43
43
 
44
44
  @pytest.fixture(scope="class")
45
45
  def fixturefile(self, downloaderfolder):
46
- return join(downloaderfolder, "extra_params_tree.yml")
46
+ return join(downloaderfolder, "extra_params_tree.yaml")
47
47
 
48
48
  @pytest.fixture(scope="class")
49
49
  def fixtureurl(self):
@@ -55,11 +55,11 @@ class TestDownloader:
55
55
 
56
56
  @pytest.fixture(scope="class")
57
57
  def getfixtureurl(self):
58
- return "http://httpbin.org/get"
58
+ return "https://httpbin.org/get"
59
59
 
60
60
  @pytest.fixture(scope="class")
61
61
  def postfixtureurl(self):
62
- return "http://httpbin.org/post"
62
+ return "https://httpbin.org/post"
63
63
 
64
64
  @pytest.fixture(scope="class")
65
65
  def fixturenotexistsurl(self):
@@ -121,7 +121,7 @@ class TestDownloader:
121
121
  assert downloader.session.auth == ("user", "pass")
122
122
  with Download(basic_auth_file=basicauthfile) as downloader:
123
123
  assert downloader.session.auth == ("testuser", "testpass")
124
- extraparamsyamltree = join(downloaderfolder, "extra_params_tree.yml")
124
+ extraparamsyamltree = join(downloaderfolder, "extra_params_tree.yaml")
125
125
  with Download(
126
126
  extra_params_yaml=extraparamsyamltree, extra_params_lookup="mykey"
127
127
  ) as downloader:
@@ -172,7 +172,7 @@ class TestDownloader:
172
172
  )
173
173
  with pytest.raises(IOError):
174
174
  Download(basic_auth_file="NOTEXIST")
175
- extraparamsyaml = join(downloaderfolder, "extra_params.yml")
175
+ extraparamsyaml = join(downloaderfolder, "extra_params.yaml")
176
176
  test_url = "http://www.lalala.com/lala"
177
177
  with Download(
178
178
  basic_auth_file=basicauthfile, extra_params_dict={"key1": "val1"}
@@ -367,7 +367,7 @@ class TestDownloader:
367
367
  f = downloader.download_file(fixturefile, folder=tmpdir)
368
368
  fpath = abspath(f)
369
369
  remove(f)
370
- assert fpath == abspath(join(tmpdir, "extra_params_tree.yml"))
370
+ assert fpath == abspath(join(tmpdir, "extra_params_tree.yaml"))
371
371
  f = downloader.download_file(fixtureurl, folder=tmpdir)
372
372
  fpath = abspath(f)
373
373
  remove(f)
@@ -13,7 +13,7 @@ class TestEmail:
13
13
 
14
14
  @pytest.fixture(scope="class")
15
15
  def email_yaml(self, configfolder):
16
- return join(configfolder, "hdx_email_configuration.yml")
16
+ return join(configfolder, "hdx_email_configuration.yaml")
17
17
 
18
18
  def test_mail(self, mocksmtp):
19
19
  smtp_initargs = {
@@ -117,17 +117,17 @@ test"""
117
117
  def test_load_empty(self, fixturesfolder):
118
118
  loaderfolder = join(fixturesfolder, "loader")
119
119
  with pytest.raises(LoadError):
120
- load_text(join(loaderfolder, "empty.yml"))
120
+ load_text(join(loaderfolder, "empty.yaml"))
121
121
  with pytest.raises(LoadError):
122
- load_yaml(join(loaderfolder, "empty.yml"))
122
+ load_yaml(join(loaderfolder, "empty.yaml"))
123
123
  with pytest.raises(LoadError):
124
124
  load_json(join(loaderfolder, "empty.json"))
125
125
 
126
126
  def test_load_and_merge_yaml(self, configfolder):
127
127
  result = load_and_merge_yaml(
128
128
  [
129
- join(configfolder, "hdx_config.yml"),
130
- join(configfolder, "project_configuration.yml"),
129
+ join(configfolder, "hdx_config.yaml"),
130
+ join(configfolder, "project_configuration.yaml"),
131
131
  ]
132
132
  )
133
133
  assert list(result.items()) == list(TestLoader.expected_yaml.items())
@@ -142,9 +142,9 @@ test"""
142
142
  assert list(result.items()) == list(TestLoader.expected_json.items())
143
143
 
144
144
  def test_load_yaml_into_existing_dict(self, configfolder):
145
- existing_dict = load_yaml(join(configfolder, "hdx_config.yml"))
145
+ existing_dict = load_yaml(join(configfolder, "hdx_config.yaml"))
146
146
  result = load_yaml_into_existing_dict(
147
- existing_dict, join(configfolder, "project_configuration.yml")
147
+ existing_dict, join(configfolder, "project_configuration.yaml")
148
148
  )
149
149
  assert list(result.items()) == list(TestLoader.expected_yaml.items())
150
150
 
@@ -99,7 +99,7 @@ class TestLoader:
99
99
 
100
100
  @pytest.fixture(scope="class")
101
101
  def json_csv_configuration(self, fixturesfolder):
102
- return load_yaml(join(fixturesfolder, "config", "json_csv.yml"))
102
+ return load_yaml(join(fixturesfolder, "config", "json_csv.yaml"))
103
103
 
104
104
  @pytest.mark.parametrize(
105
105
  "filename,pretty,sortkeys",
@@ -0,0 +1,83 @@
1
+ """State Utility Tests"""
2
+ from datetime import datetime, timezone
3
+ from os.path import join
4
+ from shutil import copyfile
5
+
6
+ import pytest
7
+
8
+ from hdx.utilities.dateparse import iso_string_from_datetime, parse_date
9
+ from hdx.utilities.path import temp_dir
10
+ from hdx.utilities.state import State
11
+
12
+
13
+ class TestState:
14
+ @pytest.fixture(scope="class")
15
+ def statefolder(self, fixturesfolder):
16
+ return join(fixturesfolder, "state")
17
+
18
+ @pytest.fixture(scope="class")
19
+ def statefile(self):
20
+ return "last_build_date.txt"
21
+
22
+ @pytest.fixture(scope="class")
23
+ def multidatestatefile(self):
24
+ return "analysis_dates.txt"
25
+
26
+ @pytest.fixture(scope="class")
27
+ def date1(self):
28
+ return datetime(2020, 9, 23, 0, 0, tzinfo=timezone.utc)
29
+
30
+ @pytest.fixture(scope="class")
31
+ def date2(self):
32
+ return datetime(2022, 5, 12, 10, 15, tzinfo=timezone.utc)
33
+
34
+ def test_state(self, statefolder, statefile, date1, date2):
35
+ with temp_dir(folder="test_state") as tmpdir:
36
+ statepath = join(tmpdir, statefile)
37
+ copyfile(join(statefolder, statefile), statepath)
38
+ with State(
39
+ statepath, parse_date, iso_string_from_datetime
40
+ ) as state:
41
+ assert state.get() == date1
42
+ with State(
43
+ statepath, parse_date, iso_string_from_datetime
44
+ ) as state:
45
+ assert state.get() == date1
46
+ state.set(date2)
47
+ with State(
48
+ statepath, parse_date, iso_string_from_datetime
49
+ ) as state:
50
+ assert state.get() == date2.replace(hour=0, minute=0)
51
+
52
+ def test_multi_date_state(
53
+ self, statefolder, multidatestatefile, date1, date2
54
+ ):
55
+ with temp_dir(folder="test_multidatestate") as tmpdir:
56
+ statepath = join(tmpdir, multidatestatefile)
57
+ copyfile(join(statefolder, multidatestatefile), statepath)
58
+ with State(
59
+ statepath,
60
+ State.dates_str_to_country_date_dict,
61
+ State.country_date_dict_to_dates_str,
62
+ ) as state:
63
+ state_dict = state.get()
64
+ assert state_dict == {"DEFAULT": date1}
65
+ with State(
66
+ statepath,
67
+ State.dates_str_to_country_date_dict,
68
+ State.country_date_dict_to_dates_str,
69
+ ) as state:
70
+ state_dict = state.get()
71
+ assert state_dict == {"DEFAULT": date1}
72
+ state_dict["AFG"] = date2
73
+ state.set(state_dict)
74
+ with State(
75
+ statepath,
76
+ State.dates_str_to_country_date_dict,
77
+ State.country_date_dict_to_dates_str,
78
+ ) as state:
79
+ state_dict = state.get()
80
+ assert state_dict == {
81
+ "DEFAULT": date1,
82
+ "AFG": date2.replace(hour=0, minute=0),
83
+ }
@@ -11,23 +11,23 @@ from hdx.utilities.useragent import UserAgent, UserAgentError
11
11
  class TestUserAgent:
12
12
  @pytest.fixture(scope="class")
13
13
  def user_agent_config_yaml(self, configfolder):
14
- return join(configfolder, "user_agent_config.yml")
14
+ return join(configfolder, "user_agent_config.yaml")
15
15
 
16
16
  @pytest.fixture(scope="class")
17
17
  def user_agent_config2_yaml(self, configfolder):
18
- return join(configfolder, "user_agent_config2.yml")
18
+ return join(configfolder, "user_agent_config2.yaml")
19
19
 
20
20
  @pytest.fixture(scope="class")
21
21
  def user_agent_config3_yaml(self, configfolder):
22
- return join(configfolder, "user_agent_config3.yml")
22
+ return join(configfolder, "user_agent_config3.yaml")
23
23
 
24
24
  @pytest.fixture(scope="class")
25
25
  def empty_yaml(self, configfolder):
26
- return join(configfolder, "empty.yml")
26
+ return join(configfolder, "empty.yaml")
27
27
 
28
28
  @pytest.fixture(scope="class")
29
29
  def user_agent_config_wrong_yaml(self, configfolder):
30
- return join(configfolder, "user_agent_config_wrong.yml")
30
+ return join(configfolder, "user_agent_config_wrong.yaml")
31
31
 
32
32
  def test_user_agent(
33
33
  self,
@@ -1,40 +0,0 @@
1
- """State Utility Tests"""
2
- from datetime import datetime, timezone
3
- from os.path import join
4
- from shutil import copyfile
5
-
6
- import pytest
7
-
8
- from hdx.utilities.dateparse import iso_string_from_datetime, parse_date
9
- from hdx.utilities.path import temp_dir
10
- from hdx.utilities.state import State
11
-
12
-
13
- class TestState:
14
- @pytest.fixture(scope="class")
15
- def statefolder(self, fixturesfolder):
16
- return join(fixturesfolder, "state")
17
-
18
- @pytest.fixture(scope="class")
19
- def statefile(self):
20
- return "last_build_date.txt"
21
-
22
- def test_state(self, statefolder, statefile):
23
- with temp_dir(folder="test_state") as tmpdir:
24
- statepath = join(tmpdir, statefile)
25
- copyfile(join(statefolder, statefile), statepath)
26
- date1 = datetime(2020, 9, 23, 0, 0, tzinfo=timezone.utc)
27
- date2 = datetime(2022, 5, 12, 10, 15, tzinfo=timezone.utc)
28
- with State(
29
- statepath, parse_date, iso_string_from_datetime
30
- ) as state:
31
- assert state.get() == date1
32
- with State(
33
- statepath, parse_date, iso_string_from_datetime
34
- ) as state:
35
- assert state.get() == date1
36
- state.set(date2)
37
- with State(
38
- statepath, parse_date, iso_string_from_datetime
39
- ) as state:
40
- assert state.get() == date2.replace(hour=0, minute=0)