fastogram 0.0.2__tar.gz → 0.0.4__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 (89) hide show
  1. {fastogram-0.0.2 → fastogram-0.0.4}/Makefile +15 -2
  2. {fastogram-0.0.2 → fastogram-0.0.4}/PKG-INFO +12 -3
  3. {fastogram-0.0.2 → fastogram-0.0.4}/README.md +11 -2
  4. {fastogram-0.0.2 → fastogram-0.0.4}/pyproject.toml +1 -1
  5. fastogram-0.0.4/scripts/bump_version.py +77 -0
  6. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/cli.py +49 -10
  7. {fastogram-0.0.2 → fastogram-0.0.4}/.gitignore +0 -0
  8. {fastogram-0.0.2 → fastogram-0.0.4}/.pypi-token.example +0 -0
  9. {fastogram-0.0.2 → fastogram-0.0.4}/scripts/sync_template.py +0 -0
  10. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/__init__.py +0 -0
  11. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/.dockerignore +0 -0
  12. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/.env.example +0 -0
  13. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/.gitignore +0 -0
  14. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/.pre-commit-config.yaml +0 -0
  15. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/.python-version +0 -0
  16. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/AGENTS.md +0 -0
  17. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/README.md +0 -0
  18. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/TODO.md +0 -0
  19. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/VIBECODER.md +0 -0
  20. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/alembic/env.py +0 -0
  21. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/alembic.ini +0 -0
  22. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/__init__.py +0 -0
  23. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/api/__init__.py +0 -0
  24. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/api/deps.py +0 -0
  25. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/api/routes/health.py +0 -0
  26. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bootstrap/__init__.py +0 -0
  27. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bootstrap/container.py +0 -0
  28. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bootstrap/logging.py +0 -0
  29. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bootstrap/request_context.py +0 -0
  30. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bootstrap/request_id_middleware.py +0 -0
  31. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bootstrap/startup_checks.py +0 -0
  32. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/__init__.py +0 -0
  33. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/dispatcher.py +0 -0
  34. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/handlers/__init__.py +0 -0
  35. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/handlers/start.py +0 -0
  36. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/keyboards/__init__.py +0 -0
  37. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/middlewares/__init__.py +0 -0
  38. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/middlewares/error_logging.py +0 -0
  39. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/middlewares/rate_limit.py +0 -0
  40. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/middlewares/rate_limit_backends.py +0 -0
  41. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/middlewares/service_injection.py +0 -0
  42. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/bot/states/__init__.py +0 -0
  43. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/cli.py +0 -0
  44. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/core/__init__.py +0 -0
  45. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/core/config.py +0 -0
  46. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/core/db.py +0 -0
  47. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/core/security.py +0 -0
  48. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/integrations/__init__.py +0 -0
  49. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/integrations/telegram.py +0 -0
  50. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/jobs/__init__.py +0 -0
  51. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/jobs/worker.py +0 -0
  52. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/main.py +0 -0
  53. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/modules/__init__.py +0 -0
  54. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/modules/users/__init__.py +0 -0
  55. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/modules/users/models.py +0 -0
  56. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/modules/users/repository.py +0 -0
  57. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/modules/users/schemas.py +0 -0
  58. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/modules/users/service.py +0 -0
  59. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/services/__init__.py +0 -0
  60. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/services/audit.py +0 -0
  61. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/services/health.py +0 -0
  62. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/services/payments.py +0 -0
  63. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/services/storage.py +0 -0
  64. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/services/telegram_webhook.py +0 -0
  65. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/services/users.py +0 -0
  66. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/webapp/static/app.js +0 -0
  67. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/app/webapp/templates/index.html +0 -0
  68. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/docker/Dockerfile +0 -0
  69. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/docker/docker-compose.yml +0 -0
  70. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/docker/nginx.conf +0 -0
  71. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/manage.py +0 -0
  72. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/pyproject.toml +0 -0
  73. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/scripts/__init__.py +0 -0
  74. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/scripts/admin_tasks.py +0 -0
  75. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/scripts/seed_data.py +0 -0
  76. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/scripts/set_webhook.py +0 -0
  77. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/__init__.py +0 -0
  78. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/architecture/test_framework_leak.py +0 -0
  79. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/architecture/test_no_db_in_handlers.py +0 -0
  80. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/architecture/test_no_db_in_routes.py +0 -0
  81. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/architecture/test_service_instantiation.py +0 -0
  82. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/architecture/test_session_scope_usage.py +0 -0
  83. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/architecture/test_transaction_ownership.py +0 -0
  84. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/conftest.py +0 -0
  85. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/test_config_delivery_mode.py +0 -0
  86. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/test_request_id.py +0 -0
  87. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/tests/test_startup_checks.py +0 -0
  88. {fastogram-0.0.2 → fastogram-0.0.4}/src/fastogram/templates/fastgram/uv.lock +0 -0
  89. {fastogram-0.0.2 → fastogram-0.0.4}/uv.lock +0 -0
