bustapi 0.14.2__tar.gz → 0.14.3__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 (262) hide show
  1. {bustapi-0.14.2 → bustapi-0.14.3}/CHANGELOG.md +6 -0
  2. {bustapi-0.14.2 → bustapi-0.14.3}/Cargo.lock +3 -3
  3. {bustapi-0.14.2 → bustapi-0.14.3}/Cargo.toml +1 -1
  4. {bustapi-0.14.2 → bustapi-0.14.3}/PKG-INFO +1 -1
  5. {bustapi-0.14.2 → bustapi-0.14.3}/docs/changelog.md +6 -0
  6. {bustapi-0.14.2 → bustapi-0.14.3}/pyproject.toml +1 -1
  7. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/__init__.py +1 -1
  8. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/websocket.py +23 -35
  9. {bustapi-0.14.2 → bustapi-0.14.3}/src/websocket/session.rs +3 -1
  10. {bustapi-0.14.2 → bustapi-0.14.3}/- +0 -0
  11. {bustapi-0.14.2 → bustapi-0.14.3}/.github/FUNDING.yml +0 -0
  12. {bustapi-0.14.2 → bustapi-0.14.3}/.github/workflows/ci-multiplatform.yml +0 -0
  13. {bustapi-0.14.2 → bustapi-0.14.3}/.github/workflows/ci.yml +0 -0
  14. {bustapi-0.14.2 → bustapi-0.14.3}/.github/workflows/docs.yml +0 -0
  15. {bustapi-0.14.2 → bustapi-0.14.3}/.github/workflows/manual-publish.yml +0 -0
  16. {bustapi-0.14.2 → bustapi-0.14.3}/.gitignore +0 -0
  17. {bustapi-0.14.2 → bustapi-0.14.3}/.python-version +0 -0
  18. {bustapi-0.14.2 → bustapi-0.14.3}/AGENT_KNOWLEDGE.md +0 -0
  19. {bustapi-0.14.2 → bustapi-0.14.3}/Dockerfile +0 -0
  20. {bustapi-0.14.2 → bustapi-0.14.3}/LICENSE +0 -0
  21. {bustapi-0.14.2 → bustapi-0.14.3}/README.md +0 -0
  22. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/CACHE_BENCHMARK.md +0 -0
  23. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/README.md +0 -0
  24. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/app.py +0 -0
  25. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/benchmark_all.py +0 -0
  26. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/benchmark_avg.py +0 -0
  27. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/benchmark_cache.py +0 -0
  28. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/benchmark_combined.png +0 -0
  29. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/bustapi.md +0 -0
  30. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/bustapi_bench.py +0 -0
  31. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/bustapi_internal.py +0 -0
  32. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/comparison_bench.py +0 -0
  33. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/comprehensive_benchmark.py +0 -0
  34. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/gen_graph.py +0 -0
  35. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/quick_bench.py +0 -0
  36. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/resource_bench.py +0 -0
  37. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/rps_comparison.png +0 -0
  38. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/run_comparison_auto.py +0 -0
  39. {bustapi-0.14.2 → bustapi-0.14.3}/benchmarks/ws_benchmark.py +0 -0
  40. {bustapi-0.14.2 → bustapi-0.14.3}/docs/advanced/async.md +0 -0
  41. {bustapi-0.14.2 → bustapi-0.14.3}/docs/advanced/blueprints.md +0 -0
  42. {bustapi-0.14.2 → bustapi-0.14.3}/docs/advanced/dependency_injection.md +0 -0
  43. {bustapi-0.14.2 → bustapi-0.14.3}/docs/advanced/deployment.md +0 -0
  44. {bustapi-0.14.2 → bustapi-0.14.3}/docs/advanced/middleware.md +0 -0
  45. {bustapi-0.14.2 → bustapi-0.14.3}/docs/advanced/security.md +0 -0
  46. {bustapi-0.14.2 → bustapi-0.14.3}/docs/advanced/validation.md +0 -0
  47. {bustapi-0.14.2 → bustapi-0.14.3}/docs/api-reference.md +0 -0
  48. {bustapi-0.14.2 → bustapi-0.14.3}/docs/assets/logo.png +0 -0
  49. {bustapi-0.14.2 → bustapi-0.14.3}/docs/complete-api-reference.md +0 -0
  50. {bustapi-0.14.2 → bustapi-0.14.3}/docs/deployment-performance-guide.md +0 -0
  51. {bustapi-0.14.2 → bustapi-0.14.3}/docs/deployment.md +0 -0
  52. {bustapi-0.14.2 → bustapi-0.14.3}/docs/examples-guide.md +0 -0
  53. {bustapi-0.14.2 → bustapi-0.14.3}/docs/index.md +0 -0
  54. {bustapi-0.14.2 → bustapi-0.14.3}/docs/installation.md +0 -0
  55. {bustapi-0.14.2 → bustapi-0.14.3}/docs/overrides/.gitkeep +0 -0
  56. {bustapi-0.14.2 → bustapi-0.14.3}/docs/quickstart.md +0 -0
  57. {bustapi-0.14.2 → bustapi-0.14.3}/docs/release_track.md +0 -0
  58. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/advanced/async_support.html +0 -0
  59. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/advanced/blueprints.html +0 -0
  60. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/advanced/dependency_injection.html +0 -0
  61. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/advanced/middleware.html +0 -0
  62. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/advanced/validation.html +0 -0
  63. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/api/all.html +0 -0
  64. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/api/app.html +0 -0
  65. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/api/context.html +0 -0
  66. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/api/utilities.html +0 -0
  67. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/assets/logo.png +0 -0
  68. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/changelog.html +0 -0
  69. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/core_concepts/request_data.html +0 -0
  70. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/core_concepts/responses.html +0 -0
  71. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/core_concepts/routing.html +0 -0
  72. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/core_concepts/templates.html +0 -0
  73. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/examples/index.html +0 -0
  74. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/getting_started/index.html +0 -0
  75. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/getting_started/quickstart.html +0 -0
  76. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/index.html +0 -0
  77. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/script.js +0 -0
  78. {bustapi-0.14.2 → bustapi-0.14.3}/docs/site/style.css +0 -0
  79. {bustapi-0.14.2 → bustapi-0.14.3}/docs/stylesheets/extra.css +0 -0
  80. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/authentication.md +0 -0
  81. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/caching.md +0 -0
  82. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/cli.md +0 -0
  83. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/database.md +0 -0
  84. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/documentation.md +0 -0
  85. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/error_handling.md +0 -0
  86. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/jwt.md +0 -0
  87. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/logging.md +0 -0
  88. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/multiprocessing.md +0 -0
  89. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/request_data.md +0 -0
  90. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/responses.md +0 -0
  91. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/routing.md +0 -0
  92. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/sessions.md +0 -0
  93. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/static_files.md +0 -0
  94. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/templates.md +0 -0
  95. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/turbo-routes.md +0 -0
  96. {bustapi-0.14.2 → bustapi-0.14.3}/docs/user-guide/video-streaming.md +0 -0
  97. {bustapi-0.14.2 → bustapi-0.14.3}/docs/websockets.md +0 -0
  98. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/08_auto_docs.py +0 -0
  99. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/12_test_modes.py +0 -0
  100. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/13_error_handling.py +0 -0
  101. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/14_middleware.py +0 -0
  102. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/16_middleware_session.py +0 -0
  103. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/20_file_uploads.py +0 -0
  104. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/24_body_and_depends.py +0 -0
  105. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/27_video_stream.py +0 -0
  106. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/28_websocket.py +0 -0
  107. {bustapi-0.14.2 → bustapi-0.14.3}/examples/advanced/29_turbo_websocket.py +0 -0
  108. {bustapi-0.14.2 → bustapi-0.14.3}/examples/basics/01_hello_world.py +0 -0
  109. {bustapi-0.14.2 → bustapi-0.14.3}/examples/basics/02_parameters.py +0 -0
  110. {bustapi-0.14.2 → bustapi-0.14.3}/examples/basics/03_async.py +0 -0
  111. {bustapi-0.14.2 → bustapi-0.14.3}/examples/basics/04_request_data.py +0 -0
  112. {bustapi-0.14.2 → bustapi-0.14.3}/examples/basics/19_all_types.py +0 -0
  113. {bustapi-0.14.2 → bustapi-0.14.3}/examples/database/07_database_raw.py +0 -0
  114. {bustapi-0.14.2 → bustapi-0.14.3}/examples/database/10_database_sqlmodel.py +0 -0
  115. {bustapi-0.14.2 → bustapi-0.14.3}/examples/routing/06_blueprints.py +0 -0
  116. {bustapi-0.14.2 → bustapi-0.14.3}/examples/routing/09_complex_routing.py +0 -0
  117. {bustapi-0.14.2 → bustapi-0.14.3}/examples/routing/21_path_validation.py +0 -0
  118. {bustapi-0.14.2 → bustapi-0.14.3}/examples/routing/22_path_docs.py +0 -0
  119. {bustapi-0.14.2 → bustapi-0.14.3}/examples/routing/23_query_validation.py +0 -0
  120. {bustapi-0.14.2 → bustapi-0.14.3}/examples/routing/blueprint_with_jwt.py +0 -0
  121. {bustapi-0.14.2 → bustapi-0.14.3}/examples/security/10_rate_limit_demo.py +0 -0
  122. {bustapi-0.14.2 → bustapi-0.14.3}/examples/security/11_security_demo.py +0 -0
  123. {bustapi-0.14.2 → bustapi-0.14.3}/examples/security/17_jwt_auth.py +0 -0
  124. {bustapi-0.14.2 → bustapi-0.14.3}/examples/security/17_safe_features.py +0 -0
  125. {bustapi-0.14.2 → bustapi-0.14.3}/examples/security/18_jwt_cookies.py +0 -0
  126. {bustapi-0.14.2 → bustapi-0.14.3}/examples/security/18_safe_advanced.py +0 -0
  127. {bustapi-0.14.2 → bustapi-0.14.3}/examples/security/18_session_login.py +0 -0
  128. {bustapi-0.14.2 → bustapi-0.14.3}/examples/templates/05_templates.py +0 -0
  129. {bustapi-0.14.2 → bustapi-0.14.3}/examples/templates/26_complex_template.py +0 -0
  130. {bustapi-0.14.2 → bustapi-0.14.3}/examples/templates/templates/index.html +0 -0
  131. {bustapi-0.14.2 → bustapi-0.14.3}/examples/turbo/cache_test.py +0 -0
  132. {bustapi-0.14.2 → bustapi-0.14.3}/examples/turbo/fair_benchmark.py +0 -0
  133. {bustapi-0.14.2 → bustapi-0.14.3}/examples/turbo/typed_turbo_example.py +0 -0
  134. {bustapi-0.14.2 → bustapi-0.14.3}/examples/ws/app.py +0 -0
  135. {bustapi-0.14.2 → bustapi-0.14.3}/examples/ws/templates/index.html +0 -0
  136. {bustapi-0.14.2 → bustapi-0.14.3}/examples/ws/websockets_demo.py +0 -0
  137. {bustapi-0.14.2 → bustapi-0.14.3}/examples/ws/ws_limit.py +0 -0
  138. {bustapi-0.14.2 → bustapi-0.14.3}/mkdocs.yml +0 -0
  139. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/app.py +0 -0
  140. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/auth/__init__.py +0 -0
  141. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/auth/csrf.py +0 -0
  142. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/auth/decorators.py +0 -0
  143. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/auth/login.py +0 -0
  144. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/auth/password.py +0 -0
  145. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/auth/tokens.py +0 -0
  146. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/auth/user.py +0 -0
  147. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/cli/__init__.py +0 -0
  148. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/cli/main.py +0 -0
  149. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/context.py +0 -0
  150. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/core/__init__.py +0 -0
  151. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/core/asgi.py +0 -0
  152. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/core/exceptions.py +0 -0
  153. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/core/helpers.py +0 -0
  154. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/core/logging.py +0 -0
  155. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/dependencies.py +0 -0
  156. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/dispatch.py +0 -0
  157. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/documentation/__init__.py +0 -0
  158. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/documentation/generator.py +0 -0
  159. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/extraction.py +0 -0
  160. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/fastapi_compat.py +0 -0
  161. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/hooks.py +0 -0
  162. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/http/__init__.py +0 -0
  163. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/http/request.py +0 -0
  164. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/http/response.py +0 -0
  165. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/jwt.py +0 -0
  166. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/logging.py +0 -0
  167. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/middleware.py +0 -0
  168. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/multiprocess.py +0 -0
  169. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/params.py +0 -0
  170. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/py.typed +0 -0
  171. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/responses.py +0 -0
  172. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/routing/__init__.py +0 -0
  173. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/routing/blueprints.py +0 -0
  174. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/routing/decorators.py +0 -0
  175. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/safe/__init__.py +0 -0
  176. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/safe/concurrency.py +0 -0
  177. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/safe/types.py +0 -0
  178. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/security/__init__.py +0 -0
  179. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/security/extension.py +0 -0
  180. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/security/rate_limit.py +0 -0
  181. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/server/__init__.py +0 -0
  182. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/server/runner.py +0 -0
  183. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/server/wsgi.py +0 -0
  184. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/sessions.py +0 -0
  185. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/templating/__init__.py +0 -0
  186. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/templating/engine.py +0 -0
  187. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/templating/mixin.py +0 -0
  188. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/testing/__init__.py +0 -0
  189. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/testing/client.py +0 -0
  190. {bustapi-0.14.2 → bustapi-0.14.3}/python/bustapi/utils.py +0 -0
  191. {bustapi-0.14.2 → bustapi-0.14.3}/run_all_examples.py +0 -0
  192. {bustapi-0.14.2 → bustapi-0.14.3}/scratch/test_abort.py +0 -0
  193. {bustapi-0.14.2 → bustapi-0.14.3}/scratch/test_headers.py +0 -0
  194. {bustapi-0.14.2 → bustapi-0.14.3}/src/bindings/app.rs +0 -0
  195. {bustapi-0.14.2 → bustapi-0.14.3}/src/bindings/converters.rs +0 -0
  196. {bustapi-0.14.2 → bustapi-0.14.3}/src/bindings/handlers.rs +0 -0
  197. {bustapi-0.14.2 → bustapi-0.14.3}/src/bindings/mod.rs +0 -0
  198. {bustapi-0.14.2 → bustapi-0.14.3}/src/bindings/request.rs +0 -0
  199. {bustapi-0.14.2 → bustapi-0.14.3}/src/bindings/typed_turbo.rs +0 -0
  200. {bustapi-0.14.2 → bustapi-0.14.3}/src/bindings/websocket.rs +0 -0
  201. {bustapi-0.14.2 → bustapi-0.14.3}/src/crypto.rs +0 -0
  202. {bustapi-0.14.2 → bustapi-0.14.3}/src/jwt.rs +0 -0
  203. {bustapi-0.14.2 → bustapi-0.14.3}/src/lib.rs +0 -0
  204. {bustapi-0.14.2 → bustapi-0.14.3}/src/logger.rs +0 -0
  205. {bustapi-0.14.2 → bustapi-0.14.3}/src/rate_limiter.rs +0 -0
  206. {bustapi-0.14.2 → bustapi-0.14.3}/src/request/methods.rs +0 -0
  207. {bustapi-0.14.2 → bustapi-0.14.3}/src/request/mod.rs +0 -0
  208. {bustapi-0.14.2 → bustapi-0.14.3}/src/request/tests.rs +0 -0
  209. {bustapi-0.14.2 → bustapi-0.14.3}/src/response/builders.rs +0 -0
  210. {bustapi-0.14.2 → bustapi-0.14.3}/src/response/methods.rs +0 -0
  211. {bustapi-0.14.2 → bustapi-0.14.3}/src/response/mod.rs +0 -0
  212. {bustapi-0.14.2 → bustapi-0.14.3}/src/router/handlers.rs +0 -0
  213. {bustapi-0.14.2 → bustapi-0.14.3}/src/router/matching.rs +0 -0
  214. {bustapi-0.14.2 → bustapi-0.14.3}/src/router/middleware.rs +0 -0
  215. {bustapi-0.14.2 → bustapi-0.14.3}/src/router/mod.rs +0 -0
  216. {bustapi-0.14.2 → bustapi-0.14.3}/src/router/tests.rs +0 -0
  217. {bustapi-0.14.2 → bustapi-0.14.3}/src/server/handlers.rs +0 -0
  218. {bustapi-0.14.2 → bustapi-0.14.3}/src/server/mod.rs +0 -0
  219. {bustapi-0.14.2 → bustapi-0.14.3}/src/server/startup.rs +0 -0
  220. {bustapi-0.14.2 → bustapi-0.14.3}/src/server/stream.rs +0 -0
  221. {bustapi-0.14.2 → bustapi-0.14.3}/src/static_files.rs +0 -0
  222. {bustapi-0.14.2 → bustapi-0.14.3}/src/templating.rs +0 -0
  223. {bustapi-0.14.2 → bustapi-0.14.3}/src/watcher.rs +0 -0
  224. {bustapi-0.14.2 → bustapi-0.14.3}/src/websocket/config.rs +0 -0
  225. {bustapi-0.14.2 → bustapi-0.14.3}/src/websocket/mod.rs +0 -0
  226. {bustapi-0.14.2 → bustapi-0.14.3}/src/websocket/turbo.rs +0 -0
  227. {bustapi-0.14.2 → bustapi-0.14.3}/static/style.css +0 -0
  228. {bustapi-0.14.2 → bustapi-0.14.3}/templates/base.html +0 -0
  229. {bustapi-0.14.2 → bustapi-0.14.3}/templates/complex.html +0 -0
  230. {bustapi-0.14.2 → bustapi-0.14.3}/tests/docs_test_all.py +0 -0
  231. {bustapi-0.14.2 → bustapi-0.14.3}/tests/docs_test_api_reference.py +0 -0
  232. {bustapi-0.14.2 → bustapi-0.14.3}/tests/docs_test_installation.py +0 -0
  233. {bustapi-0.14.2 → bustapi-0.14.3}/tests/docs_test_quickstart.py +0 -0
  234. {bustapi-0.14.2 → bustapi-0.14.3}/tests/docs_test_simple.py +0 -0
  235. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_050_features.py +0 -0
  236. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_async_hooks.py +0 -0
  237. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_async_login.py +0 -0
  238. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_auth.py +0 -0
  239. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_discussion_21.py +0 -0
  240. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_discussion_22.py +0 -0
  241. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_discussion_28.py +0 -0
  242. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_examples.py +0 -0
  243. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_hot_reload.py +0 -0
  244. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_issue_18.py +0 -0
  245. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_issue_23.py +0 -0
  246. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_issue_24.py +0 -0
  247. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_issue_29.py +0 -0
  248. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_jwt.py +0 -0
  249. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_jwt_cookies.py +0 -0
  250. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_login_manager.py +0 -0
  251. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_middleware.py +0 -0
  252. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_multiprocess_stability.py +0 -0
  253. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_new_examples.py +0 -0
  254. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_orm_conflict.py +0 -0
  255. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_path_standalone.py +0 -0
  256. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_path_validation.py +0 -0
  257. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_rate_limit_rust.py +0 -0
  258. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_safe.py +0 -0
  259. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_security_unit.py +0 -0
  260. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_sessions.py +0 -0
  261. {bustapi-0.14.2 → bustapi-0.14.3}/tests/test_zero_copy.py +0 -0
  262. {bustapi-0.14.2 → bustapi-0.14.3}/tests/verify_router.py +0 -0
