flwr-nightly 1.22.0.dev20250920__tar.gz → 1.23.0.dev20250922__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 (427) hide show
  1. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/PKG-INFO +1 -1
  2. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.baseline.toml.tpl +1 -1
  3. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.flowertune.toml.tpl +1 -1
  4. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.huggingface.toml.tpl +1 -1
  5. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.jax.toml.tpl +1 -1
  6. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.mlx.toml.tpl +1 -1
  7. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.numpy.toml.tpl +1 -1
  8. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.pytorch.toml.tpl +1 -1
  9. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.pytorch_legacy_api.toml.tpl +1 -1
  10. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.sklearn.toml.tpl +1 -1
  11. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.tensorflow.toml.tpl +1 -1
  12. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/pyproject.xgboost.toml.tpl +1 -1
  13. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/clientapp/mod/__init__.py +2 -0
  14. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/clientapp/mod/centraldp_mods.py +6 -6
  15. flwr_nightly-1.23.0.dev20250922/py/flwr/clientapp/mod/localdp_mod.py +169 -0
  16. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/__init__.py +4 -0
  17. flwr_nightly-1.23.0.dev20250922/py/flwr/serverapp/strategy/bulyan.py +238 -0
  18. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedmedian.py +34 -0
  19. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedxgb_bagging.py +36 -1
  20. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedxgb_cyclic.py +1 -1
  21. flwr_nightly-1.23.0.dev20250922/py/flwr/serverapp/strategy/krum.py +112 -0
  22. flwr_nightly-1.22.0.dev20250920/py/flwr/serverapp/strategy/krum.py → flwr_nightly-1.23.0.dev20250922/py/flwr/serverapp/strategy/multikrum.py +110 -93
  23. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/pyproject.toml +1 -1
  24. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/README.md +0 -0
  25. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/__init__.py +0 -0
  26. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/app/__init__.py +0 -0
  27. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/app/error.py +0 -0
  28. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/app/exception.py +0 -0
  29. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/app/metadata.py +0 -0
  30. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/__init__.py +0 -0
  31. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/app.py +0 -0
  32. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/auth_plugin/__init__.py +0 -0
  33. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/auth_plugin/oidc_cli_plugin.py +0 -0
  34. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/build.py +0 -0
  35. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/cli_user_auth_interceptor.py +0 -0
  36. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/config_utils.py +0 -0
  37. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/constant.py +0 -0
  38. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/example.py +0 -0
  39. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/install.py +0 -0
  40. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/log.py +0 -0
  41. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/login/__init__.py +0 -0
  42. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/login/login.py +0 -0
  43. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/ls.py +0 -0
  44. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/__init__.py +0 -0
  45. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/new.py +0 -0
  46. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/__init__.py +0 -0
  47. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/.gitignore.tpl +0 -0
  48. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/LICENSE.tpl +0 -0
  49. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/README.baseline.md.tpl +0 -0
  50. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/README.flowertune.md.tpl +0 -0
  51. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/README.md.tpl +0 -0
  52. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/__init__.py +0 -0
  53. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/__init__.baseline.py.tpl +0 -0
  54. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/__init__.py +0 -0
  55. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/__init__.py.tpl +0 -0
  56. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/__init__.pytorch_legacy_api.py.tpl +0 -0
  57. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.baseline.py.tpl +0 -0
  58. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.huggingface.py.tpl +0 -0
  59. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.jax.py.tpl +0 -0
  60. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.mlx.py.tpl +0 -0
  61. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.numpy.py.tpl +0 -0
  62. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.pytorch.py.tpl +0 -0
  63. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.pytorch_legacy_api.py.tpl +0 -0
  64. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.sklearn.py.tpl +0 -0
  65. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.tensorflow.py.tpl +0 -0
  66. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/client.xgboost.py.tpl +0 -0
  67. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/dataset.baseline.py.tpl +0 -0
  68. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/flwr_tune/__init__.py +0 -0
  69. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/flwr_tune/client_app.py.tpl +0 -0
  70. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/flwr_tune/dataset.py.tpl +0 -0
  71. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/flwr_tune/models.py.tpl +0 -0
  72. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/flwr_tune/server_app.py.tpl +0 -0
  73. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/flwr_tune/strategy.py.tpl +0 -0
  74. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/model.baseline.py.tpl +0 -0
  75. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.baseline.py.tpl +0 -0
  76. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.huggingface.py.tpl +0 -0
  77. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.jax.py.tpl +0 -0
  78. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.mlx.py.tpl +0 -0
  79. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.numpy.py.tpl +0 -0
  80. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.pytorch.py.tpl +0 -0
  81. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.pytorch_legacy_api.py.tpl +0 -0
  82. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.sklearn.py.tpl +0 -0
  83. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.tensorflow.py.tpl +0 -0
  84. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/server.xgboost.py.tpl +0 -0
  85. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/strategy.baseline.py.tpl +0 -0
  86. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.huggingface.py.tpl +0 -0
  87. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.jax.py.tpl +0 -0
  88. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.mlx.py.tpl +0 -0
  89. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.numpy.py.tpl +0 -0
  90. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.pytorch.py.tpl +0 -0
  91. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.pytorch_legacy_api.py.tpl +0 -0
  92. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.sklearn.py.tpl +0 -0
  93. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.tensorflow.py.tpl +0 -0
  94. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/task.xgboost.py.tpl +0 -0
  95. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/new/templates/app/code/utils.baseline.py.tpl +0 -0
  96. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/pull.py +0 -0
  97. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/run/__init__.py +0 -0
  98. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/run/run.py +0 -0
  99. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/stop.py +0 -0
  100. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/cli/utils.py +0 -0
  101. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/__init__.py +0 -0
  102. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/client.py +0 -0
  103. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/client_app.py +0 -0
  104. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/clientapp/__init__.py +0 -0
  105. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/clientapp/utils.py +0 -0
  106. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/dpfedavg_numpy_client.py +0 -0
  107. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/grpc_adapter_client/__init__.py +0 -0
  108. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/grpc_adapter_client/connection.py +0 -0
  109. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/grpc_rere_client/__init__.py +0 -0
  110. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/grpc_rere_client/client_interceptor.py +0 -0
  111. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/grpc_rere_client/connection.py +0 -0
  112. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/grpc_rere_client/grpc_adapter.py +0 -0
  113. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/message_handler/__init__.py +0 -0
  114. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/message_handler/message_handler.py +0 -0
  115. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/mod/__init__.py +0 -0
  116. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/mod/centraldp_mods.py +0 -0
  117. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/mod/comms_mods.py +0 -0
  118. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/mod/localdp_mod.py +0 -0
  119. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/mod/secure_aggregation/__init__.py +0 -0
  120. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/mod/secure_aggregation/secagg_mod.py +0 -0
  121. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/mod/secure_aggregation/secaggplus_mod.py +0 -0
  122. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/mod/utils.py +0 -0
  123. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/numpy_client.py +0 -0
  124. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/rest_client/__init__.py +0 -0
  125. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/rest_client/connection.py +0 -0
  126. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/run_info_store.py +0 -0
  127. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/client/typing.py +0 -0
  128. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/clientapp/__init__.py +0 -0
  129. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/clientapp/typing.py +0 -0
  130. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/__init__.py +0 -0
  131. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/address.py +0 -0
  132. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/args.py +0 -0
  133. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/auth_plugin/__init__.py +0 -0
  134. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/auth_plugin/auth_plugin.py +0 -0
  135. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/config.py +0 -0
  136. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/constant.py +0 -0
  137. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/context.py +0 -0
  138. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/date.py +0 -0
  139. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/differential_privacy.py +0 -0
  140. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/differential_privacy_constants.py +0 -0
  141. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/dp.py +0 -0
  142. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/event_log_plugin/__init__.py +0 -0
  143. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/event_log_plugin/event_log_plugin.py +0 -0
  144. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/exit/__init__.py +0 -0
  145. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/exit/exit.py +0 -0
  146. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/exit/exit_code.py +0 -0
  147. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/exit/exit_handler.py +0 -0
  148. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/exit/signal_handler.py +0 -0
  149. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/grpc.py +0 -0
  150. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/heartbeat.py +0 -0
  151. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/inflatable.py +0 -0
  152. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/inflatable_protobuf_utils.py +0 -0
  153. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/inflatable_utils.py +0 -0
  154. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/logger.py +0 -0
  155. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/message.py +0 -0
  156. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/object_ref.py +0 -0
  157. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/parameter.py +0 -0
  158. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/pyproject.py +0 -0
  159. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/__init__.py +0 -0
  160. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/array.py +0 -0
  161. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/arraychunk.py +0 -0
  162. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/arrayrecord.py +0 -0
  163. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/configrecord.py +0 -0
  164. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/conversion_utils.py +0 -0
  165. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/metricrecord.py +0 -0
  166. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/recorddict.py +0 -0
  167. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/record/typeddict.py +0 -0
  168. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/recorddict_compat.py +0 -0
  169. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/retry_invoker.py +0 -0
  170. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/secure_aggregation/__init__.py +0 -0
  171. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/secure_aggregation/crypto/__init__.py +0 -0
  172. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/secure_aggregation/crypto/shamir.py +0 -0
  173. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/secure_aggregation/crypto/symmetric_encryption.py +0 -0
  174. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/secure_aggregation/ndarrays_arithmetic.py +0 -0
  175. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/secure_aggregation/quantization.py +0 -0
  176. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/secure_aggregation/secaggplus_constants.py +0 -0
  177. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/secure_aggregation/secaggplus_utils.py +0 -0
  178. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/serde.py +0 -0
  179. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/serde_utils.py +0 -0
  180. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/telemetry.py +0 -0
  181. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/typing.py +0 -0
  182. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/common/version.py +0 -0
  183. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/__init__.py +0 -0
  184. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/client/__init__.py +0 -0
  185. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/client/app.py +0 -0
  186. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/client/grpc_client/__init__.py +0 -0
  187. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/client/grpc_client/connection.py +0 -0
  188. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/common/__init__.py +0 -0
  189. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/server/__init__.py +0 -0
  190. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/server/app.py +0 -0
  191. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/compat/simulation/__init__.py +0 -0
  192. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/__init__.py +0 -0
  193. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/appio_pb2.py +0 -0
  194. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/appio_pb2.pyi +0 -0
  195. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/appio_pb2_grpc.py +0 -0
  196. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/appio_pb2_grpc.pyi +0 -0
  197. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/clientappio_pb2.py +0 -0
  198. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/clientappio_pb2.pyi +0 -0
  199. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/clientappio_pb2_grpc.py +0 -0
  200. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/clientappio_pb2_grpc.pyi +0 -0
  201. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/control_pb2.py +0 -0
  202. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/control_pb2.pyi +0 -0
  203. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/control_pb2_grpc.py +0 -0
  204. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/control_pb2_grpc.pyi +0 -0
  205. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/error_pb2.py +0 -0
  206. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/error_pb2.pyi +0 -0
  207. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/error_pb2_grpc.py +0 -0
  208. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/error_pb2_grpc.pyi +0 -0
  209. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/fab_pb2.py +0 -0
  210. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/fab_pb2.pyi +0 -0
  211. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/fab_pb2_grpc.py +0 -0
  212. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/fab_pb2_grpc.pyi +0 -0
  213. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/fleet_pb2.py +0 -0
  214. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/fleet_pb2.pyi +0 -0
  215. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/fleet_pb2_grpc.py +0 -0
  216. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/fleet_pb2_grpc.pyi +0 -0
  217. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/grpcadapter_pb2.py +0 -0
  218. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/grpcadapter_pb2.pyi +0 -0
  219. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/grpcadapter_pb2_grpc.py +0 -0
  220. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/grpcadapter_pb2_grpc.pyi +0 -0
  221. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/heartbeat_pb2.py +0 -0
  222. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/heartbeat_pb2.pyi +0 -0
  223. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/heartbeat_pb2_grpc.py +0 -0
  224. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/heartbeat_pb2_grpc.pyi +0 -0
  225. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/log_pb2.py +0 -0
  226. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/log_pb2.pyi +0 -0
  227. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/log_pb2_grpc.py +0 -0
  228. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/log_pb2_grpc.pyi +0 -0
  229. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/message_pb2.py +0 -0
  230. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/message_pb2.pyi +0 -0
  231. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/message_pb2_grpc.py +0 -0
  232. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/message_pb2_grpc.pyi +0 -0
  233. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/node_pb2.py +0 -0
  234. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/node_pb2.pyi +0 -0
  235. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/node_pb2_grpc.py +0 -0
  236. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/node_pb2_grpc.pyi +0 -0
  237. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/recorddict_pb2.py +0 -0
  238. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/recorddict_pb2.pyi +0 -0
  239. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/recorddict_pb2_grpc.py +0 -0
  240. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/recorddict_pb2_grpc.pyi +0 -0
  241. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/run_pb2.py +0 -0
  242. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/run_pb2.pyi +0 -0
  243. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/run_pb2_grpc.py +0 -0
  244. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/run_pb2_grpc.pyi +0 -0
  245. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/serverappio_pb2.py +0 -0
  246. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/serverappio_pb2.pyi +0 -0
  247. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/serverappio_pb2_grpc.py +0 -0
  248. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/serverappio_pb2_grpc.pyi +0 -0
  249. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/simulationio_pb2.py +0 -0
  250. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/simulationio_pb2.pyi +0 -0
  251. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/simulationio_pb2_grpc.py +0 -0
  252. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/simulationio_pb2_grpc.pyi +0 -0
  253. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/transport_pb2.py +0 -0
  254. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/transport_pb2.pyi +0 -0
  255. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/transport_pb2_grpc.py +0 -0
  256. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/proto/transport_pb2_grpc.pyi +0 -0
  257. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/py.typed +0 -0
  258. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/__init__.py +0 -0
  259. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/app.py +0 -0
  260. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/client_manager.py +0 -0
  261. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/client_proxy.py +0 -0
  262. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/compat/__init__.py +0 -0
  263. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/compat/app.py +0 -0
  264. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/compat/app_utils.py +0 -0
  265. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/compat/grid_client_proxy.py +0 -0
  266. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/compat/legacy_context.py +0 -0
  267. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/criterion.py +0 -0
  268. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/fleet_event_log_interceptor.py +0 -0
  269. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/grid/__init__.py +0 -0
  270. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/grid/grid.py +0 -0
  271. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/grid/grpc_grid.py +0 -0
  272. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/grid/inmemory_grid.py +0 -0
  273. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/history.py +0 -0
  274. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/run_serverapp.py +0 -0
  275. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/server.py +0 -0
  276. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/server_app.py +0 -0
  277. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/server_config.py +0 -0
  278. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/serverapp/__init__.py +0 -0
  279. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/serverapp/app.py +0 -0
  280. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/serverapp_components.py +0 -0
  281. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/__init__.py +0 -0
  282. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/aggregate.py +0 -0
  283. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/bulyan.py +0 -0
  284. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/dp_adaptive_clipping.py +0 -0
  285. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/dp_fixed_clipping.py +0 -0
  286. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/dpfedavg_adaptive.py +0 -0
  287. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/dpfedavg_fixed.py +0 -0
  288. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fault_tolerant_fedavg.py +0 -0
  289. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedadagrad.py +0 -0
  290. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedadam.py +0 -0
  291. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedavg.py +0 -0
  292. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedavg_android.py +0 -0
  293. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedavgm.py +0 -0
  294. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedmedian.py +0 -0
  295. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedopt.py +0 -0
  296. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedprox.py +0 -0
  297. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedtrimmedavg.py +0 -0
  298. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedxgb_bagging.py +0 -0
  299. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedxgb_cyclic.py +0 -0
  300. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedxgb_nn_avg.py +0 -0
  301. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/fedyogi.py +0 -0
  302. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/krum.py +0 -0
  303. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/qfedavg.py +0 -0
  304. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/strategy/strategy.py +0 -0
  305. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/__init__.py +0 -0
  306. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/__init__.py +0 -0
  307. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_adapter/__init__.py +0 -0
  308. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_adapter/grpc_adapter_servicer.py +0 -0
  309. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_bidi/__init__.py +0 -0
  310. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_bidi/flower_service_servicer.py +0 -0
  311. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_bidi/grpc_bridge.py +0 -0
  312. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_bidi/grpc_client_proxy.py +0 -0
  313. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_bidi/grpc_server.py +0 -0
  314. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_rere/__init__.py +0 -0
  315. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_rere/fleet_servicer.py +0 -0
  316. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/grpc_rere/server_interceptor.py +0 -0
  317. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/message_handler/__init__.py +0 -0
  318. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/message_handler/message_handler.py +0 -0
  319. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/rest_rere/__init__.py +0 -0
  320. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/rest_rere/rest_api.py +0 -0
  321. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/vce/__init__.py +0 -0
  322. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/vce/backend/__init__.py +0 -0
  323. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/vce/backend/backend.py +0 -0
  324. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/vce/backend/raybackend.py +0 -0
  325. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/fleet/vce/vce_api.py +0 -0
  326. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/linkstate/__init__.py +0 -0
  327. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/linkstate/in_memory_linkstate.py +0 -0
  328. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/linkstate/linkstate.py +0 -0
  329. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/linkstate/linkstate_factory.py +0 -0
  330. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/linkstate/sqlite_linkstate.py +0 -0
  331. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/linkstate/utils.py +0 -0
  332. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/serverappio/__init__.py +0 -0
  333. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/serverappio/serverappio_grpc.py +0 -0
  334. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/serverappio/serverappio_servicer.py +0 -0
  335. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/simulation/__init__.py +0 -0
  336. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/simulation/simulationio_grpc.py +0 -0
  337. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/simulation/simulationio_servicer.py +0 -0
  338. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/superlink/utils.py +0 -0
  339. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/typing.py +0 -0
  340. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/utils/__init__.py +0 -0
  341. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/utils/tensorboard.py +0 -0
  342. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/utils/validator.py +0 -0
  343. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/workflow/__init__.py +0 -0
  344. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/workflow/constant.py +0 -0
  345. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/workflow/default_workflows.py +0 -0
  346. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/workflow/secure_aggregation/__init__.py +0 -0
  347. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/workflow/secure_aggregation/secagg_workflow.py +0 -0
  348. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/server/workflow/secure_aggregation/secaggplus_workflow.py +0 -0
  349. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/__init__.py +0 -0
  350. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/exception.py +0 -0
  351. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/dp_adaptive_clipping.py +0 -0
  352. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/dp_fixed_clipping.py +0 -0
  353. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedadagrad.py +0 -0
  354. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedadam.py +0 -0
  355. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedavg.py +0 -0
  356. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedavgm.py +0 -0
  357. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedopt.py +0 -0
  358. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedprox.py +0 -0
  359. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedtrimmedavg.py +0 -0
  360. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/fedyogi.py +0 -0
  361. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/qfedavg.py +0 -0
  362. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/result.py +0 -0
  363. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/strategy.py +0 -0
  364. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/serverapp/strategy/strategy_utils.py +0 -0
  365. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/__init__.py +0 -0
  366. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/app.py +0 -0
  367. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/legacy_app.py +0 -0
  368. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/ray_transport/__init__.py +0 -0
  369. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/ray_transport/ray_actor.py +0 -0
  370. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/ray_transport/ray_client_proxy.py +0 -0
  371. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/ray_transport/utils.py +0 -0
  372. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/run_simulation.py +0 -0
  373. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/simulation/simulationio_connection.py +0 -0
  374. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/__init__.py +0 -0
  375. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/app_utils.py +0 -0
  376. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/cli/__init__.py +0 -0
  377. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/cli/flower_superexec.py +0 -0
  378. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/constant.py +0 -0
  379. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/corestate/__init__.py +0 -0
  380. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/corestate/corestate.py +0 -0
  381. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/ffs/__init__.py +0 -0
  382. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/ffs/disk_ffs.py +0 -0
  383. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/ffs/ffs.py +0 -0
  384. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/ffs/ffs_factory.py +0 -0
  385. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/grpc_health/__init__.py +0 -0
  386. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/grpc_health/health_server.py +0 -0
  387. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/grpc_health/simple_health_servicer.py +0 -0
  388. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/license_plugin/__init__.py +0 -0
  389. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/license_plugin/license_plugin.py +0 -0
  390. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/object_store/__init__.py +0 -0
  391. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/object_store/in_memory_object_store.py +0 -0
  392. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/object_store/object_store.py +0 -0
  393. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/object_store/object_store_factory.py +0 -0
  394. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/object_store/utils.py +0 -0
  395. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/superexec/__init__.py +0 -0
  396. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/superexec/plugin/__init__.py +0 -0
  397. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/superexec/plugin/base_exec_plugin.py +0 -0
  398. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/superexec/plugin/clientapp_exec_plugin.py +0 -0
  399. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/superexec/plugin/exec_plugin.py +0 -0
  400. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/superexec/plugin/serverapp_exec_plugin.py +0 -0
  401. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/superexec/plugin/simulation_exec_plugin.py +0 -0
  402. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/superexec/run_superexec.py +0 -0
  403. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supercore/utils.py +0 -0
  404. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/__init__.py +0 -0
  405. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/artifact_provider/__init__.py +0 -0
  406. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/artifact_provider/artifact_provider.py +0 -0
  407. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/servicer/__init__.py +0 -0
  408. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/servicer/control/__init__.py +0 -0
  409. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/servicer/control/control_event_log_interceptor.py +0 -0
  410. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/servicer/control/control_grpc.py +0 -0
  411. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/servicer/control/control_license_interceptor.py +0 -0
  412. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/servicer/control/control_servicer.py +0 -0
  413. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/superlink/servicer/control/control_user_auth_interceptor.py +0 -0
  414. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/__init__.py +0 -0
  415. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/cli/__init__.py +0 -0
  416. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/cli/flower_supernode.py +0 -0
  417. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/cli/flwr_clientapp.py +0 -0
  418. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/nodestate/__init__.py +0 -0
  419. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/nodestate/in_memory_nodestate.py +0 -0
  420. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/nodestate/nodestate.py +0 -0
  421. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/nodestate/nodestate_factory.py +0 -0
  422. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/runtime/__init__.py +0 -0
  423. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/runtime/run_clientapp.py +0 -0
  424. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/servicer/__init__.py +0 -0
  425. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/servicer/clientappio/__init__.py +0 -0
  426. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/servicer/clientappio/clientappio_servicer.py +0 -0
  427. {flwr_nightly-1.22.0.dev20250920 → flwr_nightly-1.23.0.dev20250922}/py/flwr/supernode/start_client_internal.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.3
