Share similar XSLTs within session.
authorAdam Dickmeiss <adam@indexdata.dk>
Wed, 7 Oct 2009 13:37:20 +0000 (15:37 +0200)
committerAdam Dickmeiss <adam@indexdata.dk>
Wed, 7 Oct 2009 13:37:20 +0000 (15:37 +0200)
XSLTs + MARC maps are cached within a session so we don't re-parse
them over and over again. Even for a session with a single search
there's much to be gained because many targets use the same
transformation.

src/Makefile.am
src/logic.c
src/normalize_cache.c [new file with mode: 0644]
src/normalize_cache.h [new file with mode: 0644]
src/normalize_record.c
src/normalize_record.h
src/pazpar2.h
src/pazpar2_config.h
win/makefile

index 6c846ea..4b1e445 100644 (file)
@@ -27,7 +27,8 @@ libpazpar2_a_SOURCES = pazpar2_config.c pazpar2_config.h eventl.c eventl.h \
        charsets.c charsets.h \
        client.c client.h connection.c connection.h host.h parameters.h \
        dirent.c direntz.h marcmap.c marcmap.h marchash.c marchash.h \
-       jenkins_hash.c jenkins_hash.h normalize_record.c normalize_record.h
+       jenkins_hash.c jenkins_hash.h normalize_record.c normalize_record.h \
+       normalize_cache.c normalize_cache.h
 
 pazpar2_SOURCES = pazpar2.c
 pazpar2_LDADD = libpazpar2.a $(YAZLIB)
index 68ee9c5..f9cd08f 100644 (file)
@@ -320,7 +320,8 @@ static int prepare_map(struct session *se, struct session_database *sdb)
                 yaz_log(YLOG_WARN, "No pz:requestsyntax for auto stylesheet");
             }
         }
-        sdb->map = normalize_record_create(se->service, s);
+        sdb->map = normalize_cache_get(se->normalize_cache,
+                                       se->service, s);
         if (!sdb->map)
             return -1;
     }
@@ -555,7 +556,6 @@ static void session_init_databases_fun(void *context, struct database *db)
 // Doesn't free memory associated with sdb -- nmem takes care of that
 static void session_database_destroy(struct session_database *sdb)
 {
-    normalize_record_destroy(sdb->map);
     sdb->map = 0;
 }
 
@@ -627,7 +627,6 @@ void session_apply_setting(struct session *se, char *dbname, char *setting,
     case PZ_XSLT:
         if (sdb->map)
         {
-            normalize_record_destroy(sdb->map);
             sdb->map = 0;
         }
         break;
@@ -642,6 +641,7 @@ void destroy_session(struct session *s)
         client_destroy(s->clients);
     for (sdb = s->databases; sdb; sdb = sdb->next)
         session_database_destroy(sdb);
+    normalize_cache_destroy(s->normalize_cache);
     nmem_destroy(s->nmem);
     service_destroy(s->service);
     wrbuf_destroy(s->wrbuf);
@@ -673,6 +673,8 @@ struct session *new_session(NMEM nmem, struct conf_service *service)
         session->watchlist[i].data = 0;
         session->watchlist[i].fun = 0;
     }
+    session->normalize_cache = normalize_cache_create();
+
     return session;
 }
 
