roboherd 0.1.10__py3-none-any.whl → 0.1.12__py3-none-any.whl

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.

Potentially problematic release.


This version of roboherd might be problematic. Click here for more details.

roboherd/__main__.py CHANGED
@@ -4,19 +4,19 @@ import os
4
4
 
5
5
  import click
6
6
  import dynaconf
7
- import watchfiles
8
7
 
9
8
  from roboherd.herd import RoboHerd
10
9
  from roboherd.herd.manager import HerdManager
11
10
  from roboherd.util import create_connection
12
11
  from roboherd.register import register as run_register
13
12
  from roboherd.validators import validators
13
+ from roboherd.version import __version__
14
14
 
15
15
  logging.basicConfig(level=logging.INFO)
16
16
  logging.captureWarnings(True)
17
17
 
18
18
 
19
- @click.group()
19
+ @click.group(invoke_without_command=True)
20
20
  @click.option(
21
21
  "--connection_string",
22
22
  default=None,
@@ -28,9 +28,22 @@ logging.captureWarnings(True)
28
28
  help="Base url to create cows with",
29
29
  )
30
30
  @click.option("--config_file", default="roboherd.toml", help="Configuration file")
31
+ @click.option(
32
+ "--version", is_flag=True, default=False, help="display version then exit"
33
+ )
31
34
  @click.pass_context
32
- def main(ctx: click.Context, connection_string: str, base_url: str, config_file: str):
35
+ def main(
36
+ ctx: click.Context,
37
+ connection_string: str,
38
+ base_url: str,
39
+ config_file: str,
40
+ version: bool,
41
+ ):
33
42
  """Configuration is usually loaded from the config_file. These options can be overwritten by passing as a command line argument."""
