Nginx源码中按需要修改发送的流的Content

在做CDN的项目中, 由于媒体文件没有后缀, NGINX不会自动根据mime.types来自动获取Content-Type的值,之前使用默认的Content-Type: application/octet-stream;  有部分客户端不会自己去识别流的格式, 不指定正确的Content-Type值无法播放文件,所以我只有修改NGINX源码来指定要发送的Content-Type值了。

记录下我修改的东西,方便以后查阅。

ngx_int_t  ngx_http_send_response(ngx_http_request_t *r, ngx_uint_t status, ngx_str_t *ct, ngx_http_complex_value_t *cv)
ngx_int_t  ngx_http_set_content_type(ngx_http_request_t *r)
r->uri 得到文件名, 查找  文件名.type


//GDB调试时得到的调用堆栈
Breakpoint 1, ngx_http_set_content_type (r=0x7e6760) at src/http/ngx_http_core_module.c:1750
1750        if (r->headers_out.content_type.len) {
(gdb) bt
#0  ngx_http_set_content_type (r=0x7e6760) at src/http/ngx_http_core_module.c:1750
#1  0x0000000000482704 in ngx_http_static_handler (r=0x7e6760) at src/http/modules/ngx_http_static_module.c:223
#2  0x00000000004546f1 in ngx_http_core_content_phase (r=0x7e6760, ph=0x80a3e8) at src/http/ngx_http_core_module.c:1414
#3  0x00000000004531d7 in ngx_http_core_run_phases (r=0x7e6760) at src/http/ngx_http_core_module.c:888
#4  0x000000000045314e in ngx_http_handler (r=0x7e6760) at src/http/ngx_http_core_module.c:871
#5  0x0000000000461604 in ngx_http_process_request (r=0x7e6760) at src/http/ngx_http_request.c:1694
#6  0x000000000046000f in ngx_http_process_request_headers (rev=0x80cef8) at src/http/ngx_http_request.c:1144
#7  0x000000000045f7c4 in ngx_http_process_request_line (rev=0x80cef8) at src/http/ngx_http_request.c:940
#8  0x000000000045e9ac in ngx_http_init_request (rev=0x80cef8) at src/http/ngx_http_request.c:524
#9  0x0000000000448d2a in ngx_epoll_process_events (cycle=0x7a1760, timer=60000, flags=1)
    at src/event/modules/ngx_epoll_module.c:683
#10 0x0000000000439738 in ngx_process_events_and_timers (cycle=0x7a1760) at src/event/ngx_event.c:247
#11 0x0000000000445916 in ngx_single_process_cycle (cycle=0x7a1760) at src/os/unix/ngx_process_cycle.c:316
#12 0x00000000004153e8 in main (argc=1, argv=0x7fffffffe548) at src/core/nginx.c:407

//修改下面这个函数即可
ngx_int_t
ngx_http_set_content_type(ngx_http_request_t *r)
{
    u_char                    c, *exten;
    ngx_str_t                *type;
    ngx_uint_t                i, hash;
    ngx_http_core_loc_conf_t  *clcf;

if (r->headers_out.content_type.len) {
        return NGX_OK;
    }

clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);

if (r->exten.len) {

hash = 0;

for (i = 0; i < r->exten.len; i++) {
            c = r->exten.data[i];

if (c >= 'A' && c <= 'Z') {

exten = ngx_pnalloc(r->pool, r->exten.len);
                if (exten == NULL) {
                    return NGX_ERROR;
                }

hash = ngx_hash_strlow(exten, r->exten.data, r->exten.len);

r->exten.data = exten;

break;
            }

hash = ngx_hash(hash, c);
        }

type = ngx_hash_find(&clcf->types_hash, hash,
                            r->exten.data, r->exten.len);

if (type) {
            r->headers_out.content_type_len = type->len;
            r->headers_out.content_type = *type;

return NGX_OK;
        }
    }

//性能影响就影响吧,只是为了做个功能测试,把Content-Type的值记录到一个文本文件里面,暂时没想到啥好的办法
/////////////////////处理Content-Type添加的代码////////////////////////////////////

char url[1024]={0};
        strncpy (url, r->uri.data, r->uri.len);
        strcat (url, ".type");
        char filename[256]={0};
        snprintf (filename, sizeof(filename)-1, "../html%s", url);
        char stype[64]={0};
        FILE* fp = fopen (filename, "rb");
        if (fp != NULL)
        {
                fread (stype, sizeof(char), sizeof(stype), fp);
                fclose(fp);
                int slen = strlen(stype);
                char* sp = stype+slen;
                while (sp != stype)
                {
                        sp--;
                        if (*sp == '\r' || *sp == '\n' || *sp == ' ')
                                *sp = '\0';
                }
                ngx_str_t cnttype;
                cnttype.len = strlen(stype);
                cnttype.data = strdup(stype);
                r->headers_out.content_type_len = cnttype.len;
                r->headers_out.content_type = cnttype;
                return NGX_OK;
        }

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:http://www.heiqu.com/da4f2e432c5bbce987f0210fdbeb9d26.html