/* PrismJS - Minimal Core for GitHub Code Viewer */ /* This is a simplified version focused on safety and basic highlighting */ (function(){ if (typeof self === 'undefined' || !self.Prism || !self.document) { return; } var Prism = window.Prism = { languages: {}, // Simplified tokenization with infinite loop prevention tokenize: function(text, grammar) { // Prevent tokenizing huge files if (text.length > 100000) { return [text]; // Return as plain text for very large files } var tokens = []; var rest = text; var maxIterations = 10000; // Prevent infinite loops var iterations = 0; while (rest.length > 0 && iterations < maxIterations) { iterations++; var matchFound = false; for (var token in grammar) { if (!grammar.hasOwnProperty(token) || !grammar[token]) { continue; } var pattern = grammar[token]; if (pattern instanceof RegExp) { var matches = rest.match(pattern); if (matches && matches.index === 0) { matchFound = true; tokens.push({ type: token, content: matches[0] }); rest = rest.substring(matches[0].length); break; } } } // If no match found, consume one character as plain text if (!matchFound) { if (tokens.length > 0 && typeof tokens[tokens.length - 1] === 'string') { tokens[tokens.length - 1] += rest.charAt(0); } else { tokens.push(rest.charAt(0)); } rest = rest.substring(1); } } // Add any remaining text if (rest.length > 0) { tokens.push(rest); } return tokens; }, // Highlight element highlightElement: function(element) { var language = element.className.match(/language-(\w+)/); if (!language) return; language = language[1]; var grammar = Prism.languages[language]; if (!grammar) return; // Get text content (already HTML escaped by PHP) var code = element.textContent; // Simple tokenization var tokens = Prism.tokenize(code, grammar); // Build highlighted HTML (safe because content is already escaped) var highlighted = tokens.map(function(token) { if (typeof token === 'string') { return token; } return '' + token.content + ''; }).join(''); element.innerHTML = highlighted; }, // Highlight all code blocks highlightAll: function() { var elements = document.querySelectorAll('code[class*="language-"], [class*="language-"] code'); for (var i = 0, element; element = elements[i++];) { Prism.highlightElement(element); } } }; // Define basic grammars for common languages Prism.languages.javascript = { 'comment': /\/\/.*|\/\*[\s\S]*?\*\//, 'string': /(["'])(?:\\.|(?!\1)[^\\\r\n])*\1/, 'keyword': /\b(?:var|let|const|function|return|if|else|for|while|do|switch|case|break|continue|typeof|instanceof|new|this|throw|try|catch|finally|async|await|class|extends|super|import|export|default|yield)\b/, 'boolean': /\b(?:true|false)\b/, 'number': /\b0x[\da-f]+\b|(?:\b\d+\.?\d*|\B\.\d+)(?:e[+-]?\d+)?/i, 'function': /[_$a-zA-Z\xA0-\uFFFF][_$a-zA-Z0-9\xA0-\uFFFF]*(?=\s*\()/, 'operator': /[+\-*/%=!<>&|^~?:]+/, 'punctuation': /[{}[\];(),.:]/ }; Prism.languages.python = { 'comment': /#.*/, 'string': /(["'])(?:\\.|(?!\1)[^\\\r\n])*\1/, 'keyword': /\b(?:and|as|assert|async|await|break|class|continue|def|del|elif|else|except|exec|finally|for|from|global|if|import|in|is|lambda|not|or|pass|print|raise|return|try|while|with|yield)\b/, 'boolean': /\b(?:True|False|None)\b/, 'number': /\b0x[\da-f]+\b|(?:\b\d+\.?\d*|\B\.\d+)(?:e[+-]?\d+)?j?/i, 'operator': /[+\-*/%=!<>&|^~]+/, 'punctuation': /[{}[\];(),.:]/ }; Prism.languages.php = { 'comment': /\/\/.*|\/\*[\s\S]*?\*\/|#.*/, 'string': /(["'])(?:\\.|(?!\1)[^\\\r\n])*\1/, 'keyword': /\b(?:abstract|and|array|as|break|callable|case|catch|class|clone|const|continue|declare|default|die|do|echo|else|elseif|empty|enddeclare|endfor|endforeach|endif|endswitch|endwhile|eval|exit|extends|final|finally|for|foreach|function|global|goto|if|implements|include|include_once|instanceof|insteadof|interface|isset|list|namespace|new|or|print|private|protected|public|require|require_once|return|static|switch|throw|trait|try|unset|use|var|while|xor|yield)\b/i, 'boolean': /\b(?:false|true)\b/i, 'variable': /\$\w+/, 'number': /\b0x[\da-f]+\b|(?:\b\d+\.?\d*|\B\.\d+)(?:e[+-]?\d+)?/i, 'operator': /[+\-*/%=!<>&|^~?:]+/, 'punctuation': /[{}[\];(),.:]/ }; Prism.languages.html = Prism.languages.xml = { 'comment': //, 'tag': { pattern: /<\/?[^\s>\/]+(?:\s+[^\s>\/=]+(?:=(?:("|')(?:\\.|(?!\1)[^\\])*\1|[^\s'">=]+))?)*\s*\/?>/i, inside: { 'punctuation': /^<\/?|\/?>$/, 'attr-name': /[^\s>\/]+/, 'attr-value': /=(?:("|')(?:\\.|(?!\1)[^\\])*\1|[^\s'">=]+)/i } } }; Prism.languages.css = { 'comment': /\/\*[\s\S]*?\*\//, 'atrule': /@[\w-]+?.*?(?:;|(?=\s*\{))/i, 'url': /url\((?:(["'])(?:\\.|(?!\1)[^\\\r\n])*\1|.*?)\)/i, 'selector': /[^{}\s][^{}]*(?=\s*\{)/, 'string': /(["'])(?:\\.|(?!\1)[^\\\r\n])*\1/, 'property': /[-_a-z\xA0-\uFFFF][-\w\xA0-\uFFFF]*(?=\s*:)/i, 'important': /!important\b/i, 'punctuation': /[(){};:]/ }; Prism.languages.json = { 'property': /"(?:\\.|[^\\"\r\n])*"(?=\s*:)/i, 'string': /"(?:\\.|[^\\"\r\n])*"(?!\s*:)/, 'number': /\b0x[\dA-Fa-f]+\b|(?:\b\d+\.?\d*|\B\.\d+)(?:[Ee][+-]?\d+)?/, 'punctuation': /[{}[\]);,]/, 'operator': /:/g, 'boolean': /\b(?:true|false)\b/i, 'null': /\bnull\b/i }; // Language aliases Prism.languages.js = Prism.languages.javascript; Prism.languages.py = Prism.languages.python; // Auto-initialize if (document.readyState !== 'loading') { setTimeout(Prism.highlightAll, 0); } else { document.addEventListener('DOMContentLoaded', Prism.highlightAll); } })();