Skip to main content

Using hilite.me API in Python

hilite.me is a light weight website made by Alexander Kojevnikov, used to format source code from various programming languages into formatted HTML snippets which can be added to blogs, articles, and other web pages as needed. I personally use the API to format the source code snippets in this blog, and it has greatly reduced the time taken to complete an article, much thanks to the creator. In this article, an automated way of using the hilite.me API through Python and a simple HTML document is created with formatted code snippets.
Environment
The code is executed in the following environment,
  • Operating system - Windows 11
  • Interpreter - Python 3.10.1
  • Editor - Visual Studio Code
An active Internet connection is required to reach the website to use the API. From the API help page, it takes the following parameters
  • code
  • lexer
  • options
  • style
  • linenos
  • divstyles
However, only a handful of important parameters are discussed in this blog article. Other options can be added to the params list and the code shown below can be extended to use other options. First, the class that does the formatting using the hilite.me API is coded, the class has a constructor, a set method based on keyword arguments so that one or more parameters can be tuned at a time, and a format method which does the actual formatting. The requests Python library is used to POST a message to the server, with the user-defined parameters. To note, the error path is not checked since it is very rare as long as the arguments are valid. But, the API calls can fail if there are invalid arguments or the server is too busy to respond at the time. I recommend the reader to take caution and handle errors for clean and robust code.
import requests

class HiliteMeFormatter:
    def __init__(self, code="", lexer="python", style="colorful", divstyles=""):
        self.url = "http://hilite.me/api"
        self.keys = ['code', 'lexer', 'style', 'divstyles']
        self.params = {}
        self.set(code=code, lexer=lexer, style=style, divstyles=divstyles)

    def set(self, **kwargs):
        for key in self.keys:
            if key in kwargs:
                self.params[key] = kwargs[key]

    def formatCode(self):
        r = requests.post(url=self.url, data=self.params)
        formattedCode = r.text
        r.close()
        return formattedCode

To test the API, a HTML creator class is added. The class creates a simple HTML file with the formatted snippets obtained through the API. It also has a header and footer method to start and close the HTML file properly.
class HTMLFile:
    def __init__(self, fileName="test.html"):
        self.file = open(fileName, 'w')

    def writeHeader(self):
        self.file.write("<html><head><title>Test</title></head><body>")

    def writeDiv(self, divStr):
        self.file.write(divStr)
        self.writeBreak()

    def writeBreak(self):
        self.file.write("<br/><br/>")

    def writeFooter(self):
        self.file.write("</body></html>")

To test the code, three simple Python snippets are used with the monokai style, and a HTML file is generated. The advantage of an API is that it can be called many times for different snippets, and all of them can be written at separate places of the HTML document.
def main():
    hilighter = HiliteMeFormatter(style="monokai")    
    htmlFile =  HTMLFile()
    codes = ["""
with open('file.txt', 'w') as f:
    f.write("Hello World")""",
"""
with open('file.txt', 'r') as f:
    print(f.read())
""",
"""
class Test:
    def __init__(self):
        self.testList = []

    def add(self, entry):
        self.testList.append(entry)
""",
    ]
    htmlFile.writeHeader()
    for code in codes:
        hilighter.set(code=code)
        htmlFile.writeDiv(hilighter.formatCode())
    htmlFile.writeFooter()
    

if __name__ == "__main__":
    main()

The generated HTML file is as follows,
<html><head><title>Test</title></head><body><!-- HTML generated using hilite.me --><div style="background: #272822; overflow:auto;width:auto;"><pre style="margin: 0; line-height: 125%"><span style="color: #66d9ef">with</span> <span style="color: #f8f8f2">open(</span><span style="color: #e6db74">&#39;file.txt&#39;</span><span style="color: #f8f8f2">,</span> <span style="color: #e6db74">&#39;w&#39;</span><span style="color: #f8f8f2">)</span> <span style="color: #66d9ef">as</span> <span style="color: #f8f8f2">f:</span>
    <span style="color: #f8f8f2">f</span><span style="color: #f92672">.</span><span style="color: #f8f8f2">write(</span><span style="color: #e6db74">&quot;Hello World&quot;</span><span style="color: #f8f8f2">)</span>
</pre></div>
<br/><br/><!-- HTML generated using hilite.me --><div style="background: #272822; overflow:auto;width:auto;"><pre style="margin: 0; line-height: 125%"><span style="color: #66d9ef">with</span> <span style="color: #f8f8f2">open(</span><span style="color: #e6db74">&#39;file.txt&#39;</span><span style="color: #f8f8f2">,</span> <span style="color: #e6db74">&#39;r&#39;</span><span style="color: #f8f8f2">)</span> <span style="color: #66d9ef">as</span> <span style="color: #f8f8f2">f:</span>
    <span style="color: #66d9ef">print</span><span style="color: #f8f8f2">(f</span><span style="color: #f92672">.</span><span style="color: #f8f8f2">read())</span>
</pre></div>
<br/><br/><!-- HTML generated using hilite.me --><div style="background: #272822; overflow:auto;width:auto;"><pre style="margin: 0; line-height: 125%"><span style="color: #66d9ef">class</span> <span style="color: #a6e22e">Test</span><span style="color: #f8f8f2">:</span>
    <span style="color: #66d9ef">def</span> <span style="color: #a6e22e">__init__</span><span style="color: #f8f8f2">(self):</span>
        <span style="color: #f8f8f2">self</span><span style="color: #f92672">.</span><span style="color: #f8f8f2">testList</span> <span style="color: #f92672">=</span> <span style="color: #f8f8f2">[]</span>

    <span style="color: #66d9ef">def</span> <span style="color: #a6e22e">add</span><span style="color: #f8f8f2">(self,</span> <span style="color: #f8f8f2">entry):</span>
        <span style="color: #f8f8f2">self</span><span style="color: #f92672">.</span><span style="color: #f8f8f2">testList</span><span style="color: #f92672">.</span><span style="color: #f8f8f2">append(entry)</span>
</pre></div>
<br/><br/></body></html>

The screenshot for the formatted snippet is,

Thanks for reading, please leave comments/suggestions if any.

Comments

Popular posts from this blog

BMI Calculator using Python and Tkinter

Body Mass Index can be calculated using a simple formula kg/m 2 , where the weight is represented in kilograms (kg) and the height is represented in metres (m). The article presents code to create a simple GUI to calculate BMI based on user input values. The GUI is implemented using tkinter and tkinter.ttk libraries in Python language.

Tic-tac-toe game using Python and tkinter

Tic-tac-toe is a popular two player game where each player tries to occupy an empty slot in a 3x3 board until one of them wins or the entire board is filled without any winner. The winner has to occupy three continuous cells in any direction, including the two diagonals. In this article, a version of the tic-tac-toe game is coded using Python and tkinter library.