Beispiel #1
0
static struct watchman_query_result *
watchman_query_json(struct watchman_connection *conn, json_t *query,
                    struct watchman_error *error)
{
    struct watchman_query_result *result = NULL;
    struct watchman_query_result *res = NULL;

    if (watchman_send(conn, query, error)) {
        return NULL;
    }
    /* parse the result */
    json_t *obj = watchman_read(conn, error);
    if (!obj) {
        return NULL;
    }
    JSON_ASSERT(json_is_object, obj, "Failed to send watchman query %s");

    json_t *jerror = json_object_get(obj, "error");
    if (jerror) {
        watchman_err(error, "Error result from watchman: %s",
                     json_string_value(jerror));
        goto done;
    }

    res = calloc(1, sizeof(*res));

    json_t *files = json_object_get(obj, "files");
    JSON_ASSERT(json_is_array, files, "Bad files %s");

    int nr = json_array_size(files);
    res->stats = calloc(nr, sizeof(*res->stats));

    int i;
    for (i = 0; i < nr; ++i) {
        struct watchman_stat *stat = res->stats + i;
        json_t *statobj = json_array_get(files, i);
        if (json_is_string(statobj)) {
            /* then hopefully we only requested names */
            stat->name = strdup(json_string_value(statobj));
            res->nr++;
            continue;
        }

        JSON_ASSERT(json_is_object, statobj, "must be object: %s");

        json_t *name = json_object_get(statobj, "name");
        JSON_ASSERT(json_is_string, name, "name must be string: %s");
        stat->name = strdup(json_string_value(name));

        WRITE_BOOL_STAT(stat, statobj, exists);
        WRITE_INT_STAT(stat, statobj, ctime);
        WRITE_INT_STAT(stat, statobj, ctime_ms);
        WRITE_INT_STAT(stat, statobj, ctime_us);
        WRITE_INT_STAT(stat, statobj, ctime_ns);
        WRITE_INT_STAT(stat, statobj, dev);
        WRITE_INT_STAT(stat, statobj, gid);
        WRITE_INT_STAT(stat, statobj, ino);
        WRITE_INT_STAT(stat, statobj, mode);
        WRITE_INT_STAT(stat, statobj, mtime);
        WRITE_INT_STAT(stat, statobj, mtime_ms);
        WRITE_INT_STAT(stat, statobj, mtime_us);
        WRITE_INT_STAT(stat, statobj, mtime_ns);
        WRITE_INT_STAT(stat, statobj, nlink);
        WRITE_INT_STAT(stat, statobj, size);
        WRITE_INT_STAT(stat, statobj, uid);

        WRITE_STR_STAT(stat, statobj, cclock);
        WRITE_STR_STAT(stat, statobj, oclock);

        WRITE_FLOAT_STAT(stat, statobj, ctime_f);
        WRITE_FLOAT_STAT(stat, statobj, mtime_f);

        /* the one we have to do manually because we don't
         * want to use the name "new" */
        json_t *newer = json_object_get(statobj, "new");
        if (newer) {
            stat->newer = json_is_true(newer);
        }
        res->nr++;
    }

    json_t *version = json_object_get(obj, "version");
    JSON_ASSERT(json_is_string, version, "Bad version %s");
    res->version = strdup(json_string_value(version));

    json_t *clock = json_object_get(obj, "clock");
    JSON_ASSERT(json_is_string, clock, "Bad clock %s");
    res->clock = strdup(json_string_value(clock));

    json_t *fresh = json_object_get(obj, "is_fresh_instance");
    JSON_ASSERT(json_is_boolean, fresh, "Bad is_fresh_instance %s");
    res->is_fresh_instance = json_is_true(fresh);

    result = res;
    res = NULL;
done:
    if (res) {
        watchman_free_query_result(res);
    }
    json_decref(obj);
    return result;
}
Beispiel #2
0
static struct watchman_query_result *
watchman_query_json(struct watchman_connection *conn,
                    json_t *query,
                    struct timeval *timeout,
                    struct watchman_error *error)
{
    struct watchman_query_result *result = NULL;
    struct watchman_query_result *res = NULL;

