matrix-python 1.4.8a0__tar.gz → 1.4.10a0__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 (103) hide show
  1. matrix_python-1.4.10a0/.github/workflows/docs.yml +39 -0
  2. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/.gitignore +2 -1
  3. {matrix_python-1.4.8a0/matrix_python.egg-info → matrix_python-1.4.10a0}/PKG-INFO +60 -39
  4. matrix_python-1.4.10a0/README.md +99 -0
  5. matrix_python-1.4.10a0/docs/docs/examples/checks.md +15 -0
  6. matrix_python-1.4.10a0/docs/docs/examples/cooldown.md +14 -0
  7. matrix_python-1.4.10a0/docs/docs/examples/error-handling.md +17 -0
  8. matrix_python-1.4.10a0/docs/docs/examples/extension.md +26 -0
  9. matrix_python-1.4.10a0/docs/docs/examples/index.md +20 -0
  10. matrix_python-1.4.10a0/docs/docs/examples/ping.md +9 -0
  11. matrix_python-1.4.10a0/docs/docs/examples/reaction.md +14 -0
  12. matrix_python-1.4.10a0/docs/docs/examples/scheduler.md +19 -0
  13. matrix_python-1.4.10a0/docs/docs/guides/bigger-bot.md +95 -0
  14. matrix_python-1.4.10a0/docs/docs/guides/checks.md +114 -0
  15. matrix_python-1.4.10a0/docs/docs/guides/commands.md +158 -0
  16. matrix_python-1.4.10a0/docs/docs/guides/configuration.md +86 -0
  17. matrix_python-1.4.10a0/docs/docs/guides/error-handling.md +97 -0
  18. matrix_python-1.4.10a0/docs/docs/guides/events.md +115 -0
  19. matrix_python-1.4.10a0/docs/docs/guides/groups.md +111 -0
  20. matrix_python-1.4.10a0/docs/docs/guides/index.md +87 -0
  21. matrix_python-1.4.10a0/docs/docs/guides/introduction.md +126 -0
  22. matrix_python-1.4.10a0/docs/docs/img/favicon.svg +68 -0
  23. matrix_python-1.4.10a0/docs/docs/img/matrixpy-black.svg +72 -0
  24. matrix_python-1.4.10a0/docs/docs/img/matrixpy-white.svg +89 -0
  25. matrix_python-1.4.10a0/docs/docs/index.md +168 -0
  26. matrix_python-1.4.10a0/docs/docs/reference/bot.md +20 -0
  27. matrix_python-1.4.10a0/docs/docs/reference/checks.md +17 -0
  28. matrix_python-1.4.10a0/docs/docs/reference/command.md +15 -0
  29. matrix_python-1.4.10a0/docs/docs/reference/config.md +19 -0
  30. matrix_python-1.4.10a0/docs/docs/reference/content.md +34 -0
  31. matrix_python-1.4.10a0/docs/docs/reference/context.md +15 -0
  32. matrix_python-1.4.10a0/docs/docs/reference/errors.md +18 -0
  33. matrix_python-1.4.10a0/docs/docs/reference/extension.md +30 -0
  34. matrix_python-1.4.10a0/docs/docs/reference/group.md +19 -0
  35. matrix_python-1.4.10a0/docs/docs/reference/message.md +15 -0
  36. matrix_python-1.4.10a0/docs/docs/reference/protocols.md +5 -0
  37. matrix_python-1.4.10a0/docs/docs/reference/registry.md +7 -0
  38. matrix_python-1.4.10a0/docs/docs/reference/room.md +15 -0
  39. matrix_python-1.4.10a0/docs/docs/reference/scheduler.md +16 -0
  40. matrix_python-1.4.10a0/docs/docs/reference/types.md +26 -0
  41. matrix_python-1.4.10a0/docs/docs/stylesheets/extra.css +3 -0
  42. matrix_python-1.4.10a0/docs/mkdocs.yml +120 -0
  43. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/_version.py +3 -3
  44. matrix_python-1.4.10a0/matrix/checks.py +29 -0
  45. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/command.py +45 -48
  46. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/context.py +0 -3
  47. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/extension.py +17 -9
  48. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/group.py +15 -7
  49. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/help/help_command.py +62 -72
  50. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/help/pagination.py +4 -22
  51. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/protocols.py +4 -0
  52. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/registry.py +74 -11
  53. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/scheduler.py +7 -9
  54. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0/matrix_python.egg-info}/PKG-INFO +60 -39
  55. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix_python.egg-info/SOURCES.txt +39 -0
  56. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix_python.egg-info/requires.txt +6 -1
  57. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/pyproject.toml +6 -1
  58. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_extension.py +11 -4
  59. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_registry.py +63 -1
  60. matrix_python-1.4.8a0/README.md +0 -82
  61. matrix_python-1.4.8a0/matrix/checks.py +0 -21
  62. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/.github/dependabot.yml +0 -0
  63. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/.github/workflows/CODEOWNERS +0 -0
  64. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/.github/workflows/codeql.yml +0 -0
  65. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/.github/workflows/publish.yml +0 -0
  66. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/.github/workflows/scorecard.yml +0 -0
  67. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/.github/workflows/tests.yml +0 -0
  68. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/CODE_OF_CONDUCT.md +0 -0
  69. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/CONTRIBUTING.md +0 -0
  70. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/LICENSE +0 -0
  71. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/README.md +0 -0
  72. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/checks.py +0 -0
  73. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/config.yaml +0 -0
  74. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/cooldown.py +0 -0
  75. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/error_handling.py +0 -0
  76. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/extension.py +0 -0
  77. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/ping.py +0 -0
  78. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/reaction.py +0 -0
  79. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/examples/scheduler.py +0 -0
  80. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/__init__.py +0 -0
  81. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/bot.py +0 -0
  82. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/config.py +0 -0
  83. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/content.py +0 -0
  84. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/errors.py +0 -0
  85. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/help/__init__.py +0 -0
  86. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/message.py +0 -0
  87. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/py.typed +0 -0
  88. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/room.py +0 -0
  89. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix/types.py +0 -0
  90. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix_python.egg-info/dependency_links.txt +0 -0
  91. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/matrix_python.egg-info/top_level.txt +0 -0
  92. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/mypy.ini +0 -0
  93. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/setup.cfg +0 -0
  94. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/help/test_default_help_command.py +0 -0
  95. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/help/test_help_command.py +0 -0
  96. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/help/test_pagination.py +0 -0
  97. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_bot.py +0 -0
  98. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_command.py +0 -0
  99. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_config.py +0 -0
  100. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_context.py +0 -0
  101. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_group.py +0 -0
  102. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_message.py +0 -0
  103. {matrix_python-1.4.8a0 → matrix_python-1.4.10a0}/tests/test_room.py +0 -0
