geoseeq 0.7.3.dev0__tar.gz → 0.7.3.dev2__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 (139) hide show
  1. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/PKG-INFO +1 -1
  2. geoseeq-0.7.3.dev2/docs/examples/simple_python_example/project_dashboard_example.py +61 -0
  3. geoseeq-0.7.3.dev2/docs/examples/simple_python_example/sample_dashboard_example.py +44 -0
  4. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/examples/simple_python_example/smart_table_example.py +3 -2
  5. geoseeq-0.7.3.dev2/geoseeq/dashboard/dashboard.py +273 -0
  6. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/project.py +172 -54
  7. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/sample.py +88 -15
  8. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/pyproject.toml +1 -1
  9. geoseeq-0.7.3.dev0/geoseeq/dashboard/dashboard.py +0 -190
  10. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/.devcontainer/devcontainer.json +0 -0
  11. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/.github/workflows/python-publish.yml +0 -0
  12. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/.github/workflows/run_unit_tests.yml +0 -0
  13. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/.gitignore +0 -0
  14. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/.pre-commit-config.yaml +0 -0
  15. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/AGENTS.md +0 -0
  16. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/LICENSE +0 -0
  17. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/Makefile +0 -0
  18. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/README.md +0 -0
  19. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/commit_pylintrc +0 -0
  20. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/about_geoseeq.md +0 -0
  21. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/contributing.md +0 -0
  22. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/downloading_data_examples.md +0 -0
  23. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/examples/simple_python_example/README.md +0 -0
  24. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/examples/simple_python_example/simple_python_example.py +0 -0
  25. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/examples/simple_snakemake_example/README.md +0 -0
  26. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/examples/simple_snakemake_example/Snakefile +0 -0
  27. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/examples/simple_snakemake_example/config.yaml +0 -0
  28. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/docs/uploading_data_examples.md +0 -0
  29. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/__init__.py +0 -0
  30. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/app.py +0 -0
  31. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/blob_constructors.py +0 -0
  32. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/bulk_creators.py +0 -0
  33. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/__init__.py +0 -0
  34. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/constants.py +0 -0
  35. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/copy.py +0 -0
  36. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/detail.py +0 -0
  37. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/download.py +0 -0
  38. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/fastq_utils.py +0 -0
  39. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/find_grn.py +0 -0
  40. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/get_eula.py +0 -0
  41. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/main.py +0 -0
  42. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/manage.py +0 -0
  43. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/progress_bar.py +0 -0
  44. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/project.py +0 -0
  45. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/raw.py +0 -0
  46. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/run.py +0 -0
  47. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/search.py +0 -0
  48. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/shared_params/__init__.py +0 -0
  49. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/shared_params/common_state.py +0 -0
  50. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/shared_params/config.py +0 -0
  51. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/shared_params/id_handlers.py +0 -0
  52. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/shared_params/obj_getters.py +0 -0
  53. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/shared_params/opts_and_args.py +0 -0
  54. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/upload/__init__.py +0 -0
  55. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/upload/upload.py +0 -0
  56. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/upload/upload_advanced.py +0 -0
  57. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/upload/upload_reads.py +0 -0
  58. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/user.py +0 -0
  59. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/utils.py +0 -0
  60. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/cli/view.py +0 -0
  61. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/constants.py +0 -0
  62. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/contrib/__init__.py +0 -0
  63. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/contrib/ncbi/README.md +0 -0
  64. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/contrib/ncbi/__init__.py +0 -0
  65. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/contrib/ncbi/api.py +0 -0
  66. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/contrib/ncbi/bioproject.py +0 -0
  67. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/contrib/ncbi/cli.py +0 -0
  68. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/contrib/ncbi/setup_logging.py +0 -0
  69. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/file_system/filesystem_download.py +0 -0
  70. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/file_system/main.py +0 -0
  71. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/file_system_cache.py +0 -0
  72. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/id_constructors/__init__.py +0 -0
  73. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/id_constructors/from_blobs.py +0 -0
  74. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/id_constructors/from_ids.py +0 -0
  75. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/id_constructors/from_names.py +0 -0
  76. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/id_constructors/from_uuids.py +0 -0
  77. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/id_constructors/resolvers.py +0 -0
  78. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/id_constructors/utils.py +0 -0
  79. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/knex.py +0 -0
  80. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/organization.py +0 -0
  81. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/pipeline.py +0 -0
  82. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/README.md +0 -0
  83. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/__init__.py +0 -0
  84. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/constants.py +0 -0
  85. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/highcharts.py +0 -0
  86. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/map/__init__.py +0 -0
  87. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/map/base_layer.py +0 -0
  88. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/map/map.py +0 -0
  89. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/map/overlay.py +0 -0
  90. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/plotting/selectable.py +0 -0
  91. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/remote_object.py +0 -0
  92. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/__init__.py +0 -0
  93. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/bioinfo.py +0 -0
  94. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/file_chunker.py +0 -0
  95. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/file_download.py +0 -0
  96. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/file_upload.py +0 -0
  97. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/result_file.py +0 -0
  98. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/result_folder.py +0 -0
  99. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/resumable_download_tracker.py +0 -0
  100. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/resumable_upload_tracker.py +0 -0
  101. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/smart_objects.py +0 -0
  102. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/result/utils.py +0 -0
  103. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/search.py +0 -0
  104. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/smart_table.py +0 -0
  105. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/smart_tree.py +0 -0
  106. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/upload_download_manager.py +0 -0
  107. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/user.py +0 -0
  108. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/utils.py +0 -0
  109. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/README.md +0 -0
  110. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/__init__.py +0 -0
  111. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/checksum.py +0 -0
  112. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/cli.py +0 -0
  113. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/clone.py +0 -0
  114. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/constants.py +0 -0
  115. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/vc_cache.py +0 -0
  116. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/vc_dir.py +0 -0
  117. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/vc_sample.py +0 -0
  118. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/vc/vc_stub.py +0 -0
  119. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/geoseeq/work_orders.py +0 -0
  120. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/setup.py +0 -0
  121. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/__init__.py +0 -0
  122. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/conftest.py +0 -0
  123. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_api_client.py +0 -0
  124. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_download.py +0 -0
  125. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_download_cli.py +0 -0
  126. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_file_chunker.py +0 -0
  127. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_file_system_cache.py +0 -0
  128. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_files/files_path.txt +0 -0
  129. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_files/sampleclit.R1.fastq.gz +0 -0
  130. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_files/sampleclit.R2.fastq.gz +0 -0
  131. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_files/single-end.fastq.gz +0 -0
  132. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_files/test_metadata.csv +0 -0
  133. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_files/test_small.R1.fastq.gz +0 -0
  134. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_files/test_small.R2.fastq.gz +0 -0
  135. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_plotting.py +0 -0
  136. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_remote_object.py +0 -0
  137. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_upload.py +0 -0
  138. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_upload_cli.py +0 -0
  139. {geoseeq-0.7.3.dev0 → geoseeq-0.7.3.dev2}/tests/test_utils.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: geoseeq