43
+ if version:
44
+ print(f"roboherd version: {__version__}")
45
+ exit(0)
46
+
34
47
  settings = dynaconf.Dynaconf(
35
48
  settings_files=[config_file],
36
49
  envvar_prefix="ROBOHERD",
@@ -51,6 +64,8 @@ def main(ctx: click.Context, connection_string: str, base_url: str, config_file:
51
64
  else:
52
65
  ctx.obj["base_url"] = settings.base_url # type: ignore
53
66
 
67
+ print("Please specify a command")
68
+
54
69
 
55
70
  @main.command()
56
71
  @click.option("--fail", is_flag=True, default=False, help="Fail if actors do not exist")
@@ -97,6 +112,7 @@ def watch(ctx):
97
112
  """Watches the file the module is in for changes and then restarts roboherd.
98
113
 
99
114
  Note: Options for roboherd are currently ignored (FIXME)."""
115
+ import watchfiles
100
116
 
101
117
  watchfiles.run_process("roboherd", target="roboherd run")
102
118
 
@@ -1,5 +1,5 @@
1
1
  from fast_depends import Depends
2
- from typing import Annotated, Callable, Awaitable
2
+ from typing import Annotated, Any, Callable, Awaitable
3
3
 
4
4
  from almabtrieb import Almabtrieb
5
5
 
@@ -7,17 +7,17 @@ from almabtrieb import Almabtrieb
7
7
  from roboherd.cow import RoboCow
8
8
 
9
9
 
10
- def get_profile(cow: RoboCow) -> dict:
10
+ def get_profile(cow: RoboCow) -> dict[str, Any]:
11
11
  if cow.internals.profile is None:
12
12
  raise ValueError("Cow has no profile")
13
13
  return cow.internals.profile
14
14
 
15
15
 
16
- Profile = Annotated[dict, Depends(get_profile)]
16
+ Profile = Annotated[dict[str, Any], Depends(get_profile)]
17
17
  """The profile of the cow"""
18
18
 
19
19
 
20
- Publisher = Callable[[dict], Awaitable[None]]
20
+ Publisher = Callable[[dict[str, Any]], Awaitable[None]]
21
21
  """Type returned by the publishing functions"""
22
22
 
23
23
 
roboherd/cow/__init__.py CHANGED
@@ -1,6 +1,6 @@
1
1
  import logging
2
2
 
3
- from typing import Callable, List
3
+ from typing import Any, Callable, List
4
4
 
5
5
  from dataclasses import dataclass, field
6
6
  from fast_depends import inject
@@ -28,7 +28,7 @@ class CronEntry:
28
28
  class RoboCowInternals:
29
29
  """Internal data for the cow"""
30
30
 
31
- profile: dict | None = field(
31
+ profile: dict[str, Any] | None = field(
32
32
  default=None,
33
33
  metadata=dict(
34
34
  description="""The profile of the cow, aka as the actor object in ActivityPub"""
@@ -90,11 +90,33 @@ class RoboCow:
90
90
 
91
91
  @staticmethod
92
92
  def create(**kwargs):
93
- """Creates a new cow. We note that
94
- `RoboCow.create(name="my name")` is equivalent
95
- to `RoboCow(information=Information(name="my name"))`.
93
+ """Creates a new cow, by creating a new [Information][roboherd.cow.types.Information].
94
+
95
+ ```python
96
+ >>> RoboCow.create(name="my cow")
97
+ RoboCow(information=Information(type='Service', handle=None, name='my cow', ...
98
+
99
+ ```
100
+
101
+ The parameter `description_md` is transformed from markdown to html and then
102
+ assigned to `description`.
103
+
104
+ ```python
105
+ >> cow = RoboCow.create(description_md="__bold__")
106
+ >> cow.information.description
107
+ '<p><strong>bold</strong></p>'
108
+
109
+ ```
96
110
  """
97
- return RoboCow(information=Information(**kwargs))
111
+
112
+ if "description_md" in kwargs:
113
+ import markdown
114
+
115
+ kwargs["description"] = markdown.markdown(kwargs["description_md"])
116
+ del kwargs["description_md"]
117
+
118
+ information = Information.model_validate(kwargs)
119
+ return RoboCow(information=information)
98
120
 
99
121
  def action(self, action: str = "*", activity_type: str = "*"):
100
122
  """Adds a handler for an event. Use "*" as a wildcard.
roboherd/cow/test_init.py CHANGED
@@ -1,3 +1,4 @@
1
+ import pytest
1
2
  from unittest.mock import AsyncMock
2
3
 
3
4
  from . import RoboCow
@@ -39,3 +40,13 @@ async def test_skip_startup():
39
40
  await cow.run_startup(connection=connection)
40
41
 
41
42
  connection.trigger.assert_not_awaited()
43
+
44
+
45
+ @pytest.mark.skipif(
46
+ not pytest.importorskip("markdown"), reason="markdown not installed"
47
+ )
48
+ def test_create():
49
+ cow = RoboCow.create(handle="testcow", description_md="__bold__")
50
+
51
+ assert cow.information.handle == "testcow"
52
+ assert cow.information.description == "<p><strong>bold</strong></p>"
@@ -4,18 +4,6 @@ from roboherd import RoboCow, RawData, PublishObject, ObjectFactory
4
4
 
5
5
  from .meta import meta_information
6
6
 
7
- bot = RoboCow.create(
8
- handle="jsonecho",
9
- name="JSON Echo {}",
10
- description="""<p>I'm a silly bot that replies to
11
- you with the JSON as received through a HTTP
12
- post request by
13
- <a href="https://codeberg.org/helge/cattle_grid">cattle_grid</a>.</p>
14
-
15
- """,
16
- meta_information=meta_information,
17
- )
18
-
19
7
 
20
8
  def reply_content(raw: dict) -> str:
21
9
  """Formats and escapes the JSON data:
@@ -35,17 +23,29 @@ def reply_content(raw: dict) -> str:
35
23
  return f"<pre><code>{json_formatted}</code></re>"
36
24
 
37
25
 
38
- @bot.incoming_create
39
- async def create(
40
- raw: RawData, publish_object: PublishObject, object_factory: ObjectFactory
41
- ):
42
- note = (
43
- object_factory.reply( # type: ignore
44
- raw.get("object"),
45
- content=reply_content(raw),
46
- )
47
- .as_public()
48
- .build()
26
+ try:
27
+ bot = RoboCow.create(
28
+ handle="jsonecho",
29
+ name="JSON Echo {}",
30
+ description_md="""I'm a silly bot that replies to
31
+ you with the JSON as received through a HTTP
32
+ post request by [cattle_grid](https://bovine.codeberg.page/cattle_grid/).""",
33
+ meta_information=meta_information,
49
34
  )
50
35
 
51
- await publish_object(note)
36
+ @bot.incoming_create
37
+ async def create(
38
+ raw: RawData, publish_object: PublishObject, object_factory: ObjectFactory
39
+ ):
40
+ note = (
41
+ object_factory.reply( # type: ignore
42
+ raw.get("object"),
43
+ content=reply_content(raw),
44
+ )
45
+ .as_public()
46
+ .build()
47
+ )
48
+
49
+ await publish_object(note)
50
+ except ImportError:
51
+ ...
roboherd/py.typed ADDED
File without changes
roboherd/register.py CHANGED
@@ -1,4 +1,3 @@
1
- import aiohttp
2
1
  import tomli_w
3
2
 
4
3
 
@@ -24,6 +23,8 @@ def create_config(
24
23
 
25
24
 
26
25
  async def register(config_file: str, name: str, password: str, fediverse: str):
26
+ import aiohttp
27
+
27
28
  async with aiohttp.ClientSession() as session:
28
29
  result = await session.post(
29
30
  "https://dev.bovine.social/register",
roboherd/version.py ADDED
@@ -0,0 +1 @@
1
+ __version__ = "0.1.12"
@@ -1,22 +1,23 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: roboherd
3
- Version: 0.1.10
3
+ Version: 0.1.12
4
4
  Summary: A Fediverse bot framework
5
5
  Project-URL: Documentation, https://bovine.codeberg.page/roboherd/
6
6
  Project-URL: Repository, https://codeberg.org/bovine/roboherd
7
7
  Requires-Python: >=3.11
8
- Requires-Dist: aiohttp>=3.11.12
9
8
  Requires-Dist: almabtrieb[mqtt]>=0.2
10
9
  Requires-Dist: apscheduler>=3.11.0
11
10
  Requires-Dist: click>=8.1.8
12
11
  Requires-Dist: cron-descriptor>=1.4.5
13
12
  Requires-Dist: dynaconf>=3.2.6
14
- Requires-Dist: fast-depends>=2.4.12
13
+ Requires-Dist: fast-depends>=3.0.0
15
14
  Requires-Dist: tomli-w>=1.1.0
16
- Requires-Dist: watchfiles>=1.0.4
17
15
  Provides-Extra: bovine
18
16
  Requires-Dist: bovine>=0.5.15; extra == 'bovine'
19
17
  Requires-Dist: markdown>=3.7; extra == 'bovine'
18
+ Provides-Extra: dev
19
+ Requires-Dist: aiohttp>=3.11.12; extra == 'dev'
20
+ Requires-Dist: watchfiles>=1.0.4; extra == 'dev'
20
21
  Description-Content-Type: text/markdown
21
22
 
22
23
  # Roboherd
@@ -1,25 +1,27 @@
1
1
  roboherd/__init__.py,sha256=E89YtYyL77iJDJJkHS4Pn0JdTbmkmQS7Cp_XPqpRgx8,533
2
- roboherd/__main__.py,sha256=DxxPrubMXNp_rqE-1S-S7pCn065CfQo2uHmxP1FWZU4,3655
3
- roboherd/register.py,sha256=jnnHv-epeyXHcmmulxJoHqT7uWmb_efFnCbdxojKOBM,1044
2
+ roboherd/__main__.py,sha256=q_Ucf-S_TlnVMYzZA58p1I8kQFwoCvVjMSe3ks1ihUs,3983
3
+ roboherd/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
4
+ roboherd/register.py,sha256=a3RKeDfyU-Lz7AWqJvQvY34Y8osmJPeHJDbgiTE5hYw,1049
4
5
  roboherd/test_validators.py,sha256=UiFgJkutmXBLjGpdLP2IBYCEf75quwnRHX7Z51G8Xqo,222
5
6
  roboherd/util.py,sha256=gG8Scht1xRfauUOdL7GrLf9e3UO-j88X2wEdc1Ymm3o,1748
6
7
  roboherd/validators.py,sha256=2mc43ZGwFazp4f3B9J4RxZCU4Y_ErSNotib8MnYVtmY,140
8
+ roboherd/version.py,sha256=LcIlFjHZFfiF9Rd4UHoakmombOFkxIYk00I181frGBM,23
7
9
  roboherd/annotations/__init__.py,sha256=BrP5UWiVnh8FwmHc6wEY3G69BStidGUpF8uP4Ea5-dg,1140
8
10
  roboherd/annotations/bovine.py,sha256=cFLUSFzTulikNjZb1lLq5v4tGjL1i7_dR3H6wimegCg,2322
9
- roboherd/annotations/common.py,sha256=n5rm8WTgsg116RczKdzm_VoPg1mBk_IMf2V7l8UgWKQ,1351
10
- roboherd/cow/__init__.py,sha256=wSfYordSLmn3azxWkZs36h3ipbS6NdPh9kAWyyg0NIU,6223
11
+ roboherd/annotations/common.py,sha256=HOysWNm4FRnFJ8Byn6UVyJHp60gh2Hsy2_5qCifpXF8,1386
12
+ roboherd/cow/__init__.py,sha256=NqkNhEyMxC-j5AVJyh2R5VJTzwNe4xId-Ot4JCr302U,6862
11
13
  roboherd/cow/const.py,sha256=fj5nUJUIlcpr1AU2Ur55ToR7iVmYv4UnfdxiQwguv-k,166
12
14
  roboherd/cow/handlers.py,sha256=k5Tc1M--wqmZ2EZvzIfID4dp8XE0rN18puMTKkNVjjE,1491
13
15
  roboherd/cow/profile.py,sha256=ldeYq50lh97dl50QjOZiGopEbXtCoEsE5QJoXB5XUYU,3330
14
16
  roboherd/cow/test_handlers.py,sha256=SwrZZcU_BD2BpJUFg18mFEsyUqu7N81-MkjIaGv7whQ,1673
15
- roboherd/cow/test_init.py,sha256=GrOFyEKbvkddrUQM7B0RFelNLc_rmdlxU_8C-DjoUh8,999
17
+ roboherd/cow/test_init.py,sha256=GT4OQRxc8fyQhHWaNNu0Qlh7A6J3hHzZw3G7xDZCwis,1321
16
18
  roboherd/cow/test_profile.py,sha256=f7HE0iVgbpuNv6znEqi-4l1o_8UZ9ufQpjSVP7Xf1wc,2160
17
19
  roboherd/cow/test_util.py,sha256=8FLRtVdSMmIo6NSpCpB9mS0PwOCpGgUeDAA1q6Gv0P4,430
18
20
  roboherd/cow/types.py,sha256=TGXTcPuND7xMly3xFXZyIR7UE3XWyF_MLRuBHWKoFEE,1925
19
21
  roboherd/cow/util.py,sha256=ASQn7AnSl5lskECqCyqOKn5BYC8yOces4FK3uNV8010,534
20
22
  roboherd/examples/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
21
23
  roboherd/examples/dev_null.py,sha256=P2_tVh5Y6Cm7A0FQzX7lRaBlXZZqBsia89Jnoa-s5ek,217
22
- roboherd/examples/json_echo.py,sha256=TB7sdshsTj7KKOxIc1DzkGeacA9JmIOhNOHwGzyRrVY,1208
24
+ roboherd/examples/json_echo.py,sha256=K4uWpOVnDAPoxTwvFiLGobTG0oeJjYa18kptRgaT6EU,1302
23
25
  roboherd/examples/meta.py,sha256=tFhHe-DJn2J13Mm22f-gFm5I8_3uQwLU4mAkrK2xzEM,170
24
26
  roboherd/examples/moocow.py,sha256=2bZ8oZOpysuf7l3DP3zM4YiaALQHFbWpbP3h_Xlok6E,974
25
27
  roboherd/examples/number.py,sha256=c4zALxrKR5POuAUTmzAF4wHVgXMPfrP736N7dgn4xzo,1845
@@ -38,7 +40,7 @@ roboherd/herd/manager/load.py,sha256=BoeBID2UGP--sIKwITABQkQv2lMc9Y8pyp7_nleu2bw
38
40
  roboherd/herd/manager/test_config.py,sha256=I2EP7nEUdBVO8Wqot7SRhzp5UZFr5oGIuFS7cNB2iFk,1745
39
41
  roboherd/herd/manager/test_load.py,sha256=zyu5LIChMfTnxu_tYK63-bSOHYn1K1zUlbDY5DkE3GY,514
40
42
  roboherd/herd/manager/test_manager.py,sha256=9pSMaH7zmN-zagYCIBpQcV3Q0sBT7XZSCvsmLVC0rOI,1047
41
- roboherd-0.1.10.dist-info/METADATA,sha256=rYVd_FKmmzULegTCdV9Xvp8W4Vn-DcKn_xokqfoUPPA,2206
42
- roboherd-0.1.10.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
43
- roboherd-0.1.10.dist-info/entry_points.txt,sha256=WebdVUmh8Ot-FupKJY6Du8LuFbmezt9yoy2UICqV3bE,52
44
- roboherd-0.1.10.dist-info/RECORD,,
43
+ roboherd-0.1.12.dist-info/METADATA,sha256=JitOq-gB0wsm3mokPow67oBsCqd2cazmEra4n5GRMJ8,2257
44
+ roboherd-0.1.12.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
45
+ roboherd-0.1.12.dist-info/entry_points.txt,sha256=WebdVUmh8Ot-FupKJY6Du8LuFbmezt9yoy2UICqV3bE,52
46
+ roboherd-0.1.12.dist-info/RECORD,,