edsl 0.1.50__py3-none-any.whl → 0.1.52__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.
Files changed (119) hide show
  1. edsl/__init__.py +45 -34
  2. edsl/__version__.py +1 -1
  3. edsl/base/base_exception.py +2 -2
  4. edsl/buckets/bucket_collection.py +1 -1
  5. edsl/buckets/exceptions.py +32 -0
  6. edsl/buckets/token_bucket_api.py +26 -10
  7. edsl/caching/cache.py +5 -2
  8. edsl/caching/remote_cache_sync.py +5 -5
  9. edsl/caching/sql_dict.py +12 -11
  10. edsl/config/__init__.py +1 -1
  11. edsl/config/config_class.py +4 -2
  12. edsl/conversation/Conversation.py +9 -5
  13. edsl/conversation/car_buying.py +1 -3
  14. edsl/conversation/mug_negotiation.py +2 -6
  15. edsl/coop/__init__.py +11 -8
  16. edsl/coop/coop.py +15 -13
  17. edsl/coop/coop_functions.py +1 -1
  18. edsl/coop/ep_key_handling.py +1 -1
  19. edsl/coop/price_fetcher.py +2 -2
  20. edsl/coop/utils.py +2 -2
  21. edsl/dataset/dataset.py +144 -63
  22. edsl/dataset/dataset_operations_mixin.py +14 -6
  23. edsl/dataset/dataset_tree.py +3 -3
  24. edsl/dataset/display/table_renderers.py +6 -3
  25. edsl/dataset/file_exports.py +4 -4
  26. edsl/dataset/r/ggplot.py +3 -3
  27. edsl/inference_services/available_model_fetcher.py +2 -2
  28. edsl/inference_services/data_structures.py +5 -5
  29. edsl/inference_services/inference_service_abc.py +1 -1
  30. edsl/inference_services/inference_services_collection.py +1 -1
  31. edsl/inference_services/service_availability.py +3 -3
  32. edsl/inference_services/services/azure_ai.py +3 -3
  33. edsl/inference_services/services/google_service.py +1 -1
  34. edsl/inference_services/services/test_service.py +1 -1
  35. edsl/instructions/change_instruction.py +5 -4
  36. edsl/instructions/instruction.py +1 -0
  37. edsl/instructions/instruction_collection.py +5 -4
  38. edsl/instructions/instruction_handler.py +10 -8
  39. edsl/interviews/answering_function.py +20 -21
  40. edsl/interviews/exception_tracking.py +3 -2
  41. edsl/interviews/interview.py +1 -1
  42. edsl/interviews/interview_status_dictionary.py +1 -1
  43. edsl/interviews/interview_task_manager.py +7 -4
  44. edsl/interviews/request_token_estimator.py +3 -2
  45. edsl/interviews/statistics.py +2 -2
  46. edsl/invigilators/invigilators.py +34 -6
  47. edsl/jobs/__init__.py +39 -2
  48. edsl/jobs/async_interview_runner.py +1 -1
  49. edsl/jobs/check_survey_scenario_compatibility.py +5 -5
  50. edsl/jobs/data_structures.py +2 -2
  51. edsl/jobs/html_table_job_logger.py +494 -257
  52. edsl/jobs/jobs.py +2 -2
  53. edsl/jobs/jobs_checks.py +5 -5
  54. edsl/jobs/jobs_component_constructor.py +2 -2
  55. edsl/jobs/jobs_pricing_estimation.py +1 -1
  56. edsl/jobs/jobs_runner_asyncio.py +2 -2
  57. edsl/jobs/jobs_status_enums.py +1 -0
  58. edsl/jobs/remote_inference.py +47 -13
  59. edsl/jobs/results_exceptions_handler.py +2 -2
  60. edsl/language_models/language_model.py +151 -145
  61. edsl/notebooks/__init__.py +24 -1
  62. edsl/notebooks/exceptions.py +82 -0
  63. edsl/notebooks/notebook.py +7 -3
  64. edsl/notebooks/notebook_to_latex.py +1 -1
  65. edsl/prompts/__init__.py +23 -2
  66. edsl/prompts/prompt.py +1 -1
  67. edsl/questions/__init__.py +4 -4
  68. edsl/questions/answer_validator_mixin.py +0 -5
  69. edsl/questions/compose_questions.py +2 -2
  70. edsl/questions/descriptors.py +1 -1
  71. edsl/questions/question_base.py +32 -3
  72. edsl/questions/question_base_prompts_mixin.py +4 -4
  73. edsl/questions/question_budget.py +503 -102
  74. edsl/questions/question_check_box.py +658 -156
  75. edsl/questions/question_dict.py +176 -2
  76. edsl/questions/question_extract.py +401 -61
  77. edsl/questions/question_free_text.py +77 -9
  78. edsl/questions/question_functional.py +118 -9
  79. edsl/questions/{derived/question_likert_five.py → question_likert_five.py} +2 -2
  80. edsl/questions/{derived/question_linear_scale.py → question_linear_scale.py} +3 -4
  81. edsl/questions/question_list.py +246 -26
  82. edsl/questions/question_matrix.py +586 -73
  83. edsl/questions/question_multiple_choice.py +213 -47
  84. edsl/questions/question_numerical.py +360 -29
  85. edsl/questions/question_rank.py +401 -124
  86. edsl/questions/question_registry.py +3 -3
  87. edsl/questions/{derived/question_top_k.py → question_top_k.py} +3 -3
  88. edsl/questions/{derived/question_yes_no.py → question_yes_no.py} +3 -4
  89. edsl/questions/register_questions_meta.py +2 -1
  90. edsl/questions/response_validator_abc.py +6 -2
  91. edsl/questions/response_validator_factory.py +10 -12
  92. edsl/results/report.py +1 -1
  93. edsl/results/result.py +7 -4
  94. edsl/results/results.py +500 -271
  95. edsl/results/results_selector.py +2 -2
  96. edsl/scenarios/construct_download_link.py +3 -3
  97. edsl/scenarios/scenario.py +1 -2
  98. edsl/scenarios/scenario_list.py +41 -23
  99. edsl/surveys/survey_css.py +3 -3
  100. edsl/surveys/survey_simulator.py +2 -1
  101. edsl/tasks/__init__.py +22 -2
  102. edsl/tasks/exceptions.py +72 -0
  103. edsl/tasks/task_history.py +48 -11
  104. edsl/templates/error_reporting/base.html +37 -4
  105. edsl/templates/error_reporting/exceptions_table.html +105 -33
  106. edsl/templates/error_reporting/interview_details.html +130 -126
  107. edsl/templates/error_reporting/overview.html +21 -25
  108. edsl/templates/error_reporting/report.css +215 -46
  109. edsl/templates/error_reporting/report.js +122 -20
  110. edsl/tokens/__init__.py +27 -1
  111. edsl/tokens/exceptions.py +37 -0
  112. edsl/tokens/interview_token_usage.py +3 -2
  113. edsl/tokens/token_usage.py +4 -3
  114. {edsl-0.1.50.dist-info → edsl-0.1.52.dist-info}/METADATA +1 -1
  115. {edsl-0.1.50.dist-info → edsl-0.1.52.dist-info}/RECORD +118 -116
  116. edsl/questions/derived/__init__.py +0 -0
  117. {edsl-0.1.50.dist-info → edsl-0.1.52.dist-info}/LICENSE +0 -0
  118. {edsl-0.1.50.dist-info → edsl-0.1.52.dist-info}/WHEEL +0 -0
  119. {edsl-0.1.50.dist-info → edsl-0.1.52.dist-info}/entry_points.txt +0 -0
