pyproject-build

This commit is contained in:
Untone 2023-10-14 14:52:04 +03:00
parent bc2fc7c9a0
commit 499893e10b
13 changed files with 100 additions and 75 deletions

View File

@ -1,6 +0,0 @@
[flake8]
ignore = E203,W504,W191,W503
exclude = .git
max-complexity = 10
max-line-length = 108
indent-string = ' '

View File

@ -1,3 +1,9 @@
[0.2.13]
- migrated to pyproject and poetry
- validators added
- fixed graphql requests for core api
- uses official redis[hiredis] async
[0.2.12]
- sigil is back for test

View File

@ -1,8 +1,20 @@
# Use an official Python runtime as a parent image
FROM python:slim
# Set the working directory in the container to /app
WORKDIR /app
# Add metadata to the image to describe that the container is listening on port 80
EXPOSE 80
COPY requirements.txt .
RUN apt-get update && apt-get install -y gcc && pip install -r requirements.txt
COPY . .
CMD ["python", "server.py"]
# Copy the current directory contents into the container at /app
COPY . /app
# Install any needed packages specified in pyproject.toml
RUN apt-get update && apt-get install -y gcc curl && \
curl -sSL https://install.python-poetry.org | python - && \
poetry config virtualenvs.create false && \
poetry install --no-dev
# Run server.py when the container launches
CMD ["python", "server.py"]

54
pyproject.toml Normal file
View File

@ -0,0 +1,54 @@
[build-system]
requires = ["poetry-core>=1.0.0"]
build-backend = "poetry.core.masonry.api"
[tool.poetry]
name = "discoursio-inbox"
version = "0.2.13"
description = "Inbox server for discours.io"
authors = ["Tony Rewin <anton.rewin@gmail.com>"]
[tool.poetry.dependencies]
python = "^3.8"
sentry-sdk = "^1.4.3"
redis = {extras = ["hiredis"], version = "^3.5.3"}
ariadne = "^0.13.0"
starlette = "^0.14.2"
uvicorn = "^0.15.0"
httpx = "^0.18.2"
itsdangerous = "^2.0.1"
[tool.poetry.dev-dependencies]
pytest = "^6.2.5"
[tool.black]
line-length = 120
target-version = ['py312']
include = '\.pyi?$'
exclude = '''
(
/(
\.eggs # exclude a few common directories in the
| \.git # root of the project
| \.hg
| \.mypy_cache
| \.tox
| \.venv
| _build
| buck-out
| build
| dist
)/
| foo.py # also separately exclude a file named foo.py in
# the root of the project
)
'''
[tool.isort]
multi_line_output = 3
include_trailing_comma = true
force_grid_wrap = 0
use_parentheses = true
ensure_newline_before_comments = true
line_length = 120

View File

@ -1,13 +0,0 @@
sentry-sdk
redis[hiredis]
ariadne
starlette
uvicorn
httpx
itsdangerous
######## development deps
isort
brunette
flake8
mypy
its

View File

@ -1,7 +1,7 @@
import json
import uuid
from datetime import datetime, timezone
from validators.chat import Chat
from validators.inbox import Chat
from services.auth import login_required
from services.redis import redis
from services.schema import mutation
@ -85,6 +85,9 @@ async def create_chat(_, info, title="", members=None):
for member_id in members:
await redis.execute("SADD", f"chats_by_author/{member_id}", chat_id)
print(f"[resolvers.chatss] creating: {chat}")
await redis.execute("SET", f"chats/{chat_id}", json.dumps(chat))
await redis.execute("SET", f"chats/{chat_id}/next_message_id", str(0))

View File

