[gnome-builder] xml symbol resolver: add a tree builder



commit 4262209013f7cb72df0fed572492a1d66adc9b65
Author: Sebastien Lafargue <slafargue gnome org>
Date:   Sun Jan 22 12:40:52 2017 +0100

    xml symbol resolver: add a tree builder
    
    The building of the symbol trees is now done in its own class
    and in a thread.

 plugins/xml-pack/Makefile.am            |    2 +
 plugins/xml-pack/ide-xml-service.c      |  256 ++++--------------------
 plugins/xml-pack/ide-xml-tree-builder.c |  333 +++++++++++++++++++++++++++++++
 plugins/xml-pack/ide-xml-tree-builder.h |   46 +++++
 4 files changed, 425 insertions(+), 212 deletions(-)
---
diff --git a/plugins/xml-pack/Makefile.am b/plugins/xml-pack/Makefile.am
index a4de185..3404fd4 100644
--- a/plugins/xml-pack/Makefile.am
+++ b/plugins/xml-pack/Makefile.am
@@ -19,6 +19,8 @@ libxml_pack_plugin_la_SOURCES = \
        ide-xml-symbol-resolver.h \
        ide-xml-symbol-tree.c \
        ide-xml-symbol-tree.h \
+       ide-xml-tree-builder.c \
+       ide-xml-tree-builder.h \
        ide-xml.c \
        ide-xml.h \
        xml-pack-plugin.c \
diff --git a/plugins/xml-pack/ide-xml-service.c b/plugins/xml-pack/ide-xml-service.c
index af7e015..140c3d2 100644
--- a/plugins/xml-pack/ide-xml-service.c
+++ b/plugins/xml-pack/ide-xml-service.c
@@ -23,60 +23,21 @@
 #include <gtksourceview/gtksource.h>
 #include <math.h>
 
+#include "ide-xml-tree-builder.h"
+
 #include "ide-xml-service.h"
-#include "xml-reader.h"
 
 gboolean _ide_buffer_get_loading (IdeBuffer *self);
 
 #define DEFAULT_EVICTION_MSEC (60 * 1000)
 
-typedef GPtrArray IdeXmlStack;
-
-static inline IdeXmlStack *
-stack_new (void)
-{
-  return g_ptr_array_new ();
-}
-
-static inline void
-stack_push (IdeXmlStack *stack,
-            gpointer     ptr)
-{
-  g_ptr_array_add (stack, ptr);
-}
-
-static inline gpointer
-stack_pop (IdeXmlStack *stack)
-{
-  gint end = stack->len - 1;
-
-  return (end < 0) ? NULL : g_ptr_array_remove_index_fast (stack, end);
-}
-
-static inline gint
-stack_is_empty (IdeXmlStack *stack)
-{
-  return (stack->len == 0);
-}
-
-static inline void
-stack_destroy (IdeXmlStack *stack)
-{
-  g_ptr_array_unref (stack);
-}
-
-static inline gsize
-stack_get_size (IdeXmlStack *stack)
-{
-  return stack->len;
-}
-
 struct _IdeXmlService
 {
   IdeObject         parent_instance;
 
-  EggTaskCache     *trees;
-  GCancellable     *cancellable;
+  EggTaskCache      *trees;
+  IdeXmlTreeBuilder *tree_builder;
+  GCancellable      *cancellable;
 };
 
 static void service_iface_init (IdeServiceInterface *iface);
@@ -84,153 +45,25 @@ static void service_iface_init (IdeServiceInterface *iface);
 G_DEFINE_DYNAMIC_TYPE_EXTENDED (IdeXmlService, ide_xml_service, IDE_TYPE_OBJECT, 0,
                                 G_IMPLEMENT_INTERFACE (IDE_TYPE_SERVICE, service_iface_init))
 
-static IdeXmlSymbolNode *
-create_node_from_reader (XmlReader *reader)
-{
-  const gchar *name;
-  GFile *file = NULL;
-  guint line = 0;
-  guint line_offset = 0;
-
-  name = xml_reader_get_name (reader);
-
-  return ide_xml_symbol_node_new (name, file, line, line_offset);
-}
-
 static void
