[Groonga-commit] groonga/groonga at cfa6fa4 [master] Add experimental new command API

Back to archive index

Kouhei Sutou null+****@clear*****
Mon Jan 5 00:40:31 JST 2015


Kouhei Sutou	2015-01-05 00:40:31 +0900 (Mon, 05 Jan 2015)

  New Revision: cfa6fa4b7108298af319c2fa67eada42070ee9c7
  https://github.com/groonga/groonga/commit/cfa6fa4b7108298af319c2fa67eada42070ee9c7

  Message:
    Add experimental new command API

  Added files:
    include/groonga/command.h
    lib/command.c
  Modified files:
    include/groonga/Makefile.am
    include/groonga/groonga.h
    lib/db.c
    lib/expr.c
    lib/grn_db.h
    lib/sources.am

  Modified: include/groonga/Makefile.am (+1 -0)
===================================================================
--- include/groonga/Makefile.am    2015-01-04 23:55:01 +0900 (c0a0018)
+++ include/groonga/Makefile.am    2015-01-05 00:40:31 +0900 (ffdb083)
@@ -1,5 +1,6 @@
 groonga_includedir = $(pkgincludedir)/groonga
 groonga_include_HEADERS =			\
+	command.h				\
 	expr.h					\
 	groonga.h				\
 	ii.h					\

  Added: include/groonga/command.h (+79 -0) 100644
===================================================================
--- /dev/null
+++ include/groonga/command.h    2015-01-05 00:40:31 +0900 (101956a)
@@ -0,0 +1,79 @@
+/* -*- c-basic-offset: 2 -*- */
+/*
+  Copyright(C) 2015 Brazil
+
+  This library is free software; you can redistribute it and/or
+  modify it under the terms of the GNU Lesser General Public
+  License version 2.1 as published by the Free Software Foundation.
+
+  This library 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
+  Lesser General Public License for more details.
+
+  You should have received a copy of the GNU Lesser General Public
+  License along with this library; if not, write to the Free Software
+  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
+*/
+#ifndef GROONGA_COMMAND_H
+#define GROONGA_COMMAND_H
+
+#include <groonga/plugin.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif  /* __cplusplus */
+
+typedef struct _grn_command_input grn_command_input;
+
+GRN_PLUGIN_EXPORT grn_command_input *grn_command_input_open(grn_ctx *ctx,
+                                                            grn_obj *command);
+GRN_PLUGIN_EXPORT grn_rc grn_command_input_close(grn_ctx *ctx,
+                                                 grn_command_input *input);
+
+GRN_PLUGIN_EXPORT grn_obj *grn_command_input_add(grn_ctx *ctx,
+                                                 grn_command_input *input,
+                                                 const char *name,
+                                                 int name_size,
+                                                 grn_bool *added);
+GRN_PLUGIN_EXPORT grn_obj *grn_command_input_get(grn_ctx *ctx,
+                                                 grn_command_input *input,
+                                                 const char *name,
+                                                 int name_size);
+GRN_PLUGIN_EXPORT grn_obj *grn_command_input_at(grn_ctx *ctx,
+                                                grn_command_input *input,
+                                                unsigned int offset);
+
+typedef void grn_command_run_func(grn_ctx *ctx,
+                                  grn_obj *command,
+                                  grn_command_input *input,
+                                  void *user_data);
+
+/*
+  grn_command_register() registers a command to the database which is
+  associated with `ctx'. `command_name' and `command_name_size'
+  specify the command name. Alphabetic letters ('A'-'Z' and 'a'-'z'),
+  digits ('0'-'9') and an underscore ('_') are capable characters.
+
+  `run' is called for running the command.
+
+  grn_command_register() returns GRN_SUCCESS on success, an error
+  code on failure.
+ */
+GRN_PLUGIN_EXPORT grn_rc grn_command_register(grn_ctx *ctx,
+                                              const char *command_name,
+                                              int command_name_size,
+                                              grn_command_run_func *run,
+                                              grn_expr_var *vars,
+                                              unsigned int n_vars,
+                                              void *user_data);
+
+GRN_PLUGIN_EXPORT grn_rc grn_command_run(grn_ctx *ctx,
+                                         grn_obj *command,
+                                         grn_command_input *input);
+
+#ifdef __cplusplus
+}  /* extern "C" */
+#endif  /* __cplusplus */
+
+#endif  /* GROONGA_COMMAND_H */

  Modified: include/groonga/groonga.h (+1 -0)
