1 <chapter id="proxy-reference">
2 <title>Proxy Reference</title>
3 <section id="proxy-operation">
4 <title>Operating Environment</title>
6 The YAZ proxy is a single program. After startup it spawns
7 a child process (except on Windows or if option -X is given).
8 The child process is the core of the proxy and it handles all
9 communication with clients and servers. The parent process
10 will restart the child process if it dies unexpectedly and report
11 the reason. For options for YAZ proxy,
12 see <xref linkend="proxy-usage"/>.
15 As an option the proxy may change user identity to a less priviledged
19 <section id="proxy-target">
20 <title>Choosing the Backend Server</title>
22 When the proxy receives a Z39.50 Initialize Request from a Z39.50
23 client, it determines the backend server by the following rules:
26 <para>If the <literal>InitializeRequest</literal> PDU from the
28 <link linkend="otherinfo-encoding"><literal>otherInfo</literal></link>
30 <literal>1.2.840.10003.10.1000.81.1</literal>, then the
31 contents of that element specify the server to be used, in the
32 usual YAZ address format (typically
33 <literal>tcp:<parameter>hostname</parameter>:<parameter>port</parameter></literal>)
35 <ulink url="http://www.indexdata.dk/yaz/doc/comstack.addresses.tkl"
36 >the Addresses section of the YAZ manual</ulink>.
41 <para>Otherwise, the Proxy uses the default server, if one was
42 specified in the proxy configuration file. See
43 <xref linkend="proxy-config-target"/>.
48 <para>Otherwise, the Proxy uses the default server, if one was
49 specified on the command-line with the <literal>-t</literal>
54 <para>Otherwise, the proxy closes the connection with
61 If the proxy receives an SRW/SRU request, the following rules are used.
64 <para>If default target has Explain information with a
65 <literal>database</literal> that matches the path of the
66 HTTP request of SRW/SRU that backend server is used for
72 Otherwise the service will return HTTP 404 (Not found).
79 We know it is stupid to only check for explain in default target.
80 It means that it is only possible to offer one SRW/SRU server.
81 We expect to improve that in the next version of the YAZ proxy.
85 <section id="proxy-keepalive">
86 <title>Keep-alive Facility</title>
88 The keep-alive is a facility where the proxy keeps the connection to the
89 backend server - even if the client closes the connection to the proxy.
92 If a new or another client connects to the proxy again and requests the
93 same backend it will be reassigned to this backend. In this case, the
94 proxy sends an initialize response directly to the client and an
95 initialize handshake with the backend is omitted.
98 When a client reconnects, query and record caching works better, if the
99 proxy assigns it to the same backend as before. And the result set
100 (if any) is re-used. To achieve this, Index Data defined a session
101 cookie which identifies the backend session.
104 The cookie is defined by the client and is sent as part of the
105 Initialize Request and passed in an
106 <link linkend="otherinfo-encoding"><literal>otherInfo</literal></link>
107 element with OID <literal>1.2.840.10003.10.1000.81.2</literal>.
110 Clients that do not send a cookie as part of the initialize request
111 may still better performance, since the init handshake is saved.
114 Refer to <xref linkend="proxy-config-keepalive"/> on how to setup
115 configuration parameters for keepalive.
119 <section id="proxy-config-file">
120 <title>Proxy Configuration File</title>
122 The Proxy may read a configuration file using option
123 <literal>-c</literal> followed by the filename of a config file.
126 The config file is XML based. The YAZ proxy must be compiled
127 with <ulink url="http://www.xmlsoft.org/">libxml2</ulink> and
128 <ulink url="http://xmlsoft.org/XSLT/">libXSLT</ulink> support in
129 order for the config file facility to be enabled.
132 See <xref linkend="yazproxy-schema"/> for an XML schema
133 for the configuration.
136 <para>To check for a config file to be well-formed, the yazproxy may
137 be invoked without specifying a listening port, i.e.
139 yazproxy -c myconfig.xml
141 If this does not produce errors, the file is well-formed.
144 <section id="proxy-config-header">
145 <title>Proxy Configuration Header</title>
147 The proxy config file must have a root element called
148 <literal>proxy</literal> and scoped within namespace
149 <literal> xmlns="http://indexdata.dk/yazproxy/schema/0.8/</literal>.
150 All information except an optional XML header must be stored
151 within the <literal>proxy</literal> element.
154 <?xml version="1.0"?>
155 <proxy xmlns="http://indexdata.dk/yazproxy/schema/0.8/">
156 <!-- content here .. -->
160 <section id="proxy-config-target">
161 <title>target</title>
163 The element <literal>target</literal> which may be repeated zero
164 or more times with parent element <literal>proxy</literal> contains
165 information about each backend target.
166 The <literal>target</literal> element have two attributes:
167 <literal>name</literal> which holds the logical name of the backend
168 target (required) and <literal>default</literal> (optional) which
169 (when given) specifies that the backend target is the default target -
170 equivalent to command line option <literal>-t</literal>.
174 <?xml version="1.0"?>
175 <proxy xmlns="http://indexdata.dk/yazproxy/schema/0.8/">
176 <target name="server1" default="1">
177 <!-- description of server1 .. -->
179 <target name="server2">
180 <!-- description of server2 .. -->
186 <section id="proxy-config-url">
189 The <literal>url</literal> which may be repeated one or more times
190 should be the child of the <literal>target</literal> element.
191 The CDATA of <literal>url</literal> is the Z-URL of the backend.
194 Multiple <literal>url</literal> element may be used. In that case, then
195 a client initiates a session, the proxy chooses the URL with the lowest
196 number of active sessions, thereby distributing the load. It is
197 assumed that each URL represents the same database (data).
201 <section id="proxy-config-target-timeout">
202 <title>target-timeout</title>
204 The element <literal>target-timeout</literal> is the child of element
205 <literal>target</literal> and specifies the amount in seconds before
206 a target session is shut down.
209 This can also be specified on the command line by using option
210 <literal>-T</literal>. Refer to OPTIONS.
214 <section id="proxy-config-client-timeout">
215 <title>client-timeout</title>
217 The element <literal>client-timeout</literal> is the child of element
218 <literal>target</literal> and specifies the amount in seconds before
219 a client session is shut down.
222 This can also be specified on the command line by using option
223 <literal>-i</literal>. Refer to OPTIONS.
227 <section id="proxy-config-keepalive">
228 <title>keepalive</title>
229 <para>The <literal>keepalive</literal> element holds information about
230 the keepalive Z39.50 sessions. Keepalive sessions are proxy-to-backend
231 sessions that is no longer associated with a client session.
233 <para>The <literal>keepalive</literal> element which is the child of
234 the <literal>target</literal>holds two elements:
235 <literal>bandwidth</literal> and <literal>pdu</literal>.
236 The <literal>bandwidth</literal> is the maximum total bytes
237 transferred to/from the target. If a target session exceeds this
238 limit, it is shut down (and no longer kept alive).
239 The <literal>pdu</literal> is the maximum number of requests sent
240 to the target. If a target session exceeds this limit, it is
241 shut down. The idea of these two limits is that avoid very long
242 sessions that use resources in a backend (that leaks!).
245 The following sets maximum number of bytes transferred in a
246 target session to 1 MB and maxinum of requests to 400.
249 <bandwidth>1048576</bandwidth>
250 <retrieve>400</retrieve>
255 <section id="proxy-config-limit">
258 The <literal>limit</literal> section specifies bandwidth/pdu requests
259 limits for an active session.
260 The proxy records bandwidth/pdu requests during the last 60 seconds
261 (1 minute). The <literal>limit</literal> may include the
262 elements <literal>bandwidth</literal>, <literal>pdu</literal>,
263 and <literal>retrieve</literal>. The <literal>bandwidth</literal>
264 measures the number of bytes transferred within the last minute.
265 The <literal>pdu</literal> is the number of requests in the last
266 minute. The <literal>retrieve</literal> holds the maximum records to
267 be retrieved in one Present Request.
270 If a bandwidth/pdu limit is reached the proxy will postpone the
271 requests to the target and wait one or more seconds. The idea of the
272 limit is to ensure that clients that downloads hundreds or thousands of
273 records do not hurt other users.
276 The following sets maximum number of bytes transferred per minute to
277 500Kbytes and maximum number of requests to 40.
280 <bandwidth>524288</bandwidth>
281 <retrieve>40</retrieve>
287 Typically the limits for keepalive are much higher than
288 those for session minute average.
293 <section id="proxy-config-attribute">
294 <title>attribute</title>
296 The <literal>attribute</literal> element specifies accept or reject
297 or a particular attribute type, value pair.
298 Well-behaving targets will reject unsupported attributes on their
299 own. This feature is useful for targets that do not gracefully
300 handle unsupported attributes.
303 Attribute elements may be repeated. The proxy inspects the attribute
304 specifications in the order as specified in the configuration file.
305 When a given attribute specification matches a given attribute list
306 in a query, the proxy takes appropriate action (reject, accept).
309 If no attribute specifications matches the attribute list in a query,
313 The <literal>attribute</literal> element has two required attributes:
314 <literal>type</literal> which is the Attribute Type-1 type, and
315 <literal>value</literal> which is the Attribute Type-1 value.
316 The special value/type <literal>*</literal> matches any attribute
317 type/value. A value may also be specified as a list with each
318 value separated by comma, a value may also be specified as a
319 list: low value - dash - high value.
322 If attribute <literal>error</literal> is given, that holds a
323 Bib-1 diagnostic which is sent to the client if the particular
324 type, value is part of a query.
327 If attribute <literal>error</literal> is not given, the attribute
328 type, value is accepted and passed to the backend target.
331 A target that supports use attributes 1,4, 1000 through 1003 and
332 no other use attributes, could use the following rules:
334 <attribute type="1" value="1,4,1000-1003">
335 <attribute type="1" value="*" error="114"/>
339 <section id="proxy-config-syntax">
340 <title>syntax</title>
342 The <literal>syntax</literal> element specifies accept or reject
343 or a particular record syntax request from the client.
346 The <literal>syntax</literal> has one required attribute:
347 <literal>type</literal> which is the Preferred Record Syntax.
350 If attribute <literal>error</literal> is given, that holds a
351 Bib-1 diagnostic which is sent to the client if the particular
352 record syntax is part of a present - or search request.
355 If attribute <literal>error</literal> is not given, the record syntax
356 is accepted and passed to the backend target.
359 If attribute <literal>marcxml</literal> is given, the proxy will
360 perform MARC21 to MARCXML conversion. In this case the
361 <literal>type</literal> should be XML. The proxy will use
362 preferred record syntax USMARC/MARC21 against the backend target.
365 If attribute <literal>stylesheet</literal> is given, the proxy
366 will convert XML record from server via XSLT. It is important
367 that the content from server is XML. If used in conjunction with
368 attribute <literal>marcxml</literal> the MARC to MARCXML conversion
369 takes place before the XSLT conversion takes place.
372 If attribute <literal>identifier</literal> is given that is the
373 SRW/SRU record schema identifier for the resulting output record (after
374 MARCXML and/or XSLT conversion).
377 If sub element <literal>title</literal> is given (as child element
378 of <literal>syntax</literal>, then that is the official SRW/SRU
379 name of the resulting record schema.
382 If sub element <literal>name</literal> is given that is an alias
383 for the record schema identifier. Multiple <literal>name</literal>s
387 <title>MARCXML conversion</title>
388 <para>To accept USMARC and offer MARCXML XML plus Dublin Core (via
389 XSLT conversion) but the following configuration could be used:
392 <target name="mytarget">
394 <syntax type="usmarc"/>
395 <syntax type="xml" marcxml="1"
396 identifier="info:srw/schema/1/marcxml-v1.1"
397 <title>MARCXML<title>
398 <name>marcxml<name>
400 <syntax type="xml" marcxml="1" stylesheet="MARC21slim2SRWDC.xsl"
401 identifier="info:srw/schema/1/dc-v1.1">
402 <title>Dublin Core<title>
405 <syntax type="*" error="238"/>
415 <section id="proxy-config-explain">
416 <title>explain</title>
418 The <literal>explain</literal> element includes Explain information
419 for SRW/SRU about the server in the target section. This
420 information must have a <literal>serverInfo</literal> element
421 with a database that this target must be available as (URL path).
424 <explain xmlns="http://explain.z3950.org/dtd/2.0/">
426 <host>myhost.org</host>
428 <database>mydatabase</database>
430 <!-- remaining Explain stuff -->
434 In the above case, the SRW/SRU service is available as
435 <literal>http://myhost.org:8000/mydatabase</literal>.
440 <section id="proxy-config-cql2rpn">
441 <title>cql2rpn</title>
443 The CDATA of <literal>cql2rpn</literal> refers to CQL to a RPN conversion
444 file - for the server in the target section. This element
445 is required for SRW/SRU searches to operate against a Z39.50
446 server that doesn't support CQL. Most Z39.50 servers only support
447 Type-1/RPN so this is usually required.
448 See YAZ documentation for more information about the
449 <ulink url="http://indexdata.dk/yaz/doc/tools.tkl#tools.cql.pqf">CQL
450 to PQF</ulink> conversion. See also the
451 <filename>pqf.properties</filename> in the <filename>etc</filename>
452 (or <replaceable>prefix/share/yazproxy</replaceable>)
453 directory of the YAZ proxy.
457 <section id="proxy-config-preinit">
458 <title>preinit</title>
460 The element <literal>preinit</literal> is the child of element
461 <literal>target</literal> and specifies the number of spare
462 connection to a target. By default no spare connection are
463 created by the proxy. If the proxy uses a target exclusive or
464 a lot, the preinit session will ensure that target sessions
465 have been made before the client makes a connection and will therefore
466 reduce the connect-init handshake dramatically. Never set this to
471 <section id="proxy-config-max-clients">
472 <title>max-clients</title>
474 The element <literal>max-clients</literal> is the child of element
475 <literal>proxy</literal> and specifies the total number of
476 allowed connections to targets (all targets). If this limit
477 is reached the proxy will close the least recently used connection.
480 Note, that many Unix systems impose a system on the number of
481 open files allowed in a single process, typically in the
482 range 256 (Solaris) to 1024 (Linux).
483 The proxy uses 2 sockets per session + a few files
484 for logging. As a rule of thumb, ensure that 2*max-clients + 5
485 can be opened by the proxy process.
489 Using the <ulink url="http://www.gnu.org/software/bash/bash.html">
490 bash</ulink> shell, you can set the limit with
491 <literal>ulimit -n</literal><replaceable>no</replaceable>.
492 Use <literal>ulimit -a</literal> to display limits.
497 <section id="proxy-config-log">
500 The element <literal>log</literal> is the child of element
501 <literal>proxy</literal> and specifies what to be logged by the
505 Specify the log file with command-line option <literal>-l</literal>.
508 The text of the <literal>log</literal> element is a sequence of
509 options separated by white space. See the table below:
510 <table frame="top"><title>Logging options</title>
512 <colspec colwidth="1*"/>
513 <colspec colwidth="2*"/><thead>
515 <entry>Option</entry>
516 <entry>Description</entry>
521 <entry><literal>client-apdu</literal></entry>
523 Log APDUs as reported by YAZ for the
524 communication between the client and the proxy.
525 This facility is equivalent to the APDU logging that
526 happens when using option <literal>-a</literal>, however
527 this tells the proxy to log in the same file as given
528 by <literal>-l</literal>.
532 <entry><literal>server-apdu</literal></entry>
534 Log APDUs as reported by YAZ for the
535 communication between the proxy and the server (backend).
539 <entry><literal>clients-requests</literal></entry>
541 Log a brief description about requests transferred between
542 the client and the proxy. The name of the request and the size
543 of the APDU is logged.
547 <entry><literal>server-requests</literal></entry>
549 Log a brief description about requests transferred between
550 the proxy and the server (backend). The name of the request
551 and the size of the APDU is logged.
559 To log communication in details between the proxy and the backend, th
560 following configuration could be used:
562 <target name="mytarget">
563 <log>server-apdu server-requests</log>
571 <section id="query-cache">
572 <title>Query Caching</title>
574 Simple stateless clients often send identical Z39.50 searches
575 in a relatively short period of time (e.g. in order to produce a
576 results-list page, the next page,
577 a single full-record, etc). And for many targets, it's
578 much more expensive to produce a new result set than to
579 reuse an existing one.
582 The proxy tries to solve that by remembering the last query for each
583 backend target, so that if an identical query is received next, it
584 is turned into Present Requests rather than new Search Requests.
588 In a future we release will will probably allows for
589 an arbitrary-sized cache for targets supporting named result sets.
593 You can enable/disable query caching using option -o.
597 <section id="record-cache">
598 <title>Record Caching</title>
600 As an option, the proxy may also cache result set records for the
602 The proxy takes into account the Record Syntax and CompSpec.
603 The CompSpec includes simple element set names as well.
604 By default the cache is 200000 bytes per session.
608 <section id="query-validation">
609 <title>Query Validation</title>
611 The Proxy may also be configured to trap particular attributes in
612 Type-1 queries and send Bib-1 diagnostics back to the client without
613 even consulting the backend target. This facility may be useful if
614 a target does not properly issue diagnostics when unsupported attributes
619 <section id="record-validation">
620 <title>Record Syntax Validation</title>
622 The proxy may be configured to accept, reject or convert records.
623 When accepted, the target passes search/present requests to the
624 backend target under the assumption that the target can honor the
625 request (In fact it may not do that). When a record is rejected because
626 the record syntax is "unsupported" the proxy returns a diagnostic to the
627 client. Finally, the proxy may convert records.
630 The proxy can convert from MARC to MARCXML and thereby offer an
631 XML version of any MARC record as long as it is ISO2709 encoded.
632 If the proxy is compiled with libXSLT support it can also
637 <section id="other-optimizations">
638 <title>Other Optimizations</title>
640 We've had some plans to support global caching of result set records,
641 but this has not yet been implemented.
645 <section id="proxy-usage">
646 <title>Proxy Usage (man page)</title>
647 <refentry id="yazproxy-man">
652 <section id="otherinfo-encoding">
653 <title>OtherInformation Encoding</title>
655 The proxy uses the OtherInformation definition to carry
656 information about the target address and cookie.
659 OtherInformation ::= [201] IMPLICIT SEQUENCE OF SEQUENCE{
660 category [1] IMPLICIT InfoCategory OPTIONAL,
662 characterInfo [2] IMPLICIT InternationalString,
663 binaryInfo [3] IMPLICIT OCTET STRING,
664 externallyDefinedInfo [4] IMPLICIT EXTERNAL,
665 oid [5] IMPLICIT OBJECT IDENTIFIER}}
667 InfoCategory ::= SEQUENCE{
668 categoryTypeId [1] IMPLICIT OBJECT IDENTIFIER OPTIONAL,
669 categoryValue [2] IMPLICIT INTEGER}
672 The <literal>categoryTypeId</literal> is either
673 OID 1.2.840.10003.10.1000.81.1, 1.2.840.10003.10.1000.81.2
674 for proxy target and proxy cookie respectively. The
675 integer element <literal>category</literal> is set to 0.
676 The value proxy and cookie is stored in element
677 <literal>characterInfo</literal> of the <literal>information</literal>
681 <section id="yazproxy-schema">
682 <title>YAZ Proxy Configuration Schema</title>
684 Here an XML Schema for the YAZ proxy configuration file.
685 The schema, <filename>yazproxy.xsd</filename> is located in sub
686 directory <filename>etc</filename> of the distribution.
689 <?xml version="1.0"?>
690 <!-- XML Schema for YAZ proxy config file.
691 $Id: reference.xml,v 1.3 2004-04-20 23:49:48 adam Exp $
694 xmlns:xs="http://www.w3.org/2001/XMLSchema"
695 xmlns:exp="http://explain.z3950.org/dtd/2.0/"
696 xmlns="http://indexdata.dk/yazproxy/schema/0.8/"
697 targetNamespace="http://indexdata.dk/yazproxy/schema/0.8/"
699 <xs:import namespace="http://explain.z3950.org/dtd/2.0/"
700 schemaLocation="zeerex-2.0.xsd"/>
701 <xs:element name="proxy">
704 <xs:element ref="target" minOccurs="0" maxOccurs="unbounded"/>
705 <xs:element ref="max-clients" minOccurs="0"/>
706 <xs:element ref="log" minOccurs="0"/>
711 <xs:element name="target">
714 <xs:element ref="url" minOccurs="0" maxOccurs="unbounded"/>
715 <xs:element ref="target-timeout" minOccurs="0"/>
716 <xs:element ref="client-timeout" minOccurs="0"/>
717 <xs:element ref="keepalive" minOccurs="0"/>
718 <xs:element ref="limit" minOccurs="0"/>
719 <xs:element ref="attribute" minOccurs="0" maxOccurs="unbounded"/>
720 <xs:element ref="syntax" minOccurs="0" maxOccurs="unbounded"/>
721 <xs:element ref="preinit" minOccurs="0"/>
722 <xs:element name="exp:explain" minOccurs="0"/>
723 <xs:element ref="cql2rpn" minOccurs="0"/>
725 <xs:attribute name="default" type="xs:string" use="optional"/>
726 <xs:attribute name="name" type="xs:string"/>
730 <xs:element name="url" type="xs:string"/>
731 <xs:element name="target-timeout" type="xs:integer"/>
732 <xs:element name="client-timeout" type="xs:integer"/>
733 <xs:element name="bandwidth" type="xs:integer"/>
734 <xs:element name="pdu" type="xs:integer"/>
735 <xs:element name="retrieve" type="xs:integer"/>
736 <xs:element name="preinit" type="xs:integer"/>
737 <xs:element name="cql2rpn" type="xs:string"/>
739 <xs:element name="keepalive">
742 <xs:element ref="bandwidth" minOccurs="0"/>
743 <xs:element ref="pdu" minOccurs="0"/>
747 <xs:element name="limit">
750 <xs:element ref="bandwidth" minOccurs="0"/>
751 <xs:element ref="pdu" minOccurs="0"/>
752 <xs:element ref="retrieve" minOccurs="0"/>
757 <xs:element name="attribute">
759 <xs:attribute name="type" type="xs:string"/>
760 <xs:attribute name="value" type="xs:string"/>
761 <xs:attribute name="error" type="xs:integer"/>
765 <xs:element name="syntax">
768 <xs:element name="title" type="xs:string" minOccurs="0"/>
769 <xs:element name="name" type="xs:string" minOccurs="0"
770 maxOccurs="unbounded"/>
772 <xs:attribute name="error" type="xs:string" minOccurs="0"/>
773 <xs:attribute name="type" type="xs:string" minOccurs="0"/>
774 <xs:attribute name="marcxml" type="xs:string" minOccurs="0"/>
775 <xs:attribute name="identifier" type="xs:string" minOccurs="0"/>
776 <xs:attribute name="stylesheet" type="xs:string" minOccurs="0"/>
780 <xs:element name="max-clients" type="xs:integer"/>
781 <xs:element name="log" type="xs:string"/>
790 <!-- Keep this comment at the end of the file
795 sgml-minimize-attributes:nil
796 sgml-always-quote-attributes:t
799 sgml-parent-document: "yazproxy.xml"
800 sgml-local-catalogs: nil
801 sgml-namecase-general:t