-print_node (IdeXmlSymbolNode *node,
-            guint             depth)
-{
-  g_autofree gchar *spacer;
-
-  spacer = g_strnfill (depth, '\t');
-  printf ("%s%s (%i)\n",
-          spacer,
-          ide_symbol_node_get_name (IDE_SYMBOL_NODE (node)),
-          depth);
-}
-
-static IdeXmlSymbolNode *
-ide_xml_service_walk_tree (IdeXmlService    *self,
-                           XmlReader        *reader)
-{
-  IdeXmlStack *stack;
-  IdeXmlSymbolNode *root_node;
-  IdeXmlSymbolNode *parent_node;
-  IdeXmlSymbolNode *current_node;
-  IdeXmlSymbolNode *previous_node = NULL;
-  xmlReaderTypes type;
-  gint depth = 0;
-  gint current_depth = 0;
-  gboolean is_empty;
-
-  g_assert (IDE_IS_XML_SERVICE (self));
-  g_assert (XML_IS_READER (reader));
-
-  stack = stack_new ();
-
-  parent_node = root_node = ide_xml_symbol_node_new ("root", NULL, 0, 0);
-  stack_push (stack, parent_node);
-
-  while (xml_reader_read (reader))
-    {
-      type = xml_reader_get_node_type (reader);
-      if ( type == XML_READER_TYPE_ELEMENT)
-        {
-          current_node = create_node_from_reader (reader);
-          depth = xml_reader_get_depth (reader);
-          is_empty = xml_reader_is_empty_element (reader);
-
-          /* TODO: take end elements into account and use:
-           * || ABS (depth - current_depth) > 1
-           */
-          if (depth < 0)
-            {
-              g_warning ("Wrong xml element depth, current:%i new:%i\n", current_depth, depth);
-              break;
-            }
-
-          if (depth > current_depth)
-            {
-              ++current_depth;
-              stack_push (stack, parent_node);
-
-              g_assert (previous_node != NULL);
-              parent_node = previous_node;
-              ide_xml_symbol_node_take_child (parent_node, current_node);
-            }
-          else if (depth < current_depth)
-            {
-              --current_depth;
-              parent_node = stack_pop (stack);
-              if (parent_node == NULL)
-                {
-                  g_warning ("Xml nodes stack empty\n");
-                  break;
-                }
-
-              g_assert (parent_node != NULL);
-              ide_xml_symbol_node_take_child (parent_node, current_node);
-            }
-          else
-            {
-              ide_xml_symbol_node_take_child (parent_node, current_node);
-            }
-
-          previous_node = current_node;
-          print_node (current_node, depth);
-        }
-    }
-
-  printf ("stack size:%li\n", stack_get_size (stack));
-
-  stack_destroy (stack);
-
-  return root_node;
-}
-
-static IdeXmlSymbolNode *
-ide_xml_service_build_tree (IdeXmlService *self,
-                            GBytes        *content,
-                            GFile         *file)
+ide_xml_service_build_tree_cb2 (GObject      *object,
+                                GAsyncResult *result,
+                                gpointer      user_data)
 {
+  IdeXmlTreeBuilder *tree_builder = (IdeXmlTreeBuilder *)object;
+  g_autoptr(GTask) task = user_data;
   IdeXmlSymbolNode *root_node;
-  XmlReader *reader;
-  const gchar *data;
-  g_autofree gchar *uri;
-  gsize size;
-
-  g_assert (IDE_IS_XML_SERVICE (self));
-
-  data = g_bytes_get_data (content, &size);
-  uri = g_file_get_uri (file);
-  reader = xml_reader_new ();
-  xml_reader_load_from_data (reader, data, size, uri, NULL);
-  root_node = ide_xml_service_walk_tree (self, reader);
-
-  g_object_unref (reader);
-
-  return root_node;
-}
-
-static GBytes *
-ide_xml_service_get_file_content (IdeXmlService *self,
-                                  GFile         *file)
-{
-  IdeContext *context;
-  IdeBufferManager *manager;
-  IdeBuffer *buffer;
-  GBytes *content = NULL;
-
-  g_assert (IDE_IS_XML_SERVICE (self));
-  g_assert (G_IS_FILE (file));
+  GError *error = NULL;
 
-  context = ide_object_get_context (IDE_OBJECT (self));
-  manager = ide_context_get_buffer_manager (context);
-  if (NULL != (buffer = ide_buffer_manager_find_buffer (manager, file)))
-    content = ide_buffer_get_content (buffer);
+  g_assert (IDE_IS_XML_TREE_BUILDER (tree_builder));
+  g_assert (G_IS_TASK (result));
+  g_assert (G_IS_TASK (task));
 
-  return content;
+  root_node = ide_xml_tree_builder_build_tree_finish (tree_builder, result, &error);
+  if (root_node == NULL)
+    g_task_return_error (task, error);
+  else
+    g_task_return_pointer (task, root_node, g_object_unref);
 }
 
 static void