2
2
  Name: flwr-nightly
3
- Version: 1.22.0.dev20250920
3
+ Version: 1.23.0.dev20250922
4
4
  Summary: Flower: A Friendly Federated AI Framework
5
5
  License: Apache-2.0
6
6
  Keywords: Artificial Intelligence,Federated AI,Federated Analytics,Federated Evaluation,Federated Learning,Flower,Machine Learning
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets[vision]>=0.5.0",
19
19
  "torch==2.8.0",
20
20
  "torchvision==0.23.0",
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets>=0.5.0",
19
19
  "torch==2.4.0",
20
20
  "trl==0.8.1",
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets>=0.5.0",
19
19
  "torch>=2.7.1",
20
20
  "transformers>=4.30.0,<5.0",
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "jax==0.4.30",
19
19
  "jaxlib==0.4.30",
20
20
  "scikit-learn==1.6.1",
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets[vision]>=0.5.0",
19
19
  "mlx==0.29.0",
20
20
  ]
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "numpy>=2.0.2",
19
19
  ]
20
20
 
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets[vision]>=0.5.0",
19
19
  "torch==2.7.1",
20
20
  "torchvision==0.22.1",
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets[vision]>=0.5.0",
19
19
  "torch==2.7.1",
20
20
  "torchvision==0.22.1",
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets[vision]>=0.5.0",
19
19
  "scikit-learn>=1.6.1",