@@ -0,0 +1,39 @@
1
+ name: Deploy Docs
2
+
3
+ on:
4
+ push:
5
+ branches:
6
+ - main
7
+
8
+ permissions:
9
+ contents: read
10
+ pages: write
11
+ id-token: write
12
+
13
+ jobs:
14
+ deploy:
15
+ runs-on: ubuntu-latest
16
+ environment:
17
+ name: github-pages
18
+ url: ${{ steps.deployment.outputs.page_url }}
19
+
20
+ steps:
21
+ - uses: actions/checkout@v4
22
+
23
+ - uses: actions/setup-python@v5
24
+ with:
25
+ python-version: "3.10"
26
+
27
+ - name: Install dependencies
28
+ run: pip install .[doc]
29
+
30
+ - name: Build docs
31
+ run: mkdocs build --config-file docs/mkdocs.yml
32
+
33
+ - uses: actions/upload-pages-artifact@v3
34
+ with:
35
+ path: docs/site
36
+
37
+ - name: Deploy to GitHub Pages
38
+ id: deployment
39
+ uses: actions/deploy-pages@v4
@@ -176,4 +176,5 @@ cython_debug/
176
176
  .DS_Store
177
177
 
178
178
  .vscode
179
- matrix/_version.py
179
+ matrix/_version.py
180
+ site/
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: matrix-python
3
- Version: 1.4.8a0
3
+ Version: 1.4.10a0
4
4
  Summary: An easy-to-use Matrix bot framework designed for quick development and minimal setup
5
5
  Author: Simon Roy, Chris Dedman Rollet
6
6
  Maintainer-email: Code Society Lab <admin@codesociety.xyz>
@@ -40,57 +40,72 @@ Provides-Extra: dev
40
40
  Requires-Dist: pytest==9.0.3; extra == "dev"
41
41
  Requires-Dist: pytest-asyncio==1.3.0; extra == "dev"
42
42
  Requires-Dist: black==26.3.1; extra == "dev"
43
- Requires-Dist: mypy==1.20.0; extra == "dev"
43
+ Requires-Dist: mypy==1.20.1; extra == "dev"
44
44
  Requires-Dist: types-PyYAML==6.0.12.20260408; extra == "dev"
45
45
  Requires-Dist: types-Markdown==3.10.2.20260408; extra == "dev"
