Added include stdlib.h a few places to get prototype for atoi/exit/..
[idzebra-moved-to-github.git] / index / apitest.c
1 /* $Id: apitest.c,v 1.21 2005-01-16 23:14:57 adam Exp $
2    Copyright (C) 1995-2005
3    Index Data ApS
4
5 This file is part of the Zebra server.
6
7 Zebra is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 2, or (at your option) any later
10 version.
11
12 Zebra is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
15 for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with Zebra; see the file LICENSE.zebra.  If not, write to the
19 Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA
20 02111-1307, USA.
21 */
22
23 #include <stdio.h>
24 #include <stdlib.h>
25
26 #include <yaz/log.h>
27 #include <yaz/pquery.h>
28 #include <idzebra/api.h>
29
30 /* Small routine to display GRS-1 record variants ... */
31 /* Copied verbatim from yaz/client/client.c */
32 static void display_variant(Z_Variant *v, int level)
33 {
34     int i;
35
36     for (i = 0; i < v->num_triples; i++)
37     {
38         printf("%*sclass=%d,type=%d", level * 4, "", *v->triples[i]->zclass,
39             *v->triples[i]->type);
40         if (v->triples[i]->which == Z_Triple_internationalString)
41             printf(",value=%s\n", v->triples[i]->value.internationalString);
42         else
43             printf("\n");
44     }
45 }
46  
47 /* Small routine to display a GRS-1 record ... */
48 /* Copied verbatim from yaz/client/client.c */
49 static void display_grs1(Z_GenericRecord *r, int level)
50 {
51     int i;
52
53     if (!r)
54         return;
55     for (i = 0; i < r->num_elements; i++)
56     {
57         Z_TaggedElement *t;
58
59         printf("%*s", level * 4, "");
60         t = r->elements[i];
61         printf("(");
62         if (t->tagType)
63             printf("%d,", *t->tagType);
64         else
65             printf("?,");
66         if (t->tagValue->which == Z_StringOrNumeric_numeric)
67             printf("%d) ", *t->tagValue->u.numeric);
68         else
69             printf("%s) ", t->tagValue->u.string);
70         if (t->content->which == Z_ElementData_subtree)
71         {
72             printf("\n");
73             display_grs1(t->content->u.subtree, level+1);
74         }
75         else if (t->content->which == Z_ElementData_string)
76             printf("%s\n", t->content->u.string);
77         else if (t->content->which == Z_ElementData_numeric)
78             printf("%d\n", *t->content->u.numeric);
79         else if (t->content->which == Z_ElementData_oid)
80         {
81             int *ip = t->content->u.oid;
82             oident *oent;
83
84             if ((oent = oid_getentbyoid(t->content->u.oid)))
85                 printf("OID: %s\n", oent->desc);
86             else
87             {
88                 printf("{");
89                 while (ip && *ip >= 0)
90                     printf(" %d", *(ip++));
91                 printf(" }\n");
92             }
93         }
94         else if (t->content->which == Z_ElementData_noDataRequested)
95             printf("[No data requested]\n");
96         else if (t->content->which == Z_ElementData_elementEmpty)
97             printf("[Element empty]\n");
98         else if (t->content->which == Z_ElementData_elementNotThere)
99             printf("[Element not there]\n");
100         else
101             printf("??????\n");
102         if (t->appliedVariant)
103             display_variant(t->appliedVariant, level+1);
104         if (t->metaData && t->metaData->supportedVariants)
105         {
106             int c;
107
108             printf("%*s---- variant list\n", (level+1)*4, "");
109             for (c = 0; c < t->metaData->num_supportedVariants; c++)
110             {
111                 printf("%*svariant #%d\n", (level+1)*4, "", c);
112                 display_variant(t->metaData->supportedVariants[c], level + 2);
113             }
114         }
115     }
116 }
117
118 /* Small test main to illustrate the use of the C api */
119 int main (int argc, char **argv)
120 {
121     /* odr is a handle to memory assocated with RETURNED data from
122        various functions */
123     ODR odr_input, odr_output;
124     
125     /* zs is our Zebra Service - decribes whole server */
126     ZebraService zs;
127
128     /* zh is our Zebra Handle - describes database session */
129     ZebraHandle zh;
130     
131     /* the database we specify in our example */
132     const char *base = "Default";
133     int argno;
134
135     nmem_init ();
136
137     yaz_log_init_file("apitest.log");
138
139     odr_input = odr_createmem (ODR_DECODE);    
140     odr_output = odr_createmem (ODR_ENCODE);    
141     
142     zs = zebra_start ("zebra.cfg");
143     if (!zs)
144     {
145         printf ("zebra_start failed; missing zebra.cfg?\n");
146         exit (1);
147     }
148     /* open Zebra */
149     zh = zebra_open (zs);
150     if (!zh)
151     {
152         printf ("zebras_open failed\n");
153         exit (1);
154     }
155     zebra_select_databases (zh, 1, &base);
156     /* Each argument to main will be a query */
157     for (argno = 1; argno < argc; argno++)
158     {
159         /* parse the query and generate an RPN structure */
160         Z_RPNQuery *query = p_query_rpn (odr_input, PROTO_Z3950, argv[argno]);
161         char setname[64];
162         int errCode;
163         int i;
164         int hits;
165         char *errString;
166         ZebraRetrievalRecord *records;
167         int noOfRecordsToFetch;
168
169         /* bad query? */
170         if (!query)
171         {
172             yaz_log (YLOG_WARN, "bad query %s\n", argv[argno]);
173             odr_reset (odr_input);
174             continue;
175         }
176         else
177         {
178             char out_str[100];
179             int r;
180 #if 1
181             r = zebra_string_norm (zh, 'w',
182                                    argv[argno], strlen(argv[argno]),
183                                    out_str, sizeof(out_str));
184             if (r >= 0)
185             {
186                 printf ("norm: '%s'\n", out_str);
187             }
188             else
189             {
190                 printf ("norm fail: %d\n", r);
191             }
192 #endif
193
194         }
195         /* result set name will be called 1,2, etc */
196         sprintf (setname, "%d", argno);
197
198         /* fire up the search */
199         zebra_search_RPN (zh, odr_input, query, setname, &hits);
200         
201         /* status ... */
202         zebra_result (zh, &errCode, &errString);
203         
204         /* error? */
205         if (errCode)
206         {
207             printf ("Zebra Search Error %d %s\n",
208                     errCode, errString);
209             continue;
210         }
211         /* ok ... */
212         printf ("Zebra Search gave %d hits\n", hits);
213         
214         /* Deterimine number of records to fetch ... */
215         if (hits > 10)
216             noOfRecordsToFetch = 10;
217         else
218             noOfRecordsToFetch = hits;
219
220         /* reset our memory - we've finished dealing with search */
221         odr_reset (odr_input);
222         odr_reset (odr_output);
223
224         /* prepare to fetch ... */
225         records = odr_malloc (odr_input, sizeof(*records) * noOfRecordsToFetch);
226         /* specify position of each record to fetch */
227         /* first one is numbered 1 and NOT 0 */
228         for (i = 0; i<noOfRecordsToFetch; i++)
229             records[i].position = i+1;
230         /* fetch them and request for GRS-1 records */
231         zebra_records_retrieve (zh, odr_input, setname, NULL, VAL_SUTRS,
232                                 noOfRecordsToFetch, records);
233
234         /* status ... */
235
236         zebra_result (zh, &errCode, &errString);
237
238         /* error ? */
239         if (errCode)
240         {
241             printf ("Zebra Search Error %d %s\n",
242                     errCode, errString);
243         }
244         else
245         {
246             /* inspect each record in result */
247             for (i = 0; i<noOfRecordsToFetch; i++)
248             {
249                 printf ("Record %d\n", i+1);
250                 /* error when fetching this record? */
251                 if (records[i].errCode)
252                 {
253                     printf ("  Error %d\n", records[i].errCode);
254                     continue;
255                 }
256                 /* GRS-1 record ? */
257                 if (records[i].format == VAL_GRS1)
258                 {
259                     Z_GenericRecord *grs_record =
260                         (Z_GenericRecord *) records[i].buf;
261                     printf ("  GRS-1\n");
262                     display_grs1(grs_record, 0);
263                 }
264                 else if (records[i].format == VAL_SUTRS)
265                 {
266                     printf ("  SUTRS\n");
267                     printf ("%.*s", records[i].len, records[i].buf);
268                 }
269                 /* some other record we don't handle yet... */
270                 else
271                 {
272                     printf ("  Other record (ignored)\n");
273                 }
274             }
275         }
276         /* reset our memory - we've finished dealing with present */
277         odr_reset (odr_input); 
278         odr_reset (odr_output);
279     }
280     odr_destroy (odr_input);
281     odr_destroy (odr_output);
282     zebra_close (zh);
283     zebra_stop (zs);
284     return 0;
285 }