ink-docstrap
Version:
[](https://nodei.co/npm/ink-docstrap/)
342 lines (263 loc) • 15.8 kB
JavaScript
(function(sunlight, undefined){
if (sunlight === undefined || sunlight["registerLanguage"] === undefined) {
throw "Include sunlight.js before including language files";
}
sunlight.registerLanguage("nginx", {
scopes: {
string: [ ["\"", "\"", sunlight.util.escapeSequences.concat(["\\\""])], ["'", "'", ["\\'", "\\\\"]] ],
comment: [ ["#", "\n", null, true] ],
variable: [ ["$", { length: 1, regex: /[\W]/ }, null, true] ],
label: [ ["@", { length: 1, regex: /[\W]/ }, null, true] ],
ssiCommand: [ ["<!--#", "-->"] ] //http://wiki.nginx.org/HttpSsiModule#SSI_Commands
},
customParseRules: [
//context detection (server, location, upstream, http, mail, etc.)
function() {
var words = sunlight.util.createHashMap(["server", "location", "upstream", "http", "mail", "types", "map", "split-clients", "geo", "limit_except"], "\\b", false);
return function(context) {
var token = sunlight.util.matchWord(context, words, "context", true),
peek,
count;
if (!token) {
return null;
}
//if we encounter a "{" before a ";", we're good to go
count = token.value.length;
while ((peek = context.reader.peek(count++)) !== context.reader.EOF) {
if (/\{$/.test(peek)) {
context.reader.read(token.value.length - 1); //already read the first letter
return token;
}
if (/;$/.test(peek)) {
break;
}
}
return null;
};
}(),
//regex literals
function(context) {
//can come after server_name if it starts with ~ and ends with [\s;]
//or after "location ^~"
//or after "location ~"
//or after "location ~*"
var current = context.reader.current(),
token,
index,
isRegexLiteral = false,
regexLiteral = current,
peek,
prevToken,
line = context.reader.getLine(),
column = context.reader.getColumn();
if (/[\s\n]/.test(current)) {
return null;
}
index = context.count() - 1;
while ((token = context.token(index--)) !== context.reader.EOF) {
if (token.name === "regexLiteral" || (token.name === "punctuation" && (token.value === "{" || token.value === "}" || token.value === ";"))) {
return null;
}
if (token.name === "operator" && sunlight.util.contains(["^~", "~", "~*"], token.value)) {
//check previous token for "location" keyword
prevToken = sunlight.util.getPreviousWhile(context.getAllTokens(), index, function(token) {
return token.name === "default" || token.name === "comment";
});
if (prevToken.name === "context" && prevToken.value === "location") {
isRegexLiteral = true;
break;
}
} else if (token.name === "keyword" && token.value === "server_name") {
//server_name check
if (current !== "~") {
return null;
}
isRegexLiteral = true;
break;
}
}
if (!isRegexLiteral) {
return null;
}
//read to the end of the regex literal
while ((peek = context.reader.peek()) !== context.reader.EOF) {
if (/[\s;\n]/.test(peek)) {
break;
}
regexLiteral += context.reader.read();
}
return context.createToken("regexLiteral", regexLiteral, line, column);
},
//directives, can't just make them keywords because then values (not directives) will possibly be highlighted
//e.g. "index index.html" will have both "index"es highlighted when we just want the first
function() {
var directives = sunlight.util.createHashMap([
//core: http://wiki.nginx.org/CoreModule
"daemon", "env", "debug_points", "error_log", "include", "lock_file", "master_process", "pid", "ssl_engine", "timer_resolution",
"user", "worker_cpu_affinity", "worker_priority", "worker_processes", "worker_rlimit_core", "worker_rlimit_nofile",
"worker_rlimit_sigpending", "working_directory",
//events: http://wiki.nginx.org/EventsModule
"accept_mutext_delay", "accept_mutex", "debug_connection", "devpoll_changes", "devpoll_events", "kqueue_changes",
"kqueue_events", "epoll_events", "multi_accept", "rtsig_signo", "rtsig_overflow_events", "rtsig_overflow_text",
"rtsig_overflow_threshold","use", "worker_connections",
//httpCore: http://wiki.nginx.org/HttpCoreModule
"aio","alias","chunked_transfer_encoding","client_body_in_file_only","client_body_in_single_buffer","client_body_buffer_size",
"client_body_temp_path","client_body_timeout","client_header_buffer_size","client_header_timeout","client_max_body_size",
"default_type","directio","error_page","if_modified_since","internal","keepalive_timeout","keepalive_requests",
"large_client_header_buffers","limit_except","limit_rate_after","limit_rate","listen","location","log_not_found",
"log_subrequest","msie_padding","msie_refresh","open_file_cache_errors","open_file_cache_min_uses",
"open_file_cache_valid","open_file_cache","optimize_server_names","port_in_redirect","post_action","recursive_error_pages",
"resolver_timeout","resolver","root","satisfy_any","satisfy","send_timeout","sendfile","server_name","server_name_in_redirect",
"server_names_hash_max_size","server_names_hash_bucket_size","server_tokens","server","tcp_nodelay","tcp_nopush","try_files","types",
"underscores_in_headers",
//httpAccess: http://wiki.nginx.org/HttpAccessModule
"allow", "deny",
//httpAuthBasic: http://wiki.nginx.org/HttpAuthBasicModule
"auth_basic_user_file", "auth_basic",
//httpAutoindex: http://wiki.nginx.org/HttpAutoindexModule
"autoindex_exact_size", "autoindex_localtime", "autoindex",
//httpBrowser: http://wiki.nginx.org/HttpBrowserModule
"ancient_browser_value", "ancient_browser", "modern_browser_value","modern_browser",
//httpCharset: http://wiki.nginx.org/HttpCharsetModule
"charset_map", "override_charset", "source_charset", "charset",
//emptyGif: http://wiki.nginx.org/HttpEmptyGifModule
"empty_gif",
//fCgi: http://wiki.nginx.org/HttpFcgiModule
"fastcgi_bind","fastcgi_buffer_size","fastcgi_buffers","fastcgi_cache_key","fastcgi_cache_path",
"fastcgi_cache_methods","fastcgi_cache_min_uses","fastcgi_cache_use_stale","fastcgi_cache_valid","fastcgi_cache","fastcgi_connect_timeout",
"fastcgi_index","fastcgi_hide_header","fastcgi_ignore_client_abort","fastcgi_ignore_headers","fastcgi_intercept_errors",
"fastcgi_max_temp_file_size","fastcgi_no_cache","fastcgi_next_upstream","fastcgi_param","fastcgi_pass_header","fastcgi_pass",
"fastcgi_read_timeout","fastcgi_redirect_errors","fastcgi_send_timeout","fastcgi_split_path_info",
"fastcgi_store_access","fastcgi_store","fastcgi_temp_path",
//geo: http://wiki.nginx.org/HttpGeoModule
"geo",
//gzip: http://wiki.nginx.org/HttpGzipModule
"gzip_buffers", "gzip_comp_level", "gzip_disable", "gzip_http_version", "gzip_min_length", "gzip_proxied", "gzip_types", "gzip_vary", "gzip",
//headers: http://wiki.nginx.org/HttpHeadersModule
"add_header", "expires",
//index: http://wiki.nginx.org/HttpIndexModule
"index",
//limitRequests: http://wiki.nginx.org/HttpLimitReqModule
"limit_req_log_level", "limit_req_zone", "limit_req",
//limitZone: http://wiki.nginx.org/HttpLimitZoneModule
"limit_zone", "limit_conn_log_level", "limit_conn",
//log: http://wiki.nginx.org/HttpLogModule
"access_log", "log_format", "open_log_file_cache",
//map: http://wiki.nginx.org/HttpMapModule
"map_hash_max_size", "map_hash_bucket_size", "map",
//memcached: http://wiki.nginx.org/HttpMemcachedModule
"memcached_pass", "memcached_connect_timeout", "memcached_read_timeout", "memcached_send_timeout", "memcached_buffer_size", "memcached_next_upstream",
//proxy: http://wiki.nginx.org/HttpProxyModule
"proxy_bind","proxy_buffer_size","proxy_buffering","proxy_buffers","proxy_busy_buffers_size","proxy_cache_bypass","proxy_cache_key",
"proxy_cache_methods","proxy_cache_min_uses","proxy_cache_path","proxy_cache_use_stale","proxy_cache_valid","proxy_cache","proxy_connect_timeout",
"proxy_headers_hash_bucket_size","proxy_headers_hash_max_size","proxy_hide_header","proxy_ignore_client_abort","proxy_ignore_headers",
"proxy_intercept_errors","proxy_max_temp_file_size","proxy_method","proxy_next_upstream","proxy_no_cache","proxy_pass_header",
"proxy_pass_request_body","proxy_pass_request_headers","proxy_pass","proxy_read_timeout","proxy_redirect_errors","proxy_redirect","proxy_send_lowat",
"proxy_send_timeout","proxy_set_body","proxy_set_header","proxy_ssl_session_reuse","proxy_store_access","proxy_store","proxy_temp_file_write_size",
"proxy_temp_path","proxy_upstream_fail_timeout","proxy_upstream_max_fails",
//referer: http://wiki.nginx.org/HttpRefererModule
"valid_referers",
//rewrite: http://wiki.nginx.org/HttpRewriteModule
"break", "if", "return", "rewrite", "set", "uninitialized_variable_warn",
//scgi: http://wiki.nginx.org/HttpScgiModule
"scgi_bind","scgi_buffer_size","scgi_buffers","scgi_busy_buffers_size","scgi_cache_bypass","scgi_cache_key","scgi_cache_methods",
"scgi_cache_min_uses","scgi_cache_path","scgi_cache_use_stale","scgi_cache_valid","scgi_cache","scgi_connect_timeout","scgi_hide_header","scgi_ignore_client_abort",
"scgi_ignore_headers","scgi_intercept_errors","scgi_max_temp_file_size","scgi_next_upstream","scgi_no_cache","scgi_param","scgi_pass_header",
"scgi_pass_request_body","scgi_pass_request_headers","scgi_pass","scgi_read_timeout","scgi_send_timeout","scgi_store_access","scgi_store","scgi_temp_file_write_size",
"scgi_temp_path",
//clients: http://wiki.nginx.org/HttpSplitClientsModule
"split-clients", //is this a typo in the docs? should it be an underscore?
//ssi: http://wiki.nginx.org/HttpSsiModule
"ssi", "ssi_silent_errors", "ssi_types", "ssi_value_length",
//upstream: http://wiki.nginx.org/HttpUpstreamModule
"ip_hash", "server", "upstream",
//userid: http://wiki.nginx.org/HttpUserIdModule
"userid_domain", "userid_expires", "userid_name", "userid_p3p", "userid_path", "userid_service", "userid",
//uwsgi: http://wiki.nginx.org/HttpUwsgiModule
"uwsgi_bind","uwsgi_buffer_size","uwsgi_buffers","uwsgi_busy_buffers_size","uwsgi_cache_bypass","uwsgi_cache_key",
"uwsgi_cache_methods","uwsgi_cache_min_uses","uwsgi_cache_path","uwsgi_cache_use_stale","uwsgi_cache_valid","uwsgi_cache","uwsgi_connect_timeout",
"uwsgi_hide_header","uwsgi_ignore_client_abort","uwsgi_ignore_headers","uwsgi_intercept_errors","uwsgi_max_temp_file_size","uwsgi_modifier1",
"uwsgi_modifier2","uwsgi_next_upstream","uwsgi_no_cache","uwsgi_param","uwsgi_pass_header","uwsgi_pass_request_body",
"uwsgi_pass_request_headers","uwsgi_pass","uwsgi_read_timeout","uwsgi_send_timeout","uwsgi_store_access","uwsgi_store","uwsgi_string",
"uwsgi_temp_file_write_size","uwsgi_temp_path",
//optional http modules
//addition: http://wiki.nginx.org/HttpAdditionModule
"add_before_body", "add_after_body", "addition_types",
//perl: http://wiki.nginx.org/EmbeddedPerlModule
"perl_modules", "perl_require", "perl_set", "perl",
//flv: http://wiki.nginx.org/HttpFlvStreamModule
"flv",
//geoIp: http://wiki.nginx.org/HttpGeoIPModule
"geoip_country", "geoip_city",
//google performance tools: http://wiki.nginx.org/GooglePerftoolsModule
"google_perftools_profiles",
//gzip static: http://wiki.nginx.org/HttpGzipStaticModule
"gzip_static", "gzip_http_version", "gzip_proxied", /*"gzip_disable", "gzip_vary",*/ //<-- already accounted for in gzip module
//image filter: http://wiki.nginx.org/HttpImageFilterModule
"image_filter_buffer", "image_filter_jpeg_quality", "image_filter_transparency", "image_filter",
//random index: http://wiki.nginx.org/HttpRandomIndexModule
"random_index",
//realip: http://wiki.nginx.org/HttpRealIpModule
"set_real_ip_from", "real_ip_header",
//secure link: http://wiki.nginx.org/HttpSecureLinkModule
"secure_link_secret", "secure_link_md5", "secure_link",
//ssl: http://wiki.nginx.org/HttpSslModule
"ssl_certificate_key","ssl_client_certificate","ssl_certificate","ssl_dhparam","ssl_ciphers","ssl_crl",
"ssl_prefer_server_ciphers","ssl_protocols","ssl_verify_client","ssl_verify_depth","ssl_session_cache",
"ssl_session_timeout","ssl_engine", "ssl",
//stub stats: http://wiki.nginx.org/HttpStubStatusModule
"stub_status",
//sub: http://wiki.nginx.org/HttpSubModule
"sub_filter_once", "sub_filter_types", "sub_filter",
//dav: http://wiki.nginx.org/HttpDavModule
"dav_access", "dav_methods", "create_full_put_path",
//xslt: http://wiki.nginx.org/HttpXsltModule
"xml_entities", "xslt_stylesheet", "xslt_types",
//mail modules
//core: http://wiki.nginx.org/MailCoreModule
"auth","imap_capabilities","imap_client_buffer","listen","pop3_auth","pop3_capabilities",
"protocol","server","server_name","smtp_auth","smtp_capabilities","so_keepalive","timeout",
//auth: http://wiki.nginx.org/MailAuthModule
"auth_http", "auth_http_header","auth_http_timeout",
//proxy: http://wiki.nginx.org/MailProxyModule
"proxy_buffer", "proxy_pass_error_message", "proxy_timeout", "proxy", "xclient",
//ssl: http://wiki.nginx.org/MailSslModule
/*"ssl","ssl_certificate","ssl_certificate_key","ssl_ciphers","ssl_prefer_server_ciphers","ssl_protocols","ssl_session_cache","ssl_session_timeout",*/ //<- covered in http ssl module
"starttls",
//echo: http://wiki.nginx.org/HttpEchoModule
"echo_duplicate", "echo_flush", "echo_sleep", "echo_blocking_sleep", "echo_reset_timer",
"echo_read_request_body", "echo_location_async", "echo_location", "echo_subrequest_async",
"echo_subrequest", "echo_foreach_split", "echo_end", "echo_request_body", "echo_exec",
"echo_before_body", "echo_after_body", "echo",
//others
"default", "output_buffers"
], "[\\s;]", false);
return function(context) {
var token = sunlight.util.matchWord(context, directives, "keyword", true),
prevToken;
if (!token) {
return null;
}
//must be the first word in a statement
//which means first token in the string, or first non-ws token after "{", "}" or ";"
prevToken = sunlight.util.getPreviousWhile(context.getAllTokens(), context.count(), function(token) {
return token.name === "default" || token.name === "comment";
});
if (!prevToken || (prevToken.name === "punctuation" && (sunlight.util.contains(["{", "}", ";"], prevToken.value)))) {
context.reader.read(token.value.length - 1); //already read the first character
return token;
}
return null;
};
}()
],
identFirstLetter: /[A-Za-z_-]/,
identAfterFirstLetter: /[\w-]/,
operators: [
"~*", "~",
"^~",
"=",
"::", ":"
]
});
}(this["Sunlight"]));