@@ -62,7 +62,8 @@ class RegisterQuestionsMeta(ABCMeta):
62
62
  if hasattr(cls, "question_type"):
63
63
  d[cls.question_type] = cls
64
64
  else:
65
- raise Exception(
65
+ from .exceptions import QuestionMissingTypeError
66
+ raise QuestionMissingTypeError(
66
67
  f"Class {classname} does not have a question_type class attribute"
67
68
  )
68
69
  return d
@@ -77,8 +77,12 @@ class ResponseValidatorABC(ABC):
77
77
  ConstrainedNumericResponse(answer=42, comment=None, generated_tokens=None)
78
78
  """
79
79
  try:
80
- return self.response_model(**data)
81
- except ValidationError as e:
80
+ # Use model_validate instead of direct instantiation
81
+ return self.response_model.model_validate(data)
82
+ except (ValidationError, QuestionAnswerValidationError) as e:
83
+ # Pass through QuestionAnswerValidationError or convert ValidationError
84
+ if isinstance(e, QuestionAnswerValidationError):
85
+ raise
82
86
  raise QuestionAnswerValidationError(
83
87
  message=str(e), pydantic_error=e, data=data, model=self.response_model
84
88
  )
@@ -1,5 +1,6 @@
1
- from edsl.questions.data_structures import BaseModel
2
- from edsl.questions.response_validator_abc import ResponseValidatorABC
1
+ from typing import Type, List
2
+ from .data_structures import BaseModel
3
+ from .response_validator_abc import ResponseValidatorABC
3
4
 
4
5
 
5
6
  class ResponseValidatorFactory:
@@ -9,7 +10,7 @@ class ResponseValidatorFactory:
9
10
  self.question = question
10
11
 
11
12
  @property
12
- def response_model(self) -> type["BaseModel"]:
13
+ def response_model(self) -> Type["BaseModel"]:
13
14
  if self.question._response_model is not None:
14
15
  return self.question._response_model
15
16
  else:
@@ -18,17 +19,14 @@ class ResponseValidatorFactory:
18
19
  @property
19
20
  def response_validator(self) -> "ResponseValidatorABC":
20
21
  """Return the response validator."""
21
- params = (
22
- {
23
- "response_model": self.question.response_model,
24
- }
25
- | {k: getattr(self.question, k) for k in self.validator_parameters}
26
- | {"exception_to_throw": getattr(self.question, "exception_to_throw", None)}
27
- | {"override_answer": getattr(self.question, "override_answer", None)}
28
- )
22
+ params = {}
23
+ params.update({"response_model": self.question.response_model})
24
+ params.update({k: getattr(self.question, k) for k in self.validator_parameters})
25
+ params.update({"exception_to_throw": getattr(self.question, "exception_to_throw", None)})
26
+ params.update({"override_answer": getattr(self.question, "override_answer", None)})
29
27
  return self.question.response_validator_class(**params)
30
28
 
31
29
  @property
32
- def validator_parameters(self) -> list[str]:
30
+ def validator_parameters(self) -> List[str]:
33
31
  """Return the parameters required for the response validator."""
34
32
  return self.question.response_validator_class.required_params
edsl/results/report.py CHANGED
@@ -173,7 +173,7 @@ class Report:
173
173
 
174
174
  if __name__ == "__main__":
175
175
  # Suppose you have an existing Dataset
176
- from edsl import Results
176
+ from .. import Results
177
177
  ds = Results.example().select("how_feeling", "how_feeling_yesterday")
178
178
 
179
179
  # Provide a custom template string
edsl/results/result.py CHANGED
@@ -259,14 +259,16 @@ class Result(Base, UserDict):
259
259
  def check_expression(self, expression: str) -> None:
260
260
  for key in self.problem_keys:
261
261
  if key in expression and key + "." not in expression:
262
- raise ValueError(
263
- f"Key by iself {key} is problematic. Use the full key {key + '.' + key} name instead."
262
+ from .exceptions import ResultsColumnNotFoundError
263
+ raise ResultsColumnNotFoundError(
264
+ f"Key by itself {key} is problematic. Use the full key {key + '.' + key} name instead."
264
265
  )
265
266
  return None
266
267
 
267
268
  def code(self):
268
269
  """Return a string of code that can be used to recreate the Result object."""
269
- raise NotImplementedError
270
+ from .exceptions import ResultsError
271
+ raise ResultsError("The code() method is not implemented for Result objects")
270
272
 
271
273
  @property
272
274
  def problem_keys(self) -> list[str]:
@@ -567,7 +569,8 @@ class Result(Base, UserDict):
567
569
  elif v.default is not v.empty:
568
570
  params[k] = v.default
569
571
  else:
570
- raise ValueError(f"Parameter {k} not found in Result object")
572
+ from .exceptions import ResultsError
573
+ raise ResultsError(f"Parameter {k} not found in Result object")
571
574
  return scoring_function(**params)
572
575
 
573
576
  @classmethod