comparison_outcome.py 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107
  1. # Copyright Materialize, Inc. and contributors. All rights reserved.
  2. #
  3. # Use of this software is governed by the Business Source License
  4. # included in the LICENSE file at the root of this repository.
  5. #
  6. # As of the Change Date specified in that file, in accordance with
  7. # the Business Source License, use of this software will be governed
  8. # by the Apache License, Version 2.0.
  9. from __future__ import annotations
  10. from collections.abc import Sequence
  11. from materialize.scalability.df.df_totals import (
  12. DfTotalsExtended,
  13. concat_df_totals_extended,
  14. )
  15. from materialize.scalability.endpoint.endpoint import Endpoint
  16. from materialize.scalability.result.scalability_change import (
  17. Regression,
  18. ScalabilityChange,
  19. ScalabilityImprovement,
  20. )
  21. class ComparisonOutcome:
  22. def __init__(
  23. self,
  24. ):
  25. self.regressions: list[Regression] = []
  26. self.significant_improvements: list[ScalabilityImprovement] = []
  27. self.regression_df = DfTotalsExtended()
  28. self.significant_improvement_df = DfTotalsExtended()
  29. self.endpoints_with_regressions: set[Endpoint] = set()
  30. def has_regressions(self) -> bool:
  31. assert len(self.regressions) == self.regression_df.length()
  32. return len(self.regressions) > 0
  33. def has_significant_improvements(self) -> bool:
  34. assert (
  35. len(self.significant_improvements)
  36. == self.significant_improvement_df.length()
  37. )
  38. return len(self.significant_improvements) > 0
  39. def has_scalability_changes(self) -> bool:
  40. return self.has_regressions() or self.has_significant_improvements()
  41. def __str__(self) -> str:
  42. return f"{len(self.regressions)} regressions, {len(self.significant_improvements)} significant improvements"
  43. def to_description(self) -> str:
  44. regressions_description = (
  45. f"Regressions:\n{self._to_description(self.regressions)}"
  46. )
  47. improvements_description = (
  48. f"Improvements:\n{self._to_description(self.significant_improvements)}"
  49. )
  50. return "\n".join([regressions_description, improvements_description])
  51. def _to_description(self, entries: Sequence[ScalabilityChange]) -> str:
  52. if len(entries) == 0:
  53. return "* None"
  54. return "\n".join(f"* {x}" for x in entries)
  55. def merge(self, other: ComparisonOutcome) -> None:
  56. self.append_regressions(
  57. other.regressions,
  58. other.significant_improvements,
  59. other.regression_df,
  60. other.significant_improvement_df,
  61. )
  62. def append_regressions(
  63. self,
  64. regressions: list[Regression],
  65. significant_improvements: list[ScalabilityImprovement],
  66. regression_df: DfTotalsExtended,
  67. significant_improvement_df: DfTotalsExtended,
  68. ) -> None:
  69. self.regressions.extend(regressions)
  70. self.significant_improvements.extend(significant_improvements)
  71. self._append_regression_df(regression_df)
  72. self._append_significant_improvement_df(significant_improvement_df)
  73. for regression in regressions:
  74. self.endpoints_with_regressions.add(regression.endpoint)
  75. def _append_regression_df(self, regressions_data: DfTotalsExtended) -> None:
  76. self.regression_df = concat_df_totals_extended(
  77. [self.regression_df, regressions_data]
  78. )
  79. def _append_significant_improvement_df(
  80. self, significant_improvements_data: DfTotalsExtended
  81. ) -> None:
  82. self.significant_improvement_df = concat_df_totals_extended(
  83. [self.significant_improvement_df, significant_improvements_data]
  84. )
  85. def get_regressions_by_endpoint(self, endpoint: Endpoint) -> list[Regression]:
  86. return [
  87. regression
  88. for regression in self.regressions
  89. if regression.endpoint == endpoint
  90. ]