20
20
  ]
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets[vision]>=0.5.0",
19
19
  "tensorflow>=2.11.1,<2.18.0",
20
20
  ]
@@ -14,7 +14,7 @@ description = ""
14
14
  license = "Apache-2.0"
15
15
  # Dependencies for your Flower App
16
16
  dependencies = [
17
- "flwr[simulation]>=1.22.0",
17
+ "flwr[simulation]>=1.23.0",
18
18
  "flwr-datasets>=0.5.0",
19
19
  "xgboost>=2.0.0",
20
20
  ]
@@ -18,8 +18,10 @@
18
18
  from flwr.client.mod.comms_mods import arrays_size_mod, message_size_mod
19
19
 
20
20
  from .centraldp_mods import adaptiveclipping_mod, fixedclipping_mod
21
+ from .localdp_mod import LocalDpMod
21
22
 
22
23
  __all__ = [
24
+ "LocalDpMod",
23
25
  "adaptiveclipping_mod",
24
26
  "arrays_size_mod",
25
27
  "fixedclipping_mod",
@@ -89,7 +89,7 @@ def fixedclipping_mod(
89
89
  iter(out_msg.content.array_records.items())
90
90
  )
91
91
  # Ensure keys in returned ArrayRecord match those in the one sent from server
92
- if set(original_array_record.keys()) != set(client_to_server_arrecord.keys()):
92
+ if list(original_array_record.keys()) != list(client_to_server_arrecord.keys()):
93
93
  return _handle_array_key_mismatch_err("fixedclipping_mod", out_msg)
94
94
 
95
95
  client_to_server_ndarrays = client_to_server_arrecord.to_numpy_ndarrays()
@@ -158,6 +158,10 @@ def adaptiveclipping_mod(
158
158
  # Call inner app
159
159
  out_msg = call_next(msg, ctxt)
160
160
 
161
+ # Check if the msg has error
162
+ if out_msg.has_error():
163
+ return out_msg
164
+
161
165
  # Ensure reply has a single ArrayRecord
162
166
  if len(out_msg.content.array_records) != 1:
163
167
  return _handle_multi_record_err("adaptiveclipping_mod", out_msg, ArrayRecord)
@@ -166,16 +170,12 @@ def adaptiveclipping_mod(
166
170
  if len(out_msg.content.metric_records) != 1:
167
171
  return _handle_multi_record_err("adaptiveclipping_mod", out_msg, MetricRecord)
168
172
 
169
- # Check if the msg has error
170
- if out_msg.has_error():
171
- return out_msg
172
-
173
173
  new_array_record_key, client_to_server_arrecord = next(
174
174
  iter(out_msg.content.array_records.items())
175
175
  )
176
176
 
177
177
  # Ensure keys in returned ArrayRecord match those in the one sent from server
178
- if set(original_array_record.keys()) != set(client_to_server_arrecord.keys()):
178
+ if list(original_array_record.keys()) != list(client_to_server_arrecord.keys()):
179
179
  return _handle_array_key_mismatch_err("adaptiveclipping_mod", out_msg)
180
180
 
181
181
  client_to_server_ndarrays = client_to_server_arrecord.to_numpy_ndarrays()
@@ -0,0 +1,169 @@
1
+ # Copyright 2025 Flower Labs GmbH. All Rights Reserved.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+ # ==============================================================================
15
+ """Local DP modifier."""
16
+
17
+
18
+ from collections import OrderedDict
19
+ from logging import INFO
20
+
21
+ import numpy as np
22
+
23
+ from flwr.clientapp.typing import ClientAppCallable
24
+ from flwr.common import Array, ArrayRecord
25
+ from flwr.common.context import Context
26
+ from flwr.common.differential_privacy import (
27
+ add_gaussian_noise_inplace,
28
+ compute_clip_model_update,
29
+ )
30
+ from flwr.common.logger import log
31
+ from flwr.common.message import Message
32
+
33
+ from .centraldp_mods import _handle_array_key_mismatch_err, _handle_multi_record_err
34
+
35
+
36
+ class LocalDpMod:
37
+ """Modifier for local differential privacy.
38
+
39
+ This mod clips the client model updates and
40
+ adds noise to the params before sending them to the server.
41
+
42
+ It operates on messages of type `MessageType.TRAIN`.
43
+
44
+ Parameters
45
+ ----------
46
+ clipping_norm : float
47
+ The value of the clipping norm.
48
+ sensitivity : float
49
+ The sensitivity of the client model.
50
+ epsilon : float
51
+ The privacy budget.
52
+ Smaller value of epsilon indicates a higher level of privacy protection.
53
+ delta : float
54
+ The failure probability.
55
+ The probability that the privacy mechanism
56
+ fails to provide the desired level of privacy.
57
+ A smaller value of delta indicates a stricter privacy guarantee.
58
+
59
+ Examples
60
+ --------
61
+ Create an instance of the local DP mod and add it to the client-side mods::
62
+
63
+ local_dp_mod = LocalDpMod( ... )
64
+ app = fl.client.ClientApp(mods=[local_dp_mod])
65
+ """
66
+
67
+ def __init__(
68
+ self, clipping_norm: float, sensitivity: float, epsilon: float, delta: float
69
+ ) -> None:
70
+ if clipping_norm <= 0:
71
+ raise ValueError("The clipping norm should be a positive value.")
72
+
73
+ if sensitivity < 0:
74
+ raise ValueError("The sensitivity should be a non-negative value.")
75
+
76
+ if epsilon < 0:
77
+ raise ValueError("Epsilon should be a non-negative value.")
78
+
79
+ if delta < 0:
80
+ raise ValueError("Delta should be a non-negative value.")
81
+
82
+ self.clipping_norm = clipping_norm
83
+ self.sensitivity = sensitivity
84
+ self.epsilon = epsilon
85
+ self.delta = delta
86
+
87
+ def __call__(
88
+ self, msg: Message, ctxt: Context, call_next: ClientAppCallable
89
+ ) -> Message:
90
+ """Perform local DP on the client model parameters.
91
+
92
+ Parameters
93
+ ----------
94
+ msg : Message
95
+ The message received from the ServerApp.
96
+ ctxt : Context
97
+ The context of the ClientApp.
98
+ call_next : ClientAppCallable
99
+ The callable to call the next mod (or the ClientApp) in the chain.
100
+
101
+ Returns
102
+ -------
103
+ Message
104
+ The modified message to be sent back to the server.
105
+ """
106
+ if len(msg.content.array_records) != 1:
107
+ return _handle_multi_record_err("LocalDpMod", msg, ArrayRecord)
108
+
109
+ # Record array record communicated to client and clipping norm
110
+ original_array_record = next(iter(msg.content.array_records.values()))
111
+
112
+ # Call inner app
113
+ out_msg = call_next(msg, ctxt)
114
+
115
+ # Check if the msg has error
116
+ if out_msg.has_error():
117
+ return out_msg
118
+
119
+ # Ensure reply has a single ArrayRecord
120
+ if len(out_msg.content.array_records) != 1:
121
+ return _handle_multi_record_err("LocalDpMod", out_msg, ArrayRecord)
122
+
123
+ new_array_record_key, client_to_server_arrecord = next(
124
+ iter(out_msg.content.array_records.items())
125
+ )
126
+
127
+ # Ensure keys in returned ArrayRecord match those in the one sent from server
128
+ if list(original_array_record.keys()) != list(client_to_server_arrecord.keys()):
129
+ return _handle_array_key_mismatch_err("LocalDpMod", out_msg)
130
+
131
+ client_to_server_ndarrays = client_to_server_arrecord.to_numpy_ndarrays()
132
+
133
+ # Clip the client update
134
+ compute_clip_model_update(
135
+ client_to_server_ndarrays,
136
+ original_array_record.to_numpy_ndarrays(),
137
+ self.clipping_norm,
138
+ )
139
+ log(
140
+ INFO,
141
+ "LocalDpMod: parameters are clipped by value: %.4f.",
142
+ self.clipping_norm,
143
+ )
144
+
145
+ std_dev = (
146
+ self.sensitivity * np.sqrt(2 * np.log(1.25 / self.delta)) / self.epsilon
147
+ )
148
+ add_gaussian_noise_inplace(
149
+ client_to_server_ndarrays,
150
+ std_dev,
151
+ )
152
+ log(
153
+ INFO,
154
+ "LocalDpMod: local DP noise with %.4f stddev added to parameters",
155
+ std_dev,
156
+ )
157
+
158
+ # Replace outgoing ArrayRecord's Array while preserving their keys
159
+ out_msg.content[new_array_record_key] = ArrayRecord(
160
+ OrderedDict(
161
+ {
162
+ k: Array(v)
163
+ for k, v in zip(
164
+ client_to_server_arrecord.keys(), client_to_server_ndarrays
165
+ )
166
+ }
167
+ )
168
+ )
169
+ return out_msg
@@ -15,6 +15,7 @@
15
15
  """ServerApp strategies."""
16
16
 
17
17
 
18
+ from .bulyan import Bulyan
18
19
  from .dp_adaptive_clipping import (
19
20
  DifferentialPrivacyClientSideAdaptiveClipping,
20
21
  DifferentialPrivacyServerSideAdaptiveClipping,
@@ -34,11 +35,13 @@ from .fedxgb_bagging import FedXgbBagging
34
35
  from .fedxgb_cyclic import FedXgbCyclic
35
36
  from .fedyogi import FedYogi
36
37
  from .krum import Krum
38
+ from .multikrum import MultiKrum
37
39
  from .qfedavg import QFedAvg
38
40
  from .result import Result
39
41
  from .strategy import Strategy
40
42
 
41
43
  __all__ = [
44
+ "Bulyan",
42
45
  "DifferentialPrivacyClientSideAdaptiveClipping",
43
46
  "DifferentialPrivacyClientSideFixedClipping",
44
47
  "DifferentialPrivacyServerSideAdaptiveClipping",
@@ -54,6 +57,7 @@ __all__ = [
54
57
  "FedXgbCyclic",
55
58
  "FedYogi",
56
59
  "Krum",
60
+ "MultiKrum",
57
61
  "QFedAvg",
58
62
  "Result",
59
63
  "Strategy",
@@ -0,0 +1,238 @@
1
+ # Copyright 2025 Flower Labs GmbH. All Rights Reserved.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+ # ==============================================================================
15
+ """Bulyan [El Mhamdi et al., 2018] strategy.
16
+
17
+ Paper: arxiv.org/abs/1802.07927
18
+ """
19
+
20
+
21
+ from collections import OrderedDict
22
+ from collections.abc import Iterable
23
+ from logging import INFO, WARN
24
+ from typing import Callable, Optional, cast
25
+
26
+ import numpy as np
27
+
28
+ from flwr.common import (
29
+ Array,
30
+ ArrayRecord,
31
+ Message,
32
+ MetricRecord,
33
+ NDArrays,
34
+ RecordDict,
35
+ log,
36
+ )
37
+
38
+ from .fedavg import FedAvg
39
+ from .multikrum import select_multikrum
40
+
41
+
42
+ # pylint: disable=too-many-instance-attributes
43
+ class Bulyan(FedAvg):
44
+ """Bulyan strategy.
45
+
46
+ Implementation based on https://arxiv.org/abs/1802.07927.
47
+
48
+ Parameters
49
+ ----------
50
+ fraction_train : float (default: 1.0)
51
+ Fraction of nodes used during training. In case `min_train_nodes`
52
+ is larger than `fraction_train * total_connected_nodes`, `min_train_nodes`
53
+ will still be sampled.
54
+ fraction_evaluate : float (default: 1.0)
55
+ Fraction of nodes used during validation. In case `min_evaluate_nodes`
56
+ is larger than `fraction_evaluate * total_connected_nodes`,
57
+ `min_evaluate_nodes` will still be sampled.
58
+ min_train_nodes : int (default: 2)
59
+ Minimum number of nodes used during training.
60
+ min_evaluate_nodes : int (default: 2)
61
+ Minimum number of nodes used during validation.
62
+ min_available_nodes : int (default: 2)
63
+ Minimum number of total nodes in the system.
64
+ num_malicious_nodes : int (default: 0)
65
+ Number of malicious nodes in the system.
66
+ weighted_by_key : str (default: "num-examples")
67
+ The key within each MetricRecord whose value is used as the weight when
68
+ computing weighted averages for MetricRecords.
69
+ arrayrecord_key : str (default: "arrays")
70
+ Key used to store the ArrayRecord when constructing Messages.
71
+ configrecord_key : str (default: "config")
72
+ Key used to store the ConfigRecord when constructing Messages.
73
+ train_metrics_aggr_fn : Optional[callable] (default: None)
74
+ Function with signature (list[RecordDict], str) -> MetricRecord,
75
+ used to aggregate MetricRecords from training round replies.
76
+ If `None`, defaults to `aggregate_metricrecords`, which performs a weighted
77
+ average using the provided weight factor key.
78
+ evaluate_metrics_aggr_fn : Optional[callable] (default: None)
79
+ Function with signature (list[RecordDict], str) -> MetricRecord,
80
+ used to aggregate MetricRecords from training round replies.
81
+ If `None`, defaults to `aggregate_metricrecords`, which performs a weighted
82
+ average using the provided weight factor key.
83
+ selection_rule : Optional[Callable] (default: None)
84
+ Function with signature (list[RecordDict], int, int) -> list[RecordDict].
85
+ The inputs are:
86
+ - a list of contents from reply messages,
87
+ - the assumed number of malicious nodes (`num_malicious_nodes`),
88
+ - the number of nodes to select (`num_nodes_to_select`).
89
+
90
+ The function should implement a Byzantine-resilient selection rule that
91
+ serves as the first step of Bulyan. If None, defaults to `select_multikrum`,
92
+ which selects nodes according to the Multi-Krum algorithm.
93
+ """
94
+
95
+ # pylint: disable=too-many-arguments,too-many-positional-arguments
96
+ def __init__(
97
+ self,
98
+ fraction_train: float = 1.0,
99
+ fraction_evaluate: float = 1.0,
100
+ min_train_nodes: int = 2,
101
+ min_evaluate_nodes: int = 2,
102
+ min_available_nodes: int = 2,
103
+ num_malicious_nodes: int = 0,
104
+ weighted_by_key: str = "num-examples",
105
+ arrayrecord_key: str = "arrays",
106
+ configrecord_key: str = "config",
107
+ train_metrics_aggr_fn: Optional[
108
+ Callable[[list[RecordDict], str], MetricRecord]
109
+ ] = None,
110
+ evaluate_metrics_aggr_fn: Optional[
111
+ Callable[[list[RecordDict], str], MetricRecord]
112
+ ] = None,
113
+ selection_rule: Optional[
114
+ Callable[[list[RecordDict], int, int], list[RecordDict]]
115
+ ] = None,
116
+ ) -> None:
117
+ super().__init__(
118
+ fraction_train=fraction_train,
119
+ fraction_evaluate=fraction_evaluate,
120
+ min_train_nodes=min_train_nodes,
121
+ min_evaluate_nodes=min_evaluate_nodes,
122
+ min_available_nodes=min_available_nodes,
123
+ weighted_by_key=weighted_by_key,
124
+ arrayrecord_key=arrayrecord_key,
125
+ configrecord_key=configrecord_key,
126
+ train_metrics_aggr_fn=train_metrics_aggr_fn,
127
+ evaluate_metrics_aggr_fn=evaluate_metrics_aggr_fn,
128
+ )
129
+ self.num_malicious_nodes = num_malicious_nodes
130
+ self.selection_rule = selection_rule or select_multikrum
131
+
132
+ def summary(self) -> None:
133
+ """Log summary configuration of the strategy."""
134
+ log(INFO, "\t├──> Bulyan settings:")
135
+ log(INFO, "\t│\t├── Number of malicious nodes: %d", self.num_malicious_nodes)
136
+ log(INFO, "\t│\t└── Selection rule: %s", self.selection_rule.__name__)
137
+ super().summary()
138
+
139
+ def aggregate_train(
140
+ self,
141
+ server_round: int,
142
+ replies: Iterable[Message],
143
+ ) -> tuple[Optional[ArrayRecord], Optional[MetricRecord]]:
144
+ """Aggregate ArrayRecords and MetricRecords in the received Messages."""
145
+ valid_replies, _ = self._check_and_log_replies(replies, is_train=True)
146
+
147
+ # Check if sufficient replies have been received
148
+ if len(valid_replies) < 4 * self.num_malicious_nodes + 3:
149
+ log(
150
+ WARN,
151
+ "Insufficient replies, skipping Bulyan aggregation: "
152
+ "Required at least %d (4*num_malicious_nodes + 3), but received %d.",
153
+ 4 * self.num_malicious_nodes + 3,
154
+ len(valid_replies),
155
+ )
156
+ return None, None
157
+
158
+ reply_contents = [msg.content for msg in valid_replies]
159
+
160
+ # Compute theta and beta
161
+ theta = len(valid_replies) - 2 * self.num_malicious_nodes
162
+ beta = theta - 2 * self.num_malicious_nodes
163
+
164
+ # Byzantine-resilient selection rule
165
+ selected_contents = self.selection_rule(
166
+ reply_contents, self.num_malicious_nodes, theta
167
+ )
168
+
169
+ # Convert each ArrayRecord to a list of NDArray for easier computation
170
+ key = list(selected_contents[0].array_records.keys())[0]
171
+ array_keys = list(selected_contents[0][key].keys())
172
+ selected_ndarrays = [
173
+ cast(ArrayRecord, ctnt[key]).to_numpy_ndarrays(keep_input=False)
174
+ for ctnt in selected_contents
175
+ ]
176
+
177
+ # Compute median
178
+ median_ndarrays = [np.median(arr, axis=0) for arr in zip(*selected_ndarrays)]
179
+
180
+ # Aggregate the beta closest weights element-wise
181
+ aggregated_ndarrays = aggregate_n_closest_weights(
182
+ median_ndarrays, selected_ndarrays, beta
183
+ )
184
+
185
+ # Convert to ArrayRecord
186
+ arrays = ArrayRecord(
187
+ OrderedDict(zip(array_keys, map(Array, aggregated_ndarrays)))
188
+ )
189
+
190
+ # Aggregate MetricRecords
191
+ metrics = self.train_metrics_aggr_fn(
192
+ selected_contents,
193
+ self.weighted_by_key,
194
+ )
195
+ return arrays, metrics
196
+
197
+
198
+ def aggregate_n_closest_weights(
199
+ ref_weights: NDArrays, weights_list: list[NDArrays], beta: int
200
+ ) -> NDArrays:
201
+ """Compute the element-wise mean of the `beta` closest weight arrays.
202
+
203
+ For each element (i-th coordinate), the output is the average of the
204
+ `beta` weight arrays that are closest to the reference weights.
205
+
206
+ Parameters
207
+ ----------
208
+ ref_weights : NDArrays
209
+ Reference weights used to compute distances.
210
+ weights_list : list[NDArrays]
211
+ List of weight arrays (e.g., from selected nodes).
212
+ beta : int
213
+ Number of closest weight arrays to include in the averaging.
214
+
215
+ Returns
216
+ -------
217
+ aggregated_weights : NDArrays
218
+ Element-wise average of the `beta` closest weight arrays to the
219
+ reference weights.
220
+ """
221
+ aggregated_weights = []
222
+ for layer_id, ref_layer in enumerate(ref_weights):
223
+ # Shape: (n_models, *layer_shape)
224
+ layer_stack = np.stack([weights[layer_id] for weights in weights_list])
225
+
226
+ # Compute absolute differences: shape (n_models, *layer_shape)
227
+ diffs = np.abs(layer_stack - ref_layer)
228
+
229
+ # Find indices of `beta` smallest per coordinate
230
+ idx = np.argpartition(diffs, beta - 1, axis=0)[:beta]
231
+
232
+ # Gather the closest weights
233
+ closest = np.take_along_axis(layer_stack, idx, axis=0)
234
+
235
+ # Average them
236
+ aggregated_weights.append(np.mean(closest, axis=0))
237
+
238
+ return aggregated_weights
@@ -32,6 +32,40 @@ class FedMedian(FedAvg):
32
32
  """Federated Median (FedMedian) strategy.
33
33
 
34
34
  Implementation based on https://arxiv.org/pdf/1803.01498v1
35
+
36
+ Parameters
37
+ ----------
38
+ fraction_train : float (default: 1.0)
39
+ Fraction of nodes used during training. In case `min_train_nodes`
40
+ is larger than `fraction_train * total_connected_nodes`, `min_train_nodes`
41
+ will still be sampled.
42
+ fraction_evaluate : float (default: 1.0)
43
+ Fraction of nodes used during validation. In case `min_evaluate_nodes`
44
+ is larger than `fraction_evaluate * total_connected_nodes`,
45
+ `min_evaluate_nodes` will still be sampled.
46
+ min_train_nodes : int (default: 2)
47
+ Minimum number of nodes used during training.
48
+ min_evaluate_nodes : int (default: 2)
49
+ Minimum number of nodes used during validation.
50
+ min_available_nodes : int (default: 2)
51
+ Minimum number of total nodes in the system.
52
+ weighted_by_key : str (default: "num-examples")
53
+ The key within each MetricRecord whose value is used as the weight when
54
+ computing weighted averages for MetricRecords.
55
+ arrayrecord_key : str (default: "arrays")
56
+ Key used to store the ArrayRecord when constructing Messages.
57
+ configrecord_key : str (default: "config")
58
+ Key used to store the ConfigRecord when constructing Messages.
59
+ train_metrics_aggr_fn : Optional[callable] (default: None)
60
+ Function with signature (list[RecordDict], str) -> MetricRecord,
61
+ used to aggregate MetricRecords from training round replies.
62
+ If `None`, defaults to `aggregate_metricrecords`, which performs a weighted
63
+ average using the provided weight factor key.
64
+ evaluate_metrics_aggr_fn : Optional[callable] (default: None)
65
+ Function with signature (list[RecordDict], str) -> MetricRecord,
66
+ used to aggregate MetricRecords from training round replies.
67
+ If `None`, defaults to `aggregate_metricrecords`, which performs a weighted
68
+ average using the provided weight factor key.
35
69
  """
36
70
 
37
71
  def aggregate_train(