3
- Version: 0.7.3.dev0
3
+ Version: 0.7.3.dev2
4
4
  Summary: GeoSeeq command line tools and python API
5
5
  Project-URL: Homepage, https://github.com/biotia/geoseeq_api_client
6
6
  Project-URL: Issues, https://github.com/biotia/geoseeq_api_client/issues
@@ -0,0 +1,61 @@
1
+ import os
2
+ from geoseeq import Knex
3
+ from geoseeq.dashboard.dashboard import Dashboard
4
+ from geoseeq.id_constructors.from_uuids import (
5
+ project_from_uuid,
6
+ sample_group_ar_field_from_uuid,
7
+ )
8
+
9
+
10
+ endpoint = os.environ.get("GEOSEEQ_ENDPOINT", "")
11
+ token = os.environ.get("GEOSEEQ_API_TOKEN", "")
12
+ project_id = ""
13
+ file_id = ""
14
+ file2_id = ""
15
+
16
+
17
+ knex = Knex(endpoint)
18
+ knex.add_api_token(token)
19
+
20
+
21
+ project = project_from_uuid(knex, project_id)
22
+ dashboard = project.get_or_create_default_dashbaord()
23
+
24
+ # Rename dashboard
25
+ dashboard.title = "My default dashboard"
26
+
27
+ # Add tile
28
+ file = sample_group_ar_field_from_uuid(knex, file_id)
29
+ dashboard.add_tile(file, title="Tile title", width="full")
30
+ dashboard.save()
31
+
32
+ # Remove tiles
33
+ dashboard.tiles = []
34
+ dashboard.save()
35
+
36
+ # Add multiple tiles
37
+ file = sample_group_ar_field_from_uuid(knex, file_id)
38
+ dashboard.add_tile(file, title="Tile title", width="full")
39
+ file2 = sample_group_ar_field_from_uuid(knex, file2_id)
40
+ dashboard.add_tile(file2, title="Tile title 2", width="half")
41
+ dashboard.save()
42
+
43
+
44
+ dashboard2 = project.get_or_create_dashbaord_by_title(title="Dashboard Dix")
45
+ dashboard2.title = "Renamed dashboard"
46
+
47
+ # Set dashboard to default
48
+ dashboard2.default = True
49
+ dashboard2.add_tile(file, title="Best tile", width="half")
50
+ dashboard2.save()
51
+
52
+ # Delete dashboard
53
+ # dashboard2.delete()
54
+
55
+ # Using the constructors
56
+ dashboard3 = Dashboard(knex=knex, project=project, title="Third dashboard")
57
+ dashboard3.create()
58
+
59
+ dashboard2 = Dashboard(knex=knex, project=project, title="Renamed dashboard")
60
+ dashboard2.get() # Load tiles
61
+ print(dashboard.tiles)
@@ -0,0 +1,44 @@
1
+ import os
2
+ from geoseeq import Knex
3
+ from geoseeq.dashboard.dashboard import SampleDashboard
4
+ from geoseeq.id_constructors.from_uuids import (
5
+ sample_from_uuid,
6
+ sample_result_file_from_uuid,
7
+ )
8
+
9
+
10
+ endpoint = os.environ.get("GEOSEEQ_ENDPOINT", "")
11
+ token = os.environ.get("GEOSEEQ_API_TOKEN", "")
12
+ sample_id = ""
13
+ file_id = ""
14
+ file2_id = ""
15
+
16
+
17
+ knex = Knex(endpoint)
18
+ knex.add_api_token(token)
19
+
20
+
21
+ sample = sample_from_uuid(knex, sample_id)
22
+ dashboard = sample.get_or_create_default_dashbaord()
23
+
24
+ # Add tiles
25
+ file = sample_result_file_from_uuid(knex, file_id)
26
+ dashboard.add_tile(file, title="Tile title", width="full", order=2)
27
+ file2 = sample_result_file_from_uuid(knex, file2_id)
28
+ dashboard.add_tile(file2, title="Tile title 2", width="half", order=1)
29
+ dashboard.save()
30
+
31
+
32
+ dashboard2 = sample.get_or_create_dashbaord_by_title(title="BDX Dashboard")
33
+
34
+ # Rename dahboard
35
+ # dashboard2.title = "Another title"
36
+
37
+ # Remove existing tiles
38
+ dashboard2.tiles = []
39
+
40
+ dashboard2.add_tile(file, title="Tile title 2", width="half")
41
+ dashboard2.save()
42
+
43
+ # Delete dashboard
44
+ # dashboard2.delete()
@@ -1,3 +1,4 @@
1
+ import os
1
2
  import pandas as pd