===================================================================
--- include/groonga/groonga.h    2015-01-04 23:55:01 +0900 (523cd86)
+++ include/groonga/groonga.h    2015-01-05 00:40:31 +0900 (cdab232)
@@ -119,6 +119,7 @@ typedef enum {
   GRN_UNSUPPORTED_COMMAND_VERSION = -71,
   GRN_NORMALIZER_ERROR = -72,
   GRN_TOKEN_FILTER_ERROR = -73,
+  GRN_COMMAND_ERROR = -74,
 } grn_rc;
 
 GRN_API grn_rc grn_init(void);

  Added: lib/command.c (+194 -0) 100644
===================================================================
--- /dev/null
+++ lib/command.c    2015-01-05 00:40:31 +0900 (b0f7522)
@@ -0,0 +1,194 @@
+/* -*- c-basic-offset: 2 -*- */
+/*
+  Copyright(C) 2015 Brazil
+
+  This library is free software; you can redistribute it and/or
+  modify it under the terms of the GNU Lesser General Public
+  License version 2.1 as published by the Free Software Foundation.
+
+  This library 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
+  Lesser General Public License for more details.
+
+  You should have received a copy of the GNU Lesser General Public
+  License along with this library; if not, write to the Free Software
+  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
+*/
+
+#include <string.h>
+
+#include "grn.h"
+#include "grn_db.h"
+#include "grn_ctx_impl.h"
+
+struct _grn_command_input {
+  grn_obj *command;
+  grn_hash *arguments;
+};
+
+grn_command_input *
+grn_command_input_open(grn_ctx *ctx, grn_obj *command)
+{
+  grn_command_input *input = NULL;
+
+  GRN_API_ENTER;
+  input = GRN_MALLOC(sizeof(grn_command_input));
+  if (!input) {
+    ERR(GRN_NO_MEMORY_AVAILABLE,
+        "[command-input] failed to allocate grn_command_input");
+    goto exit;
+  }
+
+  input->command = command;
+  /* TODO: Allocate by self. */
+  {
+    uint32_t n;
+    input->arguments = grn_expr_get_vars(ctx, input->command, &n);
+  }
+
+exit :
+  GRN_API_RETURN(input);
+}
+
+grn_rc
+grn_command_input_close(grn_ctx *ctx, grn_command_input *input)
+{
+  GRN_API_ENTER;
+
+  /* TODO: Free input->arguments by self. */
+  grn_expr_clear_vars(ctx, input->command);
+  GRN_FREE(input);
+
+  GRN_API_RETURN(ctx->rc);
+}
+
+grn_obj *
+grn_command_input_add(grn_ctx *ctx,
+                      grn_command_input *input,
+                      const char *name,
+                      int name_size,
+                      grn_bool *added)
+{
+  grn_obj *argument = NULL;
+  /* TODO: Use grn_bool */
+  int internal_added = GRN_FALSE;
+
+  GRN_API_ENTER;
+
+  if (name_size == -1) {
+    name_size = strlen(name);
+  }
+  if (input->arguments) {
+    grn_hash_add(ctx, input->arguments, name, name_size, (void **)&argument,
+                 &internal_added);
+    if (internal_added) {
+      GRN_TEXT_INIT(argument, 0);
+    }
+  }
+  if (added) {
+    *added = internal_added;
+  }
+
+  GRN_API_RETURN(argument);
+}
+
+grn_obj *
+grn_command_input_get(grn_ctx *ctx,
+                      grn_command_input *input,
+                      const char *name,
+                      int name_size)
+{
+  grn_obj *argument = NULL;
+
+  GRN_API_ENTER;
+
+  if (name_size == -1) {
+    name_size = strlen(name);
+  }
+  if (input->arguments) {
+    grn_hash_get(ctx, input->arguments, name, name_size, (void **)&argument);
+  }
+
+  GRN_API_RETURN(argument);
+}
+
+grn_obj *
+grn_command_input_at(grn_ctx *ctx,
+                     grn_command_input *input,
+                     unsigned int offset)
+{
+  grn_obj *argument = NULL;
+
+  GRN_API_ENTER;
+  if (input->arguments) {
+    uint32_t size;
+    argument = (grn_obj *)grn_hash_get_value_(ctx, input->arguments,
+                                              offset + 1, &size);
+  }
+  GRN_API_RETURN(argument);
+}
+
+grn_rc
+grn_command_register(grn_ctx *ctx,
+                     const char *command_name,
+                     int command_name_size,
+                     grn_command_run_func *run,
+                     grn_expr_var *vars,
+                     unsigned int n_vars,
+                     void *user_data)
+{
+  GRN_API_ENTER;
+
+  if (command_name_size == -1) {
+    command_name_size = strlen(command_name);
+  }
+
+  {
+    grn_obj *command_object;
+    command_object = grn_proc_create(ctx,
+                                     command_name,
+                                     command_name_size,
+                                     GRN_PROC_COMMAND,
+                                     NULL, NULL, NULL, n_vars, vars);
+    if (!command_object) {
+      GRN_PLUGIN_ERROR(ctx, GRN_COMMAND_ERROR,
+                       "[command][%.*s] failed to grn_proc_create()",
+                       command_name_size, command_name);
+      GRN_API_RETURN(ctx->rc);
+    }
+
+    {
+      grn_proc *command = (grn_proc *)command_object;
+      command->callbacks.command.run = run;
+      command->user_data = user_data;
+    }
+  }
+
+  GRN_API_RETURN(GRN_SUCCESS);
+}
+
+grn_rc
+grn_command_run(grn_ctx *ctx,
+                grn_obj *command,
+                grn_command_input *input)
+{
+  grn_proc *proc;
+
+  GRN_API_ENTER;
+
+  proc = (grn_proc *)command;
+  if (proc->callbacks.command.run) {
+    proc->callbacks.command.run(ctx, command, input, proc->user_data);
+  } else {
+    /* TODO: REMOVE ME. For backward compatibility. */
+    uint32_t stack_curr = ctx->impl->stack_curr;
+    grn_proc_call(ctx, command, 0, command);
+    if (ctx->impl->stack_curr > stack_curr) {
+      grn_ctx_pop(ctx);
+    }
+  }
+
+  GRN_API_RETURN(ctx->rc);
+}
+

  Modified: lib/db.c (+1 -0)
