154 lines
3.9 KiB
Python
154 lines
3.9 KiB
Python
# Agenten Plattform
|
|
#
|
|
# (c) 2024 Magnus Bender
|
|
# Institute of Humanities-Centered Artificial Intelligence (CHAI)
|
|
# Universitaet Hamburg
|
|
# https://www.chai.uni-hamburg.de/~bender
|
|
#
|
|
# source code released under the terms of GNU Public License Version 3
|
|
# https://www.gnu.org/licenses/gpl-3.0.txt
|
|
|
|
"""
|
|
Access to the management, e.g., get the list of messages and single messages.
|
|
Manually send messages (if necessary, the platforms should do this).
|
|
|
|
### Example
|
|
```python
|
|
|
|
m_request = ManagementRequest()
|
|
|
|
m_request.get_message(count=12)
|
|
# MessageDbRow(count=12 sender='from' recipient='to' ...
|
|
|
|
m_request.list_messages(id="test", limit=2)
|
|
# [
|
|
# MessageDbRow(count=7256, sender='management', ...),
|
|
# MessageDbRow(count=7255, sender='management', ...),
|
|
# ]
|
|
|
|
m_request.total_messages(id="test")
|
|
# 31
|
|
|
|
```
|
|
|
|
See also `ums.example.__main__` and run in Docker via ``docker compose exec management python -m ums.example``
|
|
"""
|
|
|
|
import os
|
|
from typing import List, Dict, Any
|
|
|
|
import requests
|
|
from pydantic import validate_call
|
|
|
|
from ums.utils.types import AgentMessage, AgentResponse, MessageDbRow
|
|
|
|
|
|
class RequestException(Exception):
|
|
"""
|
|
Raised on http and similar errors.
|
|
"""
|
|
pass
|
|
|
|
class ManagementRequest():
|
|
|
|
MANAGEMENT_URL = os.environ.get('MANAGEMENT_URL', 'http://127.0.0.1:80').strip().strip('/')
|
|
|
|
@validate_call
|
|
def __init__(self, allow_lazy:bool=True):
|
|
"""
|
|
If `allow_lazy` is active, the type checking (by pydantic) is less strict.
|
|
E.g. it does not require that all files in the data section of messages must exist on the file system.
|
|
"""
|
|
self.allow_lazy = allow_lazy
|
|
self.pydantic_context = {
|
|
"require_file_exists": not self.allow_lazy
|
|
}
|
|
|
|
@validate_call
|
|
def get_message(self, count:int) -> MessageDbRow:
|
|
"""
|
|
Get a message (like a table row) from the management by using the `count`.
|
|
"""
|
|
row = self._get_request(
|
|
'list/single',
|
|
{"count": count}
|
|
)
|
|
return MessageDbRow.model_validate(
|
|
row, context=self.pydantic_context
|
|
)
|
|
|
|
@validate_call
|
|
def list_messages(self,
|
|
id:str|None=None, sender:str|None=None, recipient:str|None=None,
|
|
processed:bool|None=None, solution:bool|None=None,
|
|
time_after:int|None=None, time_before:int|None=None,
|
|
limit:int=10, offset:int=0
|
|
) -> List[MessageDbRow]:
|
|
"""
|
|
Get the rows in the tables as list of messages.
|
|
The arguments are used for filtering.
|
|
"""
|
|
|
|
kwargs = locals().copy()
|
|
params = {}
|
|
|
|
for k,v in kwargs.items():
|
|
if k not in ('self',) and not v is None:
|
|
params[k] = v
|
|
|
|
rows = self._get_request('list', params)
|
|
|
|
return [
|
|
MessageDbRow.model_validate(
|
|
row, context=self.pydantic_context
|
|
) for row in rows
|
|
]
|
|
|
|
@validate_call
|
|
def total_messages(self,
|
|
id:str|None=None, sender:str|None=None, recipient:str|None=None,
|
|
processed:bool|None=None, solution:bool|None=None,
|
|
time_after:int|None=None, time_before:int|None=None
|
|
) -> int:
|
|
"""
|
|
Get the total number of rows in the tables matching the filters.
|
|
"""
|
|
|
|
kwargs = locals().copy()
|
|
params = {}
|
|
|
|
for k,v in kwargs.items():
|
|
if k not in ('self',) and not v is None:
|
|
params[k] = v
|
|
|
|
return int(self._get_request('app/table/total', params))
|
|
|
|
def _get_request(self, endpoint:str, params:Dict[str, Any]):
|
|
r = requests.get(
|
|
"{}/{}".format(self.MANAGEMENT_URL, endpoint),
|
|
params=params
|
|
)
|
|
|
|
if r.status_code == 200:
|
|
return r.json()
|
|
else:
|
|
raise RequestException(str(r.text)+"\n"+str(r.headers))
|
|
|
|
@validate_call
|
|
def send_message(self, ) -> AgentResponse:
|
|
# TODO
|
|
pass
|
|
|
|
def _post_request(self, message:AgentMessage) -> AgentResponse:
|
|
# TODO
|
|
|
|
r = requests.post(
|
|
"{}/message".format(self.url),
|
|
data=message.model_dump_json(),
|
|
headers={"accept" : "application/json", "content-type" : "application/json"}
|
|
)
|
|
|
|
if r.status_code == 200:
|
|
return AgentResponse.model_validate_json(r.text)
|
|
else:
|
|
return AgentResponse(count=-1, error=True, error_msg=str(r.text)+str(r.headers)) |