2
3
 
3
4
  from geoseeq import Knex
@@ -7,8 +8,8 @@ from geoseeq.id_constructors.from_uuids import (
7
8
  )
8
9
  from geoseeq.smart_table import SmartTable
9
10
 
10
- endpoint = "https://backend.geoseeq.com"
11
- token = ""
11
+ endpoint = os.environ.get("GEOSEEQ_ENDPOINT", "")
12
+ token = os.environ.get("GEOSEEQ_API_TOKEN", "")
12
13
  folder_id = ""
13
14
 
14
15
  knex = Knex(endpoint)
@@ -0,0 +1,273 @@
1
+ import logging
2
+ from typing import Literal
3
+
4
+ from geoseeq import ProjectResultFile
5
+ from geoseeq.id_constructors import result_file_from_blob
6
+ from geoseeq.id_constructors.from_ids import result_file_from_id
7
+ from geoseeq.remote_object import RemoteObject
8
+ from geoseeq import GeoseeqNotFoundError
9
+
10
+ logger = logging.getLogger("geoseeq_api")
11
+
12
+
13
+ class Dashboard(RemoteObject):
14
+ parent_field = "project"
15
+ remote_fields = ["is_default"]
16
+
17
+ def __init__(
18
+ self, knex, project, title="Default dashboard", default=False, tiles=[]
19
+ ):
20
+ super().__init__(self)
21
+ self.knex = knex
22
+ self.project = project
23
+ self.title = title
24
+ self._original_title = title
25
+ self.tiles = tiles
26
+ self.default = default
27
+
28
+ def _get(self, allow_overwrite=False):
29
+ blob = self.knex.get(f"sample_groups/{self.project.uuid}/dashboard-list")
30
+ if self.title not in blob["dashboard_data"].keys():
31
+ raise GeoseeqNotFoundError(f"Dashboard '{self.title}' not found.")
32
+ blob = blob["dashboard_data"][self.title]
33
+ for tile_blob in blob["tiles"]:
34
+ tile = DashboardTile.from_blob(self, tile_blob)
35
+ self.tiles.append(tile)
36
+ blob.pop("tiles")
37
+ self.load_blob(blob, allow_overwrite=allow_overwrite)
38
+
39
+ def save(self):
40
+ put_data = {
41
+ "name": self._original_title,
42
+ "is_default": self.default,
43
+ "new_name": self.title,
44
+ }
45
+ self.knex.put(
46
+ f"sample_groups/{self.project.uuid}/dashboard-list",
47
+ json=put_data,
48
+ json_response=False,
49
+ )
50
+ self._original_title = self.title
51
+ self.save_tiles()
52
+
53
+ def save_tiles(self):
54
+ post_data = {"tiles": [tile._get_post_data() for tile in self.tiles]}
55
+ self.knex.post(
56
+ f"sample_groups/{self.project.uuid}/dashboard/{self._original_title}/tiles",
57
+ json=post_data,
58
+ json_response=False,
59
+ )
60
+
61
+ def _create(self):
62
+ post_data = {"name": self.title, "is_default": self.default}
63
+ self.knex.post(
64
+ f"sample_groups/{self.project.uuid}/dashboard-list", json=post_data
65
+ )
66
+
67
+ def add_tile(
68
+ self,
69
+ result_file,
70
+ title,
71
+ width: Literal["hafl", "full"] = "half",
72
+ ):
73
+ style = "col-span-1" if width == "half" else "col-span-2"
74
+ result_file.get()
75
+ tile = DashboardTile(self.knex, self, title, result_file, style=style)
76
+ self.tiles.append(tile)
77
+ self._modified = True
78
+
79
+ def delete(self):
80
+ self.knex.delete(
81
+ f"sample_groups/{self.project.uuid}/dashboard-list?name={self._original_title}"
82
+ )
83
+
84
+ def __str__(self):
85
+ return f'<Geoseeq Dashboard: {self.project.grn} "{self._original_title}"/>'
86
+
87
+ def __repr__(self):
88
+ return str(self)
89
+
90
+ @property
91
+ def grn(self):
92
+ return f'grn:dashboard:{self.project.uuid}:"{self._original_title}"'
93
+
94
+ def pre_hash(self):
95
+ return "DASH" + self.project.uuid + self._original_title
96
+
97
+
98
+ class DashboardTile:
99
+ def __init__(self, knex, dashboard, title, result_file, style="col-span-1"):
100
+ self.knex = knex
101
+ self.dashboard = dashboard
102
+ self.title = title
103
+ self.style = style
104
+ self.result_file = result_file
105
+
106
+ def _get_post_data(self):
107
+ out = {
108
+ "field_uuid": self.result_file.uuid,
109
+ "field_type": (
110
+ "group" if isinstance(self.result_file, ProjectResultFile) else "sample"
111
+ ),
112
+ "style": self.style,
113
+ "title": self.title,
114
+ "has_related_field": False,
115
+ }
116
+ return out
117
+
118
+ @classmethod
119
+ def from_blob(cls, dashboard, blob):
120
+ result_file = result_file_from_blob(dashboard.knex, blob["viz_field"])
121
+ return cls(
122
+ dashboard.knex, dashboard, blob["title"], result_file, style=blob["style"]
123
+ )
124
+
125
+ def __str__(self) -> str:
126
+ return f'<Geoseeq DashboardTile: {self.dashboard.grn} "{self.title}" />'
127
+
128
+ def __repr__(self) -> str:
129
+ return str(self)
130
+
131
+
132
+ class SampleDashboard(RemoteObject):
133
+ """Dashboard client for a single sample."""
134
+
135
+ parent_field = "sample"
136
+ remote_fields = ["uuid", "title", "default", "created_at", "updated_at"]
137
+
138
+ def __init__(self, knex, sample, title="Default dashboard", default=False):
139
+ super().__init__(self)
140
+ self.knex = knex
141
+ self.sample = sample
142
+ self.title = title
143
+ self.tiles = []
144
+ self.default = default
145
+
146
+ def _get(self, allow_overwrite=False):
147
+ blob = self.knex.get(f"samples/{self.sample.uuid}/dashboards")
148
+ try:
149
+ blob = [
150
+ dashboard_blob
151
+ for dashboard_blob in blob["results"]
152
+ if dashboard_blob["title"] == self.title
153
+ ][0]
154
+ except IndexError:
155
+ raise ValueError(f"There is no existing dashboard with title {self.title}")
156
+
157
+ self.load_blob(blob, allow_overwrite=allow_overwrite)
158
+
159
+ # Load tiles
160
+ tiles_res = self.knex.get(f"samples/dashboards/{self.uuid}/tiles")
161
+ for tile_blob in tiles_res["results"]:
162
+ tile = SampleDashboardTile.from_blob(self, tile_blob)
163
+ self.tiles.append(tile)
164
+
165
+ def save(self):
166
+ data = self._get_post_data()
167
+ url = f"samples/{self.sample.uuid}/dashboards/{self.uuid}"
168
+ self.knex.put(url, json=data)
169
+ self.save_tiles()
170
+
171
+ def save_tiles(self):
172
+ post_data = {"tiles": [tile._get_post_data() for tile in self.tiles]}
173
+ self.knex.put(
174
+ f"samples/dashboards/{self.uuid}/tiles",
175
+ json=post_data,
176
+ json_response=False,
177
+ )
178
+
179
+ def delete(self):
180
+ self.knex.delete(f"samples/{self.sample.uuid}/dashboards/{self.uuid}")
181
+ self._already_fetched = False
182
+ self._deleted = True
183
+
184
+ def _create(self):
185
+ post_data = {
186
+ "title": self.title,
187
+ "sample": self.sample.uuid,
188
+ "default": self.default,
189
+ }
190
+ blob = self.knex.post(f"samples/{self.sample.uuid}/dashboards", json=post_data)
191
+ self.load_blob(blob)
192
+
193
+ def _get_post_data(self):
194
+ out = {
195
+ "sample": self.sample.uuid,
196
+ "title": self.title,
197
+ "default": self.default,
198
+ }
199
+ return out
200
+
201
+ def add_tile(self, result_file, title, width="half", order=None):
202
+ result_file.get()
203
+ tile = SampleDashboardTile(
204
+ self.knex, self, title, result_file, width=width, order=order
205
+ )
206
+ self.tiles.append(tile)
207
+ self._modified = True
208
+
209
+ @classmethod
210
+ def from_blob(cls, sample, blob):
211
+ instance = cls(
212
+ sample.knex,
213
+ sample,
214
+ blob["title"],
215
+ blob["default"],
216
+ )
217
+ instance.uuid = blob["uuid"]
218
+ return instance
219
+
220
+ @property
221
+ def name(self):
222
+ return self.title
223
+
224
+ def __str__(self):
225
+ return f'<Geoseeq SampleDashboard: {self.sample.brn} "{self.name}"/>'
226
+
227
+ def __repr__(self):
228
+ return str(self)
229
+
230
+ @property
231
+ def grn(self):
232
+ return f'grn:dashboard:{self.sample.uuid}:"{self.name}"'
233
+
234
+ def pre_hash(self):
235
+ return "DASH" + self.sample.uuid + self.name
236
+
237
+
238
+ class SampleDashboardTile:
239
+ def __init__(self, knex, dashboard, title, result_file, width="half", order=None):
240
+ self.knex = knex
241
+ self.dashboard = dashboard
242
+ self.title = title
243
+ self.width = width
244
+ self.result_file = result_file
245
+ self.order = order
246
+
247
+ def _get_post_data(self):
248
+ out = {
249
+ "field": self.result_file.uuid,
250
+ "dashboard": self.dashboard.uuid,
251
+ "width": self.width,
252
+ "title": self.title,
253
+ "order": self.order,
254
+ }
255
+ return out
256
+
257
+ @classmethod
258
+ def from_blob(cls, dashboard, blob):
259
+ result_file = result_file_from_id(dashboard.knex, blob["field_obj"]["uuid"])
260
+ return cls(
261
+ dashboard.knex,
262
+ dashboard,
263
+ blob["title"],
264
+ result_file,
265
+ width=blob["width"],
266
+ order=blob["order"],
267
+ )
268
+
269
+ def __str__(self) -> str:
270
+ return f'<Geoseeq DashboardTile: {self.dashboard.grn} "{self.title}" />'
271
+
272
+ def __repr__(self) -> str:
273
+ return str(self)