@@ -2,6 +2,12 @@
2
2
 
3
3
  All notable changes to this project will be documented here.
4
4
 
5
+ ## [0.14.3] - 2026-06-19
6
+
7
+ ### Fixed
8
+ - **WebSocket Handshake**: Fixed a bug where client-initiated close frames (e.g. `socket.close()` in JS) were not properly echoed back by the Rust backend to complete the WebSocket close handshake. `on_disconnect` and `on_binary` handlers are now fully thread-safe and trigger cleanly.
9
+ - **WebSocket Config**: Clarified the usage of `WebSocketConfig` instance for the `config` parameter in WebSocket routes.
10
+
5
11
  ## [0.14.2] - 2026-06-18
6
12
 
7
13
  ### Fixed
@@ -432,7 +432,7 @@ checksum = "72f5acc6cb2ba439de613abc23857ec3d78374d8ed5ac84e9d11336e87da8649"
432
432
 
433
433
  [[package]]
434
434
  name = "bustapi_core"
435
- version = "0.14.2"
435
+ version = "0.14.3"
436
436
  dependencies = [
437
437
  "actix-files",
438
438
  "actix-http",
@@ -476,9 +476,9 @@ dependencies = [
476
476
 
477
477
  [[package]]
478
478
  name = "bytes"
479
- version = "1.11.1"
479
+ version = "1.12.0"
480
480
  source = "registry+https://github.com/rust-lang/crates.io-index"
481
- checksum = "1e748733b7cbc798e1434b6ac524f0c1ff2ab456fe201501e6497c8417a4fc33"
481
+ checksum = "8ae3f5d315924270530207e2a68396c3cc547f6dca3fbdca317cfb1a51edb593"
482
482
 
483
483
  [[package]]
484
484
  name = "bytestring"
@@ -1,6 +1,6 @@
1
1
  [package]
2
2
  name = "bustapi_core"
3
- version = "0.14.2"
3
+ version = "0.14.3"
4
4
  edition = "2021"
5
5
  readme = "README.md"
6
6
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: bustapi
3
- Version: 0.14.2
3
+ Version: 0.14.3
4
4
  Classifier: Development Status :: 3 - Alpha
5
5
  Classifier: Intended Audience :: Developers
6
6
  Classifier: License :: OSI Approved :: MIT License
@@ -2,6 +2,12 @@
2
2
 
3
3
  All notable changes to this project will be documented here.
4
4
 
5
+ ## [0.14.3] - 2026-06-19
6
+
7
+ ### Fixed
8
+ - **WebSocket Handshake**: Fixed a bug where client-initiated close frames (e.g. `socket.close()` in JS) were not properly echoed back by the Rust backend to complete the WebSocket close handshake. `on_disconnect` and `on_binary` handlers are now fully thread-safe and trigger cleanly.
9
+ - **WebSocket Config**: Clarified the usage of `WebSocketConfig` instance for the `config` parameter in WebSocket routes.
10
+
5
11
  ## [0.14.2] - 2026-06-18
6
12
 
7
13
  ### Fixed
@@ -4,7 +4,7 @@ build-backend = "maturin"
4
4
 
5
5
  [project]
6
6
  name = "bustapi"
7
- version = "0.14.2"
7
+ version = "0.14.3"
8
8
  description = "High-performance Python web framework with Rust backend"
9
9
  authors = [
10
10
  {name = "GrandpaEJ", email = ""}
@@ -22,7 +22,7 @@ import platform
22
22
  import sys
23
23
  from http import HTTPStatus
24
24
 
25
- __version__ = "0.14.2"
25
+ __version__ = "0.14.3"
26
26
  __author__ = "BustAPI" # with GrandpaEJ
27
27
  __email__ = ""
28
28
 
@@ -197,61 +197,49 @@ class WebSocketHandler:
197
197
  if hasattr(task, "add_done_callback"):
198
198
  task.add_done_callback(_task_done_callback)
199
199
 
200
+ def _get_loop(self, session_id: int):
201
+ """Find the asyncio loop associated with a session."""
202
+ if hasattr(self, "_background_loop") and self._background_loop:
203
+ return self._background_loop
204
+ task = self._tasks.get(session_id)
205
+ if task:
206
+ try:
207
+ return task.get_loop()
208
+ except Exception:
209
+ pass
210
+ return None
211
+
200
212
  def on_message(self, session_id: int, message: str) -> None:
201
213
  """Called when a text message is received."""
202
214
  if session_id in self._connections:
203
215
  ws = self._connections[session_id]
204
- # Since we might be running in a different thread (Actix thread)
205
- # than the WebSocket's loop (Background thread), we must use thread-safe scheduling.
206
- # We need to find the loop associated with this WebSocket's handler.
207
- loop = None
208
- if hasattr(self, "_background_loop") and self._background_loop:
209
- loop = self._background_loop
210
- else:
211
- # Fallback: try to get loop from registered task?
212
- pass
213
-
216
+ loop = self._get_loop(session_id)
214
217
  if loop:
215
218
  loop.call_soon_threadsafe(ws._receive_message, message)
216
219
  else:
217
- # If no specific background loop, imply we are reusing the main loop?
218
- # But if we are in Actix thread, main loop might be running in main thread.
219
- # call_soon_threadsafe is safe to call from any thread to target loop.
220
- # However, if we don't have 'loop' var ...
221
- # ws._messages is bound to a loop. We should get it.
222
- # asyncio.Queue doesn't expose public ._loop, but we can try to guess.
223
- # Actually, check self._tasks[session_id].get_loop() if available py3.7+
224
- task = self._tasks.get(session_id)
225
- if task:
226
- try:
227
- loop = task.get_loop()
228
- loop.call_soon_threadsafe(ws._receive_message, message)
229
- return
230
- except:
231
- pass
232
-
233
- # Fallback to direct call if we can't find loop (risk of race)
234
220
  ws._receive_message(message)
235
221
 
236
- return None
237
-
238
222
  def on_binary(self, session_id: int, data: bytes) -> None:
239
223
  """Called when binary data is received."""
240
224
  if session_id in self._connections:
241
225
  ws = self._connections[session_id]
242
- # Convert if necessary, but data should come as bytes/list from bindings
243
- # If bindings use Vec<u8> -> list[int] in Python usually?
244
- # Or bytes?
245
- # Let's assume bytes for now or cast.
246
226
  if isinstance(data, list):
247
227
  data = bytes(data)
248
- ws._receive_message(data)
228
+ loop = self._get_loop(session_id)
229
+ if loop:
230
+ loop.call_soon_threadsafe(ws._receive_message, data)
231
+ else:
232
+ ws._receive_message(data)
249
233
 
250
234
  def on_disconnect(self, session_id: int, reason: Optional[str] = None) -> None:
251
235
  """Called when a client disconnects."""
252
236
  if session_id in self._connections:
253
237
  ws = self._connections[session_id]
254
- ws._receive_close(reason)
238
+ loop = self._get_loop(session_id)
239
+ if loop:
240
+ loop.call_soon_threadsafe(ws._receive_close, reason)
241
+ else:
242
+ ws._receive_close(reason)
255
243
  del self._connections[session_id]
256
244
 
257
245
  self._cleanup_task(session_id)
@@ -214,12 +214,14 @@ pub async fn handle_websocket(
214
214
  }
215
215
  Message::Close(reason) => {
216
216
  let sid = ws_session.id;
217
- let reason_str = reason.map(|r| r.description.unwrap_or_default());
217
+ let reason_str = reason.as_ref().and_then(|r| r.description.clone());
218
218
  let handler_ref = Python::attach(|py| handler_for_messages.clone_ref(py));
219
219
 
220
220
  Python::attach(|py| {
221
221
  let _ = handler_ref.call_method1(py, "on_disconnect", (sid, reason_str));
222
222
  });
223
+
224
+ let _ = session.close(reason).await;
223
225
  break;
224
226
  }
225
227
  _ => {
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes