atomic-bomb-engine


Nameatomic-bomb-engine JSON
Version 0.41.3 PyPI version JSON
download
home_pageNone
Summary使用rust开发的高性能python压测工具
upload_time2024-08-19 15:12:58
maintainerNone
docs_urlNone
authorNone
requires_pythonNone
licenseMIT
keywords rust python binding
VCS
bugtrack_url
requirements No requirements were recorded.
Travis-CI No Travis.
coveralls test coverage No coveralls.
            # atomic-bomb-engine-py
#### [atomic-bomb-engine](https://github.com/we-lsp/atomic-bomb-engine)的python包装实现

<img src="img/atomic-bomb-engine-logo.png" width="350px" height="350px" alt="logo">


## 前端仓库
#### [atomic-bomb-engine-front](https://github.com/GiantAxeWhy/atomic-bomb-engine-front)

## 使用条件:
- python版本 >= 3.8
- windows(x86), linux(x86), mac

## 使用方法:
- ### 准备开始
通过pip安装 (0.5.0版本之前)
```shell
pip install atomic-bomb-engine-py
```
在python中引用时注意,需要引用atomic_bomb_engine, 而不是atomic_bomb_engine_py
<br/> 为了避免混淆,0.5.0版本之后,pip更换了包名,更改为atomic-bomb-engine,
```shell
pip install atomic-bomb-engine
```
在python中导入
```python
import atomic_bomb_engine
```
异步使用的时候,还需要引用asyncio
```python
import asyncio
```
- ### 开始压测
  - ~~单接口压测~~ (功能与多接口压测重叠,已废除)

  - 多接口压测

多接口压测可以先使用
```python 
runner = atomic_bomb_engine.BatchRunner()
```
实例化一个runner类
通过runner类中的run方法开启压测
run方法函数签名如下
```python
def run(
         self,
         test_duration_secs: int,
         concurrent_requests: int,
         api_endpoints:List[Dict],
         step_option:Dict[str, int]|None=None,
         setup_options:List[Dict[str, Any]]|None=None,
         verbose:bool=False,
         should_prevent:bool=False,
         assert_channel_buffer_size:int=1024,
         timeout_secs=0,
         cookie_store_enable=True
    ) -> None:
        """
            批量压测
            :param test_duration_secs: 测试持续时间
            :param concurrent_requests: 并发数
            :param api_endpoints: 接口信息
            :param step_option: 阶梯加压选项
            :param setup_options: 初始化选项
            :param verbose: 打印详细信息
            :param should_prevent: 是否禁用睡眠
            :param assert_channel_buffer_size: 断言队列buffer大小
            :param timeout_secs: http超时时间
            :param cookie_store_enable: 是否为客户端启用持久性cookie存储。
        """
```

