Merge branch 'master' into paz-927
authorAdam Dickmeiss <adam@indexdata.dk>
Fri, 5 Sep 2014 11:52:51 +0000 (13:52 +0200)
committerAdam Dickmeiss <adam@indexdata.dk>
Fri, 5 Sep 2014 11:52:51 +0000 (13:52 +0200)
39 files changed:
IDMETA
NEWS
etc/settings/testserver.xml
etc/xsl/primo-pz2.xsl
src/client.c
src/client.h
src/connection.c
src/eventl.c
src/http_command.c
src/normalize_record.c
src/pazpar2.c
src/pazpar2_config.c
src/pazpar2_config.h
src/service_xslt.c
src/session.c
src/session.h
test/test_facets_10.res
test/test_facets_19.res
test/test_facets_5.res
test/test_http_21.res
test/test_http_65.res
test/test_http_71.res
test/test_limit_limitmap_10.res
test/test_limit_limitmap_13.res
test/test_limit_limitmap_20.res
test/test_limit_limitmap_5.res
test/test_post_11.res
test/test_settings_7.res
test/test_settings_8.res
test/test_solr_14.res
test/test_solr_19.res
test/test_solr_26.res
test/test_solr_5.res
test/test_sort_5.res
test/test_termlist_block_10.res
test/test_termlist_block_13.res
test/test_termlist_block_5.res
test/test_turbomarcxml_8.res
win/makefile

diff --git a/IDMETA b/IDMETA
index 420050a..747e6ac 100644 (file)
--- a/IDMETA
+++ b/IDMETA
@@ -1,4 +1,4 @@
 DEBIAN_DIST="jessie wheezy squeeze"
 UBUNTU_DIST="trusty precise"
 CENTOS_DIST="centos5 centos6"
-VERSION=1.7.2
+VERSION=1.7.4
diff --git a/NEWS b/NEWS
index 610cba1..c2719ea 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -1,3 +1,25 @@
+--- 1.7.4 2014/09/02
+
+Log ingest failures and record failures:
+
+Clean up logging PAZ-942
+Use session lead in more places. Log hits/records/filtered for each
+target when fetching is complete. Log hit count when a search
+(response) is received. Remove some less useful log messages.
+
+Fix warning about about missing (internal) stylesheet PAZ-956
+
+Report number of filtered records in bytarget PAZ-954
+
+Cache XML documents as they appear after normalization. The key
+for the cache is database+record offset. Cache is removed if query
+is modified for search. This speeds up re-establishing a result set
+for databases where new query is same previous query.
+
+--- 1.7.3 2014/08/22
+
+poll: add assert for number of FDs; abort on poll failure
+
 --- 1.7.2 2014/08/18
 
 Fix hang for 2nd use of target with unresolved DNS PAZ-949
index 69a8c36..fdb7767 100644 (file)
@@ -3,7 +3,7 @@
   <!-- Simple test against a local test server (could be yaz-ztest) -->
 
   <set name="pz:name" value="Local Test"/>
-  <set name="pz:apdulog" value="1"/>
+  <set name="pz:apdulog" value="0"/>
 
   <!-- mapping for unqualified search -->
   <set name="pz:cclmap:term" value="u=1016 t=l,r s=al"/>
index 43a92a1..ec764a8 100644 (file)
   </xsl:template>
 
   <xsl:template match="prim:display">
+
+<!--
     <xsl:for-each select="prim:creator">
        <pz:metadata type="author">
         <xsl:value-of select="." />
       </pz:metadata>
-    </xsl:for-each>  
+    </xsl:for-each>
+-->
     <xsl:for-each select="prim:type">
       <xsl:variable name="type" select="."/>
       <pz:metadata type="medium">
   </xsl:template>
 
   <xsl:template match="prim:search">
+
+    <xsl:for-each select="prim:creatorcontrib">
+       <pz:metadata type="author">
+        <xsl:value-of select="." />
+      </pz:metadata>
+    </xsl:for-each>
+
     <xsl:for-each select="prim:description">
       <pz:metadata type="description">
        <xsl:value-of select="." />
index 8686ec7..dd4405f 100644 (file)
@@ -71,6 +71,8 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 #include "relevance.h"
 #include "incref.h"
 
+#define XDOC_CACHE_SIZE 100
+
 static YAZ_MUTEX g_mutex = 0;
 static int no_clients = 0;
 