46
+ Provides-Extra: doc
47
+ Requires-Dist: mkdocs==1.6.1; extra == "doc"
48
+ Requires-Dist: mkdocs-material==9.7.6; extra == "doc"
49
+ Requires-Dist: mkdocstrings[python]==1.0.4; extra == "doc"
46
50
 
47
51
  <div align="center">
48
52
  <em>A simple, developer-friendly library to create powerful <a href="https://matrix.org">Matrix</a> bots.</em>
49
53
  </div>
50
54
 
51
- <img alt="image" src="https://github.com/user-attachments/assets/d9140a9e-27fa-44e4-a5ca-87ee7bbf868f" />
55
+ <div align="center">
56
+ <img alt="matrix.py" src="https://github.com/user-attachments/assets/d9140a9e-27fa-44e4-a5ca-87ee7bbf868f" />
57
+ </div>
58
+
59
+ <div align="center">
52
60
 
53
- <hr />
61
+ [<img src="https://img.shields.io/badge/Get%20Started-black?style=for-the-badge" />](https://matrixpy.code-society.xyz/guides/introduction/)
62
+ [<img src="https://img.shields.io/badge/Reference-555555?style=for-the-badge" />](https://matrixpy.code-society.xyz/reference/bot/)
63
+
64
+ </div>
65
+
66
+ <div align="center">
54
67
 
55
- [![Static Badge](https://img.shields.io/badge/%F0%9F%93%9A-Documentation-%235c5c5c)](https://github.com/Code-Society-Lab/matrixpy/wiki)
56
68
  [![Join Discord](https://discordapp.com/api/guilds/823178343943897088/widget.png?style=shield)](https://discord.gg/code-society-823178343943897088)
57
- [![Join Matrix](https://img.shields.io/matrix/codesociety%3Amatrix.org?logo=matrix&label=%20&labelColor=%23202020&color=%23202020)](https://matrix.to/#/%23codesociety:matrix.org )
69
+ [![Join Matrix](https://img.shields.io/matrix/codesociety%3Amatrix.org?logo=matrix&label=%20&labelColor=%23202020&color=%23202020)](https://matrix.to/#/%23codesociety:matrix.org)
58
70
  [![Tests](https://github.com/Code-Society-Lab/matrixpy/actions/workflows/tests.yml/badge.svg)](https://github.com/Code-Society-Lab/matrixpy/actions/workflows/tests.yml)
59
71
  [![CodeQL Advanced](https://github.com/Code-Society-Lab/matrixpy/actions/workflows/codeql.yml/badge.svg)](https://github.com/Code-Society-Lab/matrixpy/actions/workflows/codeql.yml)
60
72
  [![OpenSSF Scorecard](https://api.securityscorecards.dev/projects/github.com/Code-Society-Lab/matrixpy/badge)](https://securityscorecards.dev/viewer/?uri=github.com/Code-Society-Lab/matrixpy)
61
73
 
62
- Matrix.py is a lightweight and intuitive Python library to build bots on
63
- the [Matrix protocol](https://matrix.org). It provides a clean,
64
- decorator-based API similar to popular event-driven frameworks, allowing
65
- developers to focus on behavior rather than boilerplate.
74
+ </div>
66
75
 
67
- #### Key Features
76
+ ---
68
77
 
69
- - Minimal setup, easy to extend
70
- - Event-driven API using async/await
71
- - Clean command registration
72
- - Automatic event handler registration
73
- - Built on [matrix-nio](https://github.com/matrix-nio/matrix-nio)
78
+ Matrix.py is a lightweight and intuitive Python library to build bots on the [Matrix protocol](https://matrix.org). It
79
+ provides a clean, decorator-based API similar to popular event-driven frameworks, allowing developers to focus on
80
+ behavior rather than boilerplate.
74
81
 
75
- # Quickstart
82
+ - **Minimal setup** — install and have a working bot running in minutes
83
+ - **Event-driven** — async/await API reacting to any Matrix room event
84
+ - **Command system** — decorator-based commands with automatic argument parsing
85
+ - **Extensions** — split your bot into modules as it grows
76
86
 
77
- **Requirements**
87
+ ## Quickstart
78
88
 
79
- - Python 3.10+
89
+ **Requirements:** Python 3.10+
80
90
 
81
- ```
91
+ ```bash
82
92
  pip install matrix-python
83
93
  ```
84
94
 
85
- If you plan on contributing to matrix.py, we recommend to install the development libraries:
95
+ Using a virtual environment is strongly recommended:
86
96
 
87
- ```
88
- pip install -e .[dev]
97
+ ```bash
98
+ python -m venv venv
99
+ source venv/bin/activate # Windows: venv\Scripts\activate
100
+ pip install matrix-python
89
101
  ```
90
102
 
91
- *Note*: It is recommended to use
92
- a [virtual environment](https://packaging.python.org/en/latest/guides/installing-using-pip-and-virtual-environments/)
93
- when installing python packages.
103
+ Create a `config.yml`:
104
+
105
+ ```yaml
106
+ USERNAME: "@yourbot:matrix.org"
107
+ PASSWORD: "your_password"
108
+ ```
94
109
 
95
110
  ```python
96
111
  from matrix import Bot, Context
@@ -106,23 +121,29 @@ async def ping(ctx: Context):
106
121
  bot.start(config="config.yml")
107
122
  ```
108
123
 
109
- [Documentation](https://github.com/Code-Society-Lab/matrixpy/wiki) - [Examples](https://github.com/Code-Society-Lab/matrixpy/tree/main/examples)
124
+ Send `!ping` in any room the bot is in, it will reply `Pong!`.
125
+
126
+ ## Where to go next
110
127
 
111
- # Contributing
128
+ - [**Guides**](https://matrixpy.codesociety.xyz/guides/introduction/) — step-by-step tutorials covering commands,
129
+ events, checks, extensions, and more
130
+ - [**Reference**](https://matrixpy.codesociety.xyz/reference/bot/) — complete API documentation for every class and
131
+ function
132
+ - [**Examples**](https://matrixpy.codesociety.xyz/examples/) — ready-to-run example bots
133
+ demonstrating common patterns
112
134
 
113
- We welcome everyone to contribute!
135
+ ## Contributing
114
136
 
115
- Whether it's fixing bugs, suggesting features, or improving the docs - every bit helps.
137
+ We welcome everyone to contribute! Whether it's fixing bugs, suggesting features, or improving the docs. Every bit
138
+ helps.
116
139
 
117
- - Submit an issue
118
- - Open a pull request
119
- - Or just hop into our [Matrix](https://matrix.to/#/%23codesociety:matrix.org)
120
- or [Discord](https://discord.gg/code-society-823178343943897088) server and say hi!
140
+ - [Submit an issue](https://github.com/Code-Society-Lab/matrixpy/issues)
141
+ - [Open a pull request](https://github.com/Code-Society-Lab/matrixpy/blob/main/CONTRIBUTING.md)
142
+ - Hop into our [Matrix](https://matrix.to/#/%23codesociety:matrix.org)
143
+ or [Discord](https://discord.gg/code-society-823178343943897088) and say hi!
121
144
 
122
- If you intend to contribute, please read the [CONTRIBUTING.md](./CONTRIBUTING.md) first. Additionally, **every
123
- contributor** is expected to follow the [code of conduct](./CODE_OF_CONDUCT.md).
145
+ Please read the [CONTRIBUTING.md](./CONTRIBUTING.md) and follow the [code of conduct](./CODE_OF_CONDUCT.md).
124
146
 
125
- # License
147
+ ## License
126
148
 
127
- This project is licensed under the terms
128
- of [MIT license](https://github.com/Code-Society-Lab/matrixpy/blob/main/LICENSE).
149
+ Released under the [MIT License](https://github.com/Code-Society-Lab/matrixpy/blob/main/LICENSE).
@@ -0,0 +1,99 @@
1
+ <div align="center">
2
+ <em>A simple, developer-friendly library to create powerful <a href="https://matrix.org">Matrix</a> bots.</em>
3
+ </div>
4
+
5
+ <div align="center">
6
+ <img alt="matrix.py" src="https://github.com/user-attachments/assets/d9140a9e-27fa-44e4-a5ca-87ee7bbf868f" />
7
+ </div>
8
+
9
+ <div align="center">
10
+
11
+ [<img src="https://img.shields.io/badge/Get%20Started-black?style=for-the-badge" />](https://matrixpy.code-society.xyz/guides/introduction/)
12
+ [<img src="https://img.shields.io/badge/Reference-555555?style=for-the-badge" />](https://matrixpy.code-society.xyz/reference/bot/)
13
+
14
+ </div>
15
+
16
+ <div align="center">
17
+
18
+ [![Join Discord](https://discordapp.com/api/guilds/823178343943897088/widget.png?style=shield)](https://discord.gg/code-society-823178343943897088)
19
+ [![Join Matrix](https://img.shields.io/matrix/codesociety%3Amatrix.org?logo=matrix&label=%20&labelColor=%23202020&color=%23202020)](https://matrix.to/#/%23codesociety:matrix.org)
20
+ [![Tests](https://github.com/Code-Society-Lab/matrixpy/actions/workflows/tests.yml/badge.svg)](https://github.com/Code-Society-Lab/matrixpy/actions/workflows/tests.yml)
21
+ [![CodeQL Advanced](https://github.com/Code-Society-Lab/matrixpy/actions/workflows/codeql.yml/badge.svg)](https://github.com/Code-Society-Lab/matrixpy/actions/workflows/codeql.yml)
22
+ [![OpenSSF Scorecard](https://api.securityscorecards.dev/projects/github.com/Code-Society-Lab/matrixpy/badge)](https://securityscorecards.dev/viewer/?uri=github.com/Code-Society-Lab/matrixpy)
23
+
24
+ </div>
25
+
26
+ ---
27
+
28
+ Matrix.py is a lightweight and intuitive Python library to build bots on the [Matrix protocol](https://matrix.org). It
29
+ provides a clean, decorator-based API similar to popular event-driven frameworks, allowing developers to focus on
30
+ behavior rather than boilerplate.
31
+
32
+ - **Minimal setup** — install and have a working bot running in minutes
33
+ - **Event-driven** — async/await API reacting to any Matrix room event
34
+ - **Command system** — decorator-based commands with automatic argument parsing
35
+ - **Extensions** — split your bot into modules as it grows
36
+
37
+ ## Quickstart
38
+
39
+ **Requirements:** Python 3.10+
40
+
41
+ ```bash
42
+ pip install matrix-python
43
+ ```
44
+
45
+ Using a virtual environment is strongly recommended:
46
+
47
+ ```bash
48
+ python -m venv venv
49
+ source venv/bin/activate # Windows: venv\Scripts\activate
50
+ pip install matrix-python
51
+ ```
52
+
53
+ Create a `config.yml`:
54
+
55
+ ```yaml
56
+ USERNAME: "@yourbot:matrix.org"
57
+ PASSWORD: "your_password"
58
+ ```
59
+
60
+ ```python
61
+ from matrix import Bot, Context
62
+
63
+ bot = Bot()
64
+
65
+
66
+ @bot.command("ping")
67
+ async def ping(ctx: Context):
68
+ await ctx.reply("Pong!")
69
+
70
+
71
+ bot.start(config="config.yml")
72
+ ```
73
+
74
+ Send `!ping` in any room the bot is in, it will reply `Pong!`.
75
+
76
+ ## Where to go next
77
+
78
+ - [**Guides**](https://matrixpy.codesociety.xyz/guides/introduction/) — step-by-step tutorials covering commands,
79
+ events, checks, extensions, and more
80
+ - [**Reference**](https://matrixpy.codesociety.xyz/reference/bot/) — complete API documentation for every class and
81
+ function
82
+ - [**Examples**](https://matrixpy.codesociety.xyz/examples/) — ready-to-run example bots
83
+ demonstrating common patterns
84
+
85
+ ## Contributing
86
+
87
+ We welcome everyone to contribute! Whether it's fixing bugs, suggesting features, or improving the docs. Every bit
88
+ helps.
89
+
90
+ - [Submit an issue](https://github.com/Code-Society-Lab/matrixpy/issues)
91
+ - [Open a pull request](https://github.com/Code-Society-Lab/matrixpy/blob/main/CONTRIBUTING.md)
92
+ - Hop into our [Matrix](https://matrix.to/#/%23codesociety:matrix.org)
93
+ or [Discord](https://discord.gg/code-society-823178343943897088) and say hi!
94
+
95
+ Please read the [CONTRIBUTING.md](./CONTRIBUTING.md) and follow the [code of conduct](./CODE_OF_CONDUCT.md).
96
+
97
+ ## License
98
+
99
+ Released under the [MIT License](https://github.com/Code-Society-Lab/matrixpy/blob/main/LICENSE).
@@ -0,0 +1,15 @@
1
+ # Checks
2
+
3
+ Shows how to restrict a command to a specific set of users using a [check](../reference/checks.md). The `!secret` command is only accessible to users in the `allowed_users` set — anyone else receives an "Access denied" reply.
4
+
5
+ ```python
6
+ --8<-- "examples/checks.py"
7
+ ```
8
+
9
+ Key points:
10
+
11
+ - `@secret_command.check` decorates an async function that returns `True` (allow) or `False` (deny). Returning `False` raises a [`CheckError`](../reference/errors.md).
12
+ - `@secret_command.error(CheckError)` handles the denial and sends a friendly reply instead of silently failing.
13
+ - `ctx.sender` is the full Matrix ID of the user who sent the command (e.g. `@alice:matrix.org`).
14
+
15
+ See the [Checks guide](../guides/checks.md) for built-in checks like `@is_owner` and how to compose multiple checks.
@@ -0,0 +1,14 @@
1
+ # Cooldowns
2
+
3
+ Demonstrates two ways to apply a rate limit to a command, and how to handle the [`CooldownError`](../reference/errors.md) when the limit is exceeded.
4
+
5
+ ```python
6
+ --8<-- "examples/cooldown.py"
7
+ ```
8
+
9
+ There are two ways to set a cooldown:
10
+
11
+ - **`@cooldown(rate, period)` decorator** — applied before `@bot.command`. `rate=2, period=10` means 2 uses per 10 seconds per user.
12
+ - **`cooldown=(rate, period)` argument** — passed directly to `@bot.command` for a more compact one-liner.
13
+
14
+ Both produce a `CooldownError` when the limit is exceeded. The error object exposes `error.retry` — the number of seconds until the user can try again — which you can surface in the reply.
@@ -0,0 +1,17 @@
1
+ # Error Handling
2
+
3
+ Shows both per-command error handlers and a global error handler, covering argument validation, runtime errors, and unknown commands.
4
+
5
+ ```python
6
+ --8<-- "examples/error_handling.py"
7
+ ```
8
+
9
+ Three layers of error handling are demonstrated:
10
+
11
+ - **Global handler** — `@bot.error(CommandNotFoundError)` catches any command the bot doesn't recognise, across the whole bot. No `ctx` is available here since no command was matched.
12
+ - **Per-command handlers** — `@division.error(ZeroDivisionError)` and `@division.error(ValueError)` handle errors raised inside the `division` function itself.
13
+ - **Argument handler** — `@division.error(MissingArgumentError)` fires when the user doesn't supply enough arguments.
14
+
15
+ Handlers are matched by exception type. If no handler is registered for a raised exception, it propagates normally.
16
+
17
+ See the [Error Handling guide](../guides/error-handling.md) for the full picture.
@@ -0,0 +1,26 @@
1
+ # Extension
2
+
3
+ Demonstrates how to split a bot into modules using [`Extension`](../reference/extension.md) and how to organise related commands into a [`Group`](../reference/group.md).
4
+
5
+ ```python
6
+ --8<-- "examples/extension.py"
7
+ ```
8
+
9
+ Key points:
10
+
11
+ - `Extension("math")` creates a standalone module. It supports commands, groups, events, checks, and error handlers — everything `Bot` supports.
12
+ - `@extension.group("math")` creates a command group. Sub-commands are registered with `@math_group.command()` and invoked as `!math add`, `!math subtract`, etc.
13
+ - Per-command error handlers work the same as on `Bot`: `@divide.error(ZeroDivisionError)` handles division by zero inside the group.
14
+
15
+ To load this extension in your bot:
16
+
17
+ ```python
18
+ from matrix import Bot
19
+ from math_extension import extension as math_extension
20
+
21
+ bot = Bot()
22
+ bot.load_extension(math_extension)
23
+ bot.start(config="config.yaml")
24
+ ```
25
+
26
+ See the [Bigger Bot guide](../guides/bigger-bot.md) for a full project layout using multiple extensions.
@@ -0,0 +1,20 @@
1
+ # Examples
2
+
3
+ Ready-to-run bots demonstrating common patterns. Each example is a complete, working bot you can copy and adapt.
4
+
5
+ All examples expect a `config.yaml` file in the same directory:
6
+
7
+ ```yaml
8
+ USERNAME: "@yourbot:matrix.org"
9
+ PASSWORD: "your_password"
10
+ ```
11
+
12
+ | Example | What it shows |
13
+ |---------|--------------|
14
+ | [Ping Bot](ping.md) | Minimal bot with a single command |
15
+ | [Reactions](reaction.md) | Listening to events and reacting to messages |
16
+ | [Checks](checks.md) | Restricting commands to specific users |
17
+ | [Cooldowns](cooldown.md) | Rate-limiting commands per user |
18
+ | [Error Handling](error-handling.md) | Per-command and global error handlers |
19
+ | [Extension](extension.md) | Splitting a bot into modules with command groups |
20
+ | [Scheduler](scheduler.md) | Running tasks on a cron schedule |
@@ -0,0 +1,9 @@
1
+ # Ping Bot
2
+
3
+ The simplest possible bot — one command that replies to `!ping` with `Pong!`. Start here if you're new to matrix.py.
4
+
5
+ ```python
6
+ --8<-- "examples/ping.py"
7
+ ```
8
+
9
+ `ctx.reply()` sends a message back to the same room the command was received in. Swap `"Pong!"` for any string, including formatted text.
@@ -0,0 +1,14 @@
1
+ # Reactions
2
+
3
+ Demonstrates event listeners and the [`Message.react()`](../reference/message.md) API. The bot watches for incoming messages and reactions, and responds with emoji reactions of its own.
4
+
5
+ ```python
6
+ --8<-- "examples/reaction.py"
7
+ ```
8
+
9
+ Two event handlers are registered here:
10
+
11
+ - `on_message` — fires on every `RoomMessageText` event. It fetches the full message object and reacts based on the message body.
12
+ - `on_react` — fires on every `ReactionEvent`. It fetches the original message that was reacted to and chains a follow-up reaction.
13
+
14
+ `room.fetch_message()` returns a [`Message`](../reference/message.md) object. You can react with an emoji string or any short text.
@@ -0,0 +1,19 @@
1
+ # Scheduler
2
+
3
+ Shows how to run tasks on a cron schedule using `@bot.schedule`. Tasks run independently of commands — they fire at the specified time whether or not anyone sends a message.
4
+
5
+ ```python
6
+ --8<-- "examples/scheduler.py"
7
+ ```
8
+
9
+ `@bot.schedule` accepts a standard 5-field cron expression:
10
+
11
+ | Expression | Meaning |
12
+ |---|---|
13
+ | `* * * * *` | Every minute |
14
+ | `0 * * * *` | Every hour (on the hour) |
15
+ | `0 9 * * 1-5` | 9 AM every weekday |
16
+
17
+ The scheduled function receives no arguments. To send a message you need a [`Room`](../reference/room.md) object — get one with `bot.get_room(room_id)` before the bot starts, then call `room.send()` inside the task.
18
+
19
+ See the [`Scheduler` reference](../reference/scheduler.md) for the full API.
@@ -0,0 +1,95 @@
1
+ # Bigger Bot - Extension
2
+
3
+ As your bot grows, keeping everything in a single file becomes harder to manage. That's where [`Extension`](../reference/extension.md) comes in, it lets you split your code into separate modules.
4
+
5
+ Here's an example file structure for a larger bot:
6
+ ```
7
+ .
8
+ ├─ bot
9
+ │ ├─ __init__.py
10
+ │ ├─ helpers.py
11
+ │ ├─ my_bot.py
12
+ │ └─ extensions
13
+ │ ├─ __init__.py
14
+ │ ├─ dev.py
15
+ │ ├─ moderation.py
16
+ │ └─ weather.py
17
+ ```
18
+
19
+ The `bot` package contains everything related to your bot, with `my_bot.py` as its entry point. It's responsible for importing and registering all extensions. This is just one way to structure your project, extensions are flexible enough to fit whatever organization works best for you.
20
+
21
+ ## What is an `Extension`?
22
+
23
+ An `Extension` is a mechanism that lets you split your bot's functionality across multiple modules. Extensions support everything a [`Bot`](../reference/bot.md) supports, including:
24
+
25
+ - Event handlers
26
+ - Error handlers
27
+ - Commands
28
+ - Groups
29
+ - Checks
30
+ - Cron tasks
31
+
32
+ ...and more.
33
+
34
+ ## How to Create an Extension
35
+
36
+ Below is a basic definition of a `moderation` extension. It registers two commands, `ban` and `kick`, and an event handler for `on_member_ban`:
37
+
38
+ ```python
39
+ from nio import RoomMemberEvent
40
+ from matrix import Extension, Context
41
+ from bot.helpers import is_admin
42
+
43
+ extension = Extension("moderation")
44
+
45
+
46
+ @is_admin
47
+ @extension.command(description="Ban a member")
48
+ async def ban(ctx: Context, username: str) -> None:
49
+ ...
50
+
51
+
52
+ @is_admin
53
+ @extension.command(description="Kick a member")
54
+ async def kick(ctx: Context, username: str) -> None:
55
+ ...
56
+
57
+
58
+ @extension.event
59
+ def on_member_ban(event: RoomMemberEvent) -> None:
60
+ # Triggered when a user is banned
61
+ ...
62
+ ```
63
+
64
+ ## How to Register Extensions
65
+
66
+ To use an extension, import it and pass it to `bot.load_extension()`:
67
+
68
+ ```python
69
+ from matrix import Bot, Context
70
+ from bot.extensions.moderation import extension as moderation_extension
71
+ from bot.extensions.weather import extension as weather_extension
72
+ from bot.extensions.dev import extension as dev_extension
73
+
74
+ bot = Bot()
75
+
76
+
77
+ @bot.command(description="Respond with 'Pong!'")
78
+ async def ping(ctx: Context):
79
+ await ctx.reply("Pong!")
80
+
81
+
82
+ bot.load_extension(moderation_extension)
83
+ bot.load_extension(weather_extension)
84
+
85
+ # Load the dev extension only in development environments
86
+ if in_dev:
87
+ bot.load_extension(dev_extension)
88
+
89
+
90
+ bot.start(config="config.yml")
91
+ ```
92
+
93
+ Your bot now has three extensions registered: `moderation`, `weather`, and `dev` (the last one only in development).
94
+
95
+ You can also unload an extension using `bot.unload_extension()`.
@@ -0,0 +1,114 @@
1
+ # What is a Check?
2
+ A check is a function that runs _before_ your command. It returns:
3
+ - `True` - Allow the command to run
4
+ - `False` - Block the command and raise [`CheckError`](../reference/errors.md)
5
+
6
+ See also the [`checks`](../reference/checks.md) reference for built-in check decorators.
7
+
8
+ # Add a Check
9
+ Let's create an admin-only command:
10
+ ```python
11
+ @bot.command()
12
+ async def restricted(ctx):
13
+ await ctx.reply("You passed all checks!")
14
+
15
+
16
+ @restricted.check
17
+ async def is_admin(ctx):
18
+ admins = ["@alice:example.com", "@bob:example.com"]
19
+ return ctx.sender in admins
20
+ ```
21
+
22
+ # Multiple Checks
23
+ You can add multiple checks to one command. ALL checks must pass:
24
+
25
+ ```python
26
+ @bot.command()
27
+ async def restricted(ctx):
28
+ await ctx.reply("You passed all checks!")
29
+
30
+ @restricted.check
31
+ async def check_one(ctx):
32
+ # Must be from a specific room
33
+ allowed_rooms = ["!room1:example.com", "!room2:example.com"]
34
+ return ctx.room_id in allowed_rooms
35
+
36
+ @restricted.check
37
+ async def check_two(ctx):
38
+ # Must not be banned
39
+ banned = ["@troublemaker:example.com"]
40
+ return ctx.sender not in banned
41
+ ```
42
+
43
+ Both checks must return `True` for the command to run.
44
+
45
+ # Global Checks (Bot-Level)
46
+ You can apply a check to _all_ commands with `@bot.check`:
47
+ ```python
48
+ @bot.check
49
+ async def not_banned(ctx):
50
+ """No banned users can run ANY commands"""
51
+ banned_users = ["@spammer:example.com", "@troll:example.com"]
52
+ return ctx.sender not in banned_users
53
+ ```
54
+ Now this check runs before _every_ command on your bot.
55
+
56
+ # What is a Cooldown?
57
+ A cooldown prevents users from running a command too frequently. It's like a check, but specifically for rate limiting. When exceeded it raises a [`CooldownError`](../reference/errors.md).
58
+
59
+ ### Adding a Cooldown
60
+ ```python
61
+ @bot.command(
62
+ description="Searches for something",
63
+ cooldown=(3, 60.0) # 3 calls per 60 seconds
64
+ )
65
+ async def search(ctx, query: str):
66
+ # Simulate expensive operation
67
+ await ctx.reply(f"Searching for: {query}")
68
+ ```
69
+
70
+ **Cooldown format:** `(rate, period)`
71
+ - `rate` (int): Number of times the command can be called
72
+ - `period` (float): Time window in seconds
73
+
74
+ **Example interpretations:**
75
+ - `(1, 10.0)` - Once every 10 seconds
76
+ - `(5, 60.0)` - 5 times per minute
77
+ - `(10, 3600.0)` - 10 times per hour
78
+
79
+
80
+ ### Setting Cooldowns Programmatically
81
+ ```python
82
+ @bot.command()
83
+ async def limited(ctx):
84
+ await ctx.reply("This command is rate-limited")
85
+
86
+ # Set cooldown after command creation
87
+ limited.set_cooldown(rate=2, period=30.0) # 2 times per 30 seconds
88
+ ```
89
+
90
+ ### Handling Cooldown Errors
91
+ When a user hits the cooldown limit, you can tell them how long to wait:
92
+
93
+ ```python
94
+ from matrix.errors import CooldownError
95
+
96
+ @bot.error(CooldownError)
97
+ async def handle_cooldown(error):
98
+ # error.retry tells you how many seconds until they can retry
99
+ wait_time = int(error.retry)
100
+ # You can send a message here if you have access to context
101
+ print(f"Cooldown hit! Wait {wait_time} seconds")
102
+ ```
103
+
104
+
105
+ # Hooks
106
+ ```python
107
+ @command.before_invoke
108
+ async def before(ctx):
109
+ # Runs before command
110
+
111
+ @command.after_invoke
112
+ async def after(ctx):
113
+ # Runs after command succeeds
114
+ ```