Esempio n. 1
0
enum http_rc_e
action_dir_srv_unlink (struct req_args_s *args)
{
	const gchar *type = TYPE();
	if (!type)
		return _reply_format_error (args, NEWERROR( CODE_BAD_REQUEST, "No service type provided"));

	GError *hook (const gchar * m1) {
		struct addr_info_s m1a;
		if (!grid_string_to_addrinfo (m1, NULL, &m1a))
			return NEWERROR (CODE_NETWORK_ERROR, "Invalid M1 address");
		GError *err = NULL;
		meta1v2_remote_unlink_service (&m1a, &err, args->url, type);
		return err;
	}

	GError *err = _m1_locate_and_action (args, hook);

	if (!err || CODE_IS_NETWORK_ERROR(err->code)) {
		/* Also decache on timeout, a majority of request succeed,
         * and it will probably silently succeed  */
		hc_decache_reference_service (resolver, args->url, type);
	}

	if (!err)
		return _reply_success_json (args, NULL);
	return _reply_common_error (args, err);
}
Esempio n. 2
0
enum http_rc_e
action_conscience_info (struct req_args_s *args)
{
    GError *err;
    const char *v = OPT("what");

    if (v && !strcmp(v, "types")) {
        if (NULL != (err = _cs_check_tokens(args)))
            return _reply_notfound_error (args, err);

        GString *out = g_string_new("");
        g_string_append_c(out, '[');
        NSINFO_DO(if (srvtypes && *srvtypes) {
        g_string_append_c(out, '"');
            g_string_append(out, *srvtypes);
            g_string_append_c(out, '"');
            for (gchar **ps = srvtypes+1; *ps ; ps++) {
                g_string_append_c(out, ',');
                g_string_append_c(out, '"');
                g_string_append(out, *ps);
                g_string_append_c(out, '"');
            }
        });
        g_string_append_c(out, ']');
        return _reply_success_json (args, out);
    }
Esempio n. 3
0
enum http_rc_e
action_dir_srv_renew (struct req_args_s *args, struct json_object *jargs)
{
	(void) jargs;
	const gchar *type = TYPE();
	if (!type)
		return _reply_format_error (args, NEWERROR(CODE_BAD_REQUEST, "No service type provided"));
	gboolean autocreate = _request_has_flag (args, PROXYD_HEADER_MODE, "autocreate");
	gboolean dryrun = _request_has_flag (args, PROXYD_HEADER_MODE, "dryrun");

	gchar **urlv = NULL;
	GError *hook (const gchar * m1) {
		struct addr_info_s m1a;
		if (!grid_string_to_addrinfo (m1, NULL, &m1a))
			return NEWERROR (CODE_NETWORK_ERROR, "Invalid M1 address");
		GError *err = NULL;
		urlv = meta1v2_remote_poll_reference_service (&m1a, &err, args->url, type, dryrun, autocreate);
		return err;
	}

	GError *err = _m1_locate_and_action (args, hook);

	if (!err || CODE_IS_NETWORK_ERROR(err->code)) {
		/* Also decache on timeout, a majority of request succeed,
         * and it will probably silently succeed  */
		hc_decache_reference_service (resolver, args->url, type);
	}

	if (err)
		return _reply_common_error (args, err);
	EXTRA_ASSERT (urlv != NULL);
	return _reply_success_json (args, _pack_and_freev_m1url_list (NULL, urlv));
}
Esempio n. 4
0
enum http_rc_e
action_cache_flush_local (struct req_args_s *args)
{
	grid_lbpool_flush (lbpool);
	hc_resolver_flush_csm0 (resolver);
	hc_resolver_flush_services (resolver);
	return _reply_success_json (args, NULL);
}
Esempio n. 5
0
enum http_rc_e
action_cs_srvcheck (struct req_args_s *args)
{
	GError *err;
	if (NULL != (err = _cs_check_tokens(args)))
		return _reply_notfound_error (args, err);

	return _reply_success_json (args, NULL);
}
Esempio n. 6
0
static enum http_rc_e
_reply_m2_error (struct req_args_s *args, GError * err)
{
	if (!err)
		return _reply_success_json (args, NULL);
	g_prefix_error (&err, "M2 error: ");
	if (err->code == CODE_CONTAINER_NOTEMPTY)
		return _reply_conflict_error (args, err);
	return _reply_common_error (args, err);
}
Esempio n. 7
0
enum http_rc_e
action_cs_del (struct req_args_s *args)
{
	GError *err;
	if (NULL != (err = _cs_check_tokens(args)))
		return _reply_notfound_error (args, err);

	if (!clear_namespace_services (NS(), TYPE(), &err)) {
		g_prefix_error (&err, "Agent error: ");
		return _reply_system_error (args, err);
	}
	return _reply_success_json (args, _create_status (CODE_FINAL_OK, "OK"));
}
Esempio n. 8
0
    enum http_rc_e
action_cs_get (struct req_args_s *args)
{
    GError *err;
    if (NULL != (err = _cs_check_tokens(args)))
        return _reply_notfound_error(args, err);

    GSList *sl = list_namespace_services (NS(), TYPE(), &err);
	if (NULL != err) {
		g_slist_free_full (sl, (GDestroyNotify) service_info_clean);
		g_prefix_error (&err, "Agent error: ");
		return _reply_system_error (args, err);
	}
	return _reply_success_json (args, _cs_pack_and_free_srvinfo_list (sl));
}
Esempio n. 9
0
enum http_rc_e
action_cache_status (struct req_args_s *args)
{
	struct hc_resolver_stats_s s = {{0}};
	hc_resolver_info (resolver, &s);

	GString *gstr = g_string_new ("{");
	g_string_append_printf (gstr, " \"csm0\":{"
		"\"count\":%" G_GINT64_FORMAT ",\"max\":%u,\"ttl\":%lu},",
		s.csm0.count, s.csm0.max, s.csm0.ttl);
	g_string_append_printf (gstr, " \"meta1\":{"
		"\"count\":%" G_GINT64_FORMAT ",\"max\":%u,\"ttl\":%lu}",
		s.services.count, s.services.max, s.services.ttl);
	g_string_append_c (gstr, '}');
	return _reply_success_json (args, gstr);
}
Esempio n. 10
0
    enum http_rc_e
action_cs_info (struct req_args_s *args)
{
    GError *err;
    if (NULL != (err = _cs_check_tokens(args)))
        return _reply_notfound_error (args, err);

    struct namespace_info_s ni;
    memset (&ni, 0, sizeof (ni));
    NSINFO_DO(namespace_info_copy (&nsinfo, &ni, NULL));

    GString *gstr = g_string_new ("");
    namespace_info_encode_json (gstr, &ni);
    namespace_info_clear (&ni);
    return _reply_success_json (args, gstr);
}
Esempio n. 11
0
static enum http_rc_e
action_cache_status (const struct cache_args_s *args)
{
    struct hc_resolver_stats_s s;
    memset (&s, 0, sizeof (s));
    hc_resolver_info (resolver, &s);

    GString *gstr = g_string_new ("{");
    g_string_append_printf (gstr, " \"clock\":%lu,", s.clock);
    g_string_append_printf (gstr, " \"csm0\":{"
    "\"count\":%" G_GINT64_FORMAT ",\"max\":%u,\"ttl\":%lu},",
    s.csm0.count, s.csm0.max, s.csm0.ttl);
    g_string_append_printf (gstr, " \"meta1\":{"
    "\"count\":%" G_GINT64_FORMAT ",\"max\":%u,\"ttl\":%lu}",
    s.services.count, s.services.max, s.services.ttl);
    g_string_append_c (gstr, '}');
    return _reply_success_json (args->rp, gstr);
}
Esempio n. 12
0
static enum http_rc_e
action_status(struct req_args_s *args)
{
    if (0 == strcasecmp("HEAD", args->rq->cmd))
        return _reply_success_json(args, NULL);
    if (0 != strcasecmp("GET", args->rq->cmd))
        return _reply_method_error(args);

    GString *gstr = g_string_sized_new (128);

    /* first, the stats about all the requests received */
    GArray *array = network_server_stat_getall(args->rq->client->server);
    for (guint i=0; i<array->len ; ++i) {
        struct server_stat_s *st = &g_array_index (array, struct server_stat_s, i);
        g_string_append_printf (gstr, "%s = %"G_GUINT64_FORMAT"\n",
        g_quark_to_string (st->which), st->value);
    }
    g_array_free (array, TRUE);

    /* some stats about the internal cache */
    struct hc_resolver_stats_s s = {0};
    hc_resolver_info(resolver, &s);

    g_string_append_printf(gstr, "gauge cache.dir.count = %"G_GINT64_FORMAT"\n", s.csm0.count);
    g_string_append_printf(gstr, "gauge cache.dir.max = %u\n", s.csm0.max);
    g_string_append_printf(gstr, "gauge cache.dir.ttl = %lu\n", s.csm0.ttl);
    g_string_append_printf(gstr, "gauge cache.dir.clock = %lu\n", s.clock);

    g_string_append_printf(gstr, "gauge cache.srv.count = %"G_GINT64_FORMAT"\n", s.services.count);
    g_string_append_printf(gstr, "gauge cache.srv.max = %u\n", s.services.max);
    g_string_append_printf(gstr, "gauge cache.srv.ttl = %lu\n", s.services.ttl);
    g_string_append_printf(gstr, "gauge cache.srv.clock = %lu\n", s.clock);

    gint64 count_down = 0;
    SRV_DO(count_down = lru_tree_count(srv_down));
    g_string_append_printf(gstr, "gauge down.srv = %"G_GINT64_FORMAT"\n",
                           count_down);

    args->rp->set_body_gstr(gstr);
    args->rp->set_status(HTTP_CODE_OK, "OK");
    args->rp->set_content_type("text/x-java-properties");
    args->rp->finalize();
    return HTTPRC_DONE;
}
Esempio n. 13
0
    static enum http_rc_e
_registration (struct req_args_s *args, enum reg_op_e op, struct json_object *jsrv)
{
    GError *err;

    if (!push_queue)
        return _reply_bad_gateway(args, NEWERROR(CODE_INTERNAL_ERROR, "Service upstream disabled"));

    if (NULL != (err = _cs_check_tokens(args)))
        return _reply_notfound_error (args, err);

    struct service_info_s *si = NULL;
    err = service_info_load_json_object (jsrv, &si);

    if (err) {
        if (err->code == CODE_BAD_REQUEST)
            return _reply_format_error (args, err);
        else
            return _reply_system_error (args, err);
    }

    if (!validate_namespace (si->ns_name)) {
        service_info_clean (si);
        return _reply_system_error (args, NEWERROR (CODE_NAMESPACE_NOTMANAGED,
                    "Unexpected NS"));
    }

    si->score.timestamp = network_server_bogonow(args->rq->client->server);

    if (op == REGOP_PUSH)
        si->score.value = SCORE_UNSET;
    else if (op == REGOP_UNLOCK)
        si->score.value = SCORE_UNLOCK;
    else /* if (op == REGOP_LOCK) */
        si->score.value = CLAMP(si->score.value, SCORE_DOWN, SCORE_MAX);

    gchar *key = service_info_key(si);
    PUSH_DO(lru_tree_insert(push_queue, key, si));
    GString *gstr = g_string_new ("");
    service_info_encode_json (gstr, si);
    return _reply_success_json (args, gstr);
}
Esempio n. 14
0
enum http_rc_e
action_dir_srv_force (struct req_args_s *args, struct json_object *jargs)
{
	struct meta1_service_url_s *m1u = NULL;
	const gchar *type = TYPE();
	if (!type)
		return _reply_format_error (args, NEWERROR(CODE_BAD_REQUEST, "No service type provided"));

	gboolean force = _request_has_flag (args, PROXYD_HEADER_MODE, "replace");
	gboolean autocreate = _request_has_flag (args, PROXYD_HEADER_MODE, "autocreate");

	GError *hook (const gchar * m1) {
		struct addr_info_s m1a;
		if (!grid_string_to_addrinfo (m1, NULL, &m1a))
			return NEWERROR (CODE_NETWORK_ERROR, "Invalid M1 address");
		GError *e = NULL;
		gchar *packed = meta1_pack_url (m1u);
		meta1v2_remote_force_reference_service (&m1a, &e, args->url, packed, autocreate, force);
		g_free (packed);
		return e;
	}

	GError *err = meta1_service_url_load_json_object (jargs, &m1u);

	if (!err)
		err = _m1_locate_and_action (args, hook);
	if (m1u) {
		meta1_service_url_clean (m1u);
		m1u = NULL;
	}

	if (!err || CODE_IS_NETWORK_ERROR(err->code)) {
		/* Also decache on timeout, a majority of request succeed,
         * and it will probably silently succeed  */
		hc_decache_reference_service (resolver, args->url, type);
	}

	if (err)
		return _reply_common_error (args, err);
	return _reply_success_json (args, NULL);
}
Esempio n. 15
0
enum http_rc_e
action_dir_srv_list (struct req_args_s *args)
{
	const gchar *type = TYPE();
	if (!type)
		return _reply_format_error (args, NEWERROR( CODE_BAD_REQUEST, "No service type provided"));

	gchar **urlv = NULL;
	GError *err = hc_resolve_reference_service (resolver, args->url, type, &urlv);
	EXTRA_ASSERT ((err != NULL) ^ (urlv != NULL));

	if (!err) {

		if ((args->flags & FLAG_NOEMPTY) && !*urlv) {
			g_strfreev (urlv);
			urlv = NULL;
			return _reply_notfound_error (args, NEWERROR (CODE_NOT_FOUND, "No service linked"));
		}
		return _reply_success_json (args, _pack_and_freev_m1url_list (NULL, urlv));
	}

	return _reply_common_error (args, err);
}
Esempio n. 16
0
static enum http_rc_e
action_cache_set_max_high (const struct cache_args_s *args)
{
    hc_resolver_set_max_csm0 (resolver, args->count);
    return _reply_success_json (args->rp, NULL);
}
Esempio n. 17
0
static enum http_rc_e
_registration (struct req_args_s *args, enum reg_op_e op, struct json_object *jsrv)
{
    GError *err;

    if (!jsrv || !json_object_is_type (jsrv, json_type_object))
        return _reply_common_error (args, BADREQ("Expected: json object"));

    if (!push_queue)
        return _reply_bad_gateway(args, NEWERROR(CODE_INTERNAL_ERROR,
        "Service upstream disabled"));

    if (NULL != (err = _cs_check_tokens(args)))
        return _reply_notfound_error (args, err);

    struct service_info_s *si = NULL;
    err = service_info_load_json_object (jsrv, &si, TRUE);

    if (err) {
        if (err->code == CODE_BAD_REQUEST)
            return _reply_format_error (args, err);
        else
            return _reply_system_error (args, err);
    }

    if (!si->type[0]) {
        service_info_clean (si);
        return _reply_format_error (args, BADREQ("Service type not specified"));
    }

    if (!si->ns_name[0]) {
        g_strlcpy (si->ns_name, nsname, sizeof(si->ns_name));
    } else if (!validate_namespace (si->ns_name)) {
        service_info_clean (si);
        return _reply_format_error (args, NEWERROR (CODE_NAMESPACE_NOTMANAGED,
        "Unexpected NS"));
    }

    si->score.timestamp = oio_ext_real_time () / G_TIME_SPAN_SECOND;

    if (op == REGOP_PUSH)
        si->score.value = SCORE_UNSET;
    else if (op == REGOP_UNLOCK)
        si->score.value = SCORE_UNLOCK;
    else /* if (op == REGOP_LOCK) */
        si->score.value = CLAMP(si->score.value, SCORE_DOWN, SCORE_MAX);

    // TODO follow the DRY principle and factorize this!
    if (flag_cache_enabled) {
        GString *gstr = g_string_new ("");
        service_info_encode_json (gstr, si, TRUE);
        PUSH_DO(lru_tree_insert(push_queue, service_info_key(si), si));
        return _reply_success_json (args, gstr);
    } else {
        CSURL(cs);
        GSList l = {.data = si, .next = NULL};
        if (NULL != (err = conscience_remote_push_services (cs, &l))) {
            service_info_clean (si);
            return _reply_common_error (args, err);
        } else {
            GString *gstr = g_string_new ("");
            service_info_encode_json (gstr, si, TRUE);
            service_info_clean (si);
            return _reply_success_json (args, gstr);
        }
    }
}
Esempio n. 18
0
enum http_rc_e
action_cache_set_ttl_low (struct req_args_s *args)
{
	hc_resolver_set_ttl_services (resolver, atoi (TOK ("COUNT")));
	return _reply_success_json (args, NULL);
}
Esempio n. 19
0
enum http_rc_e
action_forward (struct req_args_s *args)
{
	const char *id = OPT("id");
	const char *action = TOK("ACTION");

	if (!id)
		return _reply_format_error (args, BADREQ("Missing SRVID"));
	if (!action)
		return _reply_format_error (args, BADREQ("Missing action"));

	GError *err = NULL;
	if (!g_ascii_strcasecmp (action, "flush")) {
		err = sqlx_remote_execute_FLUSH (id);
		if (!err)
			return _reply_success_json (args, NULL);
		return _reply_common_error (args, err);
	}
	if (!g_ascii_strcasecmp (action, "reload")) {
		err = sqlx_remote_execute_RELOAD (id);
		if (!err)
			return _reply_success_json (args, NULL);
		return _reply_common_error (args, err);
	}
	if (!g_ascii_strcasecmp (action, "kill")) {
		GByteArray *encoded = message_marshall_gba_and_clean (
				metautils_message_create_named("REQ_KILL"));
		err = gridd_client_exec (id, 1.0, encoded);
		if (err)
			return _reply_common_error (args, err);
		return _reply_success_json (args, NULL);
	}
	if (!g_ascii_strcasecmp (action, "ping")) {
		args->rp->no_access();
		GByteArray *encoded = message_marshall_gba_and_clean (
				metautils_message_create_named("REQ_PING"));
		err = gridd_client_exec (id, 1.0, encoded);
		if (err)
			return _reply_common_error (args, err);
		return _reply_success_json (args, NULL);
	}
	if (!g_ascii_strcasecmp (action, "lean-glib")) {
		MESSAGE req = metautils_message_create_named("REQ_LEAN");
		metautils_message_add_field_str(req, "LIBC", "1");
		metautils_message_add_field_str(req, "THREADS", "1");
		GByteArray *encoded = message_marshall_gba_and_clean (req);
		err = gridd_client_exec (id, 1.0, encoded);
		if (err)
			return _reply_common_error (args, err);
		return _reply_success_json (args, NULL);
	}

	if (!g_ascii_strcasecmp (action, "lean-sqlx")) {
		GByteArray *encoded = message_marshall_gba_and_clean (
				metautils_message_create_named(NAME_MSGNAME_SQLX_LEANIFY));
		err = gridd_client_exec (id, 1.0, encoded);
		if (err)
			return _reply_common_error (args, err);
		return _reply_success_json (args, NULL);
	}

	if (!g_ascii_strcasecmp (action, "version")) {
		args->rp->no_access();
		MESSAGE req = metautils_message_create_named("REQ_VERSION");
		GByteArray *encoded = message_marshall_gba_and_clean (req);
		gchar *packed = NULL;
		err = gridd_client_exec_and_concat_string (id, 1.0, encoded, &packed);
		if (err) {
			g_free0 (packed);
			return _reply_common_error (args, err);
		}

		/* TODO(jfs): quite duplicated from _reply_json() but the original
		   was not suitable. */
		args->rp->set_status (200, "OK");
		args->rp->set_body_bytes (g_bytes_new_take((guint8*)packed, strlen(packed)));
		args->rp->finalize ();
		return HTTPRC_DONE;
	}

	if (!g_ascii_strcasecmp (action, "handlers")) {
		args->rp->no_access();
		MESSAGE req = metautils_message_create_named("REQ_HANDLERS");
		GByteArray *encoded = message_marshall_gba_and_clean (req);
		gchar *packed = NULL;
		err = gridd_client_exec_and_concat_string (id, 1.0, encoded, &packed);
		if (err) {
			g_free0 (packed);
			return _reply_common_error (args, err);
		}

		/* TODO(jfs): quite duplicated from _reply_json() but the original
		   was not suitable. */
		args->rp->set_status (200, "OK");
		args->rp->set_body_bytes (g_bytes_new_take((guint8*)packed, strlen(packed)));
		args->rp->finalize ();
		return HTTPRC_DONE;
	}

	return _reply_common_error (args, BADREQ("unexpected action"));
}
Esempio n. 20
0
enum http_rc_e
action_cache_set_max_high (struct req_args_s *args)
{
	hc_resolver_set_max_csm0 (resolver, atoi (TOK ("COUNT")));
	return _reply_success_json (args, NULL);
}
Esempio n. 21
0
enum http_rc_e
action_cache_flush_high (struct req_args_s *args)
{
	hc_resolver_flush_csm0 (resolver);
	return _reply_success_json (args, NULL);
}
Esempio n. 22
0
enum http_rc_e
action_cache_flush_low (struct req_args_s *args)
{
	hc_resolver_flush_services (resolver);
	return _reply_success_json (args, NULL);
}
Esempio n. 23
0
static enum http_rc_e
action_cache_set_ttl_low (const struct cache_args_s *args)
{
    hc_resolver_set_ttl_services (resolver, args->count);
    return _reply_success_json (args->rp, NULL);
}
Esempio n. 24
0
static enum http_rc_e
action_cache_flush_low (const struct cache_args_s *args)
{
    hc_resolver_flush_services (resolver);
    return _reply_success_json (args->rp, NULL);
}