diff --git a/src/normalize_cache.c b/src/normalize_cache.c
new file mode 100644 (file)
index 0000000..7b0baea
--- /dev/null
@@ -0,0 +1,94 @@
+/* This file is part of Pazpar2.
+   Copyright (C) 2006-2009 Index Data
+
+Pazpar2 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 2, or (at your option) any later
+version.
+
+Pazpar2 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, write to the Free Software
+Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+
+*/
+
+#include <string.h>
+
+#include <yaz/yaz-util.h>
+#include <yaz/nmem.h>
+
+#if HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include "normalize_cache.h"
+
+#include "pazpar2_config.h"
+
+struct cached_item {
+    char *spec;
+    struct cached_item *next;
+    normalize_record_t nt;
+};
+
+struct normalize_cache_s {
+    struct cached_item *items;
+    NMEM nmem;
+};
+
+normalize_cache_t normalize_cache_create(void)
+{
+    NMEM nmem = nmem_create();
+    normalize_cache_t nc = nmem_malloc(nmem, sizeof(*nc));
+    nc->nmem = nmem;
+    nc->items = 0;
+    return nc;
+}
+
+normalize_record_t normalize_cache_get(normalize_cache_t nc,
+                                       struct conf_service *service,
+                                       const char *spec)
+{
+    normalize_record_t nt;
+    struct cached_item *ci = nc->items;
+    for (; ci; ci = ci->next)
+        if (!strcmp(spec, ci->spec))
+            return ci->nt;
+
+    nt = normalize_record_create(service, spec);
+    if (nt)
+    {
+        ci = nmem_malloc(nc->nmem, sizeof(*ci));
+        ci->next = nc->items;
+        nc->items = ci;
+        ci->nt = nt;
+        ci->spec = nmem_strdup(nc->nmem, spec);
+    }
+    return nt;
+}
+
+void normalize_cache_destroy(normalize_cache_t nc)
+{
+    if (nc)
+    {
+        struct cached_item *ci = nc->items;
+        for (; ci; ci = ci->next)
+            normalize_record_destroy(ci->nt);
+        nmem_destroy(nc->nmem);
+    }
+}
+
+/*
+ * Local variables:
+ * c-basic-offset: 4
+ * c-file-style: "Stroustrup"
+ * indent-tabs-mode: nil
+ * End:
+ * vim: shiftwidth=4 tabstop=8 expandtab
+ */
+
diff --git a/src/normalize_cache.h b/src/normalize_cache.h
new file mode 100644 (file)
index 0000000..a33b0a0
--- /dev/null
@@ -0,0 +1,43 @@
+/* This file is part of Pazpar2.
+   Copyright (C) 2006-2009 Index Data
+
+Pazpar2 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 2, or (at your option) any later
+version.
+
+Pazpar2 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, write to the Free Software
+Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+
+*/
+
+#ifndef NORMALIZE_CACHE_H
+#define NORMALIZE_CACHE_H
+
+#include "normalize_record.h"
+typedef struct normalize_cache_s *normalize_cache_t;
+
+normalize_cache_t normalize_cache_create(void);
+
+normalize_record_t normalize_cache_get(normalize_cache_t nc,
+                                       struct conf_service *service,
+                                       const char *spec);
+void normalize_cache_destroy(normalize_cache_t nc);
+
+#endif
+
+/*
+ * Local variables:
+ * c-basic-offset: 4
+ * c-file-style: "Stroustrup"
+ * indent-tabs-mode: nil
+ * End:
+ * vim: shiftwidth=4 tabstop=8 expandtab
+ */
+
index c7706e5..c33cd2e 100644 (file)
@@ -42,31 +42,20 @@ struct normalize_step {
 
 struct normalize_record_s {
     struct normalize_step *steps;
-    char *spec;
     NMEM nmem;
 };
 
-const char *normalize_record_get_spec(normalize_record_t nt)
-{
-    if (nt)
-        return nt->spec;
-    return 0;
-}
-
 normalize_record_t normalize_record_create(struct conf_service *service,
                                            const char *spec)
 {
-    normalize_record_t nt = xmalloc(sizeof(*nt));
-    struct normalize_step **m;
+    NMEM nmem = nmem_create();
+    normalize_record_t nt = nmem_malloc(nmem, sizeof(*nt));
+    struct normalize_step **m = &nt->steps;
     int i, num;
     int no_errors = 0;
     char **stylesheets;
 
-    nt->nmem = nmem_create();
-
-    nt->spec = nmem_strdup(nt->nmem, spec);
-
-    m = &nt->steps;
+    nt->nmem = nmem;
 
     nmem_strsplit(nt->nmem, ",", spec, &stylesheets, &num);
     for (i = 0; i < num; i++)
@@ -128,8 +117,6 @@ void normalize_record_destroy(normalize_record_t nt)
                 xsltFreeStylesheet(m->stylesheet);
         }
         nmem_destroy(nt->nmem);
-
-        xfree(nt);
     }
 }
 
index 25f803f..2857f8d 100644 (file)
@@ -26,11 +26,10 @@ struct conf_service;
 normalize_record_t normalize_record_create(struct conf_service *service,
                                            const char *spec);
 
-const char *normalize_record_get_spec(normalize_record_t nt);
 void normalize_record_destroy(normalize_record_t nt);
 
 int normalize_record_transform(normalize_record_t nt, xmlDoc **doc,
-    const char **parms);
+                               const char **parms);
 
 #endif
 
index e70101c..14815cd 100644 (file)
@@ -131,6 +131,7 @@ struct session {
     int total_merged;
     int number_of_warnings_unknown_elements;
     int number_of_warnings_unknown_metadata;
+    normalize_cache_t normalize_cache;
 };
 
 struct statistics {
index 1fd5d55..acaba34 100644 (file)
@@ -20,7 +20,7 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 #ifndef PAZPAR2_CONFIG_H
 #define PAZPAR2_CONFIG_H
 
-#include "normalize_record.h"
+#include "normalize_cache.h"
 
 #include <yaz/nmem.h>
 #include "charsets.h"
index 8d3478d..5a7fd67 100644 (file)
@@ -200,6 +200,7 @@ PAZPAR2_OBJS = \
    "$(OBJDIR)\marcmap.obj" \
    "$(OBJDIR)\marchash.obj" \
    "$(OBJDIR)\normalize_record.obj" \
+   "$(OBJDIR)\normalize_cache.obj" \
    "$(OBJDIR)\connection.obj"