I have been thinking about approaches to writing a blog with Phoenix.
Prior to discovering Elixir & Phoenix, I was so fed up with the state of the modern web, I wanted to leave every tooling behind and just write HTML, CSS with a dash of JS to make websites.
However, now that I have gotten familiar with LiveView, I don’t want to go complete Croods on the problem.
I found out how others tackle this:
Nimble Publisher, that compiles markdown based posts into HTML and keeps them in memory.
Some prefer to use Database, to store not only the blog post, but sometimes comments and other stuff.
I was thinking, why not just write plain HEEx?
Is there any demerit?
We can create static Metadata context for the blog posts, that don’t live in the database!
And then add database for dynamic stuffs, i.e. Likes & Comments!
N.B. I’m talking about blogs created by the user of Elixir & Phoenix.
P.S. Also, a little help with a problem while trying to do so:
Heex templates by design are made to be used with non-static content, so I would not see the benefit of using them if your content is static anyway, correct me if I missed something.
HEEx is HTML aware, so I don’t think we can even compile a malformed HEEx.
And I’m talking about Elixir & Phoenix developers creating their blogs. Not for others.
It’s not about creating a blog engine for others to use. It would take too long to make something close to Ghost. The same reason there’s no Elixir forum made with Phoenix!
I saw 5 or 10 blogs by Elixir developers, who have chosen to go the Markdown route, or database route. So I asked, why not keep it straightforward.
A blog can be as simple or as complex you want it. Likes, comments are not something that a self-hosted blogpost site needs, this is why you are most likely better serving static assets than building something from scratch in phoenix.
Same reason electricians still use light switches to turn on their lights, and plumbers still use the toilet to get their waste into the sewer. When writing a blog it’s much easier to use a blog interface than a programming interface. Some specifics:
Simpler/quicker publishing mechanism (hit a button vs a deploy)
Copy-paste support for code/etc
Drag/drop support for images
Auto-adding of the publishing date
Auto indexing of the content for search
Auto linking of the post from some main menu
Auto broadcast of new posts on various social media platforms
Tagging/categorization
Basically, all the features people build into blog tools that are specific to blogging.
I briefly considered it at one point, but very quickly dismissed the idea.
A few months ago I decided to revamp my business and personal websites, including a plan to do some blogging. Since I have been writing a lot of Phoenix related code, the question: “why not use this for these sites?” was definitely considered… Phoenix was front of mind and I’d save having to learn a different technology to do something that ostensibly Phoenix could do if you ignored a lot of stuff that comes with Phoenix. I also was looking for how I’d provide my end user documentation for the application I’m building with Phoenix; some percentage of the potential users would be in scenarios where internet access to their internal staff isn’t allowed and so the ability to host the documentation locally from within the application release was a plus.
In the end, while doing all of the above could certainly be forced into the Phoenix paradigm, it really didn’t make sense for all the reasons others have already added to this thread. I’d be inventing some basics, like what to do/how to treat the metadata associated with a given content posting. I’d be spending a lot of time working problems already solved by tools more dedicated to the problem of blogging and what is really static content generation and management… I would lose time solving the problems that I’m best qualified to solve and to which my application is dedicated: business management software.
So the cost/benefit analysis favored heavily dedicated static site generators for my websites and blog as well as for my end user documentation which will ultimately ship with the Phoenix application. I haven’t regretted the choice once. When I’m writing for my sites or my documentation I’m mostly focused on the content and its metadata, not on how that content will be managed or digested. Sure, I had to learn the ways of my static site generator, but that was far less overhead than having to figure out my own bespoke solutions… which I would also have to remember how it worked. The real burden of the static site generator is deciding which of the many features it has to take advantage of or to ignore.
I landed on Hugo for static site generation and for the end user documentation, I create that as a Hugo site, run the Hugo build process, and then include the built site as static assets in my Phoenix application. I’m sure other static site builders could do things similarly.
So in closing… Elixir/Phoenix may be good choice to build the tools which manage mostly static content, but are not the tools with which to do that job directly. I could see Phoenix being compelling choice for creating a content management system a’la a Drupal or WordPress does (sorry I’m old… I don’t know what the current hotness is in the CMS space)… but for the just the content management piece by itself I’m looking elsewhere.
You’ve received a few answers, can you elaborate as to what about them is not addressing your question? If you understand the benefits, the answer is that Elixir & Phoenix bloggers also value those benefits. What is missing?
I would say long form writing in HTML is painful after experiencing markdown. I tried it recently. I used some really simple PHP (which I forgot how painful that was) for routing and layout and then wrote my posts in HTML. It quickly became cumbersome so I moved over to Hugo. At one point I did have it in LiveView (database-backed). I’m thinking of switching back to that as Hugo isn’t exactly a walk in the park either.
I did also have a version that used Surface with the <#Markdown> component. That was probably the best in terms of writing right in a LiveView but it didn’t feel like this massive revelation or anything. Nothing quite beats markdown with front matter so typical content.
Also, if I’m going to be keeping likes and comments (possibly tags and possibly other things) then it seems more complex to not also store my blog content in there.
However, if you are going to be storing inline LiveView content then that’s a different story. Like LostKobraKai’s blog does. I would be interested to know how he does it.
If an elixir developer is going to create a blog, that revolves around Elixir & Phoenix, why not keep it in HEEx, that way we have more control, and can embed a live example as well.
If we go Markdown route, then we have to have some black magic with custom element in Markdown, to be able to embed an interactive element.
@LostKobrakai, tell us your secrets. How did you modify the nimble publisher or the earmark parser to embed a live view in a page?
How would you do syntax highlighting that’s not supported by the elixir tooling?
My site isn’t blog-centric and as far as my blog goes, I only have a three posts, one of them is essentially blogspam, and I otherwise have like a million drafts I don’t only write about Elixir and code highlighting was a major factor. Hugo has JS-free code highlighting for pretty much everything.
EDIT: Wasn’t 100% sure if that was directed at my but it felt like it was, lol.
Tableau static site generator in README provides with an example using Temple, but it also allows to use the builtin EEx, or use HEEx, Surface, or HAML
This is quite an interesting idea, in theory you should be able to copy the render part from livebook itself, even though it depends on how tightly it is coupled to the other functionality of the application.
.livemd are still valid markdown files, so NimblePublisher will work. You however won’t get any interactivity that way. Code will become static code blocks. If you expect them to render back like they do within livebook than that’s likely on the opposite end of the complexity scale.