@ -4,7 +4,7 @@ from services.core import get_author, get_network
from services.redis import redis
from services.auth import login_required
from services.schema import query
from validators.chat import Message, Chat, ChatMember
from validators.inbox import Message, Chat, ChatMember
from .chats import create_chat
from .unread import get_unread_counter
import asyncio
@ -60,7 +60,7 @@ async def load_chats(
if len(cids) == 0:
print(f"[resolvers.load] no chats for user with id={author_id}")
r = await create_chat(None, info, members=[2]) # member with id = 2 is discours
print(f"[resolvers.load] created chat: {r}")
print(f"[resolvers.load] created chat: {r['chat']}")
cids.append(r["chat"]["id"])
for cid in cids:
async with lock:
@ -74,7 +74,6 @@ async def load_chats(
c["members"] = []
for member_id in member_ids:
a = await get_author(member_id)
print(f"[resolvers.load] author with id={member_id}: {a}")
if a:
a["online"] = a.get("id") in members_online
c["members"].append(a)

View File

@ -1,7 +1,7 @@
import json
from datetime import datetime, timezone
from typing import List
from validators.chat import Message
from validators.inbox import Message
from services.auth import login_required
from services.presence import notify_message
from services.redis import redis

View File

@ -47,7 +47,7 @@ async def check_auth(req):
is_authenticated = user_id is not None
return is_authenticated, user_id
except Exception as e:
print(f"response contains no proper data: {r}")
print(f"{e}: {r}")
return False, None

View File

@ -9,7 +9,9 @@ headers = {"Content-Type": "application/json"}
async def get_author(author_id):
gql = {
"query": "query GetAuthorById($author_id: Int!) { getAuthorById(author_id: $author_id) { id slug userpic name lastSeen } }",
"query": '''query GetAuthorById($author_id: Int!) {
getAuthorById(author_id: $author_id) { id slug userpic name lastSeen }
}''',
"operation": "GetAuthorById",
"variables": {"author_id": author_id},
}
@ -18,9 +20,7 @@ async def get_author(author_id):
response = await client.post(
API_BASE, headers=headers, data=json.dumps(gql)
)
print(
f"[services.core] get_author response: {response.status_code} {response.text}"
)
print(f"[services.core] get_author: {response.status_code} {response.text}")
if response.status_code != 200:
return None
r = response.json()
@ -33,7 +33,11 @@ async def get_author(author_id):
async def get_network(author_id: int, limit: int = 50, offset: int = 0) -> list:
gql = {
"query": "query LoadAuthors($author_id: Int!, $limit: Int, $offset: Int) { authorFollowings(author_id: $author_id, limit: $limit, offset: $offset) { id slug userpic name } }",
"query": '''query LoadAuthors($author_id: Int!, $limit: Int, $offset: Int) {
authorFollowings(author_id: $author_id, limit: $limit, offset: $offset) {
id slug userpic name
}
}''',
"operation": "LoadAuthors",
"variables": {"author_id": author_id, "limit": limit, "offset": offset},
}
@ -60,7 +64,11 @@ async def get_network(author_id: int, limit: int = 50, offset: int = 0) -> list:
async def get_followers(author_id, amount):
gql = {
"query": "query LoadAuthors($author_id: Int!, $limit: Int, $offset: Int) { authorFollowers(author_id: $author_id, limit: $limit) { id slug userpic name } }",
"query": '''query LoadAuthors($author_id: Int!, $limit: Int, $offset: Int) {
authorFollowers(author_id: $author_id, limit: $limit) {
id slug userpic name
}
}''',
"operation": "LoadAuthors",
"variables": {"author_id": author_id, "limit": amount},
}
@ -75,5 +83,6 @@ async def get_followers(author_id, amount):
r = response.json()
followers = r.get("data", {}).get("authorFollowers", [])
except Exception as e:
print(e)
followers = []
return followers

View File

@ -1,6 +1,6 @@
import json
from services.redis import redis
from validators.chat import Message
from validators.inbox import Message
async def notify_message(message: Message, chat_id: str):

View File

@ -1,39 +0,0 @@
[isort]
# https://github.com/PyCQA/isort
line_length = 120
multi_line_output = 3
include_trailing_comma = true
force_grid_wrap = 0
use_parentheses = true
force_alphabetical_sort = false
[tool:brunette]
# https://github.com/odwyersoftware/brunette
line-length = 120
single-quotes = false
[flake8]
# https://github.com/PyCQA/flake8
exclude = .git,__pycache__,.mypy_cache,.vercel
max-line-length = 120
max-complexity = 15
select = B,C,E,F,W,T4,B9
# E203: Whitespace before ':'
# E266: Too many leading '#' for block comment
# E501: Line too long (82 > 79 characters)
# E722: Do not use bare except, specify exception instead
# W503: Line break occurred before a binary operator
# F403: 'from module import *' used; unable to detect undefined names
# C901: Function is too complex
ignore = E203,E266,E501,E722,W503,F403,C901
[mypy]
# https://github.com/python/mypy
ignore_missing_imports = true
warn_return_any = false
warn_unused_configs = true
disallow_untyped_calls = true
disallow_untyped_defs = true
disallow_incomplete_defs = true
[mypy-api.*]
ignore_errors = true