html: embed gziped version

This commit is contained in:
Shuanglei Tao
2020-02-05 16:42:43 +08:00
parent 0e728e61ce
commit 437e63a39c
8 changed files with 8541 additions and 34036 deletions

42405
src/html.h

File diff suppressed because it is too large Load Diff

View File

@@ -1,14 +1,19 @@
#include <string.h>
#include <libwebsockets.h>
#include <openssl/ssl.h>
#include <zlib.h>
#include "server.h"
#include "html.h"
#include "utils.h"
enum {
AUTH_OK, AUTH_FAIL, AUTH_ERROR
};
char * html_cache = NULL;
size_t html_cache_len = 0;
int
check_auth(struct lws *wsi, struct pss_http *pss) {
if (server->credential == NULL)
@@ -62,6 +67,51 @@ check_auth(struct lws *wsi, struct pss_http *pss) {
return AUTH_FAIL;
}
bool accept_gzip(struct lws *wsi) {
int hdr_length = lws_hdr_total_length(wsi, WSI_TOKEN_HTTP_ACCEPT_ENCODING);
char buf[hdr_length + 1];
int len = lws_hdr_copy(wsi, buf, sizeof(buf), WSI_TOKEN_HTTP_ACCEPT_ENCODING);
return len > 0 && strstr(buf, "gzip") != NULL;
}
bool
uncompress_html(char **output, size_t *output_len) {
if (html_cache == NULL || html_cache_len == 0) {
z_stream stream;
memset(&stream, 0, sizeof(stream));
if (inflateInit2(&stream, 16 + 15) != Z_OK)
return false;
html_cache_len = index_html_size;
html_cache = xmalloc(html_cache_len);
stream.avail_in = index_html_len;
stream.avail_out = html_cache_len;
stream.next_in = (void *) index_html;
stream.next_out = (void *) html_cache;
int ret = inflate(&stream, Z_SYNC_FLUSH);
inflateEnd(&stream);
if (ret != Z_STREAM_END) {
free(html_cache);
html_cache = NULL;
html_cache_len = 0;
return false;
}
}
*output = html_cache;
*output_len = html_cache_len;
return true;
}
bool
pss_buffer_free(struct pss_http *pss) {
if (pss->buffer != (char *) index_html && pss->buffer != html_cache)
free(pss->buffer);
}
void
access_log(struct lws *wsi, const char *path) {
char rip[50];
@@ -132,23 +182,39 @@ callback_http(struct lws *wsi, enum lws_callback_reasons reason, void *user, voi
if (n < 0 || (n > 0 && lws_http_transaction_completed(wsi)))
return 1;
} else {
char *output = (char *) index_html;
size_t output_len = index_html_len;
if (lws_add_http_header_status(wsi, HTTP_STATUS_OK, &p, end))
return 1;
if (lws_add_http_header_by_token(wsi, WSI_TOKEN_HTTP_CONTENT_TYPE, (const unsigned char *) content_type, 9, &p, end))
return 1;
if (lws_add_http_header_content_length(wsi, (unsigned long) index_html_len, &p, end))
#ifdef LWS_WITH_HTTP_STREAM_COMPRESSION
if (!uncompress_html(&output, &output_len))
return 1;
#else
if (accept_gzip(wsi)) {
if (lws_add_http_header_by_token(wsi, WSI_TOKEN_HTTP_CONTENT_ENCODING, (unsigned char *) "gzip", 4, &p, end))
return 1;
} else {
if (!uncompress_html(&output, &output_len))
return 1;
}
#endif
if (lws_add_http_header_content_length(wsi, (unsigned long) output_len, &p, end))
return 1;
if (lws_finalize_http_header(wsi, &p, end))
return 1;
if (lws_write(wsi, buffer + LWS_PRE, p - (buffer + LWS_PRE), LWS_WRITE_HTTP_HEADERS) < 0)
return 1;
#if LWS_LIBRARY_VERSION_MAJOR < 2
if (lws_write_http(wsi, index_html, index_html_len) < 0)
if (lws_write_http(wsi, output, output_len) < 0)
return 1;
goto try_to_reuse;
#else
pss->buffer = pss->ptr = (char *) index_html;
pss->len = index_html_len;
pss->buffer = pss->ptr = output;
pss->len = output_len;
lws_callback_on_writable(wsi);
#endif
}
@@ -175,7 +241,7 @@ callback_http(struct lws *wsi, enum lws_callback_reasons reason, void *user, voi
memcpy(buffer + LWS_PRE, pss->ptr, n);
pss->ptr += n;
if (lws_write_http(wsi, buffer + LWS_PRE, (size_t) n) < n) {
if (pss->buffer != (char *) index_html) free(pss->buffer);
pss_buffer_free(pss);
return -1;
}
} while (!lws_send_pipe_choked(wsi) && !done);
@@ -185,9 +251,7 @@ callback_http(struct lws *wsi, enum lws_callback_reasons reason, void *user, voi
break;
}
if (pss->buffer != (char *) index_html) {
free(pss->buffer);
}
pss_buffer_free(pss);
goto try_to_reuse;
case LWS_CALLBACK_HTTP_FILE_COMPLETION: