Sort by retrieval PAZ-1006
[pazpar2-moved-to-github.git] / src / record.c
1 /* This file is part of Pazpar2.
2    Copyright (C) Index Data
3
4 Pazpar2 is free software; you can redistribute it and/or modify it under
5 the terms of the GNU General Public License as published by the Free
6 Software Foundation; either version 2, or (at your option) any later
7 version.
8
9 Pazpar2 is distributed in the hope that it will be useful, but WITHOUT ANY
10 WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12 for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
17
18 */
19
20 #include <string.h>
21
22 #include <yaz/yaz-util.h>
23 #include <yaz/nmem.h>
24
25 #if HAVE_CONFIG_H
26 #include <config.h>
27 #endif
28
29 #include "pazpar2_config.h"
30 #include "client.h"
31 #include "record.h"
32
33 union data_types * data_types_assign(NMEM nmem,
34                                      union data_types ** data1,
35                                      union data_types data2)
36 {
37     // assert(nmem);
38
39     if (!data1)
40         return 0;
41
42     if (!*data1){
43         if (!nmem)
44             return 0;
45         else
46             *data1  = nmem_malloc(nmem, sizeof(union data_types));
47     }
48
49     **data1 = data2;
50     return *data1;
51 }
52
53
54 struct record * record_create(NMEM nmem, int num_metadata, int num_sortkeys,
55                               struct client *client, int position)
56 {
57     struct record * record = 0;
58     int i = 0;
59     const char *name = client_get_id(client);
60     unsigned h = position;
61
62     // assert(nmem);
63
64     record = nmem_malloc(nmem, sizeof(struct record));
65
66     record->next = 0;
67     record->client = client;
68
69     record->metadata
70         = nmem_malloc(nmem,
71                       sizeof(struct record_metadata*) * num_metadata);
72     for (i = 0; i < num_metadata; i++)
73         record->metadata[i] = 0;
74
75     record->sortkeys
76         = nmem_malloc(nmem,
77                       sizeof(union data_types*) * num_sortkeys);
78     for (i = 0; i < num_sortkeys; i++)
79         record->sortkeys[i] = 0;
80
81     record->position = position;
82
83     for (i = 0; name[i]; i++)
84         h = h * 65509 + ((unsigned char *) name)[i];
85
86     record->checksum = h;
87
88     return record;
89 }
90
91 struct record_metadata * record_metadata_create(NMEM nmem)
92 {
93     struct record_metadata * rec_md
94         = nmem_malloc(nmem, sizeof(struct record_metadata));
95     rec_md->next = 0;
96     rec_md->attributes = 0;
97     return rec_md;
98 }
99
100
101 int record_compare(struct record *r1, struct record *r2,
102                    struct conf_service *service)
103 {
104     int i;
105     for (i = 0; i < service->num_metadata; i++)
106     {
107         struct conf_metadata *ser_md = &service->metadata[i];
108         enum conf_metadata_type type = ser_md->type;
109
110         struct record_metadata *m1 = r1->metadata[i];
111         struct record_metadata *m2 = r2->metadata[i];
112         while (m1 && m2)
113         {
114             switch (type)
115             {
116             case Metadata_type_generic:
117             case Metadata_type_skiparticle:
118                 if (strcmp(m1->data.text.disp, m2->data.text.disp))
119                     return 0;
120                 break;
121             case Metadata_type_date:
122             case Metadata_type_year:
123                 if (m1->data.number.min != m2->data.number.min ||
124                     m1->data.number.max != m2->data.number.max)
125                     return 0;
126                 break;
127             case Metadata_type_float:
128                 if (m1->data.fnumber != m2->data.fnumber)
129                     return 0;
130             case Metadata_type_position:
131             case Metadata_type_relevance:
132             case Metadata_type_retrieval:
133                 break;
134             }
135             m1 = m1->next;
136             m2 = m2->next;
137         }
138         if (m1 || m2)
139             return 0;
140     }
141     return 1;
142 }
143
144 /*
145  * Local variables:
146  * c-basic-offset: 4
147  * c-file-style: "Stroustrup"
148  * indent-tabs-mode: nil
149  * End:
150  * vim: shiftwidth=4 tabstop=8 expandtab
151  */
152