meeb / django-distill

Minimal configuration static site generator for Django
MIT License
441 stars 35 forks source link

How can I render the static generated html files without GET Request to CMS #46

Closed qlitre closed 3 years ago

qlitre commented 3 years ago

Hello. I'm trying to create a Django blog site using a headless CMS. Today I found django-distill and succeeded in generating static html files.

python ./manage.py distill-local

I don't want to send a GET request every time I render, so I'm thinking of using django-distill. How can I display the statically generated site when I run python manage.py runserver? Is the static site delivered after deployment in the first place? Sorry for the rudimentary question.

I'll paste the source code that I think is relevant below.


#project/settings.py

...

STATIC_ROOT = Path(BASE_DIR, 'static')
DISTILL_DIR = Path(BASE_DIR, 'dist')

#project/urls.py
from django.contrib import admin
from django.urls import path, include

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', include('blog.urls'))
]
#blog.urls.py

from django_distill import distill_path, distill_url
from . import views
from django.conf import settings
import requests

app_name = 'blog'

def get_index():
    return None

def get_posts():
    end_point = '/post'
    url = getattr(settings, "BASE_URL", None)
    api_key = getattr(settings, "API_KEY", None)
    headers = {'API-KEY': api_key}
    res = requests.request('GET', url=url + end_point, headers=headers)
    for data in res.json()['contents']:
        yield data['id']

urlpatterns = [
    distill_path('',
                 views.post_list,
                 name='index',
                 distill_func=get_index,
                 distill_file='index.html'),

    distill_path('post/<slug:slug>.html',
                 views.post_detail,
                 name='post_detail',
                 distill_func=get_posts),
]
# blog/views.py

from django.shortcuts import render
import requests
from django.conf import settings
from django.http import Http404

def post_list(request):
    end_point = '/post'
    url = getattr(settings, "BASE_URL", None)
    api_key = getattr(settings, "API_KEY", None)
    headers = {'API-KEY': api_key}
    res = requests.request('GET', url=url + end_point, headers=headers)
    context = {
        'post_list': res.json()['contents']
    }

    return render(request, 'blog/index.html', context)

def post_detail(request, slug):
    end_point = f'/post/{slug}'
    url = getattr(settings, "BASE_URL", None)
    api_key = getattr(settings, "API_KEY", None)
    headers = {'API-KEY': api_key}
    res = requests.request('GET', url=url + end_point, headers=headers)
    if res.status_code != 200:
        raise Http404

    context = {
        'post': res.json()
    }

    return render(request, 'blog/post_detail.html', context)
meeb commented 3 years ago

If I understand your question correctly, you would just generate the static site and then host the files somewhere (any static web server like nginx, or via a build system like github pages, netlify and the like). Typically the flow distill was designed for was:

  1. Get a site that works fine locally with runserver
  2. Wrap all the URLs in distill_path
  3. Generate a static copy of your site and host it somewhere (or use a build system to build it for you)
  4. Rebuild the site when content is updated

It's not much more complicated than that. Are you trying to do something else here?

qlitre commented 3 years ago

I understood that that the distribution of static files is done by the settings on the web server side. thank you.

Let me check at the end. Do I need to do anything more special about 2. Wrap all the URLs in distill_path ?

meeb commented 3 years ago

No not really, pretty much if your site works locally as you want it to under the local runserver dev server and distill-local writes your site out to a directory locally you're pretty much done with integrating with distill. All distill does is loop through any URLs registered with distill_path then render the output HTML and then saves it to disk. From your pasted code it looks like you've already done that so you should be generating a fully working static site and be good to go.

If you want your site to rebuild automatically if you edit content on your remote CMS you'll have to look at webhooks to trigger a build somewhere or something of that nature.

qlitre commented 3 years ago

Thanks your reply. I was able to deploy to Netlify and deliver the files in dist. But I stumbled upon updating the dist file. I will check it a bit more.

Thank you for your kind support.

meeb commented 3 years ago

Not a problem, glad you find the library useful. I'll close the issue for now but feel free to re-open it or create another one if you need any further pointers.