    if (watchman_send(conn, query, error)) {
        return NULL;
    }
    /* parse the result */
    proto_t obj = watchman_read_with_timeout(conn, timeout, error);
    if (proto_is_null(obj)) {
        return NULL;
    }
    PROTO_ASSERT(proto_is_object, obj, "Failed to send watchman query %s");

    proto_t jerror = proto_object_get(obj, "error");
    if (!proto_is_null(jerror)) {
        watchman_err(error, WATCHMAN_ERR_WATCHMAN_REPORTED,
                     "Error result from watchman: %s",
                     proto_strdup(jerror));
        goto done;
    }

    res = calloc(1, sizeof(*res));

    proto_t files = proto_object_get(obj, "files");
    PROTO_ASSERT(proto_is_array, files, "Bad files %s");

    int nr = proto_array_size(files);
    res->stats = calloc(nr, sizeof(*res->stats));

    int i;
    for (i = 0; i < nr; ++i) {
        struct watchman_stat *stat = res->stats + i;
        proto_t statobj = proto_array_get(files, i);
        if (proto_is_string(statobj)) {
            /* then hopefully we only requested names */
            stat->name = proto_strdup(statobj);
            res->nr++;
            continue;
        }

        PROTO_ASSERT(proto_is_object, statobj, "must be object: %s");

        proto_t name = proto_object_get(statobj, "name");
        PROTO_ASSERT(proto_is_string, name, "name must be string: %s");
        stat->name = proto_strdup(name);

        WRITE_BOOL_STAT(stat, statobj, exists);
        WRITE_INT_STAT(stat, statobj, ctime);
        WRITE_INT_STAT(stat, statobj, ctime_ms);
        WRITE_INT_STAT(stat, statobj, ctime_us);
        WRITE_INT_STAT(stat, statobj, ctime_ns);
        WRITE_INT_STAT(stat, statobj, dev);
        WRITE_INT_STAT(stat, statobj, gid);
        WRITE_INT_STAT(stat, statobj, ino);
        WRITE_INT_STAT(stat, statobj, mode);
        WRITE_INT_STAT(stat, statobj, mtime);
        WRITE_INT_STAT(stat, statobj, mtime_ms);
        WRITE_INT_STAT(stat, statobj, mtime_us);
        WRITE_INT_STAT(stat, statobj, mtime_ns);
        WRITE_INT_STAT(stat, statobj, nlink);
        WRITE_INT_STAT(stat, statobj, size);
        WRITE_INT_STAT(stat, statobj, uid);

        WRITE_STR_STAT(stat, statobj, cclock);
        WRITE_STR_STAT(stat, statobj, oclock);

        WRITE_FLOAT_STAT(stat, statobj, ctime_f);
        WRITE_FLOAT_STAT(stat, statobj, mtime_f);

        /* the one we have to do manually because we don't
         * want to use the name "new" */
        proto_t newer = proto_object_get(statobj, "new");
        if (!proto_is_null(newer)) {
            stat->newer = proto_is_true(newer);
        }
        res->nr++;
    }

    proto_t version = proto_object_get(obj, "version");
    PROTO_ASSERT(proto_is_string, version, "Bad version %s");
    res->version = proto_strdup(version);

    proto_t clock = proto_object_get(obj, "clock");
    PROTO_ASSERT(proto_is_string, clock, "Bad clock %s");
    res->clock = proto_strdup(clock);

    proto_t fresh = proto_object_get(obj, "is_fresh_instance");
    PROTO_ASSERT(proto_is_boolean, fresh, "Bad is_fresh_instance %s");
    res->is_fresh_instance = proto_is_true(fresh);

    result = res;
    res = NULL;
done:
    if (res) {
        watchman_free_query_result(res);
    }
    proto_free(obj);
    return result;
}