@@ -1,15 +1,28 @@
1
1
  # Fastogram CLI - Makefile for maintainers
2
2
 
3
+ BUMP ?= patch
4
+ VERSION ?=
5
+
3
6
  .PHONY: sync
4
7
  sync:
5
8
  python scripts/sync_template.py
6
9
 
10
+ .PHONY: bump-version
11
+ bump-version:
12
+ python scripts/bump_version.py $(if $(VERSION),--version $(VERSION),--bump $(BUMP))
13
+
7
14
  .PHONY: build
8
15
  build:
9
16
  rm -rf dist
10
17
  uv build
11
18
 
12
- .PHONY: publish
13
- publish: build
19
+ .PHONY: upload
20
+ upload:
14
21
  @test -f .pypi-token || (echo "Create .pypi-token with your PyPI token (see .pypi-token.example)"; exit 1)
15
22
  uv tool run twine upload -u __token__ -p $$(cat .pypi-token) dist/*
23
+
24
+ .PHONY: publish
25
+ publish:
26
+ $(MAKE) bump-version BUMP=$(BUMP) VERSION="$(VERSION)"
27
+ $(MAKE) build
28
+ $(MAKE) upload
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: fastogram
3
- Version: 0.0.2
3
+ Version: 0.0.4
4
4
  Summary: Opinionated FastAPI + Aiogram project generator (FastGram template)
5
5
  Author-email: Abubeker Afdel <ibnuafdel@gmail.com>
6
6
  License: MIT
@@ -44,7 +44,9 @@ python manage.py run --reload
44
44
 
45
45
  ```bash
46
46
  fastogram new my-bot # Create ./my-bot/
47
- fastogram new my-bot -d ~/code # Create ~/code/my-bot/
47
+ fastogram new . # Scaffold in current directory (ignores .venv)
48
+ fastogram new . --force # Scaffold in a non-empty current directory
49
+ fastogram new my-bot -d ~/code # Create ~/code/my-bot/
48
50
  ```
49
51
 
50
52
  ---
@@ -72,8 +74,15 @@ The sync copies FastGram → `src/fastogram/templates/fastgram/`, excluding `.gi
72
74
  # 1. Create .pypi-token with your PyPI API token (from pypi.org/manage/account/token/)
73
75
  echo "pypi-your-token-here" > .pypi-token
74
76
 
75
- # 2. Publish
77
+ # 2. Publish (defaults to patch bump: 0.0.3 -> 0.0.4)
76
78
  make publish
79
+
80
+ # Publish with a minor or major bump
81
+ make publish BUMP=minor
82
+ make publish BUMP=major
83
+
84
+ # Publish with an explicit version
85
+ make publish VERSION=1.2.3
77
86
  ```
78
87
 
79
88
  `.pypi-token` is in `.gitignore` — it will never be committed.
@@ -35,7 +35,9 @@ python manage.py run --reload
35
35
 
36
36
  ```bash
37
37
  fastogram new my-bot # Create ./my-bot/
38
- fastogram new my-bot -d ~/code # Create ~/code/my-bot/
38
+ fastogram new . # Scaffold in current directory (ignores .venv)
39
+ fastogram new . --force # Scaffold in a non-empty current directory
40
+ fastogram new my-bot -d ~/code # Create ~/code/my-bot/
39
41
  ```
40
42
 
41
43
  ---
@@ -63,8 +65,15 @@ The sync copies FastGram → `src/fastogram/templates/fastgram/`, excluding `.gi
63
65
  # 1. Create .pypi-token with your PyPI API token (from pypi.org/manage/account/token/)
64
66
  echo "pypi-your-token-here" > .pypi-token
65
67
 
66
- # 2. Publish
68
+ # 2. Publish (defaults to patch bump: 0.0.3 -> 0.0.4)
67
69
  make publish
70
+
71
+ # Publish with a minor or major bump
72
+ make publish BUMP=minor
73
+ make publish BUMP=major
74
+
75
+ # Publish with an explicit version
76
+ make publish VERSION=1.2.3
68
77
  ```
69
78
 
70
79
  `.pypi-token` is in `.gitignore` — it will never be committed.
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
4
4
 
5
5
  [project]
6
6
  name = "fastogram"
7
- version = "0.0.2"
7
+ version = "0.0.4"
8
8
  description = "Opinionated FastAPI + Aiogram project generator (FastGram template)"
9
9
  readme = "README.md"
10
10
  requires-python = ">=3.10"
@@ -0,0 +1,77 @@
1
+ #!/usr/bin/env python3
2
+ """Bump the package version in pyproject.toml."""
3
+
4
+ from __future__ import annotations
5
+
6
+ import argparse
7
+ import re
8
+ import sys
9
+ from pathlib import Path
10
+
11
+
12
+ VERSION_RE = re.compile(r'(?m)^(version\s*=\s*")(\d+)\.(\d+)\.(\d+)(")$')
13
+ VALID_BUMPS = {"patch", "minor", "major"}
14
+
15
+
16
+ def parse_args() -> argparse.Namespace:
17
+ parser = argparse.ArgumentParser(
18
+ description="Bump Fastogram package version in pyproject.toml."
19
+ )
20
+ parser.add_argument(
21
+ "--bump",
22
+ choices=sorted(VALID_BUMPS),
23
+ default="patch",
24
+ help="Which semver segment to increment. Default: patch",
25
+ )
26
+ parser.add_argument(
27
+ "--version",
28
+ help="Set an explicit version like 1.2.3 instead of incrementing",
29
+ )
30
+ parser.add_argument(
31
+ "--file",
32
+ default="pyproject.toml",
33
+ help="Path to pyproject.toml. Default: ./pyproject.toml",
34
+ )
35
+ return parser.parse_args()
36
+
37
+
38
+ def compute_next_version(current: str, bump: str) -> str:
39
+ major, minor, patch = map(int, current.split("."))
40
+ if bump == "major":
41
+ return f"{major + 1}.0.0"
42
+ if bump == "minor":
43
+ return f"{major}.{minor + 1}.0"
44
+ return f"{major}.{minor}.{patch + 1}"
45
+
46
+
47
+ def main() -> int:
48
+ args = parse_args()
49
+ pyproject_path = Path(args.file)
50
+ text = pyproject_path.read_text(encoding="utf-8")
51
+ match = VERSION_RE.search(text)
52
+ if not match:
53
+ print("Error: could not find a simple X.Y.Z version in pyproject.toml.", file=sys.stderr)
54
+ return 1
55
+
56
+ current_version = ".".join(match.group(i) for i in range(2, 5))
57
+
58
+ if args.version:
59
+ if not re.fullmatch(r"\d+\.\d+\.\d+", args.version):
60
+ print("Error: --version must be in X.Y.Z format.", file=sys.stderr)
61
+ return 1
62
+ next_version = args.version
63
+ else:
64
+ next_version = compute_next_version(current_version, args.bump)
65
+
66
+ if next_version == current_version:
67
+ print(f"Version unchanged: {current_version}")
68
+ return 0
69
+
70
+ updated = VERSION_RE.sub(rf"\g<1>{next_version}\g<5>", text, count=1)
71
+ pyproject_path.write_text(updated, encoding="utf-8")
72
+ print(f"Bumped version: {current_version} -> {next_version}")
73
+ return 0
74
+
75
+
76
+ if __name__ == "__main__":
77
+ raise SystemExit(main())
@@ -10,6 +10,7 @@ from pathlib import Path
10
10
  # Template lives inside the package (bundled at pip install time)
11
11
  _PACKAGE_ROOT = Path(__file__).resolve().parent
12
12
  _TEMPLATE_DIR = _PACKAGE_ROOT / "templates" / "fastgram"
13
+ _IGNORED_EXISTING_ENTRIES = {".venv"}
13
14
 
14
15
 
15
16
  def _normalize_project_name(raw: str) -> str:
@@ -45,7 +46,22 @@ def _copy_and_customize(
45
46
  )
46
47
 
47
48
 
48
- def cmd_new(project_name: str | None = None, target_dir: str | None = None) -> int:
49
+ def _blocking_entries(dest: Path, force: bool) -> list[Path]:
50
+ if force or not dest.exists():
51
+ return []
52
+
53
+ return [
54
+ entry
55
+ for entry in dest.iterdir()
56
+ if entry.name not in _IGNORED_EXISTING_ENTRIES
57
+ ]
58
+
59
+
60
+ def cmd_new(
61
+ project_name: str | None = None,
62
+ target_dir: str | None = None,
63
+ force: bool = False,
64
+ ) -> int:
49
65
  """Create a new FastGram project."""
50
66
  if not _TEMPLATE_DIR.exists():
51
67
  print(
@@ -54,11 +70,26 @@ def cmd_new(project_name: str | None = None, target_dir: str | None = None) -> i
54
70
  )
55
71
  return 1
56
72
 
57
- slug = _normalize_project_name(project_name or "fastgram-app")
58
- dest = Path(target_dir or ".").resolve() / slug
73
+ use_cwd = project_name == "." or project_name == ""
74
+ base = Path(target_dir or ".").resolve()
75
+
76
+ if use_cwd:
77
+ dest = base
78
+ slug = base.name or "fastgram-app"
79
+ else:
80
+ slug = _normalize_project_name(project_name or "fastgram-app")
81
+ dest = base / slug
59
82
 
60
- if dest.exists() and any(dest.iterdir()):
61
- print(f"Error: Directory already exists and is not empty: {dest}", file=sys.stderr)
83
+ blocking_entries = _blocking_entries(dest, force)
84
+ if blocking_entries:
85
+ print(
86
+ (
87
+ f"Error: Directory already exists and is not empty: {dest}\n"
88
+ "Hint: `.venv` is ignored automatically. "
89
+ "Use `--force` to scaffold into a non-empty directory."
90
+ ),
91
+ file=sys.stderr,
92
+ )
62
93
  return 1
63
94
 
64
95
  _copy_and_customize(_TEMPLATE_DIR, dest, slug)
@@ -66,7 +97,8 @@ def cmd_new(project_name: str | None = None, target_dir: str | None = None) -> i
66
97
  print(f"Created project: {dest}")
67
98
  print()
68
99
  print("Next steps:")
69
- print(f" cd {slug}")
100
+ if not use_cwd:
101
+ print(f" cd {dest.name}")
70
102
  print(" uv sync")
71
103
  print(" # Edit .env with your TELEGRAM_BOT_TOKEN")
72
104
  print(" python manage.py setup")
@@ -87,8 +119,8 @@ def main() -> None:
87
119
  new_parser.add_argument(
88
120
  "project_name",
89
121
  nargs="?",
90
- default="fastgram-app",
91
- help="Project name (e.g. my-telegram-bot). Default: fastgram-app",
122
+ default=".",
123
+ help='Project name (e.g. my-bot). Use "." to scaffold in current directory',
92
124
  )
93
125
  new_parser.add_argument(
94
126
  "-d",
@@ -97,14 +129,21 @@ def main() -> None:
97
129
  default=".",
98
130
  help="Directory to create the project in. Default: current directory",
99
131
  )
132
+ new_parser.add_argument(
133
+ "--force",
134
+ action="store_true",
135
+ help="Scaffold into a non-empty directory",
136
+ )
100
137
 
101
138
  args = parser.parse_args()
102
139
  if args.command == "new":
103
- sys.exit(cmd_new(args.project_name, args.target_dir))
140
+ sys.exit(cmd_new(args.project_name, args.target_dir, args.force))
104
141
  else:
105
142
  parser.print_help()
106
143
  print()
107
144
  print("Examples:")
108
- print(" fastogram new my-bot")
145
+ print(" fastogram new my-bot # Create ./my-bot/")
146
+ print(" fastogram new . # Scaffold in current directory")
147
+ print(" fastogram new . --force # Scaffold into a non-empty directory")
109
148
  print(" fastogram new my-bot -d ~/projects")
110
149
  sys.exit(0)
File without changes
File without changes
File without changes