Skip to content

Quickstart

A working blog in about five minutes — models, views, URLs, templates.

New here? Installation covers installing the buraq command first.

Terminal window
buraq startproject myblog
cd myblog
uv sync # or: python -m venv .venv && pip install buraq
source .venv/bin/activate # Windows: .venv\Scripts\activate

startproject writes the files and installs nothing. uv sync reads the pyproject.toml it just wrote and builds .venv inside the project — that is the environment the project runs in, and where your own packages go.

Terminal window
buraq startapp posts
posts/models.py
from buraq import models
class Post(models.Model):
title = models.CharField(max_length=200)
slug = models.SlugField(max_length=200, unique=True)
content = models.TextField()
is_published = models.BooleanField(default=False)
created_at = models.DateTimeField(auto_now_add=True)

Every view is async, and so is render:

posts/views.py
from buraq.shortcuts import get_object_or_404, render
from posts.models import Post
async def post_list(request):
posts = await Post.objects.filter(is_published=True).order_by("-created_at")
return await render(request, "posts/list.html", {"posts": posts})
async def post_detail(request, slug: str):
post = await get_object_or_404(Post, slug=slug)
return await render(request, "posts/detail.html", {"post": post})

Templates live under the project’s templates/ directory, in a folder matching the paths the views asked for:

templates/posts/list.html
<h1>Posts</h1>
<ul>
{% for post in posts %}
<li><a href="/posts/{{ post.slug }}">{{ post.title }}</a></li>
{% else %}
<li>Nothing published yet.</li>
{% endfor %}
</ul>
templates/posts/detail.html
<h1>{{ post.title }}</h1>
<p>{{ post.content }}</p>
<a href="/posts/">Back to all posts</a>
posts/urls.py
from buraq.urls import path
from posts import views
urlpatterns = [
path("/", views.post_list, name="post_list"),
path("/<str:slug>", views.post_detail, name="post_detail"),
]
config/urls.py
from buraq.urls import include, path
urlpatterns = [
path("/posts", include("posts.urls")),
]
config/settings.py
INSTALLED_APPS = [
"buraq.contrib.auth",
"posts", # add this
]
Terminal window
buraq migrate # apply the migrations Buraq ships
buraq makemigrations "add posts" # generate one for your model
buraq migrate # apply it

Three commands on a new project, two from then on. Autogeneration compares your models against the database and will not run while the database is behind, and a new project starts behind — buraq.contrib.auth ships migrations of its own. The first migrate clears that, and afterwards it is the usual makemigrations then migrate.

Terminal window
buraq runserver

Open http://127.0.0.1:8000/posts/. It is empty until you add a post, which the admin or buraq shell can do:

Terminal window
buraq shell -c "await Post.objects.create(title='Hello', slug='hello', content='First post.', is_published=True)"

Auto-generated API docs are at /api/docs.

  • Models — fields, relationships, Meta options
  • Views — function and class-based
  • Templates — inheritance, tags, filters
  • Admin — a working admin for your models