X-Git-Url: http://git.indexdata.com/?a=blobdiff_plain;ds=sidebyside;f=src%2Fyaz-proxy.cpp;h=935e453808203b20c16a58220d3c94bb147e6a1d;hb=2bab0500e690612c044b1d9f87a0f03bc1640743;hp=fa3b4417fdcf51697b1627c351a4836cd906d1ad;hpb=c176a974d0fbd65b6dd10369209eb1ddabf41aa7;p=yazproxy-moved-to-github.git diff --git a/src/yaz-proxy.cpp b/src/yaz-proxy.cpp index fa3b441..935e453 100644 --- a/src/yaz-proxy.cpp +++ b/src/yaz-proxy.cpp @@ -1,4 +1,4 @@ -/* $Id: yaz-proxy.cpp,v 1.12 2004-11-30 21:10:45 adam Exp $ +/* $Id: yaz-proxy.cpp,v 1.14 2004-12-13 20:52:33 adam Exp $ Copyright (c) 1998-2004, Index Data. This file is part of the yaz-proxy. @@ -36,19 +36,12 @@ Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA #include #include #include -#include +#include #include -#include +#include "proxyp.h" #include #include -#if HAVE_XSLT -#include -#include -#include -#include -#endif - static const char *apdu_name(Z_APDU *apdu) { switch (apdu->which) @@ -170,6 +163,9 @@ Yaz_Proxy::Yaz_Proxy(IYaz_PDU_Observable *the_PDU_Observable, #else m_time_tv = 0; #endif + m_usemarcon_ini_stage1 = 0; + m_usemarcon_ini_stage2 = 0; + m_usemarcon = new Yaz_usemarcon(); if (!m_parent) low_socket_open(); } @@ -196,6 +192,9 @@ Yaz_Proxy::~Yaz_Proxy() xfree (m_schema); xfree (m_backend_type); xfree (m_backend_charset); + xfree (m_usemarcon_ini_stage1); + xfree (m_usemarcon_ini_stage2); + delete m_usemarcon; if (m_s2z_odr_init) odr_destroy(m_s2z_odr_init); if (m_s2z_odr_search) @@ -756,6 +755,54 @@ void Yaz_Proxy::convert_to_frontend_type(Z_NamePlusRecordList *p) Z_External *r = npr->u.databaseRecord; if (r->which == Z_External_octet) { +#if HAVE_USEMARCON + if (m_usemarcon_ini_stage1 && *m_usemarcon_ini_stage1) + { + if (!m_usemarcon->m_stage1) + { + m_usemarcon->m_stage1 = new CDetails(); + } + m_usemarcon->m_stage1->SetIniFileName(m_usemarcon_ini_stage1); + m_usemarcon->m_stage1->SetMarcRecord((char*) r->u.octet_aligned->buf, r->u.octet_aligned->len); + int res = m_usemarcon->m_stage1->Start(); + if (res == 0) + { + char *converted; + int convlen; + m_usemarcon->m_stage1->GetMarcRecord(converted, convlen); + if (m_usemarcon_ini_stage2 && *m_usemarcon_ini_stage2) + { + if (!m_usemarcon->m_stage2) + { + m_usemarcon->m_stage2 = new CDetails(); + } + m_usemarcon->m_stage2->SetIniFileName(m_usemarcon_ini_stage2); + m_usemarcon->m_stage2->SetMarcRecord(converted, convlen); + res = m_usemarcon->m_stage2->Start(); + if (res == 0) + { + free(converted); + m_usemarcon->m_stage2->GetMarcRecord(converted, convlen); + } + else + { + yaz_log(YLOG_LOG, "%sUSEMARCON stage 2 error %d", m_session_str, res); + } + } + npr->u.databaseRecord = + z_ext_record(odr_encode(), + m_frontend_type, + converted, + strlen(converted)); + free(converted); + } + else + { + yaz_log(YLOG_LOG, "%sUSEMARCON stage 1 error %d", m_session_str, res); + } + continue; + } +#endif npr->u.databaseRecord = z_ext_record(odr_encode(), m_frontend_type, @@ -1107,7 +1154,11 @@ int Yaz_Proxy::send_to_client(Z_APDU *apdu) { if (p && p->which == Z_Records_DBOSD) { - if (m_backend_type) + if (m_backend_type +#if HAVE_USEMARCON + || m_usemarcon_ini_stage1 || m_usemarcon_ini_stage2 +#endif + ) convert_to_frontend_type(p->u.databaseOrSurDiagnostics); if (m_marcxml_flag) convert_to_marcxml(p->u.databaseOrSurDiagnostics, @@ -1148,7 +1199,11 @@ int Yaz_Proxy::send_to_client(Z_APDU *apdu) } if (p && p->which == Z_Records_DBOSD) { - if (m_backend_type) + if (m_backend_type +#if HAVE_USEMARCON + || m_usemarcon_ini_stage1 || m_usemarcon_ini_stage2 +#endif + ) convert_to_frontend_type(p->u.databaseOrSurDiagnostics); if (m_marcxml_flag) convert_to_marcxml(p->u.databaseOrSurDiagnostics, @@ -1505,6 +1560,7 @@ void Yaz_Proxy::recv_GDU(Z_GDU *apdu, int len) reduce = (reduce > nreduce) ? reduce : nreduce; } } + m_http_version = 0; if (reduce) { yaz_log(YLOG_LOG, "%sdelay=%d bw=%d pdu=%d limit-bw=%d limit-pdu=%d", @@ -1664,7 +1720,9 @@ Z_APDU *Yaz_Proxy::handle_syntax_validation(Z_APDU *apdu) m_default_target, sr->preferredRecordSyntax, rc, &addinfo, &stylesheet_name, &m_schema, - &m_backend_type, &m_backend_charset); + &m_backend_type, &m_backend_charset, + &m_usemarcon_ini_stage1, + &m_usemarcon_ini_stage2); if (stylesheet_name) { m_parent->low_socket_close(); @@ -1738,7 +1796,10 @@ Z_APDU *Yaz_Proxy::handle_syntax_validation(Z_APDU *apdu) pr->preferredRecordSyntax, pr->recordComposition, &addinfo, &stylesheet_name, &m_schema, - &m_backend_type, &m_backend_charset); + &m_backend_type, &m_backend_charset, + &m_usemarcon_ini_stage1, + &m_usemarcon_ini_stage2 + ); if (stylesheet_name) { m_parent->low_socket_close(); @@ -1822,6 +1883,70 @@ void Yaz_Proxy::srw_get_client(const char *db, const char **backend_db) m_default_target = xstrdup(t); } } + +int Yaz_Proxy::file_access(Z_HTTP_Request *hreq) +{ + yaz_log(YLOG_LOG, "file_access"); + if (strcmp(hreq->method, "GET")) + return 0; + struct stat sbuf; + if (hreq->path[0] != '/') + { + yaz_log(YLOG_WARN, "Path != /"); + return 0; + } + const char *cp = hreq->path; + while (*cp) + { + if (*cp == '/' && strchr("/.", cp[1])) + return 0; + cp++; + } + const char *fname = hreq->path+1; + if (stat(fname, &sbuf)) + { + yaz_log(YLOG_WARN, "stat %s failed", fname); + return 0; + } + if ((sbuf.st_mode & S_IFMT) != S_IFREG) + return 0; + if (sbuf.st_size > (off_t) 1000000) + return 0; + + ODR o = odr_encode(); + Yaz_ProxyConfig *cfg = check_reconfigure(); + const char *ctype = cfg->check_mime_type(fname); + Z_GDU *gdu = z_get_HTTP_Response(o, 200); + Z_HTTP_Response *hres = gdu->u.HTTP_Response; + if (m_http_version) + hres->version = odr_strdup(o, m_http_version); + z_HTTP_header_add(o, &hres->headers, "Content-Type", ctype); + if (m_http_keepalive) + z_HTTP_header_add(o, &hres->headers, "Connection", "Keep-Alive"); + else + timeout(0); + + hres->content_len = sbuf.st_size; + hres->content_buf = (char*) odr_malloc(o, hres->content_len); + FILE *f = fopen(fname, "rb"); + if (f) + { + fread(hres->content_buf, 1, hres->content_len, f); + fclose(f); + } + else + { + return 0; + } + if (m_log_mask & PROXY_LOG_REQ_CLIENT) + { + yaz_log (YLOG_LOG, "%sSending file %s to client", m_session_str, + fname); + } + int len; + send_GDU(gdu, &len); + return 1; +} void Yaz_Proxy::handle_incoming_HTTP(Z_HTTP_Request *hreq) { @@ -1862,10 +1987,15 @@ void Yaz_Proxy::handle_incoming_HTTP(Z_HTTP_Request *hreq) char *charset = 0; Z_SRW_diagnostic *diagnostic = 0; int num_diagnostic = 0; - if (yaz_srw_decode(hreq, &srw_pdu, &soap_package, odr_decode(), - &charset) == 0 - || yaz_sru_decode(hreq, &srw_pdu, &soap_package, odr_decode(), - &charset, &diagnostic, &num_diagnostic) == 0) + + if (file_access(hreq)) + { + return; + } + else if (yaz_srw_decode(hreq, &srw_pdu, &soap_package, odr_decode(), + &charset) == 0 + || yaz_sru_decode(hreq, &srw_pdu, &soap_package, odr_decode(), + &charset, &diagnostic, &num_diagnostic) == 0) { m_s2z_odr_init = odr_createmem(ODR_ENCODE); m_s2z_odr_search = odr_createmem(ODR_ENCODE); @@ -2121,10 +2251,7 @@ void Yaz_Proxy::handle_incoming_HTTP(Z_HTTP_Request *hreq) send_to_srw_client_error(4, 0); } } - int len = 0; - Z_GDU *p = z_get_HTTP_Response(odr_encode(), 400); - timeout(0); - send_GDU(p, &len); + send_http_response(400); } void Yaz_Proxy::handle_incoming_Z_PDU(Z_APDU *apdu) @@ -2156,8 +2283,16 @@ void Yaz_Proxy::handle_incoming_Z_PDU(Z_APDU *apdu) m_client = get_client(apdu, get_cookie(oi), get_proxy(oi)); if (!m_client) { - delete this; - return; + if (m_http_version) + { + send_http_response(404); + return; + } + else + { + delete this; + return; + } } m_client->m_server = this;