static int on_config_hosts(h2o_configurator_command_t *cmd, h2o_configurator_context_t *ctx, yoml_t *node) { size_t i; if (node->data.mapping.size == 0) { h2o_configurator_errprintf(cmd, node, "the mapping cannot be empty"); return -1; } for (i = 0; i != node->data.mapping.size; ++i) { yoml_t *key = node->data.mapping.elements[i].key; yoml_t *value = node->data.mapping.elements[i].value; h2o_iovec_t hostname; uint16_t port; if (key->type != YOML_TYPE_SCALAR) { h2o_configurator_errprintf(cmd, key, "key (representing the hostname) must be a string"); return -1; } if (h2o_url_parse_hostport(key->data.scalar, strlen(key->data.scalar), &hostname, &port) == NULL) { h2o_configurator_errprintf(cmd, key, "invalid key (must be either `host` or `host:port`)"); return -1; } ctx->hostconf = h2o_config_register_host(ctx->globalconf, hostname, port); if (h2o_configurator_apply_commands(ctx, value, H2O_CONFIGURATOR_FLAG_HOST, NULL) != 0) return -1; if (yoml_get(value, "paths") == NULL) { h2o_configurator_errprintf(NULL, value, "mandatory configuration directive `paths` is missing"); return -1; } ctx->hostconf = NULL; } return 0; }
static int on_config_paths(h2o_configurator_command_t *cmd, h2o_configurator_context_t *ctx, yoml_t *node) { size_t i; /* sort by the length of the path (descending) */ for (i = 0; i != node->data.mapping.size; ++i) { yoml_t *key = node->data.mapping.elements[i].key; if (key->type != YOML_TYPE_SCALAR) { h2o_configurator_errprintf(cmd, key, "key (representing the virtual path) must be a string"); return -1; } } qsort(node->data.mapping.elements, node->data.mapping.size, sizeof(node->data.mapping.elements[0]), (void *)sort_from_longer_paths); for (i = 0; i != node->data.mapping.size; ++i) { yoml_t *key = node->data.mapping.elements[i].key; yoml_t *value = node->data.mapping.elements[i].value; ctx->pathconf = h2o_config_register_path(ctx->hostconf, key->data.scalar); if (h2o_configurator_apply_commands(ctx, value, H2O_CONFIGURATOR_FLAG_PATH, NULL) != 0) return -1; ctx->pathconf = NULL; } return 0; }
int h2o_configurator_apply(h2o_globalconf_t *config, yoml_t *node) { h2o_configurator_context_t ctx = {config}; if (h2o_configurator_apply_commands(&ctx, node, H2O_CONFIGURATOR_FLAG_GLOBAL, NULL) != 0) return -1; if (config->hosts[0] == NULL) { h2o_configurator_errprintf(NULL, node, "mandatory configuration directive `hosts` is missing"); return -1; } return 0; }
static int on_config_custom_handler(h2o_configurator_command_t *cmd, h2o_configurator_context_t *ctx, yoml_t *node) { static const char *ignore_commands[] = {"extension", NULL}; struct st_h2o_file_configurator_t *self = (void *)cmd->configurator; h2o_pathconf_t *prev_pathconf = ctx->pathconf; yoml_t *ext_node; h2o_mimemap_type_t *type = NULL; int ret = -1; if (node->type != YOML_TYPE_MAPPING) { h2o_configurator_errprintf(cmd, node, "argument must be a MAPPING"); goto Exit; } if ((ext_node = yoml_get(node, "extension")) == NULL) { h2o_configurator_errprintf(cmd, node, "mandatory key `extension` is missing"); goto Exit; } type = h2o_mimemap_create_dynamic_type(ctx->globalconf); ctx->pathconf = &type->data.dynamic.pathconf; if (h2o_configurator_apply_commands(ctx, node, H2O_CONFIGURATOR_FLAG_EXTENSION, ignore_commands) != 0) goto Exit; switch (type->data.dynamic.pathconf.handlers.size) { case 1: break; case 0: h2o_configurator_errprintf(cmd, node, "no handler declared for given extension"); goto Exit; default: h2o_configurator_errprintf(cmd, node, "cannot assign more than one handler for given extension"); goto Exit; } clone_mimemap_if_clean(self); switch (ext_node->type) { case YOML_TYPE_SCALAR: if (assert_is_extension(cmd, ext_node) != 0) goto Exit; h2o_mimemap_set_type(self->vars->mimemap, ext_node->data.scalar + 1, type, 1); break; case YOML_TYPE_SEQUENCE: { size_t i; for (i = 0; i != ext_node->data.sequence.size; ++i) { yoml_t *n = ext_node->data.sequence.elements[i]; if (assert_is_extension(cmd, n) != 0) goto Exit; h2o_mimemap_set_type(self->vars->mimemap, n->data.scalar + 1, type, 1); } } break; default: h2o_configurator_errprintf(cmd, ext_node, "only scalar or sequence of scalar is permitted at the value part of the argument"); goto Exit; } ret = 0; Exit: if (type != NULL) h2o_mem_release_shared(type); ctx->pathconf = prev_pathconf; return ret; }