📄 mod_expires.c
字号:
/* <base> [plus] {<num> <type>}* */ /* <base> */ word = ap_getword_conf(p, &code); if (!strncasecmp(word, "now", 1) || !strncasecmp(word, "access", 1)) { base = 'A'; } else if (!strncasecmp(word, "modification", 1)) { base = 'M'; } else { return ap_pstrcat(p, "bad expires code, unrecognised <base> '", word, "'", NULL); }; /* [plus] */ word = ap_getword_conf(p, &code); if (!strncasecmp(word, "plus", 1)) { word = ap_getword_conf(p, &code); }; /* {<num> <type>}* */ while (word[0]) { /* <num> */ if (ap_isdigit(word[0])) { num = atoi(word); } else { return ap_pstrcat(p, "bad expires code, numeric value expected <num> '", word, "'", NULL); }; /* <type> */ word = ap_getword_conf(p, &code); if (word[0]) { /* do nothing */ } else { return ap_pstrcat(p, "bad expires code, missing <type>", NULL); }; factor = 0; if (!strncasecmp(word, "years", 1)) { factor = 60 * 60 * 24 * 365; } else if (!strncasecmp(word, "months", 2)) { factor = 60 * 60 * 24 * 30; } else if (!strncasecmp(word, "weeks", 1)) { factor = 60 * 60 * 24 * 7; } else if (!strncasecmp(word, "days", 1)) { factor = 60 * 60 * 24; } else if (!strncasecmp(word, "hours", 1)) { factor = 60 * 60; } else if (!strncasecmp(word, "minutes", 2)) { factor = 60; } else if (!strncasecmp(word, "seconds", 1)) { factor = 1; } else { return ap_pstrcat(p, "bad expires code, unrecognised <type>", "'", word, "'", NULL); }; modifier = modifier + factor * num; /* next <num> */ word = ap_getword_conf(p, &code); }; *real_code = ap_psprintf(p, "%c%d", base, modifier); return NULL;}static const char *set_expiresbytype(cmd_parms *cmd, expires_dir_config * dir_config, char *mime, char *code){ char *response, *real_code; if ((response = check_code(cmd->pool, code, &real_code)) == NULL) { ap_table_setn(dir_config->expiresbytype, mime, real_code); return NULL; }; return ap_pstrcat(cmd->pool, "'ExpiresByType ", mime, " ", code, "': ", response, NULL);}static const char *set_expiresdefault(cmd_parms *cmd, expires_dir_config * dir_config, char *code){ char *response, *real_code; if ((response = check_code(cmd->pool, code, &real_code)) == NULL) { dir_config->expiresdefault = real_code; return NULL; }; return ap_pstrcat(cmd->pool, "'ExpiresDefault ", code, "': ", response, NULL);}static const command_rec expires_cmds[] ={ {"ExpiresActive", set_expiresactive, NULL, DIR_CMD_PERMS, FLAG, "Limited to 'on' or 'off'"}, {"ExpiresBytype", set_expiresbytype, NULL, DIR_CMD_PERMS, TAKE2, "a MIME type followed by an expiry date code"}, {"ExpiresDefault", set_expiresdefault, NULL, DIR_CMD_PERMS, TAKE1, "an expiry date code"}, {NULL}};static void *merge_expires_dir_configs(pool *p, void *basev, void *addv){ expires_dir_config *new = (expires_dir_config *) ap_pcalloc(p, sizeof(expires_dir_config)); expires_dir_config *base = (expires_dir_config *) basev; expires_dir_config *add = (expires_dir_config *) addv; if (add->active == ACTIVE_DONTCARE) { new->active = base->active; } else { new->active = add->active; }; if (add->expiresdefault != '\0') { new->expiresdefault = add->expiresdefault; }; new->expiresbytype = ap_overlay_tables(p, add->expiresbytype, base->expiresbytype); return new;}static int add_expires(request_rec *r){ expires_dir_config *conf; char *code; time_t base; time_t additional; time_t expires; char age[20]; if (ap_is_HTTP_ERROR(r->status)) /* Don't add Expires headers to errors */ return DECLINED; if (r->main != NULL) /* Say no to subrequests */ return DECLINED; conf = (expires_dir_config *) ap_get_module_config(r->per_dir_config, &expires_module); if (conf == NULL) { ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, r, "internal error: %s", r->filename); return SERVER_ERROR; }; if (conf->active != ACTIVE_ON) return DECLINED; /* we perhaps could use the default_type(r) in its place but that * may be 2nd guesing the desired configuration... calling table_get * with a NULL key will SEGV us * * I still don't know *why* r->content_type would ever be NULL, this * is possibly a result of fixups being called in many different * places. Fixups is probably the wrong place to be doing all this * work... Bah. * * Changed as of 08.Jun.96 don't DECLINE, look for an ExpiresDefault. */ if (r->content_type == NULL) code = NULL; else code = (char *) ap_table_get(conf->expiresbytype, r->content_type); if (code == NULL) { /* no expires defined for that type, is there a default? */ code = conf->expiresdefault; if (code[0] == '\0') return OK; }; /* we have our code */ switch (code[0]) { case 'M': if (r->finfo.st_mode == 0) { /* file doesn't exist on disk, so we can't do anything based on * modification time. Note that this does _not_ log an error. */ return DECLINED; } base = r->finfo.st_mtime; additional = atoi(&code[1]); break; case 'A': /* there's been some discussion and it's possible that * 'access time' will be stored in request structure */ base = r->request_time; additional = atoi(&code[1]); break; default: /* expecting the add_* routines to be case-hardened this * is just a reminder that module is beta */ ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, r, "internal error: bad expires code: %s", r->filename); return SERVER_ERROR; }; expires = base + additional; ap_snprintf(age, sizeof(age), "max-age=%d", (int) expires - (int) r->request_time); ap_table_setn(r->headers_out, "Cache-Control", ap_pstrdup(r->pool, age)); tzset(); /* redundant? called implicitly by localtime, at least * under FreeBSD */ ap_table_setn(r->headers_out, "Expires", ap_gm_timestr_822(r->pool, expires)); return OK;}module MODULE_VAR_EXPORT expires_module ={ STANDARD_MODULE_STUFF, NULL, /* initializer */ create_dir_expires_config, /* dir config creater */ merge_expires_dir_configs, /* dir merger --- default is to override */ NULL, /* server config */ NULL, /* merge server configs */ expires_cmds, /* command table */ NULL, /* handlers */ NULL, /* filename translation */ NULL, /* check_user_id */ NULL, /* check auth */ NULL, /* check access */ NULL, /* type_checker */ add_expires, /* fixups */ NULL, /* logger */ NULL, /* header parser */ NULL, /* child_init */ NULL, /* child_exit */ NULL /* post read-request */};
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -