static int http_admin_start()

in bundles/http_admin/http_admin/src/activator.c [44:140]


static int http_admin_start(http_admin_activator_t *act, celix_bundle_context_t *ctx) {
    celix_bundle_t *bundle = celix_bundleContext_getBundle(ctx);
    char* storeRoot = celix_bundle_getDataFile(bundle, "");
    if (storeRoot == NULL) {
        celix_bundleContext_log(ctx, CELIX_LOG_LEVEL_ERROR, "Cannot get bundle store root for the http admin bundle.");
        return CELIX_BUNDLE_EXCEPTION;
    }

    char* httpRoot = NULL;
    int rc = asprintf(&httpRoot, "%s/root", storeRoot);
    if (rc < 0) {
        celix_bundleContext_log(ctx, CELIX_LOG_LEVEL_ERROR, "Cannot create http root directory for the http admin bundle.");
        free(storeRoot);
        return CELIX_ENOMEM;
    }
    free(storeRoot);

    celix_status_t status = celix_utils_createDirectory(httpRoot, false, NULL);
    if (status != CELIX_SUCCESS) {
        celix_bundleContext_log(ctx, CELIX_LOG_LEVEL_ERROR, "Cannot create http root directory for the http admin bundle.");
        free(httpRoot);
        return status;
    }
    celix_bundleContext_log(ctx, CELIX_LOG_LEVEL_DEBUG, "Using http root directory %s", httpRoot);

    bool prop_use_websockets = celix_bundleContext_getPropertyAsBool(ctx, HTTP_ADMIN_USE_WEBSOCKETS_KEY, HTTP_ADMIN_USE_WEBSOCKETS_DFT);
    long listPort = celix_bundleContext_getPropertyAsLong(ctx,    HTTP_ADMIN_LISTENING_PORTS_KEY, HTTP_ADMIN_LISTENING_PORTS_DFT);
    long websocketTimeoutMs = celix_bundleContext_getPropertyAsLong(ctx, HTTP_ADMIN_WEBSOCKET_TIMEOUT_MS_KEY, HTTP_ADMIN_WEBSOCKET_TIMEOUT_MS_DFT);
    long prop_port_min = celix_bundleContext_getPropertyAsLong(ctx, HTTP_ADMIN_PORT_RANGE_MIN_KEY, HTTP_ADMIN_PORT_RANGE_MIN_DFT);
    long prop_port_max = celix_bundleContext_getPropertyAsLong(ctx, HTTP_ADMIN_PORT_RANGE_MAX_KEY, HTTP_ADMIN_PORT_RANGE_MAX_DFT);
    long num_threads = celix_bundleContext_getPropertyAsLong(ctx, HTTP_ADMIN_NUM_THREADS_KEY, HTTP_ADMIN_NUM_THREADS_DFT);

    char prop_port[64];
    snprintf(prop_port, 64, "%li", listPort);
    char prop_timeout[64];
    snprintf(prop_timeout, 64, "%li", websocketTimeoutMs);
    char prop_num_threads[64];
    snprintf(prop_num_threads, 64, "%li", num_threads);


    act->useWebsockets = prop_use_websockets;

    const char *svr_opts[] = {
            "document_root", httpRoot,
            "listening_ports", prop_port,
            "websocket_timeout_ms", prop_timeout,
            "websocket_root", httpRoot,
            "num_threads", prop_num_threads,
            NULL
    };

    //Try the 'LISTENING_PORT' property first, if failing continue with the port range functionality
    act->httpManager = httpAdmin_create(ctx, httpRoot, svr_opts);

    for(long port = prop_port_min; act->httpManager == NULL && port <= prop_port_max; port++) {
        char *port_str;
        asprintf(&port_str, "%li", port);
        svr_opts[3] = port_str;
        act->httpManager = httpAdmin_create(ctx, httpRoot, svr_opts);
        free(port_str);
    }

    if (act->httpManager != NULL) {
        {
            celix_service_tracking_options_t opts = CELIX_EMPTY_SERVICE_TRACKING_OPTIONS;
            opts.callbackHandle = act->httpManager;
            opts.addWithProperties = http_admin_addHttpService;
            opts.removeWithProperties = http_admin_removeHttpService;
            opts.filter.serviceName = HTTP_ADMIN_SERVICE_NAME;
            act->httpAdminSvcId = celix_bundleContext_trackServicesWithOptions(ctx, &opts);
        }
        {
            celix_bundle_tracking_options_t opts = CELIX_EMPTY_BUNDLE_TRACKING_OPTIONS;
            opts.callbackHandle = act->httpManager;
            opts.onStarted = http_admin_startBundle;
            opts.onStopped = http_admin_stopBundle;
            act->bundleTrackerId = celix_bundleContext_trackBundlesWithOptions(ctx, &opts);
        }

        //Websockets are dependent from the http admin, which starts the server.
        if(act->useWebsockets) {
            //Retrieve some data from the http admin and reuse it for the websocket admin
            struct mg_context *svr_ctx = httpAdmin_getServerContext(act->httpManager);
            act->sockManager = websocketAdmin_create(ctx, svr_ctx);
            if (act->sockManager != NULL) {
                celix_service_tracking_options_t opts = CELIX_EMPTY_SERVICE_TRACKING_OPTIONS;
                opts.callbackHandle = act->sockManager;
                opts.addWithProperties = websocket_admin_addWebsocketService;
                opts.removeWithProperties = websocket_admin_removeWebsocketService;
                opts.filter.serviceName = WEBSOCKET_ADMIN_SERVICE_NAME;
                act->sockAdminSvcId = celix_bundleContext_trackServicesWithOptions(ctx, &opts);
            }
        }
    }

    return CELIX_SUCCESS;
}