sbrl / Pepperminty-Wiki

A wiki in a box
https://peppermint.mooncarrot.space/
Mozilla Public License 2.0
183 stars 22 forks source link

Mega Enhancement: Syntax Highlighting #164

Open sbrl opened 5 years ago

sbrl commented 5 years ago

It sounds simple on the surface, but syntax highlighting is proving to be a really thorny issue. The trick is going to be to do it whilst maintaining the following principles of Pepperminty Wiki:

  1. Everything is in a single file
  2. Be compatible with a reasonable number of different web servers & environment setups (though this does not include old PHP versions!)
  3. No additional installation steps required (or a done transparently on first load - e.g. creation of peppermint.json, pageindex.json, etc.)

Initially, I thought that utilising a phar would be a great idea - because we can have our own internal file structure - but present a single file!

Unfortunately, this comes with a bit of a caveat: It requires the .phar extension - which isn't usually configured on web servers - breaking point #2.

After about 15 minutes of head-scratching, I've managed to remember the name of a very special PHP function that halts the PHP processor, allowing arbitrary data to be embedded at the end of the file: __halt_compiler();. We could pack up our extra dependencies into a compressed archive (zip? .tar.gz? .tar.bz2? we'll have to see what's available).

There are other questions too:

Definitely something to mull over.

sbrl commented 5 years ago

If we did it server-side, we'd want to use a composer package. luminous looks good, but it's slow apparently - and has a caching system built-in. We'd probably want to cache the output of the currently selected parser here in some fashion in order to use this method.

If we did it client-side, I'd love to be able to use prism.js. We'll have to figure out how to use the web-based downloader on the command-line though and specify the plugins we want.

sbrl commented 5 years ago

We've implemented a cache system (and fixed a nasty bug in #165). Now that v0.18 is out, I think it's time to think about refactoring the downloading system to enable us to work on the server-side syntax highlighting.

It's probably worth noting that although this will allow us to bundle all sorts of extra files with Pepperminty Wiki, the intention here is to avoid using it except when we really need to. In other words, this won't be for packing multi-file modules etc - only for essential libraries that are needed to perform a function. Good examples of things include:

The intention here is to keep Pepperminty Wiki targeted at what it's good at: setting up a new small wiki really quickly - and avoid what we can't possibly hope to compete with (i.e. the full power of MediaWiki). Pepperminty Wiki is small, fast, and light. It's not without any bells and whistles though - we just need to be selective in the ones that we include :P

sbrl commented 5 years ago

Looks like this rework it more urgent than I thought. RawGit, the mechanism we use to download Parsedown, is shutting down in October this year. To this end, I'd like to move away from the current system of downloading files from RawGit to a system on unpacking from index.php and make a stable release before October 2019.

We should open a separate issue for this.

sbrl commented 5 years ago

We've got our new packaging system, so now we can consider adding syntax highlighting.

Luminous looks good - maybe we could use that?

ElDani82 commented 1 year ago

Hey there. I stumbled over Pepperminty Wiki earlier today, because I was looking for a self-hosted but public (thus web-based) note-taking application that would support the markdown language and this seemed like a simple and easy thing to use.

But on to this issue: I'm not sure about the project's stance toward the use of first vs third-party resources, but it's trivially easy to implement code highlighting on the client side. I've created a proof of concept in form of a userscript, which uses the javascript library highlight.js:

image

// ==UserScript==
// @name         Pepperminty Wiki - Syntax Highlighting
// @description  Adds client-side syntax highlighting to a Pepperminty Wiki instance
// @namespace    pepperminty-eldani
// @author       eldani
// @version      1.0
// @match        *://192.168.0.155/pepperminty-wiki/*
// @resource     CSS_LIGHT https://cdn.jsdelivr.net/gh/highlightjs/cdn-release@11.7.0/build/styles/default.min.css
// @resource     CSS_DARK https://raw.githubusercontent.com/dracula/highlightjs/master/dracula.css
// @require      https://cdn.jsdelivr.net/gh/highlightjs/cdn-release@11.7.0/build/highlight.min.js
// @grant        unsafeWindow
// @grant        GM_getResourceText
// @grant        GM_addStyle
// ==/UserScript==

(function() {
    'use strict';

    const use_dark_theme = window?.matchMedia('(prefers-color-scheme: dark)')?.matches || false;
    GM_addStyle(
        GM_getResourceText(use_dark_theme ? "CSS_DARK" : "CSS_LIGHT")
    );
    unsafeWindow.document.querySelectorAll("pre code").forEach((el) => {
        el.className.startsWith("language-")
        ? hljs.highlightElement(el)
        : el.className = "hljs";
    });

})();

Ignore the theme detection; it works for me, because I use the Blue theme and the Dark Reader extension.

If this were to be integrated as-is into the wiki, it would increase the size of the single .php file by 123 KB (121 KB of which is minified javascript code).