2 * Copyright (c) 1998-2003, Index Data.
3 * See the file LICENSE for details.
5 * $Id: yaz-proxy-config.cpp,v 1.10 2003-10-16 13:40:41 adam Exp $
10 #include <yaz++/proxy.h>
12 Yaz_ProxyConfig::Yaz_ProxyConfig()
21 Yaz_ProxyConfig::~Yaz_ProxyConfig()
24 if (!m_copy && m_docPtr)
29 int Yaz_ProxyConfig::read_xml(const char *fname)
32 xmlDocPtr ndoc = xmlParseFile(fname);
36 yaz_log(LOG_WARN, "Config file %s not found or parse error", fname);
39 xmlNodePtr proxyPtr = xmlDocGetRootElement(ndoc);
40 if (!proxyPtr || proxyPtr->type != XML_ELEMENT_NODE ||
41 strcmp((const char *) proxyPtr->name, "proxy"))
43 yaz_log(LOG_WARN, "No proxy element in %s", fname);
47 m_proxyPtr = proxyPtr;
49 // OK: release previous and make it the current one.
60 const char *Yaz_ProxyConfig::get_text(xmlNodePtr ptr)
62 for(ptr = ptr->children; ptr; ptr = ptr->next)
63 if (ptr->type == XML_TEXT_NODE)
65 xmlChar *t = ptr->content;
70 return (const char *) t;
78 void Yaz_ProxyConfig::return_limit(xmlNodePtr ptr,
83 for (ptr = ptr->children; ptr; ptr = ptr->next)
85 if (ptr->type == XML_ELEMENT_NODE
86 && !strcmp((const char *) ptr->name, "bandwidth"))
88 const char *t = get_text(ptr);
92 if (ptr->type == XML_ELEMENT_NODE
93 && !strcmp((const char *) ptr->name, "retrieve"))
95 const char *t = get_text(ptr);
99 if (ptr->type == XML_ELEMENT_NODE
100 && !strcmp((const char *) ptr->name, "pdu"))
102 const char *t = get_text(ptr);
104 *limit_pdu = atoi(t);
111 void Yaz_ProxyConfig::return_target_info(xmlNodePtr ptr,
116 int *target_idletime,
117 int *client_idletime,
118 int *keepalive_limit_bw,
119 int *keepalive_limit_pdu,
126 for (; ptr; ptr = ptr->next)
128 if (ptr->type == XML_ELEMENT_NODE
129 && !strcmp((const char *) ptr->name, "log"))
131 const char *v = get_text(ptr);
136 while (*cp && *cp != ',' && !isspace(*cp))
139 if (len == 4 && !memcmp(v, "apdu", 4))
140 *log_mask |= PROXY_LOG_APDU;
141 if (len == 3 && !memcmp(v, "req", 3))
142 *log_mask |= PROXY_LOG_REQ;
144 *log_mask |= atoi(v);
147 while (*cp && isspace(*cp))
152 if (ptr->type == XML_ELEMENT_NODE
153 && !strcmp((const char *) ptr->name, "preinit"))
155 const char *v = get_text(ptr);
156 *pre_init = v ? atoi(v) : 1;
158 if (ptr->type == XML_ELEMENT_NODE
159 && !strcmp((const char *) ptr->name, "url"))
161 const char *t = get_text(ptr);
162 if (t && no_url < MAX_ZURL_PLEX)
168 if (ptr->type == XML_ELEMENT_NODE
169 && !strcmp((const char *) ptr->name, "keepalive"))
172 *keepalive_limit_bw = 500000;
173 *keepalive_limit_pdu = 1000;
174 return_limit(ptr, keepalive_limit_bw, keepalive_limit_pdu,
177 if (ptr->type == XML_ELEMENT_NODE
178 && !strcmp((const char *) ptr->name, "limit"))
179 return_limit(ptr, limit_bw, limit_pdu, limit_req);
180 if (ptr->type == XML_ELEMENT_NODE
181 && !strcmp((const char *) ptr->name, "target-timeout"))
183 const char *t = get_text(ptr);
186 *target_idletime = atoi(t);
187 if (*target_idletime < 0)
188 *target_idletime = 0;
191 if (ptr->type == XML_ELEMENT_NODE
192 && !strcmp((const char *) ptr->name, "client-timeout"))
194 const char *t = get_text(ptr);
197 *client_idletime = atoi(t);
198 if (*client_idletime < 0)
199 *client_idletime = 0;
206 int Yaz_ProxyConfig::atoi_l(const char **cp)
209 while (**cp && isdigit(**cp))
211 v = v*10 + (**cp - '0');
217 int Yaz_ProxyConfig::match_list(int v, const char *m)
221 while(*m && isspace(*m))
232 if (v >= l && v <= h)
241 int Yaz_ProxyConfig::check_type_1_attributes(ODR odr, xmlNodePtr ptr,
242 Z_AttributeList *attrs,
245 for(ptr = ptr->children; ptr; ptr = ptr->next)
247 if (ptr->type == XML_ELEMENT_NODE &&
248 !strcmp((const char *) ptr->name, "attribute"))
250 const char *match_type = 0;
251 const char *match_value = 0;
252 const char *match_error = 0;
253 struct _xmlAttr *attr;
254 for (attr = ptr->properties; attr; attr = attr->next)
256 if (!strcmp((const char *) attr->name, "type") &&
257 attr->children && attr->children->type == XML_TEXT_NODE)
258 match_type = (const char *) attr->children->content;
259 if (!strcmp((const char *) attr->name, "value") &&
260 attr->children && attr->children->type == XML_TEXT_NODE)
261 match_value = (const char *) attr->children->content;
262 if (!strcmp((const char *) attr->name, "error") &&
263 attr->children && attr->children->type == XML_TEXT_NODE)
264 match_error = (const char *) attr->children->content;
268 if (match_type && match_value)
270 for (i = 0; i<attrs->num_attributes; i++)
272 Z_AttributeElement *el = attrs->attributes[i];
276 if (!el->attributeType)
278 int type = *el->attributeType;
280 if (!match_list(type, match_type))
282 if (el->which == Z_AttributeValue_numeric &&
285 if (!match_list(*el->value.numeric, match_value))
287 sprintf (value_str, "%d", *el->value.numeric);
294 *addinfo = odr_strdup(odr, value_str);
295 return atoi(match_error);
307 int Yaz_ProxyConfig::check_type_1_structure(ODR odr, xmlNodePtr ptr,
312 if (q->which == Z_RPNStructure_complex)
314 int e = check_type_1_structure(odr, ptr, q->u.complex->s1, addinfo);
317 e = check_type_1_structure(odr, ptr, q->u.complex->s2, addinfo);
320 else if (q->which == Z_RPNStructure_simple)
322 if (q->u.simple->which == Z_Operand_APT)
324 return check_type_1_attributes(
325 odr, ptr, q->u.simple->u.attributesPlusTerm->attributes,
334 int Yaz_ProxyConfig::check_type_1(ODR odr, xmlNodePtr ptr, Z_RPNQuery *query,
337 // possibly check for Bib-1
338 return check_type_1_structure(odr, ptr, query->RPNStructure, addinfo);
342 int Yaz_ProxyConfig::check_query(ODR odr, const char *name, Z_Query *query,
348 ptr = find_target_node(name);
351 if (query->which == Z_Query_type_1 || query->which == Z_Query_type_101)
352 return check_type_1(odr, ptr, query->u.type_1, addinfo);
358 int Yaz_ProxyConfig::check_syntax(ODR odr, const char *name,
359 Odr_oid *syntax, char **addinfo)
364 ptr = find_target_node(name);
367 for(ptr = ptr->children; ptr; ptr = ptr->next)
369 if (ptr->type == XML_ELEMENT_NODE &&
370 !strcmp((const char *) ptr->name, "syntax"))
372 int match = 0; // if we match record syntax
373 const char *match_type = 0;
374 const char *match_error = 0;
375 const char *match_marcxml = 0;
376 struct _xmlAttr *attr;
377 for (attr = ptr->properties; attr; attr = attr->next)
379 if (!strcmp((const char *) attr->name, "type") &&
380 attr->children && attr->children->type == XML_TEXT_NODE)
381 match_type = (const char *) attr->children->content;
382 if (!strcmp((const char *) attr->name, "error") &&
383 attr->children && attr->children->type == XML_TEXT_NODE)
384 match_error = (const char *) attr->children->content;
385 if (!strcmp((const char *) attr->name, "marcxml") &&
386 attr->children && attr->children->type == XML_TEXT_NODE)
387 match_marcxml = (const char *) attr->children->content;
391 if (!strcmp(match_type, "*"))
393 else if (!strcmp(match_type, "none"))
400 int match_oid[OID_SIZE];
401 oid_name_to_oid(CLASS_RECSYN, match_type, match_oid);
402 if (oid_oidcmp(match_oid, syntax) == 0)
416 char dotoid_str[100];
417 oid_to_dotstring(syntax, dotoid_str);
418 *addinfo = odr_strdup(odr, dotoid_str);
420 return atoi(match_error);
431 xmlNodePtr Yaz_ProxyConfig::find_target_node(const char *name)
436 for (ptr = m_proxyPtr->children; ptr; ptr = ptr->next)
438 if (ptr->type == XML_ELEMENT_NODE &&
439 !strcmp((const char *) ptr->name, "target"))
444 // <target default="1"> ?
445 struct _xmlAttr *attr;
446 for (attr = ptr->properties; attr; attr = attr->next)
447 if (!strcmp((const char *) attr->name, "default") &&
448 attr->children && attr->children->type == XML_TEXT_NODE)
450 xmlChar *t = attr->children->content;
457 // <target name="name"> ?
458 struct _xmlAttr *attr;
459 for (attr = ptr->properties; attr; attr = attr->next)
460 if (!strcmp((const char *) attr->name, "name"))
463 && attr->children->type==XML_TEXT_NODE
464 && attr->children->content
465 && (!strcmp((const char *) attr->children->content,
467 || !strcmp((const char *) attr->children->content,
480 int Yaz_ProxyConfig::get_target_no(int no,
486 int *target_idletime,
487 int *client_idletime,
489 int *keepalive_limit_bw,
490 int *keepalive_limit_pdu,
499 for (ptr = m_proxyPtr->children; ptr; ptr = ptr->next)
500 if (ptr->type == XML_ELEMENT_NODE &&
501 !strcmp((const char *) ptr->name, "target"))
505 struct _xmlAttr *attr;
506 for (attr = ptr->properties; attr; attr = attr->next)
507 if (!strcmp((const char *) attr->name, "name"))
510 && attr->children->type==XML_TEXT_NODE
511 && attr->children->content)
512 *name = (const char *) attr->children->content;
514 return_target_info(ptr, url, limit_bw, limit_pdu, limit_req,
515 target_idletime, client_idletime,
516 keepalive_limit_bw, keepalive_limit_pdu,
526 void Yaz_ProxyConfig::get_target_info(const char *name,
531 int *target_idletime,
532 int *client_idletime,
534 int *keepalive_limit_bw,
535 int *keepalive_limit_pdu,
548 for (ptr = m_proxyPtr->children; ptr; ptr = ptr->next)
550 if (ptr->type == XML_ELEMENT_NODE &&
551 !strcmp((const char *) ptr->name, "max-clients"))
553 const char *t = get_text(ptr);
556 *max_clients = atoi(t);
557 if (*max_clients < 1)
562 ptr = find_target_node(name);
570 return_target_info(ptr, url, limit_bw, limit_pdu, limit_req,
571 target_idletime, client_idletime,
572 keepalive_limit_bw, keepalive_limit_pdu,