* Copyright (C) 1995-2007, Index Data ApS
* See the file LICENSE for details.
*
- * $Id: zoom-c.c,v 1.120 2007-03-21 09:23:11 adam Exp $
+ * $Id: zoom-c.c,v 1.140 2007-08-15 17:53:11 mike Exp $
*/
/**
* \file zoom-c.c
#include <yaz/srw.h>
#include <yaz/cql.h>
#include <yaz/ccl.h>
+#include <yaz/query-charset.h>
+#include <yaz/copy_types.h>
+#include <yaz/snprintf.h>
static int log_api = 0;
static int log_details = 0;
* if it could cause failure when a lookup fails, but that's hard.
*/
static Odr_oid *zoom_yaz_str_to_z3950oid(ZOOM_connection c,
- int oid_class, const char *str) {
- Odr_oid *res = yaz_str_to_z3950oid(c->odr_out, oid_class, str);
+ int oid_class, const char *str) {
+ Odr_oid *res = yaz_string_to_oid_odr(yaz_oid_std(), oid_class, str,
+ c->odr_out);
if (res == 0)
yaz_log(YLOG_WARN, "%p OID lookup (%d, '%s') failed",
c, (int) oid_class, str);
c->client_IP = 0;
c->tasks = 0;
+ c->user = 0;
+ c->group = 0;
+ c->password = 0;
+
+ c->maximum_record_size = 0;
+ c->preferred_message_size = 0;
+
c->odr_in = odr_createmem(ODR_DECODE);
c->odr_out = odr_createmem(ODR_ENCODE);
}
if (!cp)
cp = "Default";
- nmem_strsplit(odr->mem, "+", cp, &databaseNames, num);
+ nmem_strsplit(odr_getmem(odr), "+", cp, &databaseNames, num);
return databaseNames;
}
}
yaz_log(log_details, "%p ZOOM_connection_connect connect", c);
xfree(c->proxy);
+ c->proxy = 0;
val = ZOOM_options_get(c->options, "proxy");
if (val && *val)
{
yaz_log(log_details, "%p ZOOM_connection_connect proxy=%s", c, val);
c->proxy = xstrdup(val);
}
- else
- c->proxy = 0;
xfree(c->charset);
+ c->charset = 0;
val = ZOOM_options_get(c->options, "charset");
if (val && *val)
{
yaz_log(log_details, "%p ZOOM_connection_connect charset=%s", c, val);
c->charset = xstrdup(val);
}
- else
- c->charset = 0;
xfree(c->lang);
val = ZOOM_options_get(c->options, "lang");
ZOOM_options_set(c->options, "host", c->host_port);
+ xfree(c->cookie_out);
+ c->cookie_out = 0;
val = ZOOM_options_get(c->options, "cookie");
if (val && *val)
{
c->cookie_out = xstrdup(val);
}
+ xfree(c->client_IP);
+ c->client_IP = 0;
val = ZOOM_options_get(c->options, "clientIP");
if (val && *val)
{
c->client_IP = xstrdup(val);
}
+ xfree(c->group);
+ c->group = 0;
+ val = ZOOM_options_get(c->options, "group");
+ if (val && *val)
+ c->group = xstrdup(val);
+
+ xfree(c->user);
+ c->user = 0;
+ val = ZOOM_options_get(c->options, "user");
+ if (val && *val)
+ c->user = xstrdup(val);
+
+ xfree(c->password);
+ c->password = 0;
+ val = ZOOM_options_get(c->options, "password");
+ if (!val)
+ val = ZOOM_options_get(c->options, "pass");
+
+ if (val && *val)
+ c->password = xstrdup(val);
+
+ c->maximum_record_size =
+ ZOOM_options_get_int(c->options, "maximumRecordSize", 1024*1024);
+ c->preferred_message_size =
+ ZOOM_options_get_int(c->options, "preferredMessageSize", 1024*1024);
+
c->async = ZOOM_options_get_bool(c->options, "async", 0);
yaz_log(log_details, "%p ZOOM_connection_connect async=%d", c, c->async);
s->query_string = odr_strdup(s->odr, str);
s->z_query = (Z_Query *) odr_malloc(s->odr, sizeof(*s->z_query));
s->z_query->which = Z_Query_type_1;
- s->z_query->u.type_1 = p_query_rpn(s->odr, PROTO_Z3950, str);
+ s->z_query->u.type_1 = p_query_rpn(s->odr, str);
if (!s->z_query->u.type_1)
{
yaz_log(log_details, "%p ZOOM_query_prefix str=%s failed", s, str);
xfree(c->cookie_out);
xfree(c->cookie_in);
xfree(c->client_IP);
+ xfree(c->user);
+ xfree(c->group);
+ xfree(c->password);
xfree(c);
}
r->next = 0;
r->databaseNames = 0;
r->num_databaseNames = 0;
+ r->rpn_iconv = 0;
return r;
}
r->query = q;
r->options = ZOOM_options_create_with_parent(c->options);
+
+ {
+ const char *cp = ZOOM_options_get(r->options, "rpnCharset");
+ if (cp)
+ r->rpn_iconv = yaz_iconv_open(cp, "UTF-8");
+ }
+
start = ZOOM_options_get_int(r->options, "start", 0);
count = ZOOM_options_get_int(r->options, "count", 0);
r->next = c->resultsets;
c->resultsets = r;
+
+
if (c->host_port && c->proto == PROTO_HTTP)
{
if (!c->cs)
return r;
}
-ZOOM_API(int)
+ZOOM_API(void)
ZOOM_resultset_sort(ZOOM_resultset r,
- const char *sort_type, const char *sort_spec)
+ const char *sort_type, const char *sort_spec)
+{
+ (void) ZOOM_resultset_sort1(r, sort_type, sort_spec);
+}
+
+ZOOM_API(int)
+ ZOOM_resultset_sort1(ZOOM_resultset r,
+ const char *sort_type, const char *sort_spec)
{
ZOOM_connection c = r->connection;
ZOOM_task task;
}
ZOOM_query_destroy(r->query);
ZOOM_options_destroy(r->options);
+ if (r->rpn_iconv)
+ yaz_iconv_close(r->rpn_iconv);
odr_destroy(r->odr);
xfree(r->setname);
xfree(r->schema);
for (i = 0; i<200; i++)
{
size_t len;
+ Odr_oid *oid;
Z_OtherInformation **oi;
char buf[80];
const char *val;
const char *cp;
- int oidval;
sprintf(buf, "otherInfo%d", i);
val = ZOOM_options_get(c->options, buf);
len = sizeof(buf)-1;
memcpy(buf, val, len);
buf[len] = '\0';
- oidval = oid_getvalbyname(buf);
- if (oidval == VAL_NONE)
+
+ oid = yaz_string_to_oid_odr(yaz_oid_std(), CLASS_USERINFO,
+ buf, out);
+ if (!oid)
continue;
yaz_oi_APDU(a, &oi);
- yaz_oi_set_string_oidval(oi, out, oidval, 1, cp+1);
+ yaz_oi_set_string_oid(oi, out, oid, 1, cp+1);
}
}
{
Z_OtherInformation **oi;
yaz_oi_APDU(a, &oi);
- yaz_oi_set_string_oidval(oi, out, VAL_COOKIE, 1, c->cookie_out);
+ yaz_oi_set_string_oid(oi, out, yaz_oid_userinfo_cookie,
+ 1, c->cookie_out);
}
if (c->client_IP)
{
Z_OtherInformation **oi;
yaz_oi_APDU(a, &oi);
- yaz_oi_set_string_oidval(oi, out, VAL_CLIENT_IP, 1, c->client_IP);
+ yaz_oi_set_string_oid(oi, out, yaz_oid_userinfo_client_ip,
+ 1, c->client_IP);
}
otherInfo_attach(c, a, out);
if (!z_APDU(out, &a, 0, 0))
Z_InitRequest *ireq = apdu->u.initRequest;
Z_IdAuthentication *auth = (Z_IdAuthentication *)
odr_malloc(c->odr_out, sizeof(*auth));
- const char *auth_groupId = ZOOM_options_get(c->options, "group");
- const char *auth_userId = ZOOM_options_get(c->options, "user");
- const char *auth_password = ZOOM_options_get(c->options, "password");
char *version;
- /* support the pass for backwards compatibility */
- if (!auth_password)
- auth_password = ZOOM_options_get(c->options, "pass");
-
ODR_MASK_SET(ireq->options, Z_Options_search);
ODR_MASK_SET(ireq->options, Z_Options_present);
ODR_MASK_SET(ireq->options, Z_Options_scan);
odr_prepend(c->odr_out, "ZOOM-C",
ireq->implementationName));
- version = odr_strdup(c->odr_out, "$Revision: 1.120 $");
+ version = odr_strdup(c->odr_out, "$Revision: 1.140 $");
if (strlen(version) > 10) /* check for unexpanded CVS strings */
version[strlen(version)-2] = '\0';
ireq->implementationVersion =
odr_prepend(c->odr_out, &version[11],
ireq->implementationVersion));
- *ireq->maximumRecordSize =
- ZOOM_options_get_int(c->options, "maximumRecordSize", 1024*1024);
- *ireq->preferredMessageSize =
- ZOOM_options_get_int(c->options, "preferredMessageSize", 1024*1024);
+ *ireq->maximumRecordSize = c->maximum_record_size;
+ *ireq->preferredMessageSize = c->preferred_message_size;
- if (auth_groupId || auth_password)
+ if (c->group || c->password)
{
Z_IdPass *pass = (Z_IdPass *) odr_malloc(c->odr_out, sizeof(*pass));
- int i = 0;
pass->groupId = 0;
- if (auth_groupId && *auth_groupId)
- {
- pass->groupId = (char *)
- odr_malloc(c->odr_out, strlen(auth_groupId)+1);
- strcpy(pass->groupId, auth_groupId);
- i++;
- }
+ if (c->group)
+ pass->groupId = odr_strdup(c->odr_out, c->group);
pass->userId = 0;
- if (auth_userId && *auth_userId)
- {
- pass->userId = (char *)
- odr_malloc(c->odr_out, strlen(auth_userId)+1);
- strcpy(pass->userId, auth_userId);
- i++;
- }
+ if (c->user)
+ pass->userId = odr_strdup(c->odr_out, c->user);
pass->password = 0;
- if (auth_password && *auth_password)
- {
- pass->password = (char *)
- odr_malloc(c->odr_out, strlen(auth_password)+1);
- strcpy(pass->password, auth_password);
- i++;
- }
- if (i)
- {
- auth->which = Z_IdAuthentication_idPass;
- auth->u.idPass = pass;
- ireq->idAuthentication = auth;
- }
+ if (c->password)
+ pass->password = odr_strdup(c->odr_out, c->password);
+ auth->which = Z_IdAuthentication_idPass;
+ auth->u.idPass = pass;
+ ireq->idAuthentication = auth;
}
- else if (auth_userId)
+ else if (c->user)
{
auth->which = Z_IdAuthentication_open;
- auth->u.open = (char *)
- odr_malloc(c->odr_out, strlen(auth_userId)+1);
- strcpy(auth->u.open, auth_userId);
+ auth->u.open = odr_strdup(c->odr_out, c->user);
ireq->idAuthentication = auth;
}
if (c->proxy)
- yaz_oi_set_string_oidval(&ireq->otherInfo, c->odr_out,
- VAL_PROXY, 1, c->host_port);
+ {
+ yaz_oi_set_string_oid(&ireq->otherInfo, c->odr_out,
+ yaz_oid_userinfo_proxy, 1, c->host_port);
+ }
if (c->charset || c->lang)
{
Z_OtherInformation **oi;
set_ZOOM_error(c, ZOOM_ERROR_INVALID_QUERY, 0);
return zoom_complete;
}
-
+ if (r->query->z_query->which == Z_Query_type_1 && r->rpn_iconv)
+ {
+ search_req->query = yaz_copy_Z_Query(r->query->z_query, c->odr_out);
+
+ yaz_query_charset_convert_rpnquery(search_req->query->u.type_1,
+ c->odr_out, r->rpn_iconv);
+ }
search_req->databaseNames = r->databaseNames;
search_req->num_databaseNames = r->num_databaseNames;
static void response_default_diag(ZOOM_connection c, Z_DefaultDiagFormat *r)
{
- int oclass;
+ char oid_name_buf[OID_STR_MAX];
+ const char *oid_name;
char *addinfo = 0;
+ oid_name = yaz_oid_to_string_buf(r->diagnosticSetId, 0, oid_name_buf);
switch (r->which)
{
case Z_DefaultDiagFormat_v2Addinfo:
}
xfree(c->addinfo);
c->addinfo = 0;
- set_dset_error(c, *r->condition,
- yaz_z3950oid_to_str(r->diagnosticSetId, &oclass),
- addinfo, 0);
+ set_dset_error(c, *r->condition, oid_name, addinfo, 0);
}
static void response_diag(ZOOM_connection c, Z_DiagRec *p)
if (diag_rec->which == Z_DiagRec_defaultFormat)
{
Z_DefaultDiagFormat *ddf = diag_rec->u.defaultFormat;
- int oclass;
+ oid_class oclass;
error = *ddf->condition;
switch (ddf->which)
break;
}
if (diagset)
- *diagset = yaz_z3950oid_to_str(ddf->diagnosticSetId, &oclass);
+ *diagset =
+ yaz_oid_to_string(yaz_oid_std(),
+ ddf->diagnosticSetId, &oclass);
}
else
{
if (npr->which == Z_NamePlusRecord_databaseRecord)
{
Z_External *r = (Z_External *) npr->u.databaseRecord;
- oident *ent = oid_getentbyoid(r->direct_reference);
- if (ent)
- desc = ent->desc;
+ desc = yaz_oid_to_string(yaz_oid_std(), r->direct_reference, 0);
}
if (!desc)
desc = "none";
if (!strcmp(type, "render"))
{
Z_External *r = (Z_External *) npr->u.databaseRecord;
- oident *ent = oid_getentbyoid(r->direct_reference);
+ const Odr_oid *oid = r->direct_reference;
/* render bibliographic record .. */
if (r->which == Z_External_OPAC)
r = r->u.opac->bibliographicRecord;
if (!r)
return 0;
- ent = oid_getentbyoid(r->direct_reference);
+ oid = r->direct_reference;
}
if (r->which == Z_External_sutrs)
return record_iconv_return(rec, len,
charset);
else if (r->which == Z_External_octet)
{
- const char *ret_buf;
- switch (ent->value)
+ if (yaz_oid_is_iso2709(oid))
{
- case VAL_SOIF:
- case VAL_HTML:
- case VAL_SUTRS:
- break;
- case VAL_TEXT_XML:
- case VAL_APPLICATION_XML:
- break;
- default:
- ret_buf = marc_iconv_return(
+ const char *ret_buf = marc_iconv_return(
rec, YAZ_MARC_LINE, len,
(const char *) r->u.octet_aligned->buf,
r->u.octet_aligned->len,
else if (!strcmp(type, "xml"))
{
Z_External *r = (Z_External *) npr->u.databaseRecord;
- oident *ent = oid_getentbyoid(r->direct_reference);
+ const Odr_oid *oid = r->direct_reference;
/* render bibliographic record .. */
if (r->which == Z_External_OPAC)
r = r->u.opac->bibliographicRecord;
if (!r)
return 0;
- ent = oid_getentbyoid(r->direct_reference);
+ oid = r->direct_reference;
}
if (r->which == Z_External_sutrs)
charset);
else if (r->which == Z_External_octet)
{
- const char *ret_buf;
int marc_decode_type = YAZ_MARC_MARCXML;
-
- switch (ent->value)
+ if (yaz_oid_is_iso2709(oid))
{
- case VAL_SOIF:
- case VAL_HTML:
- case VAL_SUTRS:
- break;
- case VAL_TEXT_XML:
- case VAL_APPLICATION_XML:
- break;
- default:
- ret_buf = marc_iconv_return(
+ const char *ret_buf = marc_iconv_return(
rec, marc_decode_type, len,
(const char *) r->u.octet_aligned->buf,
r->u.octet_aligned->len,
resultset, *start, *count);
/* transfer our response to search_nmem .. we need it later */
- nmem_transfer(resultset->odr->mem, nmem);
+ nmem_transfer(odr_getmem(resultset->odr), nmem);
nmem_destroy(nmem);
if (present_phase && p->num_records == 0)
{
if (res->entries && res->entries->nonsurrogateDiagnostics)
response_diag(c, res->entries->nonsurrogateDiagnostics[0]);
scan->scan_response = res;
- nmem_transfer(scan->odr->mem, nmem);
+ nmem_transfer(odr_getmem(scan->odr), nmem);
if (res->stepSize)
ZOOM_options_set_int(scan->options, "stepSize", *res->stepSize);
if (res->positionOfTerm)
}
ZOOM_API(ZOOM_scanset)
- ZOOM_connection_scan_pqf(ZOOM_connection c, const char *start)
+ ZOOM_connection_scan(ZOOM_connection c, const char *start)
{
ZOOM_scanset s;
ZOOM_query q = ZOOM_query_create();
ZOOM_query_prefix(q, start);
- s = ZOOM_connection_scan(c, q);
+ s = ZOOM_connection_scan1(c, q);
ZOOM_query_destroy(q);
return s;
}
ZOOM_API(ZOOM_scanset)
- ZOOM_connection_scan(ZOOM_connection c, ZOOM_query q)
+ ZOOM_connection_scan1(ZOOM_connection c, ZOOM_query q)
{
char *start;
char *freeme = 0;
{
yaz_log(log_api, "%p ZOOM_connection_scan1 q=%p CQL '%s'",
c, q, q->query_string);
+ /*
+ * ### This is wrong: if ZOOM_query_cql2rpn() was used, then
+ * the query already been translated to PQF, so we'd be in the
+ * previous branch. We only get here if the client submitted
+ * CQL to be interepreted by the server using
+ * ZOOM_query_cql(), in which case we should send it as-is.
+ * We can't do that in Z39.50 as the ScanRequest APDU has no
+ * slot in which to place the CQL, but we could and should do
+ * it for SRU connections. At present, we can't do that
+ * because there is no slot in the ZOOM_scanset structure to
+ * save the CQL so that it can be sent when the ZOOM_TASK_SCAN
+ * fires.
+ */
start = freeme = cql2pqf(c, q->query_string);
if (start == 0)
return 0;
p_query_scan(scan->odr, PROTO_Z3950, &scan->attributeSet, start);
xfree(freeme);
+ {
+ const char *cp = ZOOM_options_get(scan->options, "rpnCharset");
+ if (cp)
+ {
+ yaz_iconv_t cd = yaz_iconv_open(cp, "UTF-8");
+ if (cd)
+ {
+ yaz_query_charset_convert_apt(scan->termListAndStartPoint,
+ scan->odr, cd);
+ }
+ }
+ }
+
+
scan->databaseNames = set_DatabaseNames(c, c->options,
&scan->num_databaseNames,
scan->odr);
return ZOOM_options_get(scan->options, key);
}
-ZOOM_API(int)
+ZOOM_API(void)
ZOOM_scanset_option_set(ZOOM_scanset scan, const char *key,
const char *val)
{
ZOOM_options_set(scan->options, key, val);
- return 0;
}
-static Z_APDU *create_es_package(ZOOM_package p, int type)
+static Z_APDU *create_es_package(ZOOM_package p, const Odr_oid *oid)
{
const char *str;
Z_APDU *apdu = zget_APDU(p->odr_out, Z_APDU_extendedServicesRequest);
Z_ExtendedServicesRequest *req = apdu->u.extendedServicesRequest;
- *req->function = Z_ExtendedServicesRequest_create;
-
str = ZOOM_options_get(p->options, "package-name");
if (str && *str)
- req->packageName = nmem_strdup(p->odr_out->mem, str);
+ req->packageName = odr_strdup(p->odr_out, str);
str = ZOOM_options_get(p->options, "user-id");
if (str)
- req->userId = nmem_strdup(p->odr_out->mem, str);
+ req->userId = odr_strdup(p->odr_out, str);
- req->packageType = yaz_oidval_to_z3950oid(p->odr_out, CLASS_EXTSERV,
- type);
+ req->packageType = odr_oiddup(p->odr_out, oid);
str = ZOOM_options_get(p->options, "function");
if (str)
{
if (!strcmp (str, "create"))
- *req->function = 1;
+ *req->function = Z_ExtendedServicesRequest_create;
if (!strcmp (str, "delete"))
- *req->function = 2;
+ *req->function = Z_ExtendedServicesRequest_delete;
if (!strcmp (str, "modify"))
- *req->function = 3;
+ *req->function = Z_ExtendedServicesRequest_modify;
+ }
+
+ str = ZOOM_options_get(p->options, "waitAction");
+ if (str)
+ {
+ if (!strcmp (str, "wait"))
+ *req->waitAction = Z_ExtendedServicesRequest_wait;
+ if (!strcmp (str, "waitIfPossible"))
+ *req->waitAction = Z_ExtendedServicesRequest_waitIfPossible;
+ if (!strcmp (str, "dontWait"))
+ *req->waitAction = Z_ExtendedServicesRequest_dontWait;
+ if (!strcmp (str, "dontReturnPackage"))
+ *req->waitAction = Z_ExtendedServicesRequest_dontReturnPackage;
}
return apdu;
}
}
else
{
- oident oid;
int illRequest_size = 0;
char *illRequest_buf = odr_getbuf(out, &illRequest_size, 0);
- oid.proto = PROTO_GENERAL;
- oid.oclass = CLASS_GENERAL;
- oid.value = VAL_ISO_ILL_1;
-
r = (Z_External *) odr_malloc(out, sizeof(*r));
- r->direct_reference = odr_oiddup(out,oid_getoidbyent(&oid));
+ r->direct_reference = odr_oiddup(out, yaz_oid_general_isoill_1);
r->indirect_reference = 0;
r->descriptor = 0;
r->which = Z_External_single;
str = ZOOM_options_get(p->options, "contact-name");
req->u.esRequest->toKeep->contact->name = str ?
- nmem_strdup(p->odr_out->mem, str) : 0;
+ odr_strdup(p->odr_out, str) : 0;
str = ZOOM_options_get(p->options, "contact-phone");
req->u.esRequest->toKeep->contact->phone = str ?
- nmem_strdup(p->odr_out->mem, str) : 0;
+ odr_strdup(p->odr_out, str) : 0;
str = ZOOM_options_get(p->options, "contact-email");
req->u.esRequest->toKeep->contact->email = str ?
- nmem_strdup(p->odr_out->mem, str) : 0;
+ odr_strdup(p->odr_out, str) : 0;
req->u.esRequest->toKeep->addlBilling = 0;
odr_malloc(p->odr_out, sizeof(Z_IOResultSetItem));
req->u.esRequest->notToKeep->resultSetItem->resultSetId =
- nmem_strdup(p->odr_out->mem, str);
+ odr_strdup(p->odr_out, str);
req->u.esRequest->notToKeep->resultSetItem->item =
(int *) odr_malloc(p->odr_out, sizeof(int));
str = ZOOM_options_get(p->options, "doc");
if (str)
+ {
req->u.esRequest->notToKeep->itemRequest =
- z_ext_record(p->odr_out, VAL_TEXT_XML, str, strlen(str));
+ z_ext_record_xml(p->odr_out, str, strlen(str));
+ }
else
req->u.esRequest->notToKeep->itemRequest = encode_ill_request(p);
Z_ESAdminOriginPartToKeep **toKeepP,
Z_ESAdminOriginPartNotToKeep **notToKeepP)
{
- Z_APDU *apdu = create_es_package(p, VAL_ADMINSERVICE);
+ Z_APDU *apdu = create_es_package(p, yaz_oid_extserv_admin);
if (apdu)
{
Z_ESAdminOriginPartToKeep *toKeep;
if (num_db > 0)
first_db = db[0];
- r->direct_reference =
- yaz_oidval_to_z3950oid(p->odr_out, CLASS_EXTSERV,
- VAL_ADMINSERVICE);
+ r->direct_reference = odr_oiddup(p->odr_out, yaz_oid_extserv_admin);
r->descriptor = 0;
r->indirect_reference = 0;
r->which = Z_External_ESAdmin;
static Z_APDU *create_xmlupdate_package(ZOOM_package p)
{
- Z_APDU *apdu = create_es_package(p, VAL_XMLES);
+ Z_APDU *apdu = create_es_package(p, yaz_oid_extserv_xml_es);
Z_ExtendedServicesRequest *req = apdu->u.extendedServicesRequest;
Z_External *ext = (Z_External *) odr_malloc(p->odr_out, sizeof(*ext));
const char *doc = ZOOM_options_get(p->options, "doc");
const char *recordIdNumber = ZOOM_options_get(p->options, "recordIdNumber");
const char *record_buf = ZOOM_options_get(p->options, "record");
const char *syntax_str = ZOOM_options_get(p->options, "syntax");
- int syntax_oid = VAL_NONE;
+ const char *version = ZOOM_options_get(p->options, "updateVersion");
+
+ const char *correlationInfo_note =
+ ZOOM_options_get(p->options, "correlationInfo.note");
+ const char *correlationInfo_id =
+ ZOOM_options_get(p->options, "correlationInfo.id");
int action_no = -1;
-
- if (syntax_str)
- syntax_oid = oid_getvalbyname(syntax_str);
+ Odr_oid *syntax_oid = 0;
+ const Odr_oid *package_oid = yaz_oid_extserv_database_update;
+
+ if (!version)
+ version = "3";
+ if (!syntax_str)
+ syntax_str = "xml";
if (!record_buf)
{
record_buf = "void";
- syntax_oid = VAL_SUTRS;
+ syntax_str = "SUTRS";
}
- if (syntax_oid == VAL_NONE)
- syntax_oid = VAL_TEXT_XML;
-
+
+ if (syntax_str)
+ {
+ syntax_oid = yaz_string_to_oid_odr(yaz_oid_std(),
+ CLASS_RECSYN, syntax_str,
+ p->odr_out);
+ }
+ if (!syntax_oid)
+ return 0;
+
if (num_db > 0)
first_db = db[0];
- if (!action)
- action = "specialUpdate";
+ switch(*version)
+ {
+ case '1':
+ package_oid = yaz_oid_extserv_database_update_first_version;
+ /* old update does not support specialUpdate */
+ if (!action)
+ action = "recordInsert";
+ break;
+ case '2':
+ if (!action)
+ action = "specialUpdate";
+ package_oid = yaz_oid_extserv_database_update_second_version;
+ break;
+ case '3':
+ if (!action)
+ action = "specialUpdate";
+ package_oid = yaz_oid_extserv_database_update;
+ break;
+ default:
+ return 0;
+ }
if (!strcmp(action, "recordInsert"))
action_no = Z_IUOriginPartToKeep_recordInsert;
else
return 0;
- apdu = create_es_package(p, VAL_DBUPDATE);
+ apdu = create_es_package(p, package_oid);
if (apdu)
{
Z_IUOriginPartToKeep *toKeep;
Z_IUSuppliedRecords *notToKeep;
Z_External *r = (Z_External *)
odr_malloc(p->odr_out, sizeof(*r));
+ const char *elementSetName =
+ ZOOM_options_get(p->options, "elementSetName");
apdu->u.extendedServicesRequest->taskSpecificParameters = r;
- r->direct_reference =
- yaz_oidval_to_z3950oid(p->odr_out, CLASS_EXTSERV,
- VAL_DBUPDATE);
+ r->direct_reference = odr_oiddup(p->odr_out, package_oid);
r->descriptor = 0;
r->which = Z_External_update;
r->indirect_reference = 0;
toKeep->databaseName = odr_strdup(p->odr_out, first_db);
toKeep->schema = 0;
+
toKeep->elementSetName = 0;
+ if (elementSetName)
+ toKeep->elementSetName = odr_strdup(p->odr_out, elementSetName);
+
toKeep->actionQualifier = 0;
toKeep->action = odr_intdup(p->odr_out, action_no);
else
notToKeep->elements[0]->u.opaque = 0;
notToKeep->elements[0]->supplementalId = 0;
- notToKeep->elements[0]->correlationInfo = 0;
+ if (correlationInfo_note || correlationInfo_id)
+ {
+ Z_IUCorrelationInfo *ci;
+ ci = notToKeep->elements[0]->correlationInfo =
+ odr_malloc(p->odr_out, sizeof(*ci));
+ ci->note = correlationInfo_note ?
+ odr_strdup(p->odr_out, correlationInfo_note) : 0;
+ ci->id = correlationInfo_id ?
+ odr_intdup(p->odr_out, atoi(correlationInfo_id)) : 0;
+ }
+ else
+ notToKeep->elements[0]->correlationInfo = 0;
notToKeep->elements[0]->record =
- z_ext_record(p->odr_out, syntax_oid,
- record_buf, strlen(record_buf));
+ z_ext_record_oid(p->odr_out, syntax_oid,
+ record_buf, strlen(record_buf));
}
if (0 && apdu)
{
p->buf_out = 0;
if (!strcmp(type, "itemorder"))
{
- apdu = create_es_package(p, VAL_ITEMORDER);
+ apdu = create_es_package(p, yaz_oid_extserv_item_order);
if (apdu)
{
Z_External *r = (Z_External *) odr_malloc(p->odr_out, sizeof(*r));
- r->direct_reference =
- yaz_oidval_to_z3950oid(p->odr_out, CLASS_EXTSERV,
- VAL_ITEMORDER);
+ r->direct_reference =
+ odr_oiddup(p->odr_out, yaz_oid_extserv_item_order);
r->descriptor = 0;
r->which = Z_External_itemOrder;
r->indirect_reference = 0;
}
-ZOOM_API(int)
+ZOOM_API(void)
ZOOM_package_option_set(ZOOM_package p, const char *key,
const char *val)
{
ZOOM_options_set(p->options, key, val);
- return 0;
}
static int ZOOM_connection_exec_task(ZOOM_connection c)
static void set_init_option(const char *name, void *clientData) {
- ZOOM_connection c = clientData;
+ ZOOM_connection c = (ZOOM_connection) clientData;
char buf[80];
sprintf(buf, "init_opt_%.70s", name);
switch(apdu->which)
{
case Z_APDU_initResponse:
- yaz_log(log_api, "%p recv_apd: Received Init response", c);
+ yaz_log(log_api, "%p recv_apdu: Received Init response", c);
initrs = apdu->u.initResponse;
ZOOM_connection_option_set(c, "serverImplementationId",
initrs->implementationId ?
else
{
char *cookie =
- yaz_oi_get_string_oidval(&apdu->u.initResponse->otherInfo,
- VAL_COOKIE, 1, 0);
+ yaz_oi_get_string_oid(&apdu->u.initResponse->otherInfo,
+ yaz_oid_userinfo_cookie, 1, 0);
xfree(c->cookie_in);
c->cookie_in = 0;
if (cookie)
odr_malloc(c->odr_in, sizeof(Z_External));
npr->u.databaseRecord->descriptor = 0;
npr->u.databaseRecord->direct_reference =
- yaz_oidval_to_z3950oid(c->odr_in, CLASS_RECSYN, VAL_TEXT_XML);
+ odr_oiddup(c->odr_in, yaz_oid_recsyn_xml);
npr->u.databaseRecord->which = Z_External_octet;
npr->u.databaseRecord->u.octet_aligned = (Odr_oct *)
}
}
nmem = odr_extract_mem(c->odr_in);
- nmem_transfer(resultset->odr->mem, nmem);
+ nmem_transfer(odr_getmem(resultset->odr), nmem);
nmem_destroy(nmem);
}
#endif
static void handle_http(ZOOM_connection c, Z_HTTP_Response *hres)
{
int ret = -1;
- const char *content_type = z_HTTP_header_lookup(hres->headers,
- "Content-Type");
+ const char *addinfo = 0;
const char *connection_head = z_HTTP_header_lookup(hres->headers,
"Connection");
ZOOM_connection_set_mask(c, 0);
yaz_log(log_details, "%p handle_http", c);
-
- if (content_type && !yaz_strcmp_del("text/xml", content_type, "; "))
+
+ if (!yaz_srw_check_content_type(hres))
+ addinfo = "content-type";
+ else
{
Z_SOAP *soap_package = 0;
ODR o = c->odr_in;
if (hres->code != 200)
set_HTTP_error(c, hres->code, 0, 0);
else
- set_ZOOM_error(c, ZOOM_ERROR_DECODE, 0);
+ set_ZOOM_error(c, ZOOM_ERROR_DECODE, addinfo);
do_close(c);
}
ZOOM_connection_remove_task(c);
{
int x;
int err = odr_geterrorx(c->odr_in, &x);
- char msg[60];
+ char msg[100];
const char *element = odr_getelement(c->odr_in);
- sprintf(msg, "ODR code %d:%d element=%-20s",
- err, x, element ? element : "<unknown>");
+ yaz_snprintf(msg, sizeof(msg),
+ "ODR code %d:%d element=%s offset=%d",
+ err, x, element ? element : "<unknown>",
+ odr_offset(c->odr_in));
set_ZOOM_error(c, ZOOM_ERROR_DECODE, msg);
+ if (log_api)
+ {
+ FILE *ber_file = yaz_log_file();
+ if (ber_file)
+ odr_dumpBER(ber_file, c->buf_in, r);
+ }
do_close(c);
}
else if (gdu->which == Z_GDU_Z3950)
return ZOOM_options_getl(c->options, key, lenp);
}
-ZOOM_API(int)
+ZOOM_API(void)
ZOOM_connection_option_set(ZOOM_connection c, const char *key,
const char *val)
{
ZOOM_options_set(c->options, key, val);
- return 0;
}
-ZOOM_API(int)
+ZOOM_API(void)
ZOOM_connection_option_setl(ZOOM_connection c, const char *key,
const char *val, int len)
{
ZOOM_options_setl(c->options, key, val, len);
- return 0;
}
ZOOM_API(const char *)
return ZOOM_options_get(r->options, key);
}
-ZOOM_API(int)
+ZOOM_API(void)
ZOOM_resultset_option_set(ZOOM_resultset r, const char *key,
const char *val)
{
ZOOM_options_set(r->options, key, val);
- return 0;
}
if (c->cs->io_pending & CS_WANT_READ)
mask += ZOOM_SELECT_READ;
ZOOM_connection_set_mask(c, mask);
+ event = ZOOM_Event_create(ZOOM_EVENT_NONE);
+ ZOOM_connection_put_event(c, event);
}
else if (ret == 0)
{
}
+static void cql2pqf_wrbuf_puts(const char *buf, void *client_data)
+{
+ WRBUF wrbuf = (WRBUF) client_data;
+ wrbuf_puts(wrbuf, buf);
+}
+
/*
* Returns an xmalloc()d string containing RPN that corresponds to the
* CQL passed in. On error, sets the Connection object's error state
{
CQL_parser parser;
int error;
- struct cql_node *node;
const char *cqlfile;
- static cql_transform_t trans;
- char pqfbuf[512];
+ cql_transform_t trans;
+ char *result = 0;
parser = cql_parser_create();
if ((error = cql_parser_string(parser, cql)) != 0) {
return 0;
}
- node = cql_parser_result(parser);
- /* ### Do not call cql_parser_destroy() yet: it destroys `node'! */
-
cqlfile = ZOOM_connection_option_get(c, "cqlfile");
- if (cqlfile == 0) {
- cql_parser_destroy(parser);
- cql_node_destroy(node);
+ if (cqlfile == 0)
+ {
set_ZOOM_error(c, ZOOM_ERROR_CQL_TRANSFORM, "no CQL transform file");
- return 0;
}
-
- if ((trans = cql_transform_open_fname(cqlfile)) == 0) {
+ else if ((trans = cql_transform_open_fname(cqlfile)) == 0)
+ {
char buf[512];
- cql_parser_destroy(parser);
- cql_node_destroy(node);
sprintf(buf, "can't open CQL transform file '%.200s': %.200s",
cqlfile, strerror(errno));
set_ZOOM_error(c, ZOOM_ERROR_CQL_TRANSFORM, buf);
- return 0;
}
-
- error = cql_transform_buf(trans, node, pqfbuf, sizeof pqfbuf);
- cql_parser_destroy(parser);
- cql_node_destroy(node);
- if (error != 0) {
- char buf[512];
- const char *addinfo;
- error = cql_transform_error(trans, &addinfo);
- sprintf(buf, "%.200s (addinfo=%.200s)", cql_strerror(error), addinfo);
- set_ZOOM_error(c, ZOOM_ERROR_CQL_TRANSFORM, buf);
+ else
+ {
+ WRBUF wrbuf_result = wrbuf_alloc();
+ error = cql_transform(trans, cql_parser_result(parser),
+ cql2pqf_wrbuf_puts, wrbuf_result);
+ if (error != 0) {
+ char buf[512];
+ const char *addinfo;
+ error = cql_transform_error(trans, &addinfo);
+ sprintf(buf, "%.200s (addinfo=%.200s)",
+ cql_strerror(error), addinfo);
+ set_ZOOM_error(c, ZOOM_ERROR_CQL_TRANSFORM, buf);
+ }
+ else
+ {
+ result = xstrdup(wrbuf_cstr(wrbuf_result));
+ }
cql_transform_close(trans);
- return 0;
+ wrbuf_destroy(wrbuf_result);
}
-
- cql_transform_close(trans);
- return xstrdup(pqfbuf);
+ cql_parser_destroy(parser);
+ return result;
}
ZOOM_API(int) ZOOM_connection_fire_event_timeout(ZOOM_connection c)