使用assert_option方法可以返回断言选项字典
```python
assert_options=[
atomic_bomb_engine.assert_option("$.code", 429),
atomic_bomb_engine.assert_option("$.code", 200)
])
```
jsonpath如果不会用的话,建议去[jsonpath](https://jsonpath.com/)学习

使用step_option方法可以返回阶梯加压选项字典
```python
def step_option(increase_step: int, increase_interval: int) -> Dict[str, int]:
    """
    生成step option
    :param increase_step: 阶梯步长
    :param increase_interval: 阶梯间隔
    """
```

同样的本包中也包含了一个对api_endpoint的包装:endpoint方法,方便调用,endpoint中的assert_options中也可以套用assert_option方法
 ```python
async def run_batch():
  result = await atomic_bomb_engine.batch_async(
    # 测试持续时间
    test_duration_secs=60,
    # 并发量
    concurrent_requests=200,
    # 阶梯设置(每5秒增加30个并发)
    step_option=atomic_bomb_engine.step_option(increase_step=30, increase_interval=5),
    # 接口超时时间
    timeout_secs=10,
    # 是否开启客户端启用持久性cookie存储
    cookie_store_enable=True,
    # 全局初始化
    setup_options=[
      atomic_bomb_engine.setup_option(
        name="初始化-1",
        url="http://localhost:8080/setup",
        method="get",
        jsonpath_extract=[
          atomic_bomb_engine.jsonpath_extract_option(key="test-msg", jsonpath="$.msg"),
          atomic_bomb_engine.jsonpath_extract_option(key="test-code", jsonpath="$.code"),
        ]
      )],
    # 是否开启详细日志
    verbose=False,
    # 被压接口设置
    api_endpoints=[
      atomic_bomb_engine.endpoint(
        # 接口任务命名
        name="test-1",
        # 针对每个接口初始化
        setup_options=[
          atomic_bomb_engine.setup_option(
            name="api-初始化-1",
            url="http://localhost:8080/api_setup",
            method="get",
            jsonpath_extract=[
              atomic_bomb_engine.jsonpath_extract_option(key="api-test-msg-1", jsonpath="$.msg"),
              atomic_bomb_engine.jsonpath_extract_option(key="api-test-code-1", jsonpath="$.code"),
            ]
          )
        ],
        # 被压接口url
        url="http://localhost:8080/direct",
        # 请求方式
        method="POST",
        # 权重
        weight=1,
        # 发送json请求
        json={"name": "{{api-test-msg-1}}", "number": 1},
        # 断言选项
        assert_options=[
          atomic_bomb_engine.assert_option(jsonpath="$.number", reference_object=1),
        ],
        # 思考时间选项(在最大和最小之间随机,单位毫秒)
        think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),
      ),
    ])
  print(result)
  return result
 ```
    
监听时可以在使用完run方法后,继续迭代runner即可

压测+同时监听

```python 
import asyncio


async def batch_async():
  runner = atomic_bomb_engine.BatchRunner()
  runner.run(
    test_duration_secs=30,
    concurrent_requests=30,
    step_option=atomic_bomb_engine.step_option(increase_step=3, increase_interval=3),
    timeout_secs=15,
    cookie_store_enable=True,
    verbose=False,
    api_endpoints=[
      atomic_bomb_engine.endpoint(
        name="test-1",
        url="http://127.0.0.1:8080/direct",
        method="POST",
        json={"name": "test-1", "number": 1},
        weight=100,
        assert_options=[
          atomic_bomb_engine.assert_option(jsonpath="$.msg", reference_object="操作成功"),
        ],
      ),
    ])
  return runner


async def main():
  results = await batch_async()
  for res in results:
    if res.get("should_wait"):
      await asyncio.sleep(0.1)
    print(res)


if __name__ == '__main__':
  asyncio.run(main())
```

# 压测时使用ui界面监控

0.5.0版本后,添加了ui页面,支持批量压测方法
<br/>导入
```python
from atomic_bomb_engine import server
```
使用
```python
import asyncio

import atomic_bomb_engine
from atomic_bomb_engine import server


@server.ui(port=8000)
async def batch_async():
    runner = atomic_bomb_engine.BatchRunner()
    runner.run(
      # 测试持续时间
      test_duration_secs=60,
      # 并发量
      concurrent_requests=200,
      # 阶梯设置(每5秒增加30个并发)
      step_option=atomic_bomb_engine.step_option(increase_step=30, increase_interval=5),
      # 接口超时时间
      timeout_secs=10,
      # 是否开启客户端启用持久性cookie存储
      cookie_store_enable=True,
      # 全局初始化
      setup_options=[
        atomic_bomb_engine.setup_option(
          name="初始化-1",
          url="http://localhost:8080/setup",
          method="get",
          jsonpath_extract=[
            atomic_bomb_engine.jsonpath_extract_option(key="test-msg", jsonpath="$.msg"),
            atomic_bomb_engine.jsonpath_extract_option(key="test-code", jsonpath="$.code"),
          ]
        )],
      # 是否开启详细日志
      verbose=False,
      # 被压接口设置
      api_endpoints=[
        atomic_bomb_engine.endpoint(
          # 接口任务命名
          name="test-1",
          # 针对每个接口初始化
          setup_options=[
            atomic_bomb_engine.setup_option(
              name="api-初始化-1",
              url="http://localhost:8080/api_setup",
              method="get",
              jsonpath_extract=[
                atomic_bomb_engine.jsonpath_extract_option(key="api-test-msg-1", jsonpath="$.msg"),
                atomic_bomb_engine.jsonpath_extract_option(key="api-test-code-1", jsonpath="$.code"),
              ]
            )
          ],
          # 被压接口url
          url="http://localhost:8080/direct",
          # 请求方式
          method="POST",
          # 权重
          weight=1,
          # 发送json请求
          json={"name": "{{api-test-msg-1}}", "number": 1},
          # 断言选项
          assert_options=[
            atomic_bomb_engine.assert_option(jsonpath="$.number", reference_object=1),
          ],
          # 思考时间选项(在最大和最小之间随机,单位毫秒)
          think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),
        ),
      ])
    return runner


if __name__ == '__main__':
    asyncio.run(batch_async())
```

使用server.ui装饰器,可以给批量压测方法启动一个简单的web服务器,不需要再手动监听BatchListenIter生成器

## 内部架构图
![architecture.png](img/architecture.png)

## [0.19.0] - 2024-04-16
### Added
- 增加了初始化和参数模版功能
```python
setup_options=[
  atomic_bomb_engine.setup_option(
    name="初始化-1",
    url="http://localhost:8080/setup",
    method="get",
    jsonpath_extract=[
      atomic_bomb_engine.jsonpath_extract_option(key="test-msg", jsonpath="$.msg"),
      atomic_bomb_engine.jsonpath_extract_option(key="test-code", jsonpath="$.code"),
    ]
  )]
```
上述实例展示了如何在初始化的时候调用某个接口,并且通过jsonpath将数据提取出来,保存在全局变量test-msg和test-code中
提取完全局变量后,就可以在后续的api_endpoints中使用
```python
api_endpoints=[
  atomic_bomb_engine.endpoint(
    # 接口任务命名
    name="test-1",
    # 针对每个接口初始化
    setup_options=[
      atomic_bomb_engine.setup_option(
        name="api-初始化-1",
        url="http://localhost:8080/api_setup",
        method="get",
        jsonpath_extract=[
          atomic_bomb_engine.jsonpath_extract_option(key="api-test-msg-1", jsonpath="$.msg"),
          atomic_bomb_engine.jsonpath_extract_option(key="api-test-code-1", jsonpath="$.code"),
        ]
      )
    ],
    # 被压接口url
    url="http://localhost:8080/direct",
    # 请求方式
    method="POST",
    # 权重
    weight=1,
    # 发送json请求
    json={"name": "{{api-test-msg-1}}", "number": 1},
    # 断言选项
    assert_options=[
      atomic_bomb_engine.assert_option(jsonpath="$.number", reference_object=1),
    ],
    # 思考时间选项(在最大和最小之间随机,单位毫秒)
    think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),
  ),
]
```
上述实例展示了如何在请求中使用全局变量,使用双大括号即可使用

### Fixed
- 修复了如果http状态码错误时,不会记录
- 修复了json反序列化的问题

## [0.20.0] - 2024-04-17
### Added
断言更改为异步生产消费,提升性能

## bug和需求
- 如果发现了bug,把复现步骤一起写到Issus中哈
- 如果有需求也可以在Issues中讨论
- 本程序是本人业余时间开发,不太准备保证时效性,但是如果有时间,一定第一时间回复和修改bug

## [0.22.0] - 2024-04-18
### Added
前端进行了性能优化

## [0.24.0] - 2024-04-22
### Added
异步断言使用了补偿消息,保证消息的一致性

## [0.25.0] - 2024-04-23
### Added
在endpoints中增加思考时间,模拟用户行为
```python
think_time_option(min_millis=200, max_millis=300)
```
  - min_millis:最小思考时间(毫秒)
  - max_millis:最大思考时间(毫秒)

使用时在endpoint中增加think_time_option参数

```python
api_endpoints=[
  atomic_bomb_engine.endpoint(
    name="test-1",
    url="http://localhost:8080/a",
    method="POST",
    weight=1,
    timeout_secs=10,
    json={"name": "{{test-msg}}", "number": "{{test-code}}"},
    think_time_option=atomic_bomb_engine.think_time_option(min_millis=200, max_millis=300),
  ),
]
```

## [0.26.0] - 2024-04-24
### Added
- 增加endpoint中的setup,在并发中可以做接口断言
- 增加有关联条件下的cookie自动管理功能
```python
atomic_bomb_engine.endpoint(
  # 接口任务命名
  name="test-1",
  # 针对每个接口初始化
  setup_options=[
    atomic_bomb_engine.setup_option(
      name="api-初始化-1",
      url="http://localhost:8080/api_setup",
      method="get",
      jsonpath_extract=[
        atomic_bomb_engine.jsonpath_extract_option(key="api-test-msg-1", jsonpath="$.msg"),
        atomic_bomb_engine.jsonpath_extract_option(key="api-test-code-1", jsonpath="$.code"),
      ]
    )
  ],
  # 被压接口url
  url="http://localhost:8080/direct",
  # 请求方式
  method="POST",
  # 权重
  weight=1,
  # 发送json请求
  json={"name": "{{api-test-msg-1}}", "number": 1},
  # 断言选项
  assert_options=[
    atomic_bomb_engine.assert_option(jsonpath="$.number", reference_object=1),
  ],
  # 思考时间选项(在最大和最小之间随机,单位毫秒)
  think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),
)
```
- 参数cookie_store_enable控制是否自动管理cookie,前置条件的cookie会带入到最终的压测接口中
- 在endpoint中使用setup_options可以传入多个接口,并且提取参数
- 提取到的参数如果和全局的setup的key冲突,会覆盖全局提取到的参数
- 接口中提取的参数只能在本线程(v-user)中使用
- ⚠️ 使用时注意:setup_options是顺序执行的,没有并发,但是相当于添加了think time

## [0.28.0] - 2024-04-25
### Added
- 将持久化cookie添加到全局选项中
- 复用http client
- 选择性开启断言任务
- 接口初始化时出现错误等待后重试##

## [0.29.0] - 2024-04-25
### Added
- 优化并发逻辑
- 前端更改为web worker发送心跳

## [0.38.0] - 2024-05-7
### Added
- 增加附件上传功能
  - 在初始化和每个接口中增加了multipart_options参数用于附件上传
  - 增加multipart_option方法封装附件参数
    - form_key: form表单的key
    - path: 附件路径
    - file_name: 附件名
    - mime: 附件类型 (类型可以参考[这里](https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Basics_of_HTTP/MIME_types/Common_types))
```python
api_endpoints=[
            atomic_bomb_engine.endpoint(
                name="test-file",
                url="http://127.0.0.1:8888/upload",
                method="post",
                weight=100,
                multipart_options=[atomic_bomb_engine.multipart_option(form_key="file", path="./ui.py", file_name="ui.py", mime="text/plain")],
                assert_options=[
                    atomic_bomb_engine.assert_option(jsonpath="$.message", reference_object="File uploaded successfully!"),
                ],
                think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),
            ),]
```

## [0.39.0] - 2024-05-15
### Added
- 启用BatchRunner类,每次执行可以返回一个迭代器
- 废除run_batch方法
- 废除ResultsIter迭代器

## [0.40.0] - 2024-05-16
### Added
- 将rps统计改为滑动窗口的形式

## [0.41.0] - 2024-05-20
### Added
- run方法增加指数滑动平均参数: ema_alpha
  - 参数为0-1之间的一个浮点数
  - 参数为0时不启用
  - 数值越大越平滑,但是失真越多
  - 建议使用0.1以下

## bug和需求
- 如果发现了bug,把复现步骤一起写到Issus中哈
- 如果有需求也可以在Issues中讨论
- 本程序是本人业余时间开发,不太准备保证时效性,但是如果有时间,一定第一时间回复和修改bug

## TODO
- [x] 前端展示页面 ✅
- [x] 接口关联 ✅
- [x] 每个接口可以配置思考时间 ✅
- [x] 增加form支持 ✅
- [ ] 增加代理支持
- [x] 增加附件支持 ✅
- [ ] 断言支持不等于等更多表达方式

## 联系方式
- 邮箱:[qyzhg@qyzhg.com](mailto:qyzhg@qyzhg.com)
- 微信:qy-zhg

## 👏🏻👏🏻👏🏻欢迎加群交流
![img.png](img/img.png)


            

Raw data

            {
    "_id": null,
    "home_page": null,
    "name": "atomic-bomb-engine",
    "maintainer": null,
    "docs_url": null,
    "requires_python": null,
    "maintainer_email": null,
    "keywords": "rust, python, binding",
    "author": null,
    "author_email": "qyzhg <qyzhg@qyzhg.com>",
    "download_url": null,
    "platform": null,
    "description": "# atomic-bomb-engine-py\n#### [atomic-bomb-engine](https://github.com/we-lsp/atomic-bomb-engine)\u7684python\u5305\u88c5\u5b9e\u73b0\n\n<img src=\"img/atomic-bomb-engine-logo.png\" width=\"350px\" height=\"350px\" alt=\"logo\">\n\n\n## \u524d\u7aef\u4ed3\u5e93\n#### [atomic-bomb-engine-front](https://github.com/GiantAxeWhy/atomic-bomb-engine-front)\n\n## \u4f7f\u7528\u6761\u4ef6\uff1a\n- python\u7248\u672c >= 3.8\n- windows(x86), linux(x86), mac\n\n## \u4f7f\u7528\u65b9\u6cd5\uff1a\n- ### \u51c6\u5907\u5f00\u59cb\n\u901a\u8fc7pip\u5b89\u88c5 \uff080.5.0\u7248\u672c\u4e4b\u524d\uff09\n```shell\npip install atomic-bomb-engine-py\n```\n\u5728python\u4e2d\u5f15\u7528\u65f6\u6ce8\u610f\uff0c\u9700\u8981\u5f15\u7528atomic_bomb_engine, \u800c\u4e0d\u662fatomic_bomb_engine_py\n<br/> \u4e3a\u4e86\u907f\u514d\u6df7\u6dc6\uff0c0.5.0\u7248\u672c\u4e4b\u540e\uff0cpip\u66f4\u6362\u4e86\u5305\u540d\uff0c\u66f4\u6539\u4e3aatomic-bomb-engine\uff0c\n```shell\npip install atomic-bomb-engine\n```\n\u5728python\u4e2d\u5bfc\u5165\n```python\nimport atomic_bomb_engine\n```\n\u5f02\u6b65\u4f7f\u7528\u7684\u65f6\u5019\uff0c\u8fd8\u9700\u8981\u5f15\u7528asyncio\n```python\nimport asyncio\n```\n- ### \u5f00\u59cb\u538b\u6d4b\n  - ~~\u5355\u63a5\u53e3\u538b\u6d4b~~ \uff08\u529f\u80fd\u4e0e\u591a\u63a5\u53e3\u538b\u6d4b\u91cd\u53e0\uff0c\u5df2\u5e9f\u9664\uff09\n\n  - \u591a\u63a5\u53e3\u538b\u6d4b\n\n\u591a\u63a5\u53e3\u538b\u6d4b\u53ef\u4ee5\u5148\u4f7f\u7528\n```python \nrunner = atomic_bomb_engine.BatchRunner()\n```\n\u5b9e\u4f8b\u5316\u4e00\u4e2arunner\u7c7b\n\u901a\u8fc7runner\u7c7b\u4e2d\u7684run\u65b9\u6cd5\u5f00\u542f\u538b\u6d4b\nrun\u65b9\u6cd5\u51fd\u6570\u7b7e\u540d\u5982\u4e0b\n```python\ndef run(\n         self,\n         test_duration_secs: int,\n         concurrent_requests: int,\n         api_endpoints:List[Dict],\n         step_option:Dict[str, int]|None=None,\n         setup_options:List[Dict[str, Any]]|None=None,\n         verbose:bool=False,\n         should_prevent:bool=False,\n         assert_channel_buffer_size:int=1024,\n         timeout_secs=0,\n         cookie_store_enable=True\n    ) -> None:\n        \"\"\"\n            \u6279\u91cf\u538b\u6d4b\n            :param test_duration_secs: \u6d4b\u8bd5\u6301\u7eed\u65f6\u95f4\n            :param concurrent_requests: \u5e76\u53d1\u6570\n            :param api_endpoints: \u63a5\u53e3\u4fe1\u606f\n            :param step_option: \u9636\u68af\u52a0\u538b\u9009\u9879\n            :param setup_options: \u521d\u59cb\u5316\u9009\u9879\n            :param verbose: \u6253\u5370\u8be6\u7ec6\u4fe1\u606f\n            :param should_prevent: \u662f\u5426\u7981\u7528\u7761\u7720\n            :param assert_channel_buffer_size: \u65ad\u8a00\u961f\u5217buffer\u5927\u5c0f\n            :param timeout_secs: http\u8d85\u65f6\u65f6\u95f4\n            :param cookie_store_enable: \u662f\u5426\u4e3a\u5ba2\u6237\u7aef\u542f\u7528\u6301\u4e45\u6027cookie\u5b58\u50a8\u3002\n        \"\"\"\n```\n\n\u4f7f\u7528assert_option\u65b9\u6cd5\u53ef\u4ee5\u8fd4\u56de\u65ad\u8a00\u9009\u9879\u5b57\u5178\n```python\nassert_options=[\natomic_bomb_engine.assert_option(\"$.code\", 429),\natomic_bomb_engine.assert_option(\"$.code\", 200)\n])\n```\njsonpath\u5982\u679c\u4e0d\u4f1a\u7528\u7684\u8bdd\uff0c\u5efa\u8bae\u53bb[jsonpath](https://jsonpath.com/)\u5b66\u4e60\n\n\u4f7f\u7528step_option\u65b9\u6cd5\u53ef\u4ee5\u8fd4\u56de\u9636\u68af\u52a0\u538b\u9009\u9879\u5b57\u5178\n```python\ndef step_option(increase_step: int, increase_interval: int) -> Dict[str, int]:\n    \"\"\"\n    \u751f\u6210step option\n    :param increase_step: \u9636\u68af\u6b65\u957f\n    :param increase_interval: \u9636\u68af\u95f4\u9694\n    \"\"\"\n```\n\n\u540c\u6837\u7684\u672c\u5305\u4e2d\u4e5f\u5305\u542b\u4e86\u4e00\u4e2a\u5bf9api_endpoint\u7684\u5305\u88c5\uff1aendpoint\u65b9\u6cd5\uff0c\u65b9\u4fbf\u8c03\u7528\uff0cendpoint\u4e2d\u7684assert_options\u4e2d\u4e5f\u53ef\u4ee5\u5957\u7528assert_option\u65b9\u6cd5\n ```python\nasync def run_batch():\n  result = await atomic_bomb_engine.batch_async(\n    # \u6d4b\u8bd5\u6301\u7eed\u65f6\u95f4\n    test_duration_secs=60,\n    # \u5e76\u53d1\u91cf\n    concurrent_requests=200,\n    # \u9636\u68af\u8bbe\u7f6e\uff08\u6bcf5\u79d2\u589e\u52a030\u4e2a\u5e76\u53d1\uff09\n    step_option=atomic_bomb_engine.step_option(increase_step=30, increase_interval=5),\n    # \u63a5\u53e3\u8d85\u65f6\u65f6\u95f4\n    timeout_secs=10,\n    # \u662f\u5426\u5f00\u542f\u5ba2\u6237\u7aef\u542f\u7528\u6301\u4e45\u6027cookie\u5b58\u50a8\n    cookie_store_enable=True,\n    # \u5168\u5c40\u521d\u59cb\u5316\n    setup_options=[\n      atomic_bomb_engine.setup_option(\n        name=\"\u521d\u59cb\u5316-1\",\n        url=\"http://localhost:8080/setup\",\n        method=\"get\",\n        jsonpath_extract=[\n          atomic_bomb_engine.jsonpath_extract_option(key=\"test-msg\", jsonpath=\"$.msg\"),\n          atomic_bomb_engine.jsonpath_extract_option(key=\"test-code\", jsonpath=\"$.code\"),\n        ]\n      )],\n    # \u662f\u5426\u5f00\u542f\u8be6\u7ec6\u65e5\u5fd7\n    verbose=False,\n    # \u88ab\u538b\u63a5\u53e3\u8bbe\u7f6e\n    api_endpoints=[\n      atomic_bomb_engine.endpoint(\n        # \u63a5\u53e3\u4efb\u52a1\u547d\u540d\n        name=\"test-1\",\n        # \u9488\u5bf9\u6bcf\u4e2a\u63a5\u53e3\u521d\u59cb\u5316\n        setup_options=[\n          atomic_bomb_engine.setup_option(\n            name=\"api-\u521d\u59cb\u5316-1\",\n            url=\"http://localhost:8080/api_setup\",\n            method=\"get\",\n            jsonpath_extract=[\n              atomic_bomb_engine.jsonpath_extract_option(key=\"api-test-msg-1\", jsonpath=\"$.msg\"),\n              atomic_bomb_engine.jsonpath_extract_option(key=\"api-test-code-1\", jsonpath=\"$.code\"),\n            ]\n          )\n        ],\n        # \u88ab\u538b\u63a5\u53e3url\n        url=\"http://localhost:8080/direct\",\n        # \u8bf7\u6c42\u65b9\u5f0f\n        method=\"POST\",\n        # \u6743\u91cd\n        weight=1,\n        # \u53d1\u9001json\u8bf7\u6c42\n        json={\"name\": \"{{api-test-msg-1}}\", \"number\": 1},\n        # \u65ad\u8a00\u9009\u9879\n        assert_options=[\n          atomic_bomb_engine.assert_option(jsonpath=\"$.number\", reference_object=1),\n        ],\n        # \u601d\u8003\u65f6\u95f4\u9009\u9879\uff08\u5728\u6700\u5927\u548c\u6700\u5c0f\u4e4b\u95f4\u968f\u673a\uff0c\u5355\u4f4d\u6beb\u79d2\uff09\n        think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),\n      ),\n    ])\n  print(result)\n  return result\n ```\n    \n\u76d1\u542c\u65f6\u53ef\u4ee5\u5728\u4f7f\u7528\u5b8crun\u65b9\u6cd5\u540e\uff0c\u7ee7\u7eed\u8fed\u4ee3runner\u5373\u53ef\n\n\u538b\u6d4b+\u540c\u65f6\u76d1\u542c\n\n```python \nimport asyncio\n\n\nasync def batch_async():\n  runner = atomic_bomb_engine.BatchRunner()\n  runner.run(\n    test_duration_secs=30,\n    concurrent_requests=30,\n    step_option=atomic_bomb_engine.step_option(increase_step=3, increase_interval=3),\n    timeout_secs=15,\n    cookie_store_enable=True,\n    verbose=False,\n    api_endpoints=[\n      atomic_bomb_engine.endpoint(\n        name=\"test-1\",\n        url=\"http://127.0.0.1:8080/direct\",\n        method=\"POST\",\n        json={\"name\": \"test-1\", \"number\": 1},\n        weight=100,\n        assert_options=[\n          atomic_bomb_engine.assert_option(jsonpath=\"$.msg\", reference_object=\"\u64cd\u4f5c\u6210\u529f\"),\n        ],\n      ),\n    ])\n  return runner\n\n\nasync def main():\n  results = await batch_async()\n  for res in results:\n    if res.get(\"should_wait\"):\n      await asyncio.sleep(0.1)\n    print(res)\n\n\nif __name__ == '__main__':\n  asyncio.run(main())\n```\n\n# \u538b\u6d4b\u65f6\u4f7f\u7528ui\u754c\u9762\u76d1\u63a7\n\n0.5.0\u7248\u672c\u540e\uff0c\u6dfb\u52a0\u4e86ui\u9875\u9762\uff0c\u652f\u6301\u6279\u91cf\u538b\u6d4b\u65b9\u6cd5\n<br/>\u5bfc\u5165\n```python\nfrom atomic_bomb_engine import server\n```\n\u4f7f\u7528\n```python\nimport asyncio\n\nimport atomic_bomb_engine\nfrom atomic_bomb_engine import server\n\n\n@server.ui(port=8000)\nasync def batch_async():\n    runner = atomic_bomb_engine.BatchRunner()\n    runner.run(\n      # \u6d4b\u8bd5\u6301\u7eed\u65f6\u95f4\n      test_duration_secs=60,\n      # \u5e76\u53d1\u91cf\n      concurrent_requests=200,\n      # \u9636\u68af\u8bbe\u7f6e\uff08\u6bcf5\u79d2\u589e\u52a030\u4e2a\u5e76\u53d1\uff09\n      step_option=atomic_bomb_engine.step_option(increase_step=30, increase_interval=5),\n      # \u63a5\u53e3\u8d85\u65f6\u65f6\u95f4\n      timeout_secs=10,\n      # \u662f\u5426\u5f00\u542f\u5ba2\u6237\u7aef\u542f\u7528\u6301\u4e45\u6027cookie\u5b58\u50a8\n      cookie_store_enable=True,\n      # \u5168\u5c40\u521d\u59cb\u5316\n      setup_options=[\n        atomic_bomb_engine.setup_option(\n          name=\"\u521d\u59cb\u5316-1\",\n          url=\"http://localhost:8080/setup\",\n          method=\"get\",\n          jsonpath_extract=[\n            atomic_bomb_engine.jsonpath_extract_option(key=\"test-msg\", jsonpath=\"$.msg\"),\n            atomic_bomb_engine.jsonpath_extract_option(key=\"test-code\", jsonpath=\"$.code\"),\n          ]\n        )],\n      # \u662f\u5426\u5f00\u542f\u8be6\u7ec6\u65e5\u5fd7\n      verbose=False,\n      # \u88ab\u538b\u63a5\u53e3\u8bbe\u7f6e\n      api_endpoints=[\n        atomic_bomb_engine.endpoint(\n          # \u63a5\u53e3\u4efb\u52a1\u547d\u540d\n          name=\"test-1\",\n          # \u9488\u5bf9\u6bcf\u4e2a\u63a5\u53e3\u521d\u59cb\u5316\n          setup_options=[\n            atomic_bomb_engine.setup_option(\n              name=\"api-\u521d\u59cb\u5316-1\",\n              url=\"http://localhost:8080/api_setup\",\n              method=\"get\",\n              jsonpath_extract=[\n                atomic_bomb_engine.jsonpath_extract_option(key=\"api-test-msg-1\", jsonpath=\"$.msg\"),\n                atomic_bomb_engine.jsonpath_extract_option(key=\"api-test-code-1\", jsonpath=\"$.code\"),\n              ]\n            )\n          ],\n          # \u88ab\u538b\u63a5\u53e3url\n          url=\"http://localhost:8080/direct\",\n          # \u8bf7\u6c42\u65b9\u5f0f\n          method=\"POST\",\n          # \u6743\u91cd\n          weight=1,\n          # \u53d1\u9001json\u8bf7\u6c42\n          json={\"name\": \"{{api-test-msg-1}}\", \"number\": 1},\n          # \u65ad\u8a00\u9009\u9879\n          assert_options=[\n            atomic_bomb_engine.assert_option(jsonpath=\"$.number\", reference_object=1),\n          ],\n          # \u601d\u8003\u65f6\u95f4\u9009\u9879\uff08\u5728\u6700\u5927\u548c\u6700\u5c0f\u4e4b\u95f4\u968f\u673a\uff0c\u5355\u4f4d\u6beb\u79d2\uff09\n          think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),\n        ),\n      ])\n    return runner\n\n\nif __name__ == '__main__':\n    asyncio.run(batch_async())\n```\n\n\u4f7f\u7528server.ui\u88c5\u9970\u5668\uff0c\u53ef\u4ee5\u7ed9\u6279\u91cf\u538b\u6d4b\u65b9\u6cd5\u542f\u52a8\u4e00\u4e2a\u7b80\u5355\u7684web\u670d\u52a1\u5668\uff0c\u4e0d\u9700\u8981\u518d\u624b\u52a8\u76d1\u542cBatchListenIter\u751f\u6210\u5668\n\n## \u5185\u90e8\u67b6\u6784\u56fe\n![architecture.png](img/architecture.png)\n\n## [0.19.0] - 2024-04-16\n### Added\n- \u589e\u52a0\u4e86\u521d\u59cb\u5316\u548c\u53c2\u6570\u6a21\u7248\u529f\u80fd\n```python\nsetup_options=[\n  atomic_bomb_engine.setup_option(\n    name=\"\u521d\u59cb\u5316-1\",\n    url=\"http://localhost:8080/setup\",\n    method=\"get\",\n    jsonpath_extract=[\n      atomic_bomb_engine.jsonpath_extract_option(key=\"test-msg\", jsonpath=\"$.msg\"),\n      atomic_bomb_engine.jsonpath_extract_option(key=\"test-code\", jsonpath=\"$.code\"),\n    ]\n  )]\n```\n\u4e0a\u8ff0\u5b9e\u4f8b\u5c55\u793a\u4e86\u5982\u4f55\u5728\u521d\u59cb\u5316\u7684\u65f6\u5019\u8c03\u7528\u67d0\u4e2a\u63a5\u53e3\uff0c\u5e76\u4e14\u901a\u8fc7jsonpath\u5c06\u6570\u636e\u63d0\u53d6\u51fa\u6765\uff0c\u4fdd\u5b58\u5728\u5168\u5c40\u53d8\u91cftest-msg\u548ctest-code\u4e2d\n\u63d0\u53d6\u5b8c\u5168\u5c40\u53d8\u91cf\u540e\uff0c\u5c31\u53ef\u4ee5\u5728\u540e\u7eed\u7684api_endpoints\u4e2d\u4f7f\u7528\n```python\napi_endpoints=[\n  atomic_bomb_engine.endpoint(\n    # \u63a5\u53e3\u4efb\u52a1\u547d\u540d\n    name=\"test-1\",\n    # \u9488\u5bf9\u6bcf\u4e2a\u63a5\u53e3\u521d\u59cb\u5316\n    setup_options=[\n      atomic_bomb_engine.setup_option(\n        name=\"api-\u521d\u59cb\u5316-1\",\n        url=\"http://localhost:8080/api_setup\",\n        method=\"get\",\n        jsonpath_extract=[\n          atomic_bomb_engine.jsonpath_extract_option(key=\"api-test-msg-1\", jsonpath=\"$.msg\"),\n          atomic_bomb_engine.jsonpath_extract_option(key=\"api-test-code-1\", jsonpath=\"$.code\"),\n        ]\n      )\n    ],\n    # \u88ab\u538b\u63a5\u53e3url\n    url=\"http://localhost:8080/direct\",\n    # \u8bf7\u6c42\u65b9\u5f0f\n    method=\"POST\",\n    # \u6743\u91cd\n    weight=1,\n    # \u53d1\u9001json\u8bf7\u6c42\n    json={\"name\": \"{{api-test-msg-1}}\", \"number\": 1},\n    # \u65ad\u8a00\u9009\u9879\n    assert_options=[\n      atomic_bomb_engine.assert_option(jsonpath=\"$.number\", reference_object=1),\n    ],\n    # \u601d\u8003\u65f6\u95f4\u9009\u9879\uff08\u5728\u6700\u5927\u548c\u6700\u5c0f\u4e4b\u95f4\u968f\u673a\uff0c\u5355\u4f4d\u6beb\u79d2\uff09\n    think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),\n  ),\n]\n```\n\u4e0a\u8ff0\u5b9e\u4f8b\u5c55\u793a\u4e86\u5982\u4f55\u5728\u8bf7\u6c42\u4e2d\u4f7f\u7528\u5168\u5c40\u53d8\u91cf\uff0c\u4f7f\u7528\u53cc\u5927\u62ec\u53f7\u5373\u53ef\u4f7f\u7528\n\n### Fixed\n- \u4fee\u590d\u4e86\u5982\u679chttp\u72b6\u6001\u7801\u9519\u8bef\u65f6\uff0c\u4e0d\u4f1a\u8bb0\u5f55\n- \u4fee\u590d\u4e86json\u53cd\u5e8f\u5217\u5316\u7684\u95ee\u9898\n\n## [0.20.0] - 2024-04-17\n### Added\n\u65ad\u8a00\u66f4\u6539\u4e3a\u5f02\u6b65\u751f\u4ea7\u6d88\u8d39\uff0c\u63d0\u5347\u6027\u80fd\n\n## bug\u548c\u9700\u6c42\n- \u5982\u679c\u53d1\u73b0\u4e86bug\uff0c\u628a\u590d\u73b0\u6b65\u9aa4\u4e00\u8d77\u5199\u5230Issus\u4e2d\u54c8\n- \u5982\u679c\u6709\u9700\u6c42\u4e5f\u53ef\u4ee5\u5728Issues\u4e2d\u8ba8\u8bba\n- \u672c\u7a0b\u5e8f\u662f\u672c\u4eba\u4e1a\u4f59\u65f6\u95f4\u5f00\u53d1\uff0c\u4e0d\u592a\u51c6\u5907\u4fdd\u8bc1\u65f6\u6548\u6027\uff0c\u4f46\u662f\u5982\u679c\u6709\u65f6\u95f4\uff0c\u4e00\u5b9a\u7b2c\u4e00\u65f6\u95f4\u56de\u590d\u548c\u4fee\u6539bug\n\n## [0.22.0] - 2024-04-18\n### Added\n\u524d\u7aef\u8fdb\u884c\u4e86\u6027\u80fd\u4f18\u5316\n\n## [0.24.0] - 2024-04-22\n### Added\n\u5f02\u6b65\u65ad\u8a00\u4f7f\u7528\u4e86\u8865\u507f\u6d88\u606f\uff0c\u4fdd\u8bc1\u6d88\u606f\u7684\u4e00\u81f4\u6027\n\n## [0.25.0] - 2024-04-23\n### Added\n\u5728endpoints\u4e2d\u589e\u52a0\u601d\u8003\u65f6\u95f4,\u6a21\u62df\u7528\u6237\u884c\u4e3a\n```python\nthink_time_option(min_millis=200, max_millis=300)\n```\n  - min_millis:\u6700\u5c0f\u601d\u8003\u65f6\u95f4(\u6beb\u79d2)\n  - max_millis:\u6700\u5927\u601d\u8003\u65f6\u95f4(\u6beb\u79d2)\n\n\u4f7f\u7528\u65f6\u5728endpoint\u4e2d\u589e\u52a0think_time_option\u53c2\u6570\n\n```python\napi_endpoints=[\n  atomic_bomb_engine.endpoint(\n    name=\"test-1\",\n    url=\"http://localhost:8080/a\",\n    method=\"POST\",\n    weight=1,\n    timeout_secs=10,\n    json={\"name\": \"{{test-msg}}\", \"number\": \"{{test-code}}\"},\n    think_time_option=atomic_bomb_engine.think_time_option(min_millis=200, max_millis=300),\n  ),\n]\n```\n\n## [0.26.0] - 2024-04-24\n### Added\n- \u589e\u52a0endpoint\u4e2d\u7684setup\uff0c\u5728\u5e76\u53d1\u4e2d\u53ef\u4ee5\u505a\u63a5\u53e3\u65ad\u8a00\n- \u589e\u52a0\u6709\u5173\u8054\u6761\u4ef6\u4e0b\u7684cookie\u81ea\u52a8\u7ba1\u7406\u529f\u80fd\n```python\natomic_bomb_engine.endpoint(\n  # \u63a5\u53e3\u4efb\u52a1\u547d\u540d\n  name=\"test-1\",\n  # \u9488\u5bf9\u6bcf\u4e2a\u63a5\u53e3\u521d\u59cb\u5316\n  setup_options=[\n    atomic_bomb_engine.setup_option(\n      name=\"api-\u521d\u59cb\u5316-1\",\n      url=\"http://localhost:8080/api_setup\",\n      method=\"get\",\n      jsonpath_extract=[\n        atomic_bomb_engine.jsonpath_extract_option(key=\"api-test-msg-1\", jsonpath=\"$.msg\"),\n        atomic_bomb_engine.jsonpath_extract_option(key=\"api-test-code-1\", jsonpath=\"$.code\"),\n      ]\n    )\n  ],\n  # \u88ab\u538b\u63a5\u53e3url\n  url=\"http://localhost:8080/direct\",\n  # \u8bf7\u6c42\u65b9\u5f0f\n  method=\"POST\",\n  # \u6743\u91cd\n  weight=1,\n  # \u53d1\u9001json\u8bf7\u6c42\n  json={\"name\": \"{{api-test-msg-1}}\", \"number\": 1},\n  # \u65ad\u8a00\u9009\u9879\n  assert_options=[\n    atomic_bomb_engine.assert_option(jsonpath=\"$.number\", reference_object=1),\n  ],\n  # \u601d\u8003\u65f6\u95f4\u9009\u9879\uff08\u5728\u6700\u5927\u548c\u6700\u5c0f\u4e4b\u95f4\u968f\u673a\uff0c\u5355\u4f4d\u6beb\u79d2\uff09\n  think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),\n)\n```\n- \u53c2\u6570cookie_store_enable\u63a7\u5236\u662f\u5426\u81ea\u52a8\u7ba1\u7406cookie\uff0c\u524d\u7f6e\u6761\u4ef6\u7684cookie\u4f1a\u5e26\u5165\u5230\u6700\u7ec8\u7684\u538b\u6d4b\u63a5\u53e3\u4e2d\n- \u5728endpoint\u4e2d\u4f7f\u7528setup_options\u53ef\u4ee5\u4f20\u5165\u591a\u4e2a\u63a5\u53e3\uff0c\u5e76\u4e14\u63d0\u53d6\u53c2\u6570\n- \u63d0\u53d6\u5230\u7684\u53c2\u6570\u5982\u679c\u548c\u5168\u5c40\u7684setup\u7684key\u51b2\u7a81\uff0c\u4f1a\u8986\u76d6\u5168\u5c40\u63d0\u53d6\u5230\u7684\u53c2\u6570\n- \u63a5\u53e3\u4e2d\u63d0\u53d6\u7684\u53c2\u6570\u53ea\u80fd\u5728\u672c\u7ebf\u7a0b\uff08v-user\uff09\u4e2d\u4f7f\u7528\n- \u26a0\ufe0f \u4f7f\u7528\u65f6\u6ce8\u610f:setup_options\u662f\u987a\u5e8f\u6267\u884c\u7684\uff0c\u6ca1\u6709\u5e76\u53d1\uff0c\u4f46\u662f\u76f8\u5f53\u4e8e\u6dfb\u52a0\u4e86think time\n\n## [0.28.0] - 2024-04-25\n### Added\n- \u5c06\u6301\u4e45\u5316cookie\u6dfb\u52a0\u5230\u5168\u5c40\u9009\u9879\u4e2d\n- \u590d\u7528http client\n- \u9009\u62e9\u6027\u5f00\u542f\u65ad\u8a00\u4efb\u52a1\n- \u63a5\u53e3\u521d\u59cb\u5316\u65f6\u51fa\u73b0\u9519\u8bef\u7b49\u5f85\u540e\u91cd\u8bd5##\n\n## [0.29.0] - 2024-04-25\n### Added\n- \u4f18\u5316\u5e76\u53d1\u903b\u8f91\n- \u524d\u7aef\u66f4\u6539\u4e3aweb worker\u53d1\u9001\u5fc3\u8df3\n\n## [0.38.0] - 2024-05-7\n### Added\n- \u589e\u52a0\u9644\u4ef6\u4e0a\u4f20\u529f\u80fd\n  - \u5728\u521d\u59cb\u5316\u548c\u6bcf\u4e2a\u63a5\u53e3\u4e2d\u589e\u52a0\u4e86multipart_options\u53c2\u6570\u7528\u4e8e\u9644\u4ef6\u4e0a\u4f20\n  - \u589e\u52a0multipart_option\u65b9\u6cd5\u5c01\u88c5\u9644\u4ef6\u53c2\u6570\n    - form_key: form\u8868\u5355\u7684key\n    - path: \u9644\u4ef6\u8def\u5f84\n    - file_name: \u9644\u4ef6\u540d\n    - mime: \u9644\u4ef6\u7c7b\u578b (\u7c7b\u578b\u53ef\u4ee5\u53c2\u8003[\u8fd9\u91cc](https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Basics_of_HTTP/MIME_types/Common_types))\n```python\napi_endpoints=[\n            atomic_bomb_engine.endpoint(\n                name=\"test-file\",\n                url=\"http://127.0.0.1:8888/upload\",\n                method=\"post\",\n                weight=100,\n                multipart_options=[atomic_bomb_engine.multipart_option(form_key=\"file\", path=\"./ui.py\", file_name=\"ui.py\", mime=\"text/plain\")],\n                assert_options=[\n                    atomic_bomb_engine.assert_option(jsonpath=\"$.message\", reference_object=\"File uploaded successfully!\"),\n                ],\n                think_time_option=atomic_bomb_engine.think_time_option(min_millis=500, max_millis=1200),\n            ),]\n```\n\n## [0.39.0] - 2024-05-15\n### Added\n- \u542f\u7528BatchRunner\u7c7b\uff0c\u6bcf\u6b21\u6267\u884c\u53ef\u4ee5\u8fd4\u56de\u4e00\u4e2a\u8fed\u4ee3\u5668\n- \u5e9f\u9664run_batch\u65b9\u6cd5\n- \u5e9f\u9664ResultsIter\u8fed\u4ee3\u5668\n\n## [0.40.0] - 2024-05-16\n### Added\n- \u5c06rps\u7edf\u8ba1\u6539\u4e3a\u6ed1\u52a8\u7a97\u53e3\u7684\u5f62\u5f0f\n\n## [0.41.0] - 2024-05-20\n### Added\n- run\u65b9\u6cd5\u589e\u52a0\u6307\u6570\u6ed1\u52a8\u5e73\u5747\u53c2\u6570: ema_alpha\n  - \u53c2\u6570\u4e3a0-1\u4e4b\u95f4\u7684\u4e00\u4e2a\u6d6e\u70b9\u6570\n  - \u53c2\u6570\u4e3a0\u65f6\u4e0d\u542f\u7528\n  - \u6570\u503c\u8d8a\u5927\u8d8a\u5e73\u6ed1\uff0c\u4f46\u662f\u5931\u771f\u8d8a\u591a\n  - \u5efa\u8bae\u4f7f\u75280.1\u4ee5\u4e0b\n\n## bug\u548c\u9700\u6c42\n- \u5982\u679c\u53d1\u73b0\u4e86bug\uff0c\u628a\u590d\u73b0\u6b65\u9aa4\u4e00\u8d77\u5199\u5230Issus\u4e2d\u54c8\n- \u5982\u679c\u6709\u9700\u6c42\u4e5f\u53ef\u4ee5\u5728Issues\u4e2d\u8ba8\u8bba\n- \u672c\u7a0b\u5e8f\u662f\u672c\u4eba\u4e1a\u4f59\u65f6\u95f4\u5f00\u53d1\uff0c\u4e0d\u592a\u51c6\u5907\u4fdd\u8bc1\u65f6\u6548\u6027\uff0c\u4f46\u662f\u5982\u679c\u6709\u65f6\u95f4\uff0c\u4e00\u5b9a\u7b2c\u4e00\u65f6\u95f4\u56de\u590d\u548c\u4fee\u6539bug\n\n## TODO\n- [x] \u524d\u7aef\u5c55\u793a\u9875\u9762 \u2705\n- [x] \u63a5\u53e3\u5173\u8054 \u2705\n- [x] \u6bcf\u4e2a\u63a5\u53e3\u53ef\u4ee5\u914d\u7f6e\u601d\u8003\u65f6\u95f4 \u2705\n- [x] \u589e\u52a0form\u652f\u6301 \u2705\n- [ ] \u589e\u52a0\u4ee3\u7406\u652f\u6301\n- [x] \u589e\u52a0\u9644\u4ef6\u652f\u6301 \u2705\n- [ ] \u65ad\u8a00\u652f\u6301\u4e0d\u7b49\u4e8e\u7b49\u66f4\u591a\u8868\u8fbe\u65b9\u5f0f\n\n## \u8054\u7cfb\u65b9\u5f0f\n- \u90ae\u7bb1:[qyzhg@qyzhg.com](mailto:qyzhg@qyzhg.com)\n- \u5fae\u4fe1:qy-zhg\n\n## \ud83d\udc4f\ud83c\udffb\ud83d\udc4f\ud83c\udffb\ud83d\udc4f\ud83c\udffb\u6b22\u8fce\u52a0\u7fa4\u4ea4\u6d41\n![img.png](img/img.png)\n\n",
    "bugtrack_url": null,
    "license": "MIT",
    "summary": "\u4f7f\u7528rust\u5f00\u53d1\u7684\u9ad8\u6027\u80fdpython\u538b\u6d4b\u5de5\u5177",
    "version": "0.41.3",
    "project_urls": null,
    "split_keywords": [
        "rust",
        " python",
        " binding"
    ],
    "urls": [
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "e34b276414768cce33d55725c83782c2a6013d286fedcb8d35a3182501da0289",
                "md5": "5214d24640edcc88307f19cb1937390e",
                "sha256": "99c61130ae84da4f4cfc7748a338b729f2289cd8f6905369335cd01965b8bdb9"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp310-cp310-macosx_10_12_x86_64.whl",
            "has_sig": false,
            "md5_digest": "5214d24640edcc88307f19cb1937390e",
            "packagetype": "bdist_wheel",
            "python_version": "cp310",
            "requires_python": null,
            "size": 3699220,
            "upload_time": "2024-08-19T15:12:58",
            "upload_time_iso_8601": "2024-08-19T15:12:58.823793Z",
            "url": "https://files.pythonhosted.org/packages/e3/4b/276414768cce33d55725c83782c2a6013d286fedcb8d35a3182501da0289/atomic_bomb_engine-0.41.3-cp310-cp310-macosx_10_12_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "054d2cde9d279533b02284b3b02d8d7cd37679270531b51d49205839fe40cf63",
                "md5": "749248604248ad487badf5509e71aaed",
                "sha256": "9206804a1a93361293271022f193e1c012169f91c406567b7d41e06769aa7aca"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp310-cp310-macosx_11_0_arm64.whl",
            "has_sig": false,
            "md5_digest": "749248604248ad487badf5509e71aaed",
            "packagetype": "bdist_wheel",
            "python_version": "cp310",
            "requires_python": null,
            "size": 3634433,
            "upload_time": "2024-08-19T15:11:54",
            "upload_time_iso_8601": "2024-08-19T15:11:54.195354Z",
            "url": "https://files.pythonhosted.org/packages/05/4d/2cde9d279533b02284b3b02d8d7cd37679270531b51d49205839fe40cf63/atomic_bomb_engine-0.41.3-cp310-cp310-macosx_11_0_arm64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "5f96bdfb489a088a3f55900b3a90bbd5522e9b3affcc1d74e60bdd783e29bce0",
                "md5": "a677da2910b3bb9556643cf2441c6eac",
                "sha256": "9d3d7a0fbd1a7628c1552ef2cac3642c21306c84acbba7d3bc10f9d4f3405fc3"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp310-cp310-manylinux_2_34_x86_64.whl",
            "has_sig": false,
            "md5_digest": "a677da2910b3bb9556643cf2441c6eac",
            "packagetype": "bdist_wheel",
            "python_version": "cp310",
            "requires_python": null,
            "size": 6047312,
            "upload_time": "2024-08-19T15:14:51",
            "upload_time_iso_8601": "2024-08-19T15:14:51.925694Z",
            "url": "https://files.pythonhosted.org/packages/5f/96/bdfb489a088a3f55900b3a90bbd5522e9b3affcc1d74e60bdd783e29bce0/atomic_bomb_engine-0.41.3-cp310-cp310-manylinux_2_34_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "ab04f5210e3c09b1c1a9ca743ab400de1dbd4d8d5a7dc35b7c9ce5b71f0cde35",
                "md5": "f75919e877ed09be5c07f05e35996204",
                "sha256": "23531fcbce6117fb13711077944b0f6e3485d66e1564db03812c69efe4616b58"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp310-cp310-musllinux_1_2_x86_64.whl",
            "has_sig": false,
            "md5_digest": "f75919e877ed09be5c07f05e35996204",
            "packagetype": "bdist_wheel",
            "python_version": "cp310",
            "requires_python": null,
            "size": 4647416,
            "upload_time": "2024-08-19T15:13:36",
            "upload_time_iso_8601": "2024-08-19T15:13:36.407230Z",
            "url": "https://files.pythonhosted.org/packages/ab/04/f5210e3c09b1c1a9ca743ab400de1dbd4d8d5a7dc35b7c9ce5b71f0cde35/atomic_bomb_engine-0.41.3-cp310-cp310-musllinux_1_2_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "7f8bf9877966c2279d6e8f8cae7380d9a9fb8f2ccd38f2ff9befe1f6e945da83",
                "md5": "d8f5dde4b7e92b17b87f88b09bc1a356",
                "sha256": "52c31b671ebda64f9eec0ab2a78f185b505a0818d2793004211da33431685374"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp310-none-win_amd64.whl",
            "has_sig": false,
            "md5_digest": "d8f5dde4b7e92b17b87f88b09bc1a356",
            "packagetype": "bdist_wheel",
            "python_version": "cp310",
            "requires_python": null,
            "size": 3448319,
            "upload_time": "2024-08-19T15:12:36",
            "upload_time_iso_8601": "2024-08-19T15:12:36.630196Z",
            "url": "https://files.pythonhosted.org/packages/7f/8b/f9877966c2279d6e8f8cae7380d9a9fb8f2ccd38f2ff9befe1f6e945da83/atomic_bomb_engine-0.41.3-cp310-none-win_amd64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "50bfc5be84cdbda4a3e6c295c4600edd51f8e65ceb90106dcef833cfcbf51ae9",
                "md5": "031a1fbce3c39d710bce24cc54df5ae5",
                "sha256": "ac35c1b537b04944a64462f16012248b2ed9254aba464176c69019e1f32f3a11"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp311-cp311-macosx_10_12_x86_64.whl",
            "has_sig": false,
            "md5_digest": "031a1fbce3c39d710bce24cc54df5ae5",
            "packagetype": "bdist_wheel",
            "python_version": "cp311",
            "requires_python": null,
            "size": 3698557,
            "upload_time": "2024-08-19T15:13:32",
            "upload_time_iso_8601": "2024-08-19T15:13:32.798385Z",
            "url": "https://files.pythonhosted.org/packages/50/bf/c5be84cdbda4a3e6c295c4600edd51f8e65ceb90106dcef833cfcbf51ae9/atomic_bomb_engine-0.41.3-cp311-cp311-macosx_10_12_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "0db7414aa2f519f28430b5596aa96c6b215c965af374e7895ea6412bbe2bb126",
                "md5": "1a2359032dfa17bba6fd34f49fb82060",
                "sha256": "42390f7db3d7d9705d4b529b283d92fb4919be3388be758486934ae213f1571d"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp311-cp311-macosx_11_0_arm64.whl",
            "has_sig": false,
            "md5_digest": "1a2359032dfa17bba6fd34f49fb82060",
            "packagetype": "bdist_wheel",
            "python_version": "cp311",
            "requires_python": null,
            "size": 3636585,
            "upload_time": "2024-08-19T15:12:32",
            "upload_time_iso_8601": "2024-08-19T15:12:32.552038Z",
            "url": "https://files.pythonhosted.org/packages/0d/b7/414aa2f519f28430b5596aa96c6b215c965af374e7895ea6412bbe2bb126/atomic_bomb_engine-0.41.3-cp311-cp311-macosx_11_0_arm64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "e2f34c7c730b8650997dbe7483e163bf739e4eaa0d410537297533d9eb398c09",
                "md5": "bf82fac7f262b455f89df84776338cf9",
                "sha256": "e4c3b8bab3e49eb7e2efae18c7f445d3d1791170486b0b76c0ed2d37cc3fac63"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp311-cp311-manylinux_2_34_x86_64.whl",
            "has_sig": false,
            "md5_digest": "bf82fac7f262b455f89df84776338cf9",
            "packagetype": "bdist_wheel",
            "python_version": "cp311",
            "requires_python": null,
            "size": 6047537,
            "upload_time": "2024-08-19T15:14:02",
            "upload_time_iso_8601": "2024-08-19T15:14:02.533264Z",
            "url": "https://files.pythonhosted.org/packages/e2/f3/4c7c730b8650997dbe7483e163bf739e4eaa0d410537297533d9eb398c09/atomic_bomb_engine-0.41.3-cp311-cp311-manylinux_2_34_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "f4f98a3c909f4020ff45cb627afb3db8c94bc05572a294e1cd8aef4fab69eda4",
                "md5": "1cec68e85fd9c53c3a5bbc66fce3242f",
                "sha256": "9cc6a690f1a6ca08577b9e91ae6fae69a959093620ad49d6123169d64edcb2de"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp311-cp311-musllinux_1_2_x86_64.whl",
            "has_sig": false,
            "md5_digest": "1cec68e85fd9c53c3a5bbc66fce3242f",
            "packagetype": "bdist_wheel",
            "python_version": "cp311",
            "requires_python": null,
            "size": 4647335,
            "upload_time": "2024-08-19T15:13:33",
            "upload_time_iso_8601": "2024-08-19T15:13:33.950232Z",
            "url": "https://files.pythonhosted.org/packages/f4/f9/8a3c909f4020ff45cb627afb3db8c94bc05572a294e1cd8aef4fab69eda4/atomic_bomb_engine-0.41.3-cp311-cp311-musllinux_1_2_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "11d9fdca9de9d4bb62bb53f792adb1b11f63fbd27d9a996f8aa5a1f4eea50829",
                "md5": "2c8e14971ed986d8efce5d17d4bd57e0",
                "sha256": "d4a6098e4979202b38b6a9f4d88bcfd6e2574a332059f9e4229a8aecdf9fc647"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp311-none-win_amd64.whl",
            "has_sig": false,
            "md5_digest": "2c8e14971ed986d8efce5d17d4bd57e0",
            "packagetype": "bdist_wheel",
            "python_version": "cp311",
            "requires_python": null,
            "size": 3446533,
            "upload_time": "2024-08-19T15:12:50",
            "upload_time_iso_8601": "2024-08-19T15:12:50.025993Z",
            "url": "https://files.pythonhosted.org/packages/11/d9/fdca9de9d4bb62bb53f792adb1b11f63fbd27d9a996f8aa5a1f4eea50829/atomic_bomb_engine-0.41.3-cp311-none-win_amd64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "7e2acfe21a586951f869cf6e1303e5c7670cdade847762a0bb1f53ff26bc2b02",
                "md5": "7856cdb69db2b20c17286889bcad0208",
                "sha256": "6af17b6562294b0f88b903dcfed3bfedaaae8a478dc2020bfb71fa7ec17031e9"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp312-cp312-macosx_10_12_x86_64.whl",
            "has_sig": false,
            "md5_digest": "7856cdb69db2b20c17286889bcad0208",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": null,
            "size": 3698517,
            "upload_time": "2024-08-19T15:13:12",
            "upload_time_iso_8601": "2024-08-19T15:13:12.184628Z",
            "url": "https://files.pythonhosted.org/packages/7e/2a/cfe21a586951f869cf6e1303e5c7670cdade847762a0bb1f53ff26bc2b02/atomic_bomb_engine-0.41.3-cp312-cp312-macosx_10_12_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "08f01d947775dfb91e1d6d7c8b3fa79a7cac805a524828e9096222ef45ec32a0",
                "md5": "7b6c454d973602cd5ef5eea84337c8c5",
                "sha256": "491e967f8ee63e45ff1b54a2bb3ca01a2895f7a58dfa7b63df5102e1f5ac39f0"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp312-cp312-macosx_11_0_arm64.whl",
            "has_sig": false,
            "md5_digest": "7b6c454d973602cd5ef5eea84337c8c5",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": null,
            "size": 3638628,
            "upload_time": "2024-08-19T15:12:18",
            "upload_time_iso_8601": "2024-08-19T15:12:18.210760Z",
            "url": "https://files.pythonhosted.org/packages/08/f0/1d947775dfb91e1d6d7c8b3fa79a7cac805a524828e9096222ef45ec32a0/atomic_bomb_engine-0.41.3-cp312-cp312-macosx_11_0_arm64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "0e242e699b457b3e3e8a4d6caefcbeb520f4ee992214404e2317cbd0f7f567c1",
                "md5": "e9cd19122a82a46edd2d8e89a8d377f2",
                "sha256": "cfc9bb62938967bee45be591bcd02069f19a24378ddd44b2bbf35d4c014d056a"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp312-cp312-manylinux_2_34_x86_64.whl",
            "has_sig": false,
            "md5_digest": "e9cd19122a82a46edd2d8e89a8d377f2",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": null,
            "size": 6053188,
            "upload_time": "2024-08-19T15:16:20",
            "upload_time_iso_8601": "2024-08-19T15:16:20.216180Z",
            "url": "https://files.pythonhosted.org/packages/0e/24/2e699b457b3e3e8a4d6caefcbeb520f4ee992214404e2317cbd0f7f567c1/atomic_bomb_engine-0.41.3-cp312-cp312-manylinux_2_34_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "80ad221daae17825c3ed8f396c040dc3d27fb5c005f406a3f53019d4f1db69a6",
                "md5": "d286a6f30160ee8bcaa3a2b6adab755d",
                "sha256": "27b3d26ffdd03447120762541728b46a9f2887232f544cac6e2cb43ebb1629b1"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp312-cp312-musllinux_1_2_x86_64.whl",
            "has_sig": false,
            "md5_digest": "d286a6f30160ee8bcaa3a2b6adab755d",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": null,
            "size": 4649365,
            "upload_time": "2024-08-19T15:13:52",
            "upload_time_iso_8601": "2024-08-19T15:13:52.458873Z",
            "url": "https://files.pythonhosted.org/packages/80/ad/221daae17825c3ed8f396c040dc3d27fb5c005f406a3f53019d4f1db69a6/atomic_bomb_engine-0.41.3-cp312-cp312-musllinux_1_2_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "c0bcdedb1893629dc93a4bd3e5761eb2e2d826e8c82078b3a03af734c267f74a",
                "md5": "03d726c0cfcd563396f09ce7064139b4",
                "sha256": "bbd55801d1c4cbb47795b60aeddb99393c63514189de4a23de9b452e2e253148"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp312-none-win_amd64.whl",
            "has_sig": false,
            "md5_digest": "03d726c0cfcd563396f09ce7064139b4",
            "packagetype": "bdist_wheel",
            "python_version": "cp312",
            "requires_python": null,
            "size": 3449612,
            "upload_time": "2024-08-19T15:12:50",
            "upload_time_iso_8601": "2024-08-19T15:12:50.191766Z",
            "url": "https://files.pythonhosted.org/packages/c0/bc/dedb1893629dc93a4bd3e5761eb2e2d826e8c82078b3a03af734c267f74a/atomic_bomb_engine-0.41.3-cp312-none-win_amd64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "70065b5f34195e9672cb2a76e5b4dd3ea129a28b800d2e1edb9a7bfb2f8f329f",
                "md5": "2321eaff9ae585e888bde58e85ef262f",
                "sha256": "36593362ea9ffe834709c76d3edd2eccd5ce2cb13e694ab9d15c2de23b906790"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp38-cp38-macosx_10_12_x86_64.whl",
            "has_sig": false,
            "md5_digest": "2321eaff9ae585e888bde58e85ef262f",
            "packagetype": "bdist_wheel",
            "python_version": "cp38",
            "requires_python": null,
            "size": 3699597,
            "upload_time": "2024-08-19T15:12:48",
            "upload_time_iso_8601": "2024-08-19T15:12:48.343869Z",
            "url": "https://files.pythonhosted.org/packages/70/06/5b5f34195e9672cb2a76e5b4dd3ea129a28b800d2e1edb9a7bfb2f8f329f/atomic_bomb_engine-0.41.3-cp38-cp38-macosx_10_12_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "a1e4c962804d350cdae2e548542e3c99be26a9bb5a0313d6af04403a9d2fac02",
                "md5": "8a3a65857315d6ffbf3426346f8429d1",
                "sha256": "0631ac243d69e520358adca0ab4751f67f38fc652c9e477f8a4aa76c4c46a0a2"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp38-cp38-macosx_11_0_arm64.whl",
            "has_sig": false,
            "md5_digest": "8a3a65857315d6ffbf3426346f8429d1",
            "packagetype": "bdist_wheel",
            "python_version": "cp38",
            "requires_python": null,
            "size": 3634711,
            "upload_time": "2024-08-19T15:11:50",
            "upload_time_iso_8601": "2024-08-19T15:11:50.431247Z",
            "url": "https://files.pythonhosted.org/packages/a1/e4/c962804d350cdae2e548542e3c99be26a9bb5a0313d6af04403a9d2fac02/atomic_bomb_engine-0.41.3-cp38-cp38-macosx_11_0_arm64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "7d5166ac7cca67b1172a8d34f58f5e971d11fd93bf7b504ea1a5ab0d33f53b09",
                "md5": "d4f3abdf0557cc15e7d34bef065295a6",
                "sha256": "08166ad66e6b26e527a14cce8a241e274988b858fad08866d6f77538bd801ebf"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp38-cp38-manylinux_2_34_x86_64.whl",
            "has_sig": false,
            "md5_digest": "d4f3abdf0557cc15e7d34bef065295a6",
            "packagetype": "bdist_wheel",
            "python_version": "cp38",
            "requires_python": null,
            "size": 6048496,
            "upload_time": "2024-08-19T15:15:55",
            "upload_time_iso_8601": "2024-08-19T15:15:55.728021Z",
            "url": "https://files.pythonhosted.org/packages/7d/51/66ac7cca67b1172a8d34f58f5e971d11fd93bf7b504ea1a5ab0d33f53b09/atomic_bomb_engine-0.41.3-cp38-cp38-manylinux_2_34_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "911ba602b0575aba447f112c94316cbb32b53f85878d7e8b2fe53f5b20dcbc24",
                "md5": "f9fec04f7d95dcfaed548263c098d602",
                "sha256": "3b64c93d570005c971e82b02b24b9554acd509e1bd18cc04b542c39329248016"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp38-cp38-musllinux_1_2_x86_64.whl",
            "has_sig": false,
            "md5_digest": "f9fec04f7d95dcfaed548263c098d602",
            "packagetype": "bdist_wheel",
            "python_version": "cp38",
            "requires_python": null,
            "size": 4647218,
            "upload_time": "2024-08-19T15:13:26",
            "upload_time_iso_8601": "2024-08-19T15:13:26.421004Z",
            "url": "https://files.pythonhosted.org/packages/91/1b/a602b0575aba447f112c94316cbb32b53f85878d7e8b2fe53f5b20dcbc24/atomic_bomb_engine-0.41.3-cp38-cp38-musllinux_1_2_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "6200dc3ace8c029c94554ff89164f9e26d59e90e6b6caad0a210a802cee9bad6",
                "md5": "458b2894fe58c939866d295d33d2dbee",
                "sha256": "f47870f27df8012d1e59e143f59616497b695fdd39a77334fe0a562e6d8ff4b1"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp38-none-win_amd64.whl",
            "has_sig": false,
            "md5_digest": "458b2894fe58c939866d295d33d2dbee",
            "packagetype": "bdist_wheel",
            "python_version": "cp38",
            "requires_python": null,
            "size": 3448466,
            "upload_time": "2024-08-19T15:12:21",
            "upload_time_iso_8601": "2024-08-19T15:12:21.270895Z",
            "url": "https://files.pythonhosted.org/packages/62/00/dc3ace8c029c94554ff89164f9e26d59e90e6b6caad0a210a802cee9bad6/atomic_bomb_engine-0.41.3-cp38-none-win_amd64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "48cd3727d56152e4c7e5fc7d5d2a498d1dd28b3b0c6222372c53967da69dc864",
                "md5": "f10587a71b5dc0228523b4ec24a4cf56",
                "sha256": "8bc7ed17342e1b197dfabc0a24db1a1215a2f66c6fea752bda8590030ff5f6f8"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp39-cp39-macosx_10_12_x86_64.whl",
            "has_sig": false,
            "md5_digest": "f10587a71b5dc0228523b4ec24a4cf56",
            "packagetype": "bdist_wheel",
            "python_version": "cp39",
            "requires_python": null,
            "size": 3699463,
            "upload_time": "2024-08-19T15:12:57",
            "upload_time_iso_8601": "2024-08-19T15:12:57.217372Z",
            "url": "https://files.pythonhosted.org/packages/48/cd/3727d56152e4c7e5fc7d5d2a498d1dd28b3b0c6222372c53967da69dc864/atomic_bomb_engine-0.41.3-cp39-cp39-macosx_10_12_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "381f6856dd0f60c22cba2b98012208c85d8a3bb599c18d7266e8ba2bc54acca3",
                "md5": "84efc0f4d9388e19c9466efac055452a",
                "sha256": "d82a76e5fc4319ec9ee72bacaa8f7e2f7965af2500ccd094e46385412bf173dd"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp39-cp39-macosx_11_0_arm64.whl",
            "has_sig": false,
            "md5_digest": "84efc0f4d9388e19c9466efac055452a",
            "packagetype": "bdist_wheel",
            "python_version": "cp39",
            "requires_python": null,
            "size": 3634957,
            "upload_time": "2024-08-19T15:14:42",
            "upload_time_iso_8601": "2024-08-19T15:14:42.032950Z",
            "url": "https://files.pythonhosted.org/packages/38/1f/6856dd0f60c22cba2b98012208c85d8a3bb599c18d7266e8ba2bc54acca3/atomic_bomb_engine-0.41.3-cp39-cp39-macosx_11_0_arm64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "aa221a2b8563d339ce75b4ef2200dc21da2ef29edfebc187b72ea241762ec43e",
                "md5": "242a5e379dd9ea12a8b47fb1ee74e492",
                "sha256": "914f1b1641f40aa44d2a488045e054595fce69d081c650df63024fb1622aecc5"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp39-cp39-manylinux_2_34_x86_64.whl",
            "has_sig": false,
            "md5_digest": "242a5e379dd9ea12a8b47fb1ee74e492",
            "packagetype": "bdist_wheel",
            "python_version": "cp39",
            "requires_python": null,
            "size": 6047943,
            "upload_time": "2024-08-19T15:16:17",
            "upload_time_iso_8601": "2024-08-19T15:16:17.106966Z",
            "url": "https://files.pythonhosted.org/packages/aa/22/1a2b8563d339ce75b4ef2200dc21da2ef29edfebc187b72ea241762ec43e/atomic_bomb_engine-0.41.3-cp39-cp39-manylinux_2_34_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "c4b33a8a53d349a3c3bed1f2c4d226ead4b7098d7913b326b074c988208ee47e",
                "md5": "d05dad626cf14a41e71b91ac4f694176",
                "sha256": "41ab10fbcdd811030c3199814b5d5f282e91e39c39afee044699daa7bfaf0821"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp39-cp39-musllinux_1_2_x86_64.whl",
            "has_sig": false,
            "md5_digest": "d05dad626cf14a41e71b91ac4f694176",
            "packagetype": "bdist_wheel",
            "python_version": "cp39",
            "requires_python": null,
            "size": 4647475,
            "upload_time": "2024-08-19T15:13:30",
            "upload_time_iso_8601": "2024-08-19T15:13:30.097609Z",
            "url": "https://files.pythonhosted.org/packages/c4/b3/3a8a53d349a3c3bed1f2c4d226ead4b7098d7913b326b074c988208ee47e/atomic_bomb_engine-0.41.3-cp39-cp39-musllinux_1_2_x86_64.whl",
            "yanked": false,
            "yanked_reason": null
        },
        {
            "comment_text": "",
            "digests": {
                "blake2b_256": "85fb7b964d9eaeb9d0c194e0703ad89674b8d6e414ac283a76f22ff98d1f3022",
                "md5": "3214e54801fa97db5570dcbaa627a1ee",
                "sha256": "4adc3bfb2cbbd484037725300345ff05fae364656cc6cd880bbcd301cf401d80"
            },
            "downloads": -1,
            "filename": "atomic_bomb_engine-0.41.3-cp39-none-win_amd64.whl",
            "has_sig": false,
            "md5_digest": "3214e54801fa97db5570dcbaa627a1ee",
            "packagetype": "bdist_wheel",
            "python_version": "cp39",
            "requires_python": null,
            "size": 3448707,
            "upload_time": "2024-08-19T15:12:38",
            "upload_time_iso_8601": "2024-08-19T15:12:38.822505Z",
            "url": "https://files.pythonhosted.org/packages/85/fb/7b964d9eaeb9d0c194e0703ad89674b8d6e414ac283a76f22ff98d1f3022/atomic_bomb_engine-0.41.3-cp39-none-win_amd64.whl",
            "yanked": false,
            "yanked_reason": null
        }
    ],
    "upload_time": "2024-08-19 15:12:58",
    "github": false,
    "gitlab": false,
    "bitbucket": false,
    "codeberg": false,
    "lcname": "atomic-bomb-engine"
}
        
Elapsed time: 9.12453s