@@ -241,11 +74,8 @@ ide_xml_service_build_tree_cb (EggTaskCache  *cache,
 {
   IdeXmlService *self = user_data;
   g_autofree gchar *path = NULL;
-  IdeContext *context;
   IdeFile *ifile = (IdeFile *)key;
   GFile *gfile;
-  IdeXmlSymbolNode *root_node;
-  GBytes *content = NULL;
 
   IDE_ENTRY;
 
@@ -255,8 +85,6 @@ ide_xml_service_build_tree_cb (EggTaskCache  *cache,
   g_assert (G_IS_TASK (task));
 
   gfile = ide_file_get_file (ifile);
-  context = ide_object_get_context (IDE_OBJECT (self));
-
   if (!gfile || !(path = g_file_get_path (gfile)))
     {
       g_task_return_new_error (task,
@@ -267,19 +95,11 @@ ide_xml_service_build_tree_cb (EggTaskCache  *cache,
     }
 
   printf ("tree path:%s\n", path);
-  if (NULL != (content = ide_xml_service_get_file_content (self, gfile)))
-    {
-      root_node = ide_xml_service_build_tree (self, content, gfile);
-      g_task_return_pointer (task, root_node, g_object_unref);
-    }
-  else
-    {
-      g_task_return_new_error (task,
-                               G_IO_ERROR,
-                               G_IO_ERROR_FAILED,
-                               _("Failed to create xml tree."));
-      return;
-    }
+  ide_xml_tree_builder_build_tree_async (self->tree_builder,
+                                         gfile,
+                                         g_task_get_cancellable (task),
+                                         ide_xml_service_build_tree_cb2,
+                                         g_object_ref (task));
 
   IDE_EXIT;
 }
@@ -306,18 +126,20 @@ ide_xml_service_get_root_node_cb (GObject      *object,
                                   gpointer      user_data)
 {
   EggTaskCache *cache = (EggTaskCache *)object;
-  g_autoptr(IdeXmlSymbolNode) ret = NULL;
   g_autoptr(GTask) task = user_data;
+  IdeXmlSymbolNode *ret;
   GError *error = NULL;
 
   g_assert (EGG_IS_TASK_CACHE (cache));
+  g_assert (G_IS_TASK (result));
+  g_assert (G_IS_TASK (task));
 
   if (!(ret = egg_task_cache_get_finish (cache, result, &error)))
     g_task_return_error (task, error);
   else
     {
       printf ("new tree:%p\n", ret);
-    g_task_return_pointer (task, g_steal_pointer (&ret), g_object_unref);
+      g_task_return_pointer (task, ret, g_object_unref);
     }
 }
 
@@ -338,7 +160,7 @@ ide_xml_service__buffer_loaded_cb (IdeBuffer *buffer,
   g_autoptr(GTask) task = state->task;
 
   g_assert (IDE_IS_XML_SERVICE (self));
-  g_assert (G_IS_TASK (state->task));
+  g_assert (G_IS_TASK (task));
   g_assert (state->cancellable == NULL || G_IS_CANCELLABLE (state->cancellable));
   g_assert (IDE_IS_FILE (state->ifile));
   g_assert (IDE_IS_BUFFER (state->buffer));
@@ -433,7 +255,7 @@ ide_xml_service_get_root_node_async (IdeXmlService       *self,
       /* Wait for the buffer to be fully loaded */
       state = g_slice_new0 (TaskState);
       state->self = self;
-      state->task = g_object_ref (task);
+      state->task = g_steal_pointer (&task);
       state->cancellable = cancellable;
       state->ifile = g_object_ref (file);
       state->buffer = g_object_ref (buffer);
@@ -449,7 +271,7 @@ ide_xml_service_get_root_node_async (IdeXmlService       *self,
                               TRUE,
                               cancellable,
                               ide_xml_service_get_root_node_cb,
-                              g_object_ref (task));
+                              g_steal_pointer (&task));
 }
 
 /**
@@ -468,6 +290,7 @@ ide_xml_service_get_root_node_finish (IdeXmlService  *self,
   GTask *task = (GTask *)result;
 
   g_return_val_if_fail (IDE_IS_XML_SERVICE (self), NULL);
+  g_return_val_if_fail (G_IS_TASK (result), NULL);
 
   return g_task_propagate_pointer (task, error);
 }
@@ -475,9 +298,9 @@ ide_xml_service_get_root_node_finish (IdeXmlService  *self,
 static void
 ide_xml_service_context_loaded (IdeService *service)
 {
-  IdeBufferManager *buffer_manager;
   IdeXmlService *self = (IdeXmlService *)service;
   IdeContext *context;
+  IdeBufferManager *buffer_manager;
 
   IDE_ENTRY;
 
@@ -492,6 +315,13 @@ ide_xml_service_context_loaded (IdeService *service)
                            self,
                            G_CONNECT_SWAPPED);
 
+  if (self->tree_builder == NULL)
+    self->tree_builder = g_object_new (IDE_TYPE_XML_TREE_BUILDER,
+                                       "context", context,
+                                       NULL);
+
+  /* TODO: schedule caching of open views trees */
+
   IDE_EXIT;
 }
 
@@ -537,8 +367,10 @@ ide_xml_service_finalize (GObject *object)
 
   IDE_ENTRY;
 
-  g_clear_object (&self->trees);
-  g_clear_object (&self->cancellable);
+ ide_xml_service_stop (IDE_SERVICE (self));
+
+  if (self->tree_builder != NULL)
+    g_clear_object (&self->tree_builder);
 
   G_OBJECT_CLASS (ide_xml_service_parent_class)->finalize (object);
 
diff --git a/plugins/xml-pack/ide-xml-tree-builder.c b/plugins/xml-pack/ide-xml-tree-builder.c
new file mode 100644
index 0000000..a5fff45
--- /dev/null
+++ b/plugins/xml-pack/ide-xml-tree-builder.c
@@ -0,0 +1,333 @@
+/* ide-xml-tree-builder.c
+ *
+ * Copyright (C) 2017 Sebastien Lafargue <slafargue gnome org>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <egg-task-cache.h>
+#include <glib/gi18n.h>
+
+#include "xml-reader.h"
+
+#include "ide-xml-tree-builder.h"
+
+typedef GPtrArray IdeXmlStack;
+
+static inline IdeXmlStack *
+stack_new (void)
+{
+  return g_ptr_array_new ();
+}
+
+static inline void
+stack_push (IdeXmlStack *stack,
+            gpointer     ptr)
+{
+  g_ptr_array_add (stack, ptr);
+}
+
+static inline gpointer
+stack_pop (IdeXmlStack *stack)
+{
+  gint end = stack->len - 1;
+
+  return (end < 0) ? NULL : g_ptr_array_remove_index_fast (stack, end);
+}
+
+static inline gint
+stack_is_empty (IdeXmlStack *stack)
+{
+  return (stack->len == 0);
+}
+
+static inline void
+stack_destroy (IdeXmlStack *stack)
+{
+  g_ptr_array_unref (stack);
+}
+
+static inline gsize
+stack_get_size (IdeXmlStack *stack)
+{
+  return stack->len;
+}
+
+struct _IdeXmlService
+{
+  IdeObject         parent_instance;
+
+  EggTaskCache     *trees;
+  GCancellable     *cancellable;
+};
+struct _IdeXmlTreeBuilder
+{
+  IdeObject parent_instance;
+};
+
+typedef struct{
+  XmlReader *reader;
+  GBytes    *content;
+  GFile     *file;
+} BuilderState;
+
+static void
+builder_state_free (BuilderState *state)
+{
+  g_clear_object (&state->reader);
+  g_clear_pointer (&state->content, g_bytes_unref);
+  g_clear_object (&state->file);
+}
+
+G_DEFINE_TYPE (IdeXmlTreeBuilder, ide_xml_tree_builder, IDE_TYPE_OBJECT)
+
+static IdeXmlSymbolNode *
+create_node_from_reader (XmlReader *reader)
+{
+  const gchar *name;
+  GFile *file = NULL;
+  guint line = 0;
+  guint line_offset = 0;
+
+  name = xml_reader_get_name (reader);
+
+  return ide_xml_symbol_node_new (name, IDE_SYMBOL_UI_OBJECT,
+                                  file, line, line_offset);
+}
+
+static void
+print_node (IdeXmlSymbolNode *node,
+            guint             depth)
+{
+  g_autofree gchar *spacer;
+
+  spacer = g_strnfill (depth, '\t');
+  printf ("%s%s (%i)\n",
+          spacer,
+          ide_symbol_node_get_name (IDE_SYMBOL_NODE (node)),
+          depth);
+}
+
+static IdeXmlSymbolNode *
+ide_xml_service_walk_tree (IdeXmlTreeBuilder  *self,
+                           XmlReader          *reader)
+{
+  IdeXmlStack *stack;
+  IdeXmlSymbolNode *root_node;
+  IdeXmlSymbolNode *parent_node;
+  IdeXmlSymbolNode *current_node;
+  IdeXmlSymbolNode *previous_node = NULL;
+  xmlReaderTypes type;
+  gint depth = 0;
+  gint current_depth = 0;
+  gboolean is_empty;
+
+  g_assert (IDE_IS_XML_TREE_BUILDER (self));
+  g_assert (XML_IS_READER (reader));
+
+  stack = stack_new ();
+
+  parent_node = root_node = ide_xml_symbol_node_new ("root", IDE_SYMBOL_NONE,
+                                                     NULL, 0, 0);
+  stack_push (stack, parent_node);
+
+  while (xml_reader_read (reader))
+    {
+      type = xml_reader_get_node_type (reader);
+      if ( type == XML_READER_TYPE_ELEMENT)
+        {
+          current_node = create_node_from_reader (reader);
+          depth = xml_reader_get_depth (reader);
+          is_empty = xml_reader_is_empty_element (reader);
+
+          /* TODO: take end elements into account and use:
+           * || ABS (depth - current_depth) > 1
+           */
+          if (depth < 0)
+            {
+              g_warning ("Wrong xml element depth, current:%i new:%i\n", current_depth, depth);
+              break;
+            }
+
+          if (depth > current_depth)
+            {
+              ++current_depth;
+              stack_push (stack, parent_node);
+
+              g_assert (previous_node != NULL);
+              parent_node = previous_node;
+              ide_xml_symbol_node_take_child (parent_node, current_node);
+            }
+          else if (depth < current_depth)
+            {
+              --current_depth;
+              parent_node = stack_pop (stack);
+              if (parent_node == NULL)
+                {
+                  g_warning ("Xml nodes stack empty\n");
+                  break;
+                }
+
+              g_assert (parent_node != NULL);
+              ide_xml_symbol_node_take_child (parent_node, current_node);
+            }
+          else
+            {
+              ide_xml_symbol_node_take_child (parent_node, current_node);
+            }
+
+          previous_node = current_node;
+          print_node (current_node, depth);
+        }
+    }
+
+  printf ("stack size:%li\n", stack_get_size (stack));
+
+  stack_destroy (stack);
+
+  return root_node;
+}
+
+static GBytes *
+ide_xml_service_get_file_content (IdeXmlTreeBuilder *self,
+                                  GFile             *file)
+{
+  IdeContext *context;
+  IdeBufferManager *manager;
+  IdeBuffer *buffer;
+  GBytes *content = NULL;
+
+  g_assert (IDE_IS_XML_TREE_BUILDER (self));
+  g_assert (G_IS_FILE (file));
+
+  context = ide_object_get_context (IDE_OBJECT (self));
+  manager = ide_context_get_buffer_manager (context);
+
+  printf ("found buffer:%p\n", ide_buffer_manager_find_buffer (manager, file));
+
+  if (NULL != (buffer = ide_buffer_manager_find_buffer (manager, file)))
+    content = ide_buffer_get_content (buffer);
+
+  return content;
+}
+
+static void
+build_tree_worker (GTask        *task,
+                   gpointer      source_object,
+                   gpointer      task_data,
+                   GCancellable *cancellable)
+{
+  IdeXmlTreeBuilder *self = (IdeXmlTreeBuilder *)source_object;
+  BuilderState *state = (BuilderState *)task_data;
+  IdeXmlSymbolNode *root_node;
+  const gchar *data;
+  g_autofree gchar *uri;
+  gsize size;
+
+  g_assert (IDE_IS_XML_TREE_BUILDER (self));
+  g_assert (G_IS_TASK (task));
+  g_assert (state != NULL);
+  g_assert (!cancellable || G_IS_CANCELLABLE (cancellable));
+
+  printf ("build_tree_worker thread\n");
+
+  data = g_bytes_get_data (state->content, &size);
+  uri = g_file_get_uri (state->file);
+  xml_reader_load_from_data (state->reader, data, size, uri, NULL);
+
+  if (NULL == (root_node = ide_xml_service_walk_tree (self, state->reader)))
+    {
+      g_task_return_new_error (task,
+                               G_IO_ERROR,
+                               G_IO_ERROR_FAILED,
+                               _("Failed to create xml tree."));
+      return;
+    }
+
+  g_task_return_pointer (task, root_node, g_object_unref);
+}
+
+void
+ide_xml_tree_builder_build_tree_async (IdeXmlTreeBuilder   *self,
+                                       GFile               *file,
+                                       GCancellable        *cancellable,
+                                       GAsyncReadyCallback  callback,
+                                       gpointer             user_data)
+{
+  g_autoptr(GTask) task = NULL;
+  BuilderState *state;
+  GBytes *content = NULL;
+
+  g_return_if_fail (IDE_IS_XML_TREE_BUILDER (self));
+  g_return_if_fail (G_IS_FILE (file));
+  g_return_if_fail (!cancellable || G_IS_CANCELLABLE (cancellable));
+
+  task = g_task_new (self, cancellable, callback, user_data);
+  g_task_set_source_tag (task, ide_xml_tree_builder_build_tree_async);
+
+  if (NULL == (content = ide_xml_service_get_file_content (self, file)))
+    {
+      g_task_return_new_error (task,
+                               G_IO_ERROR,
+                               G_IO_ERROR_FAILED,
+                               _("Failed to create xml tree."));
+      return;
+    }
+
+  state = g_slice_new0 (BuilderState);
+  state->reader = xml_reader_new ();
+  state->content = g_bytes_ref (content);
+  state->file = g_object_ref (file);
+
+  g_task_set_task_data (task, state, (GDestroyNotify)builder_state_free);
+  g_task_run_in_thread (task, build_tree_worker);
+}
+
+IdeXmlSymbolNode *
+ide_xml_tree_builder_build_tree_finish (IdeXmlTreeBuilder  *self,
+                                        GAsyncResult       *result,
+                                        GError            **error)
+{
+  GTask *task = (GTask *)result;
+
+  g_return_val_if_fail (IDE_IS_XML_TREE_BUILDER (self), NULL);
+  g_return_val_if_fail (G_IS_TASK (task), NULL);
+
+  return g_task_propagate_pointer (task, error);
+}
+
+IdeXmlTreeBuilder *
+ide_xml_tree_builder_new (void)
+{
+  return g_object_new (IDE_TYPE_XML_TREE_BUILDER, NULL);
+}
+
+static void
+ide_xml_tree_builder_finalize (GObject *object)
+{
+  G_OBJECT_CLASS (ide_xml_tree_builder_parent_class)->finalize (object);
+}
+
+static void
+ide_xml_tree_builder_class_init (IdeXmlTreeBuilderClass *klass)
+{
+  GObjectClass *object_class = G_OBJECT_CLASS (klass);
+
+  object_class->finalize = ide_xml_tree_builder_finalize;
+}
+
+static void
+ide_xml_tree_builder_init (IdeXmlTreeBuilder *self)
+{
+}
diff --git a/plugins/xml-pack/ide-xml-tree-builder.h b/plugins/xml-pack/ide-xml-tree-builder.h
new file mode 100644
index 0000000..9043103
--- /dev/null
+++ b/plugins/xml-pack/ide-xml-tree-builder.h
@@ -0,0 +1,46 @@
+/* ide-xml-tree-builder.h
+ *
+ * Copyright (C) 2017 Sebastien Lafargue <slafargue gnome org>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef IDE_XML_TREE_BUILDER_H
+#define IDE_XML_TREE_BUILDER_H
+
+#include "ide-xml-symbol-node.h"
+
+#include <glib-object.h>
+#include <ide.h>
+
+G_BEGIN_DECLS
+
+#define IDE_TYPE_XML_TREE_BUILDER (ide_xml_tree_builder_get_type())
+
+G_DECLARE_FINAL_TYPE (IdeXmlTreeBuilder, ide_xml_tree_builder, IDE, XML_TREE_BUILDER, IdeObject)
+
+IdeXmlTreeBuilder   *ide_xml_tree_builder_new                    (void);
+void                 ide_xml_tree_builder_build_tree_async       (IdeXmlTreeBuilder     *self,
+                                                                  GFile                 *file,
+                                                                  GCancellable          *cancellable,
+                                                                  GAsyncReadyCallback    callback,
+                                                                  gpointer               user_data);
+IdeXmlSymbolNode    *ide_xml_tree_builder_build_tree_finish      (IdeXmlTreeBuilder     *self,
+                                                                  GAsyncResult          *result,
+                                                                  GError               **error);
+
+G_END_DECLS
+
+#endif /* IDE_XML_TREE_BUILDER_H */
+


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]