lektor / lektor-website

The main lektor website.
https://www.getlektor.com/
Other
160 stars 134 forks source link

Add HAL plugin #346

Closed truenicoco closed 1 year ago

dairiki commented 2 years ago

@truenicoco Thank you for the contribution!

I have created a couple of PRs for updates to the lektor-hal documentation:

Once those are addressed, I will merge this PR.

truenicoco commented 2 years ago

Hello! Thanks for your reply and contributions that I have merged. I moved the project to sourcehut, but this does not change anything for the lektor website I guess.

Unrelated, but I tried to reach out on gitter and the chat does not seem to have any active users. So maybe you could guide me here. :) Is there an easy way to invalidate the cache of pages using this plugin? I guess this would require to do something more subtle than "add something to the global namespace of jinja templates", but I am not sure what would be the right approach.

dairiki commented 2 years ago

Is there an easy way to invalidate the cache of pages using this plugin? I guess this would require to do something more subtle than "add something to the global namespace of jinja templates", but I am not sure what would be the right approach.

I think what you're looking for is someway mark an artifact (built page) as "always stale" so that it gets rebuilt on every full rebuild. Is that right?

I'm not sure there's currently a clean way to do that.

A plugin could export a jinja function that would declare a dependency on a custom virtual source object. That virtual source object's get_mtime method would report an mtime of "now", so that it always appears to be changed. That seems very kludgy, but I think it could be made to work. (Let me know if you'd like me to flesh this out a bit more.)

In your specific case, the virtual source could be made smarter and only report as changed when there are actually changes. In this case, there would be a virtual source instance for each specific HAL query. Its get_checksum method would return a hash of the query results. This would result in the page being rebuilt only when the query results change. I think this is the "strictly correct" solution, but seems like probably overkill. (Lektor-git-timestamp does something like this to trigger rebuilds of pages when git-deduced timestamps change.)

For now, doing what you're doing — running lektor clean before publishing — might be the easiest/best solution.

dairiki commented 2 years ago

Thanks for your reply and contributions that I have merged.

Thank you!

Lektor-website pulls project metadata (description, project URL) from PyPI, so you'll still need to push a new release to PyPI in order for our build process to get the corrected data.

dairiki commented 2 years ago

@truenicoco

Is there an easy way to invalidate the cache of pages using this plugin?

Artifact.set_dirty_flag() can be used to mark an artifact as dirty so that it will be rebuilt on the next build.

As a dumb example, here's minimal plugin code that will define a global jinja function named volatile, which, when invoked from a template, will mark the current page as dirty.

from lektor.context import get_ctx
from lektor.pluginsystem import Plugin

def volatile():
    """Set the dirty flag on the artifact currently being built."""
    ctx = get_ctx()
    ctx.artifact.set_dirty_flag()

class VolatileTestPlugin(Plugin):
    name = 'Volatile Test'
    description = u'Add your description here.'

    def on_setup_env(self, **extra):
        self.env.jinja_env.globals['volatile'] = volatile

Now, in a template, if you do:

Mark this page so that it will be rebuilt on every build.
{{ volatile() }}
dairiki commented 2 years ago

@truenicoco Just in case it got lost in the discussion...

Before I can merge this PR, you'll need to publish a new release to PyPI. Lektor-website pulls the project URL and description from PyPI. Though you've corrected the URL in your source repo, it is still broken on your distribution's PyPI page.

(If there have not been any code changes since the last release and you're reluctant to bump the minor version, you can make a post-release.)

truenicoco commented 1 year ago

@dairiki It's been a while, but since I finally took the time to fix the URL in the package metadata and include your volatile() helper which works great. I just had it return an empty string to avoid an ugly None on the "always-stale" page. Thanks!

dairiki commented 1 year ago

@truenicoco Thank you! Merged.