===================================================================
--- lib/db.c    2015-01-04 23:55:01 +0900 (1be1494)
+++ lib/db.c    2015-01-05 00:40:31 +0900 (28b8cbf)
@@ -617,6 +617,7 @@ grn_proc_create(grn_ctx *ctx, const char *name, int name_size, grn_proc_type typ
     res->funcs[PROC_NEXT] = next;
     res->funcs[PROC_FIN] = fin;
     res->selector = NULL;
+    memset(&(res->callbacks), 0, sizeof(res->callbacks));
     GRN_TEXT_INIT(&res->name_buf, 0);
     res->vars = NULL;
     res->nvars = 0;

  Modified: lib/expr.c (+10 -1)
===================================================================
--- lib/expr.c    2015-01-04 23:55:01 +0900 (c14818e)
+++ lib/expr.c    2015-01-05 00:40:31 +0900 (b4e0f1e)
@@ -2955,7 +2955,16 @@ grn_expr_exec(grn_ctx *ctx, grn_obj *expr, int nargs)
   uint32_t stack_curr = ctx->impl->stack_curr;
   GRN_API_ENTER;
   if (expr->header.type == GRN_PROC) {
-    grn_proc_call(ctx, expr, nargs, expr);
+    grn_proc *proc = (grn_proc *)expr;
+    if (proc->type == GRN_PROC_COMMAND) {
+      grn_command_input *input;
+      input = grn_command_input_open(ctx, expr);
+      grn_command_run(ctx, expr, input);
+      grn_command_input_close(ctx, input);
+      GRN_API_RETURN(NULL);
+    } else {
+      grn_proc_call(ctx, expr, nargs, expr);
+    }
   } else {
     grn_expr *e = (grn_expr *)expr;
     register grn_obj **s_ = ctx->impl->stack, *s0 = NULL, *s1 = NULL, **sp, *vp = e->values;

  Modified: lib/grn_db.h (+4 -0)
===================================================================
--- lib/grn_db.h    2015-01-04 23:55:01 +0900 (252ec92)
+++ lib/grn_db.h    2015-01-05 00:40:31 +0900 (67b9c23)
@@ -21,6 +21,7 @@
 #include "grn_ctx.h"
 #include "grn_store.h"
 
+#include <groonga/command.h>
 #include <groonga/token_filter.h>
 
 #ifdef __cplusplus
@@ -181,6 +182,9 @@ struct _grn_proc {
 
   union {
     struct {
+      grn_command_run_func *run;
+    } command;
+    struct {
       grn_token_filter_init_func   *init;
       grn_token_filter_filter_func *filter;
       grn_token_filter_fin_func    *fin;

  Modified: lib/sources.am (+1 -0)
===================================================================
--- lib/sources.am    2015-01-04 23:55:01 +0900 (0be9ded)
+++ lib/sources.am    2015-01-05 00:40:31 +0900 (4fa37c9)
@@ -1,6 +1,7 @@
 libgroonga_la_SOURCES =				\
 	com.c					\
 	grn_com.h				\
+	command.c				\
 	ctx.c					\
 	grn_ctx.h				\
 	grn_ctx_impl.h				\
-------------- next part --------------
HTML����������������������������...
Download 



More information about the Groonga-commit mailing list
Back to archive index