Пример #1
0
static guint
_mex_grilo_feed_search (MexGriloFeed      *feed,
                        const char        *search_text,
                        int                offset,
                        int                limit,
                        GrlSourceResultCb  callback)
{
  MexGriloFeedPrivate *priv = feed->priv;
  GrlOperationOptions *options;
	int op_id;

  options = grl_operation_options_new (NULL);
  grl_operation_options_set_flags (options, BROWSE_FLAGS);
  grl_operation_options_set_skip (options, priv->op->offset);
  grl_operation_options_set_count (options, priv->op->limit);

  op_id = grl_source_search (priv->source, priv->op->text,
                             priv->query_keys,
                             options,
                             callback, feed);

	g_object_unref (options);

	return op_id;
}
static GrlOperationOptions *
make_operation_options (RBGriloSource *source, GrlSupportedOps op, int position)
{
	GrlOperationOptions *options;
	GrlCaps *caps;

	caps = grl_source_get_caps (source->priv->grilo_source, op);

	options = grl_operation_options_new (caps);
	grl_operation_options_set_skip (options, position);
	grl_operation_options_set_count (options,
					 CONTAINER_FETCH_SIZE);
	grl_operation_options_set_type_filter (options, GRL_TYPE_FILTER_AUDIO);
	grl_operation_options_set_flags (options, GRL_RESOLVE_NORMAL);

	return options;
}
Пример #3
0
static struct MultipleSearchData *
start_multiple_search_operation (guint search_id,
				 const GList *sources,
				 const gchar *text,
				 const GList *keys,
				 const GList *skip_counts,
				 gint count,
				 GrlOperationOptions *options,
				 GrlSourceResultCb user_callback,
				 gpointer user_data)
{
  GRL_DEBUG ("start_multiple_search_operation");

  struct MultipleSearchData *msd;
  GList *iter_sources, *iter_skips;
  guint n;
  gint first_count, individual_count;

  /* Prepare data required to execute the operation */
  msd = g_new0 (struct MultipleSearchData, 1);
  msd->table = g_hash_table_new_full (g_direct_hash, g_direct_equal,
				      NULL, g_free);
  msd->remaining =
      (count == GRL_COUNT_INFINITY) ? GRL_COUNT_INFINITY : (count - 1);
  msd->search_id = search_id;
  msd->text = g_strdup (text);
  msd->keys = g_list_copy ((GList *) keys);
  msd->options = g_object_ref (options);
  msd->user_callback = user_callback;
  msd->user_data = user_data;

  /* Compute the # of items to request by each source */
  n = g_list_length ((GList *) sources);
  if (count == GRL_COUNT_INFINITY) {
    individual_count = GRL_COUNT_INFINITY;
    first_count = GRL_COUNT_INFINITY;
  } else {
    individual_count = count / n;
    first_count = individual_count + count % n;
  }

  /* Issue search operations on each source */
  iter_sources = (GList *) sources;
  iter_skips = (GList *) skip_counts;
  n = 0;
  while (iter_sources) {
    GrlSource *source;
    guint c, id;
    struct ResultCount *rc;
    guint skip;

    source = GRL_SOURCE (iter_sources->data);

    /* c is the count to use for this source */
    c = (n == 0) ? first_count : individual_count;
    n++;

    /* Only interested in sources with c != 0 */
    if (c != 0) {
      GrlOperationOptions *source_options = NULL;
      GrlCaps *source_caps;

      /* We use ResultCount to keep track of results emitted by this source */
      rc = g_new0 (struct ResultCount, 1);
      rc->count = c;
      g_hash_table_insert (msd->table, source, rc);

      /* Check if we have to apply a "skip" parameter to this source
	 (useful when we are chaining queries to complete the result count) */
      if (iter_skips) {
	skip = GPOINTER_TO_INT (iter_skips->data);
      } else {
	skip = 0;
      }

      source_caps = grl_source_get_caps (source, GRL_OP_SEARCH);
      grl_operation_options_obey_caps (options, source_caps, &source_options, NULL);
      grl_operation_options_set_skip (source_options, skip);
      grl_operation_options_set_count (source_options, rc->count);

      /* Execute the search on this source */
      id = grl_source_search (source,
				    msd->text,
				    msd->keys,
				    source_options,
				    multiple_search_cb,
				    msd);

      GRL_DEBUG ("Operation %s:%u: Searching %u items from offset %u",
                 grl_source_get_name (GRL_SOURCE (source)),
                 id, rc->count, skip);

      g_object_unref (source_options);

      /* Keep track of this operation and this source */
      msd->search_ids = g_list_prepend (msd->search_ids, GINT_TO_POINTER (id));
      msd->sources = g_list_prepend (msd->sources, source);
      msd->sources_count++;
    }

    /* Move to the next source */
    iter_sources = g_list_next (iter_sources);
    iter_skips = g_list_next (iter_skips);
  }
static GList *
search_objects_cb (MS2Server *server,
                   const gchar *id,
                   const gchar *query,
                   guint offset,
                   guint max_count,
                   const gchar **properties,
                   gpointer data,
                   GError **error)
{
  GList *objects;
  GriloMs2Data *grdata;
  gint count;

  /* Browse is only allowed in root container */
  if (g_strcmp0 (id, MS2_ROOT) != 0) {
    if (error) {
      /* FIXME: a better error should be reported */
      *error = g_error_new (0, 0, "search is only allowed in root container");
    }
    return NULL;
  }

  grdata = g_slice_new0 (GriloMs2Data);
  grdata->server = g_object_ref (server);
  grdata->source = (GrlSource *) data;
  grdata->options = grl_operation_options_new (NULL);
  grdata->keys = get_grilo_keys (properties, &grdata->other_keys);
  grdata->parent_id = g_strdup (id);
  grdata->list_type = LIST_ALL;

  grl_operation_options_set_resolution_flags (grdata->options,
                                              GRL_RESOLVE_FULL |
                                              GRL_RESOLVE_IDLE_RELAY);

  /* Adjust limits */
  if (offset >= limit) {
    browse_cb (grdata->source, 0, NULL, 0, grdata, NULL);
  } else {
    count = max_count == 0? (limit - offset): CLAMP (max_count,
                                                     1,
                                                     limit - offset);
    grl_operation_options_set_count (grdata->options, count);
    grl_operation_options_set_skip (grdata->options, offset);
    grl_source_search (grdata->source,
                       query,
                       grdata->keys,
                       grdata->options,
                       browse_cb,
                       grdata);
  }

  wait_for_result (grdata);

  if (grdata->error) {
    if (error) {
      *error = grdata->error;
    }
    g_list_foreach (grdata->children, (GFunc) g_hash_table_unref, NULL);
    g_list_free (grdata->children);
    objects = NULL;
  } else {
    objects = grdata->children;
  }

  g_list_free (grdata->keys);
  g_list_free (grdata->other_keys);
  g_free (grdata->parent_id);
  g_object_unref (grdata->server);
  g_object_unref (grdata->options);
  g_slice_free (GriloMs2Data, grdata);

  return objects;
}
static GList *
list_children_cb (MS2Server *server,
                  const gchar *id,
                  ListType list_type,
                  guint offset,
                  guint max_count,
                  const gchar **properties,
                  gpointer data,
                  GError **error)
{
  GList *children;
  GrlMedia *media;
  GriloMs2Data *grdata;
  gint count;

  grdata = g_slice_new0 (GriloMs2Data);
  grdata->server = g_object_ref (server);
  grdata->source = (GrlSource *) data;
  grdata->options = grl_operation_options_new (NULL);
  grdata->keys = get_grilo_keys (properties, &grdata->other_keys);
  grdata->parent_id = g_strdup (id);
  grdata->offset = offset;
  grdata->list_type = list_type;

  grl_operation_options_set_resolution_flags (grdata->options,
                                              GRL_RESOLVE_FULL |
                                              GRL_RESOLVE_IDLE_RELAY);

  media = unserialize_media (grdata->source, id);

  /* Adjust limits */
  if (offset >= limit) {
    browse_cb (grdata->source, 0, NULL, 0, grdata, NULL);
  } else {
    /* TIP: as Grilo is not able to split containers and items, in this case we
       will ask for all elements and then remove unneeded children in callback */
    switch (list_type) {
    case LIST_ALL:
      count = max_count == 0? (limit - offset): CLAMP (max_count,
                                                       1,
                                                       limit - offset);
      grl_operation_options_set_count (grdata->options, count);
      grl_operation_options_set_skip (grdata->options, offset);
      grdata->operation_id = grl_source_browse (grdata->source,
                                                media,
                                                grdata->keys,
                                                grdata->options,
                                                browse_cb,
                                                grdata);
      break;
    case LIST_CONTAINERS:
    case LIST_ITEMS:
      count = max_count == 0? limit: max_count;
      grl_operation_options_set_count  (grdata->options, count);
      grl_operation_options_set_skip (grdata->options, 0);
      grdata->operation_id = grl_source_browse (grdata->source,
                                                media,
                                                grdata->keys,
                                                grdata->options,
                                                browse_cb,
                                                grdata);
      break;
    default:
      /* Protection. It should never be reached, unless ListType is extended */
      browse_cb (grdata->source, 0, NULL, 0, grdata, NULL);
    }
  }

  wait_for_result (grdata);

  if (grdata->error) {
    if (error) {
      *error = grdata->error;
    }
    g_list_foreach (grdata->children, (GFunc) g_hash_table_unref, NULL);
    g_list_free (grdata->children);
    children = NULL;
  } else {
    children = grdata->children;
  }

  g_object_unref (media);
  g_list_free (grdata->keys);
  g_list_free (grdata->other_keys);
  g_free (grdata->parent_id);
  g_object_unref (grdata->server);
  g_object_unref (grdata->options);
  g_slice_free (GriloMs2Data, grdata);

  return children;
}