/** \brief COMSTACK synopsis from manual, doc/comstack.xml */ static int comstack_example(const char *server_address_str) { COMSTACK stack; char *buf = 0; int size = 0, length_incoming; void *server_address_ip; int status; char *protocol_package = "GET / HTTP/1.0\r\n\r\n"; int protocol_package_length = strlen(protocol_package); stack = cs_create(tcpip_type, 1, PROTO_HTTP); if (!stack) { perror("cs_create"); /* use perror() here since we have no stack yet */ return -1; } server_address_ip = cs_straddr(stack, server_address_str); if (!server_address_ip) { fprintf(stderr, "cs_straddr: address could not be resolved\n"); return -1; } status = cs_connect(stack, server_address_ip); if (status) { fprintf(stderr, "cs_connect: %s\n", cs_strerror(stack)); return -1; } status = cs_rcvconnect(stack); if (status) { fprintf(stderr, "cs_rcvconnect: %s\n", cs_strerror(stack)); return -1; } status = cs_put(stack, protocol_package, protocol_package_length); if (status) { fprintf(stderr, "cs_put: %s\n", cs_strerror(stack)); return -1; } /* Now get a response */ length_incoming = cs_get(stack, &buf, &size); if (!length_incoming) { fprintf(stderr, "Connection closed\n"); return -1; } else if (length_incoming < 0) { fprintf(stderr, "cs_get: %s\n", cs_strerror(stack)); return -1; } /* Print result */ fwrite(buf, length_incoming, 1, stdout); /* clean up */ cs_close(stack); if (buf) xfree(buf); return 0; }
Z_HTTP_Response *yaz_url_exec(yaz_url_t p, const char *uri, const char *method, Z_HTTP_Header *user_headers, const char *buf, size_t len) { Z_HTTP_Response *res = 0; int number_of_redirects = 0; yaz_cookies_reset(p->cookies); wrbuf_rewind(p->w_error); while (1) { void *add; COMSTACK conn = 0; int code; const char *location = 0; char *http_user = 0; char *http_pass = 0; char *uri_lean = 0; Z_GDU *gdu; extract_user_pass(p->odr_out->mem, uri, &uri_lean, &http_user, &http_pass); gdu = z_get_HTTP_Request_uri(p->odr_out, uri_lean, 0, p->proxy ? 1 : 0); gdu->u.HTTP_Request->method = odr_strdup(p->odr_out, method); yaz_cookies_request(p->cookies, p->odr_out, gdu->u.HTTP_Request); for ( ; user_headers; user_headers = user_headers->next) { /* prefer new Host over user-supplied Host */ if (!strcmp(user_headers->name, "Host")) ; /* prefer user-supplied User-Agent over YAZ' own */ else if (!strcmp(user_headers->name, "User-Agent")) z_HTTP_header_set(p->odr_out, &gdu->u.HTTP_Request->headers, user_headers->name, user_headers->value); else z_HTTP_header_add(p->odr_out, &gdu->u.HTTP_Request->headers, user_headers->name, user_headers->value); } if (http_user && http_pass) z_HTTP_header_add_basic_auth(p->odr_out, &gdu->u.HTTP_Request->headers, http_user, http_pass); res = 0; if (buf && len) { gdu->u.HTTP_Request->content_buf = (char *) buf; gdu->u.HTTP_Request->content_len = len; } if (!z_GDU(p->odr_out, &gdu, 0, 0)) { wrbuf_printf(p->w_error, "Can not encode HTTP request for URL %s", uri); log_warn(p); return 0; } conn = cs_create_host_proxy(uri_lean, 1, &add, p->proxy); if (!conn) { wrbuf_printf(p->w_error, "Can not resolve URL %s", uri); log_warn(p); } else if (cs_connect(conn, add) < 0) { wrbuf_printf(p->w_error, "Can not connect to URL %s", uri); log_warn(p); } else { int len; char *buf = odr_getbuf(p->odr_out, &len, 0); if (p->verbose) fwrite(buf, 1, len, stdout); if (cs_put(conn, buf, len) < 0) { wrbuf_printf(p->w_error, "cs_put fail for URL %s", uri); log_warn(p); } else { char *netbuffer = 0; int netlen = 0; int cs_res = cs_get(conn, &netbuffer, &netlen); if (cs_res <= 0) { wrbuf_printf(p->w_error, "cs_get failed for URL %s", uri); log_warn(p); } else { Z_GDU *gdu; if (p->verbose) fwrite(netbuffer, 1, cs_res, stdout); odr_setbuf(p->odr_in, netbuffer, cs_res, 0); if (!z_GDU(p->odr_in, &gdu, 0, 0) || gdu->which != Z_GDU_HTTP_Response) { wrbuf_printf(p->w_error, "HTTP decoding fail for " "URL %s", uri); log_warn(p); } else { res = gdu->u.HTTP_Response; } } xfree(netbuffer); } } if (conn) cs_close(conn); if (!res) break; code = res->code; location = z_HTTP_header_lookup(res->headers, "Location"); if (++number_of_redirects <= p->max_redirects && location && (code == 301 || code == 302 || code == 307)) { int host_change = 0; const char *nlocation = yaz_check_location(p->odr_in, uri, location, &host_change); odr_reset(p->odr_out); uri = odr_strdup(p->odr_out, nlocation); } else break; yaz_cookies_response(p->cookies, res); odr_reset(p->odr_in); } return res; }