@@ -104,7 +106,9 @@ struct client {
     Odr_int hits;
     int record_offset;
     int show_stat_no;
-    int filtered; // When using local:, this will count the number of filtered records.
+    int filtered; /* number of records ignored for local filtering */
+    int ingest_failures; /* number of records where XSLT/other failed */
+    int record_failures; /* number of records where ZOOM reported error */
     int maxrecs;
     int startrecs;
     int diagnostic;
@@ -121,6 +125,7 @@ struct client {
     int same_search;
     char *sort_strategy;
     char *sort_criteria;
+    xmlDoc **xdoc;
 };
 
 struct suggestions {
@@ -192,6 +197,50 @@ void client_set_state(struct client *cl, enum client_state st)
     }
 }
 
+static void client_init_xdoc(struct client *cl)
+{
+    int i;
+
+    cl->xdoc = xmalloc(sizeof(*cl->xdoc) * XDOC_CACHE_SIZE);
+    for (i = 0; i < XDOC_CACHE_SIZE; i++)
+        cl->xdoc[i] = 0;
+}
+
+static void client_destroy_xdoc(struct client *cl)
+{
+    int i;
+
+    assert(cl->xdoc);
+    for (i = 0; i < XDOC_CACHE_SIZE; i++)
+        if (cl->xdoc[i])
+            xmlFreeDoc(cl->xdoc[i]);
+    xfree(cl->xdoc);
+}
+
+xmlDoc *client_get_xdoc(struct client *cl, int record_no)
+{
+    assert(cl->xdoc);
+    if (record_no >= 0 && record_no < XDOC_CACHE_SIZE)
+        return cl->xdoc[record_no];
+    return 0;
+}
+
+void client_store_xdoc(struct client *cl, int record_no, xmlDoc *xdoc)
+{
+    assert(cl->xdoc);
+    if (record_no >= 0 && record_no < XDOC_CACHE_SIZE)
+    {
+        if (cl->xdoc[record_no])
+            xmlFreeDoc(cl->xdoc[record_no]);
+        cl->xdoc[record_no] = xdoc;
+    }
+    else
+    {
+        xmlFreeDoc(xdoc);
+    }
+}
+
+
 static void client_show_raw_error(struct client *cl, const char *addinfo);
 
 struct connection *client_get_connection(struct client *cl)
@@ -523,23 +572,24 @@ void client_search_response(struct client *cl)
     struct connection *co = cl->connection;
     ZOOM_connection link = connection_get_link(co);
     ZOOM_resultset resultset = cl->resultset;
+    struct session *se = client_get_session(cl);
 
     const char *error, *addinfo = 0;
 
     if (ZOOM_connection_error(link, &error, &addinfo))
     {
         cl->hits = 0;
+        session_log(se, YLOG_WARN, "%s: Error %s (%s)",
+                    client_get_id(cl), error, addinfo);
         client_set_state(cl, Client_Error);
-        yaz_log(YLOG_WARN, "Search error %s (%s): %s",
-                error, addinfo, client_get_id(cl));
     }
     else
     {
         client_report_facets(cl, resultset);
         cl->record_offset = cl->startrecs;
         cl->hits = ZOOM_resultset_size(resultset);
-        yaz_log(YLOG_DEBUG, "client_search_response: hits " ODR_INT_PRINTF,
-                cl->hits);
+        session_log(se, YLOG_LOG, "%s: hits: " ODR_INT_PRINTF,
+                    client_get_id(cl), cl->hits);
         if (cl->suggestions)
             client_suggestions_destroy(cl);
         cl->suggestions =
@@ -571,16 +621,38 @@ static void client_record_ingest(struct client *cl)
     ZOOM_record rec = 0;
     ZOOM_resultset resultset = cl->resultset;
     struct session *se = client_get_session(cl);
+    xmlDoc *xdoc;
+    int offset = cl->record_offset + 1; /* 0 versus 1 numbered offsets */
 
-    if ((rec = ZOOM_resultset_record_immediate(resultset, cl->record_offset)))
+    xdoc = client_get_xdoc(cl, offset);
+    if (xdoc)
+    {
+        if (cl->session)
+        {
+            NMEM nmem = nmem_create();
+            int rc = ingest_xml_record(cl, xdoc, offset, nmem, 1);
+            if (rc == -1)
+            {
+                session_log(se, YLOG_WARN,
+                            "%s: #%d: failed to ingest xdoc",
+                            client_get_id(cl), offset);
+                cl->ingest_failures++;
+            }
+            else if (rc == -2)
+                cl->filtered++;
+            nmem_destroy(nmem);
+        }
+    }
+    else if ((rec = ZOOM_resultset_record_immediate(resultset,
+                                                    cl->record_offset)))
     {
-        int offset = ++cl->record_offset;
         if (cl->session == 0)
             ;  /* no operation */
         else if (ZOOM_record_error(rec, &msg, &addinfo, 0))
         {
             session_log(se, YLOG_WARN, "Record error %s (%s): %s #%d",
                         msg, addinfo, client_get_id(cl), offset);
+            cl->record_failures++;
         }
         else
         {
@@ -596,30 +668,32 @@ static void client_record_ingest(struct client *cl)
             if (!xmlrec)
             {
                 const char *rec_syn =  ZOOM_record_get(rec, "syntax", NULL);
-                session_log(se, YLOG_WARN, "ZOOM_record_get failed from %s #%d",
+                session_log(se, YLOG_WARN, "%s: #%d: ZOOM_record_get failed",
                             client_get_id(cl), offset);
                 session_log(se, YLOG_LOG, "pz:nativesyntax=%s . "
                             "ZOOM record type=%s . Actual record syntax=%s",
                             s ? s : "null", type,
                             rec_syn ? rec_syn : "null");
+                cl->ingest_failures++;
             }
             else
             {
                 /* OK = 0, -1 = failure, -2 = Filtered */
-                int rc = ingest_record(cl, xmlrec, cl->record_offset, nmem);
+                int rc = ingest_record(cl, xmlrec, offset, nmem);
                 if (rc == -1)
                 {
                     const char *rec_syn =  ZOOM_record_get(rec, "syntax", NULL);
                     session_log(se, YLOG_WARN,
-                                "Failed to ingest record from %s #%d",
+                                "%s: #%d: failed to ingest record",
                                 client_get_id(cl), offset);
                     session_log(se, YLOG_LOG, "pz:nativesyntax=%s . "
                                 "ZOOM record type=%s . Actual record syntax=%s",
                                 s ? s : "null", type,
                                 rec_syn ? rec_syn : "null");
+                    cl->ingest_failures++;
                 }
-                if (rc == -2)
-                    cl->filtered += 1;
+                else if (rc == -2)
+                    cl->filtered++;
             }
             nmem_destroy(nmem);
         }
@@ -627,8 +701,9 @@ static void client_record_ingest(struct client *cl)
     else
     {
         session_log(se, YLOG_WARN, "Got NULL record from %s #%d",
-                    client_get_id(cl), cl->record_offset);
+                    client_get_id(cl), offset);
     }
+    cl->record_offset++;
 }
 
 void client_record_response(struct client *cl, int *got_records)
@@ -640,9 +715,10 @@ void client_record_response(struct client *cl, int *got_records)
 
     if (ZOOM_connection_error(link, &error, &addinfo))
     {
+        struct session *se = client_get_session(cl);
+        session_log(se, YLOG_WARN, "%s: Error %s (%s)",
+                    client_get_id(cl), error, addinfo);
         client_set_state(cl, Client_Error);
-        yaz_log(YLOG_WARN, "Search error %s (%s): %s",
-            error, addinfo, client_get_id(cl));
     }
     else
     {
@@ -673,7 +749,7 @@ int client_reingest(struct client *cl)
 {
     int i = cl->startrecs;
     int to = cl->record_offset;
-    cl->filtered = 0;
+    cl->record_failures = cl->ingest_failures = cl->filtered = 0;
 
     cl->record_offset = i;
     for (; i < to; i++)
@@ -867,13 +943,13 @@ int client_start_search(struct client *cl)
     /* Nothing has changed and we already have a result */
     if (cl->same_search == 1 && rc_prep_connection == 2)
     {
-        session_log(se, YLOG_LOG, "client %s resuse result", client_get_id(cl));
+        session_log(se, YLOG_LOG, "%s: reuse result", client_get_id(cl));
         client_report_facets(cl, cl->resultset);
         return client_reingest(cl);
     }
     else if (!rc_prep_connection)
     {
-        session_log(se, YLOG_LOG, "client %s postponing search: No connection",
+        session_log(se, YLOG_LOG, "%s: postponing search: No connection",
                     client_get_id(cl));
         client_set_state_nb(cl, Client_Working);
         return -1;
@@ -883,10 +959,13 @@ int client_start_search(struct client *cl)
     link = connection_get_link(co);
     assert(link);
 
-    session_log(se, YLOG_LOG, "client %s new search", client_get_id(cl));
+    session_log(se, YLOG_LOG, "%s: new search", client_get_id(cl));
 
     cl->diagnostic = 0;
-    cl->filtered = 0;
+    cl->record_failures = cl->ingest_failures = cl->filtered = 0;
+
+    client_destroy_xdoc(cl);
+    client_init_xdoc(cl);
 
     if (extra_args && *extra_args)
         ZOOM_connection_option_set(link, "extraArgs", extra_args);
@@ -940,17 +1019,16 @@ int client_start_search(struct client *cl)
     query = ZOOM_query_create();
     if (cl->cqlquery)
     {
-        yaz_log(YLOG_LOG, "Client %s: Search CQL: %s", client_get_id(cl),
-                cl->cqlquery);
+        session_log(se, YLOG_LOG, "%s: Search CQL: %s", client_get_id(cl),
+                    cl->cqlquery);
         ZOOM_query_cql(query, cl->cqlquery);
         if (*opt_sort)
             ZOOM_query_sortby(query, opt_sort);
     }
     else
     {
-        yaz_log(YLOG_LOG, "Client %s: Search PQF: %s", client_get_id(cl),
-                cl->pquery);
-
+        session_log(se, YLOG_LOG, "%s: Search PQF: %s", client_get_id(cl),
+                    cl->pquery);
         ZOOM_query_prefix(query, cl->pquery);
     }
     if (cl->sort_strategy && cl->sort_criteria) {
@@ -1001,6 +1079,7 @@ struct client *client_create(const char *id)
     cl->sort_criteria = 0;
     assert(id);
     cl->id = xstrdup(id);
+    client_init_xdoc(cl);
     client_use(1);
 
     yaz_log(YLOG_DEBUG, "client_create c=%p %s", cl, id);
@@ -1046,6 +1125,7 @@ int client_destroy(struct client *c)
             assert(!c->connection);
             facet_limits_destroy(c->facet_limits);
 
+            client_destroy_xdoc(c);
             if (c->resultset)
             {
                 ZOOM_resultset_destroy(c->resultset);
@@ -1601,16 +1681,18 @@ Odr_int client_get_approximation(struct client *cl)
     return cl->hits;
 }
 
-int client_get_num_records(struct client *cl)
+int client_get_num_records(struct client *cl, int *filtered, int *ingest,
+                           int *failed)
 {
+    if (filtered)
+        *filtered = cl->filtered;
+    if (ingest)
+        *ingest = cl->ingest_failures;
+    if (failed)
+        *failed = cl->record_failures;
     return cl->record_offset;
 }
 
-int client_get_num_records_filtered(struct client *cl)
-{
-    return cl->filtered;
-}
-
 void client_set_diagnostic(struct client *cl, int diagnostic,
                            const char *message, const char *addinfo)
 {
index bca9c46..c7f5d3a 100644 (file)
@@ -88,8 +88,8 @@ int client_parse_query(struct client *cl, const char *query,
                        facet_limits_t facet_limits, const char **error_msg);
 Odr_int client_get_hits(struct client *cl);
 Odr_int client_get_approximation(struct client *cl);
-int client_get_num_records(struct client *cl);
-int client_get_num_records_filtered(struct client *cl);
+int client_get_num_records(struct client *cl, int *filtered, int *ingest,
+                           int *failed);
 int client_get_diagnostic(struct client *cl,
                           const char **message, const char **addinfo);
 void client_set_diagnostic(struct client *cl, int diagnostic,
@@ -113,6 +113,8 @@ const char *client_get_facet_limit_local(struct client *cl,
 
 void client_update_show_stat(struct client *cl, int cmd);
 
+void client_store_xdoc(struct client *cl, int record_no, xmlDoc *xdoc);
+
 #endif
 
 /*
index 15bfc56..2c7c0c2 100644 (file)
@@ -194,8 +194,10 @@ static void non_block_events(struct connection *co)
                 int err;
                 if ((err = ZOOM_connection_error(link, &error, &addinfo)))
                 {
-                    yaz_log(YLOG_LOG, "Error %s from %s",
-                            error, client_get_id(cl));
+                    struct session *se = client_get_session(cl);
+
+                    session_log(se, YLOG_WARN, "%s: Error %s (%s)",
+                                client_get_id(cl), error, addinfo);
                     client_set_diagnostic(cl, err, error, addinfo);
                     client_set_state(cl, Client_Error);
                 }
@@ -219,7 +221,6 @@ static void non_block_events(struct connection *co)
         case ZOOM_EVENT_RECV_APDU:
             break;
         case ZOOM_EVENT_CONNECT:
-            yaz_log(YLOG_LOG, "Connected to %s", client_get_id(cl));
             co->state = Conn_Open;
             break;
         case ZOOM_EVENT_RECV_SEARCH:
index 1bcba5b..2e39b3a 100644 (file)
@@ -272,6 +272,7 @@ static int event_loop(iochan_man_t man, IOCHAN *iochans)
             if (fds[i].input_mask)
                 fds[i].fd = p->fd;
         }
+        assert(i == no_fds);
         yaz_log(man->log_level, "yaz_poll begin nofds=%d", no_fds);
         res = yaz_poll(fds, no_fds, tv_sec, 0);
         yaz_log(man->log_level, "yaz_poll returned res=%d", res);
@@ -282,7 +283,7 @@ static int event_loop(iochan_man_t man, IOCHAN *iochans)
             else
             {
                 yaz_log(YLOG_ERRNO | YLOG_WARN, "poll");
-                return 0;
+                abort();
             }
         }
         if (man->sel_fd != -1)
index 64331a4..f4cc792 100644 (file)
@@ -788,9 +788,9 @@ static void bytarget_response(struct http_channel *c, struct http_session *s,
 
         wrbuf_printf(c->wrbuf, "<records>%d</records>\n",
                      ht[i].records - ht[i].filtered);
+        wrbuf_printf(c->wrbuf, "<filtered>%d</filtered>\n", ht[i].filtered);
         if (version >= 2)
         {
-            wrbuf_printf(c->wrbuf, "<filtered>%d</filtered>\n", ht[i].filtered);
             wrbuf_printf(c->wrbuf, "<approximation>" ODR_INT_PRINTF
                          "</approximation>\n", ht[i].approximation);
         }
index ea15f46..70082fd 100644 (file)
@@ -89,17 +89,15 @@ normalize_record_t normalize_record_create(struct conf_service *service,
 
         for (i = 0; i < num; i++)
         {
-            WRBUF fname = conf_get_fname(conf, stylesheets[i]);
-
             *m = nmem_malloc(nt->nmem, sizeof(**m));
             (*m)->marcmap = NULL;
             (*m)->stylesheet1 = NULL;
-
             (*m)->stylesheet2 = service_xslt_get(service, stylesheets[i]);
             if ((*m)->stylesheet2)
                 ;
             else if (!strcmp(&stylesheets[i][strlen(stylesheets[i])-4], ".xsl"))
             {
+                WRBUF fname = conf_get_fname(conf, stylesheets[i]);
                 if (!((*m)->stylesheet1 =
                       xsltParseStylesheetFile((xmlChar *) wrbuf_cstr(fname))))
                 {
@@ -107,23 +105,24 @@ normalize_record_t normalize_record_create(struct conf_service *service,
                             stylesheets[i]);
                     no_errors++;
                 }
+                wrbuf_destroy(fname);
             }
             else if (!strcmp(&stylesheets[i][strlen(stylesheets[i])-5], ".mmap"))
             {
+                WRBUF fname = conf_get_fname(conf, stylesheets[i]);
                 if (!((*m)->marcmap = marcmap_load(wrbuf_cstr(fname), nt->nmem)))
                 {
                     yaz_log(YLOG_FATAL|YLOG_ERRNO, "Unable to load marcmap: %s",
                             stylesheets[i]);
                     no_errors++;
                 }
+                wrbuf_destroy(fname);
             }
             else
             {
                 yaz_log(YLOG_FATAL, "Cannot handle stylesheet: %s", stylesheets[i]);
                 no_errors++;
             }
-
-            wrbuf_destroy(fname);
             m = &(*m)->next;
         }
     }
index 24526d0..51b7249 100644 (file)
@@ -208,7 +208,17 @@ static int sc_main(
     }
     pazpar2_mutex_init();
 
-    config = config_create(config_fname, global_parameters.dump_records);
+    if (!test_mode)
+    {
+        yaz_log(YLOG_LOG, "Pazpar2 start " VERSION " "
+#ifdef PAZPAR2_VERSION_SHA1
+                PAZPAR2_VERSION_SHA1
+#else
+                "-"
+#endif
+            );
+    }
+    config = config_create(config_fname);
     if (!config)
         return 1;
     sc_stop_config = config;
@@ -219,13 +229,6 @@ static int sc_main(
     }
     else
     {
-        yaz_log(YLOG_LOG, "Pazpar2 start " VERSION  " "
-#ifdef PAZPAR2_VERSION_SHA1
-                PAZPAR2_VERSION_SHA1
-#else
-                "-"
-#endif
-                );
         ret = 0;
         if (daemon && !log_file_in_use)
         {
index c8ae0a8..838d322 100644 (file)
@@ -1274,7 +1274,7 @@ static int parse_config(struct conf_config *config, xmlNode *root)
     return 0;
 }
 
-struct conf_config *config_create(const char *fname, int verbose)
+struct conf_config *config_create(const char *fname)
 {
     xmlDoc *doc = xmlReadFile(fname,
                               NULL,
@@ -1327,16 +1327,13 @@ struct conf_config *config_create(const char *fname, int verbose)
     r = yaz_xml_include_simple(n, wrbuf_cstr(config->confdir));
     if (r == 0) /* OK */
     {
-        if (verbose)
-        {
-            yaz_log(YLOG_LOG, "Configuration %s after include processing",
-                    fname);
+        yaz_log(YLOG_LOG, "Configuration %s after include processing",
+                fname);
 #if LIBXML_VERSION >= 20600
-            xmlDocFormatDump(yaz_log_file(), doc, 0);
+        xmlDocFormatDump(yaz_log_file(), doc, 0);
 #else
-            xmlDocDump(yaz_log_file(), doc);
+        xmlDocDump(yaz_log_file(), doc);
 #endif
-        }
         r = parse_config(config, n);
     }
     xmlFreeDoc(doc);
index a5f4a81..ab10abd 100644 (file)
@@ -155,7 +155,7 @@ struct conf_server
     iochan_man_t iochan_man;
 };
 
-struct conf_config *config_create(const char *fname, int verbose);
+struct conf_config *config_create(const char *fname);
 void config_destroy(struct conf_config *config);
 void config_process_events(struct conf_config *config);
 void info_services(struct conf_server *server, WRBUF w);
index e654232..e126bfb 100644 (file)
@@ -30,7 +30,6 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 #include <yaz/yaz-util.h>
 #include <yaz/nmem.h>
 #include <yaz/snprintf.h>
-#include <yaz/tpath.h>
 #include <yaz/xml_include.h>
 
 #include "service_xslt.h"
index 4e15246..5d93d06 100644 (file)
@@ -57,7 +57,7 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 #include <yaz/oid_db.h>
 #include <yaz/snprintf.h>
 
-#define USE_TIMING 1
+#define USE_TIMING 0
 #if USE_TIMING
 #include <yaz/timing.h>
 #endif
@@ -1038,13 +1038,13 @@ static struct hitsbytarget *hitsbytarget_nb(struct session *se,
         WRBUF w = wrbuf_alloc();
         const char *name = session_setting_oneval(client_get_database(cl),
                                                   PZ_NAME);
-
         res[*count].id = client_get_id(cl);
         res[*count].name = *name ? name : "Unknown";
         res[*count].hits = client_get_hits(cl);
         res[*count].approximation = client_get_approximation(cl);
-        res[*count].records = client_get_num_records(cl);
-        res[*count].filtered = client_get_num_records_filtered(cl);
+        res[*count].records = client_get_num_records(cl,
+                                                     &res[*count].filtered,
+                                                     0, 0);
         res[*count].diagnostic =
             client_get_diagnostic(cl, &res[*count].message,
                                   &res[*count].addinfo);
@@ -1280,8 +1280,24 @@ int session_fetch_more(struct session *se)
             }
             else
             {
-                session_log(se, YLOG_LOG, "%s: no more to fetch",
-                            client_get_id(cl));
+                int filtered;
+                int ingest_failures;
+                int record_failures;
+                int num = client_get_num_records(
+                    cl, &filtered, &ingest_failures, &record_failures);
+
+                session_log(se, YLOG_LOG, "%s: hits=" ODR_INT_PRINTF
+                            " fetched=%d filtered=%d",
+                            client_get_id(cl),
+                            client_get_hits(cl),
+                            num, filtered);
+                if (ingest_failures || record_failures)
+                {
+                    session_log(se, YLOG_WARN, "%s:"
+                                " ingest failures=%d record failures=%d",
+                                client_get_id(cl),
+                                ingest_failures, record_failures);
+                }
             }
         }
         else
@@ -1687,9 +1703,6 @@ static int ingest_sub_record(struct client *cl, xmlDoc *xdoc, xmlNode *root,
 {
     int ret = 0;
     struct session *se = client_get_session(cl);
-    struct conf_service *service = se->service;
-
-    insert_settings_values(sdb, xdoc, root, service);
 
     if (!check_record_filter(root, sdb))
     {
@@ -1722,9 +1735,19 @@ int ingest_record(struct client *cl, const char *rec,
     struct session_database *sdb = client_get_database(cl);
     struct conf_service *service = se->service;
     xmlDoc *xdoc = normalize_record(se, sdb, service, rec, nmem);
-    int r = 0;
-    xmlNode *root;
+    int r = ingest_xml_record(cl, xdoc, record_no, nmem, 0);
+    client_store_xdoc(cl, record_no, xdoc);
+    return r;
+}
 
+int ingest_xml_record(struct client *cl, xmlDoc *xdoc,
+                      int record_no, NMEM nmem, int cached_copy)
+{
+    struct session *se = client_get_session(cl);
+    struct session_database *sdb = client_get_database(cl);
+    struct conf_service *service = se->service;
+    xmlNode *root;
+    int r = 0;
     if (!xdoc)
         return -1;
 
@@ -1781,6 +1804,8 @@ int ingest_record(struct client *cl, const char *rec,
             if (sroot->type == XML_ELEMENT_NODE &&
                 !strcmp((const char *) sroot->name, "record"))
             {
+                if (!cached_copy)
+                    insert_settings_values(sdb, xdoc, root, service);
                 r = ingest_sub_record(cl, xdoc, sroot, record_no, nmem, sdb,
                                       mk);
             }
@@ -1798,6 +1823,8 @@ int ingest_record(struct client *cl, const char *rec,
             mk->value = nmem_strdup(nmem, mergekey_norm);
             mk->next = 0;
 
+            if (!cached_copy)
+                insert_settings_values(sdb, xdoc, root, service);
             r = ingest_sub_record(cl, xdoc, root, record_no, nmem, sdb, mk);
         }
     }
@@ -1807,7 +1834,6 @@ int ingest_record(struct client *cl, const char *rec,
                     (const char *) root->name);
         r = -1;
     }
-    xmlFreeDoc(xdoc);
     return r;
 }
 
@@ -2067,8 +2093,6 @@ static int ingest_to_cluster(struct client *cl,
 
     if (check_limit_local(cl, record, record_no))
     {
-        session_log(se, YLOG_LOG, "Facet filtered out record no %d from %s",
-                    record_no, sdb->database->id);
         if (type)
             xmlFree(type);
         if (value)
index a607c77..32243de 100644 (file)
@@ -186,6 +186,8 @@ void session_apply_setting(struct session *se, char *dbname, char *setting, char
 const char *session_setting_oneval(struct session_database *db, int offset);
 
 int ingest_record(struct client *cl, const char *rec, int record_no, NMEM nmem);
+int ingest_xml_record(struct client *cl, xmlDoc *xdoc,
+                      int record_no, NMEM nmem, int cached_copy);
 void session_alert_watch(struct session *s, int what);
 void add_facet(struct session *s, const char *type, const char *value, int count);
 
index 44f1bb9..7bac2b5 100644 (file)
@@ -5,5 +5,6 @@
 <hits>4</hits>
 <diagnostic>0</diagnostic>
 <records>2</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index b91448e..1910a36 100644 (file)
@@ -5,5 +5,6 @@
 <hits>6</hits>
 <diagnostic>0</diagnostic>
 <records>2</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 8b8a807..ffc2e84 100644 (file)
@@ -5,5 +5,6 @@
 <hits>7</hits>
 <diagnostic>0</diagnostic>
 <records>7</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index a156563..48290d2 100644 (file)
@@ -5,5 +5,6 @@
 <hits>0</hits>
 <diagnostic>0</diagnostic>
 <records>0</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index efe653d..bd79080 100644 (file)
@@ -5,5 +5,6 @@
 <hits>1</hits>
 <diagnostic>0</diagnostic>
 <records>1</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index efe653d..bd79080 100644 (file)
@@ -5,5 +5,6 @@
 <hits>1</hits>
 <diagnostic>0</diagnostic>
 <records>1</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 44ad1fb..7aa85fa 100644 (file)
@@ -5,6 +5,7 @@
 <hits>10</hits>
 <diagnostic>0</diagnostic>
 <records>10</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target>
 <target><id>Target-2</id>
@@ -12,5 +13,6 @@
 <hits>2015</hits>
 <diagnostic>0</diagnostic>
 <records>100</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 44ad1fb..7aa85fa 100644 (file)
@@ -5,6 +5,7 @@
 <hits>10</hits>
 <diagnostic>0</diagnostic>
 <records>10</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target>
 <target><id>Target-2</id>
@@ -12,5 +13,6 @@
 <hits>2015</hits>
 <diagnostic>0</diagnostic>
 <records>100</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 2fd0767..3802c69 100644 (file)
@@ -5,5 +5,6 @@
 <hits>1</hits>
 <diagnostic>0</diagnostic>
 <records>1</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 7735835..d23fbc8 100644 (file)
@@ -5,5 +5,6 @@
 <hits>10</hits>
 <diagnostic>0</diagnostic>
 <records>10</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 944b7ac..f5a8e90 100644 (file)
@@ -5,5 +5,6 @@
 <hits>10</hits>
 <diagnostic>0</diagnostic>
 <records>10</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 6ef303f..cf7fcd5 100644 (file)
@@ -7,6 +7,7 @@
 <message>Unsupported Use attribute</message>
 <addinfo>host_wildcard</addinfo>
 <records>0</records>
+<filtered>0</filtered>
 <state>Client_Error</state>
 <settings>
 <set name="pz:elements" value="F"/>
index 066eca1..63a213d 100644 (file)
@@ -5,6 +5,7 @@
 <hits>0</hits>
 <diagnostic>0</diagnostic>
 <records>0</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 <settings>
 <set name="pz:elements" value="F"/>
index b709f6e..313fc4a 100644 (file)
@@ -5,5 +5,6 @@
 <hits>1995</hits>
 <diagnostic>0</diagnostic>
 <records>100</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 67dffe0..a47a5d4 100644 (file)
@@ -5,5 +5,6 @@
 <hits>1995</hits>
 <diagnostic>0</diagnostic>
 <records>200</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index b709f6e..313fc4a 100644 (file)
@@ -5,5 +5,6 @@
 <hits>1995</hits>
 <diagnostic>0</diagnostic>
 <records>100</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index b709f6e..313fc4a 100644 (file)
@@ -5,5 +5,6 @@
 <hits>1995</hits>
 <diagnostic>0</diagnostic>
 <records>100</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 67dffe0..a47a5d4 100644 (file)
@@ -5,5 +5,6 @@
 <hits>1995</hits>
 <diagnostic>0</diagnostic>
 <records>200</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index fe72f49..3d39b01 100644 (file)
@@ -5,6 +5,7 @@
 <hits>23</hits>
 <diagnostic>0</diagnostic>
 <records>23</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target>
 <target><id>id_solr</id>
@@ -12,5 +13,6 @@
 <hits>2015</hits>
 <diagnostic>0</diagnostic>
 <records>100</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index fe72f49..3d39b01 100644 (file)
@@ -5,6 +5,7 @@
 <hits>23</hits>
 <diagnostic>0</diagnostic>
 <records>23</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target>
 <target><id>id_solr</id>
@@ -12,5 +13,6 @@
 <hits>2015</hits>
 <diagnostic>0</diagnostic>
 <records>100</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 129dfa4..9643e8a 100644 (file)
@@ -5,5 +5,6 @@
 <hits>23</hits>
 <diagnostic>0</diagnostic>
 <records>23</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index 76e330a..2df4e9a 100644 (file)
@@ -5,5 +5,6 @@
 <hits>3</hits>
 <diagnostic>0</diagnostic>
 <records>3</records>
+<filtered>0</filtered>
 <state>Client_Idle</state>
 </target></bytarget>
\ No newline at end of file
index bd847df..ac0bb56 100644 (file)
@@ -5,7 +5,7 @@
 DEBUG=0   # 0 for release, 1 for debug
 USE_MANIFEST = 1 # Can be enabled Visual Studio 2005/2008
 PACKAGE_NAME=pazpar2
-PACKAGE_VERSION=1.7.2
+PACKAGE_VERSION=1.7.4
 
 # YAZ
 YAZ_DIR=..\..\yaz