/**
 * soup_message_headers_set_encoding:
 * @hdrs: a #SoupMessageHeaders
 * @encoding: a #SoupEncoding
 *
 * Sets the message body encoding that @hdrs will declare. In particular,
 * you should use this if you are going to send a request or response in
 * chunked encoding.
 **/
void
soup_message_headers_set_encoding (SoupMessageHeaders *hdrs,
				   SoupEncoding        encoding)
{
	if (encoding == hdrs->encoding)
		return;

	switch (encoding) {
	case SOUP_ENCODING_NONE:
	case SOUP_ENCODING_EOF:
		soup_message_headers_remove (hdrs, "Transfer-Encoding");
		soup_message_headers_remove (hdrs, "Content-Length");
		break;

	case SOUP_ENCODING_CONTENT_LENGTH:
		soup_message_headers_remove (hdrs, "Transfer-Encoding");
		break;

	case SOUP_ENCODING_CHUNKED:
		soup_message_headers_remove (hdrs, "Content-Length");
		soup_message_headers_replace (hdrs, "Transfer-Encoding", "chunked");
		break;

	default:
		g_return_if_reached ();
	}

	hdrs->encoding = encoding;
}
/**
 * soup_message_headers_replace:
 * @hdrs: a #SoupMessageHeaders
 * @name: the header name to replace
 * @value: the new value of @name
 *
 * Replaces the value of the header @name in @hdrs with @value. (See
 * also soup_message_headers_append().)
 *
 * The caller is expected to make sure that @name and @value are
 * syntactically correct.
 **/
void
soup_message_headers_replace (SoupMessageHeaders *hdrs,
			      const char *name, const char *value)
{
	soup_message_headers_remove (hdrs, name);
	soup_message_headers_append (hdrs, name, value);
}
示例#3
0
文件: ext-main.c 项目: cdlscpmv/vimb
/**
 * Callback for web pages send-request signal.
 */
static gboolean on_web_page_send_request(WebKitWebPage *webpage, WebKitURIRequest *request,
        WebKitURIResponse *response, gpointer extension)
{
    char *name, *value;
    SoupMessageHeaders *headers;
    GHashTableIter iter;

    if (!ext.headers) {
        return FALSE;
    }

    /* Change request headers according to the users preferences. */
    headers = webkit_uri_request_get_http_headers(request);
    if (!headers) {
        return FALSE;
    }

    g_hash_table_iter_init(&iter, ext.headers);
    while (g_hash_table_iter_next(&iter, (gpointer*)&name, (gpointer*)&value)) {
        /* Null value is used to indicate that the header should be
         * removed completely. */
        if (value == NULL) {
            soup_message_headers_remove(headers, name);
        } else {
            soup_message_headers_replace(headers, name, value);
        }
    }

    return FALSE;
}
示例#4
0
static gboolean
soup_input_stream_seek (GSeekable     *seekable,
			goffset        offset,
			GSeekType      type,
			GCancellable  *cancellable,
			GError       **error)
{
  GInputStream *stream = G_INPUT_STREAM (seekable);
  SoupInputStreamPrivate *priv = SOUP_INPUT_STREAM_GET_PRIVATE (seekable);
  char *range;

  if (type == G_SEEK_END)
    {
      /* FIXME: we could send "bytes=-offset", but unless we know the
       * Content-Length, we wouldn't be able to answer a tell() properly.
       * We could find the Content-Length by doing a HEAD...
       */

      g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
	                   "G_SEEK_END not currently supported");
      return FALSE;
    }

  if (!g_input_stream_set_pending (stream, error))
      return FALSE;

  soup_session_cancel_message (priv->session, priv->msg, SOUP_STATUS_CANCELLED);
  soup_message_io_cleanup (priv->msg);

  switch (type)
    {
    case G_SEEK_CUR:
      offset += priv->offset;
      /* fall through */

    case G_SEEK_SET:
      range = g_strdup_printf ("bytes=%"G_GUINT64_FORMAT"-", (guint64)offset);
      priv->offset = offset;
      break;

    case G_SEEK_END:
      range = NULL; /* keep compilers happy */
      g_return_val_if_reached (FALSE);
      break;

    default:
      g_return_val_if_reached (FALSE);
    }

  soup_message_headers_remove (priv->msg->request_headers, "Range");
  soup_message_headers_append (priv->msg->request_headers, "Range", range);
  g_free (range);

  soup_input_stream_queue_message (SOUP_INPUT_STREAM (stream));

  g_input_stream_clear_pending (stream);
  return TRUE;
}
示例#5
0
static void
disappear_request_read (SoupServer *server, SoupMessage *msg,
			SoupClientContext *context, gpointer user_data)
{
	/* Remove the WWW-Authenticate header if this was a failed attempt */
	if (soup_message_headers_get_one (msg->request_headers, "Authorization") &&
	    msg->status_code == SOUP_STATUS_UNAUTHORIZED)
		soup_message_headers_remove (msg->response_headers, "WWW-Authenticate");
}
示例#6
0
static void
server_callback (SoupServer *server, SoupMessage *msg,
		 const char *path, GHashTable *query,
		 SoupClientContext *context, gpointer data)
{
	SoupMessage *msg2;
	char *uristr;

	uristr = soup_uri_to_string (soup_message_get_uri (msg), FALSE);
	printf ("[%p] %s %s HTTP/1.%d\n", msg, msg->method, uristr,
		soup_message_get_http_version (msg));

	if (msg->method == SOUP_METHOD_CONNECT) {
		soup_message_set_status (msg, SOUP_STATUS_NOT_IMPLEMENTED);
		return;
	}

	msg2 = soup_message_new (msg->method, uristr);
        msg2 = soup_message_new (msg->method, uristr);
	soup_message_headers_foreach (msg->request_headers, copy_header,
				      msg2->request_headers);
	soup_message_headers_remove (msg2->request_headers, "Host");
	soup_message_headers_remove (msg2->request_headers, "Connection");

	if (msg->request_body->length) {
		SoupBuffer *request = soup_message_body_flatten (msg->request_body);
		soup_message_body_append_buffer (msg2->request_body, request);
		soup_buffer_free (request);
	}
	soup_message_headers_set_encoding (msg->response_headers,
					   SOUP_ENCODING_CHUNKED);

	g_signal_connect (msg2, "got_headers",
			  G_CALLBACK (send_headers), msg);
	g_signal_connect (msg2, "got_chunk",
			  G_CALLBACK (send_chunk), msg);

	g_signal_connect (msg, "finished", G_CALLBACK (client_msg_failed), msg2);

	soup_session_queue_message (session, msg2, finish_msg, msg);

	g_object_ref (msg);
	soup_server_pause_message (server, msg);
}
/**
 * soup_message_headers_set_content_length:
 * @hdrs: a #SoupMessageHeaders
 * @content_length: the message body length
 *
 * Sets the message body length that @hdrs will declare, and sets
 * @hdrs's encoding to %SOUP_ENCODING_CONTENT_LENGTH.
 *
 * You do not normally need to call this; if @hdrs is set to use
 * Content-Length encoding, libsoup will automatically set its
 * Content-Length header for you immediately before sending the
 * headers. One situation in which this method is useful is when
 * generating the response to a HEAD request; Calling
 * soup_message_headers_set_content_length() allows you to put the
 * correct content length into the response without needing to waste
 * memory by filling in a response body which won't actually be sent.
 **/
void
soup_message_headers_set_content_length (SoupMessageHeaders *hdrs,
					 goffset             content_length)
{
	char length[128];

	snprintf (length, sizeof (length), "%" G_GUINT64_FORMAT,
		  content_length);
	soup_message_headers_remove (hdrs, "Transfer-Encoding");
	soup_message_headers_replace (hdrs, "Content-Length", length);
}
/**
 * soup_message_headers_set_expectations:
 * @hdrs: a #SoupMessageHeaders
 * @expectations: the expectations to set
 *
 * Sets @hdrs's "Expect" header according to @expectations.
 *
 * Currently %SOUP_EXPECTATION_CONTINUE is the only known expectation
 * value. You should set this value on a request if you are sending a
 * large message body (eg, via POST or PUT), and want to give the
 * server a chance to reject the request after seeing just the headers
 * (eg, because it will require authentication before allowing you to
 * post, or because you're POSTing to a URL that doesn't exist). This
 * saves you from having to transmit the large request body when the
 * server is just going to ignore it anyway.
 **/
void
soup_message_headers_set_expectations (SoupMessageHeaders *hdrs,
				       SoupExpectation     expectations)
{
	g_return_if_fail ((expectations & ~SOUP_EXPECTATION_CONTINUE) == 0);

	if (expectations & SOUP_EXPECTATION_CONTINUE)
		soup_message_headers_replace (hdrs, "Expect", "100-continue");
	else
		soup_message_headers_remove (hdrs, "Expect");
}
示例#9
0
文件: surf.c 项目: bobrippling/bin
void
newrequest(SoupSession *s, SoupMessage *msg, gpointer v) {
	SoupMessageHeaders *h = msg->request_headers;
	SoupURI *uri;
	const char *c;

	soup_message_headers_remove(h, "Cookie");
	uri = soup_message_get_uri(msg);
	if((c = getcookies(uri)))
		soup_message_headers_append(h, "Cookie", c);
	g_signal_connect_after(G_OBJECT(msg), "got-headers", G_CALLBACK(gotheaders), NULL);
}
示例#10
0
static void
send_headers (SoupMessage *from, SoupMessage *to)
{
	g_print ("[%p] HTTP/1.%d %d %s\n", to,
		 soup_message_get_http_version (from),
		 from->status_code, from->reason_phrase);

	soup_message_set_status_full (to, from->status_code,
				      from->reason_phrase);
	soup_message_headers_foreach (from->response_headers, copy_header,
				      to->response_headers);
	soup_message_headers_remove (to->response_headers, "Content-Length");
	soup_server_unpause_message (server, to);
}
示例#11
0
void trex_callback(SoupServer *server, SoupMessage *msg,
	const char *path, GHashTable *query, const char *dest)
{
	SoupMessage *new_msg;
	SoupSession *session;
	char *uri_str;

	struct destination_info *to = malloc(sizeof(struct destination_info));
	to->server = server;
	to->msg = msg;

	session = soup_session_async_new();

	uri_str = soup_uri_to_string(soup_message_get_uri(msg), true);
	/*
	 * TODO Memory Leak :-)
	*/
	uri_str = g_strjoin(NULL, dest, uri_str, NULL);

	g_print("[%p] %s %s HTTP/1.%d\n", msg, msg->method, uri_str,
		soup_message_get_http_version(msg));

	/* build new request */
	new_msg = soup_message_new(msg->method, uri_str);
	soup_message_headers_foreach(msg->request_headers, copy_header,
		new_msg->request_headers);
	soup_message_headers_remove(new_msg->request_headers, "Host");
	if (msg->request_body->length) {
		SoupBuffer *request =
			soup_message_body_flatten(msg->request_body);
		soup_message_body_append_buffer(new_msg->request_body,
			request);
		soup_buffer_free(request);
	}
	soup_message_headers_set_encoding(msg->response_headers,
		SOUP_ENCODING_CHUNKED);

	soup_server_pause_message(server, msg);

	g_signal_connect(new_msg, "got_headers",
		G_CALLBACK(recv_headers), to);
	g_signal_connect(new_msg, "got_chunk",
		G_CALLBACK(recv_chunk), to);

	soup_session_queue_message(session, new_msg, finish_msg, to);

	g_object_ref(msg);

	g_object_unref(session);
}
/**
 * soup_message_headers_clean_connection_headers:
 * @hdrs: a #SoupMessageHeaders
 *
 * Removes all the headers listed in the Connection header.
 *
 * Since: 2.36
 */
void
soup_message_headers_clean_connection_headers (SoupMessageHeaders *hdrs)
{
	/* RFC 2616 14.10 */
	const char *connection;
	GSList *tokens, *t;

	connection = soup_message_headers_get_list (hdrs, "Connection");
	if (!connection)
		return;

	tokens = soup_header_parse_list (connection);
	for (t = tokens; t; t = t->next)
		soup_message_headers_remove (hdrs, t->data);
	soup_header_free_list (tokens);
}
示例#13
0
static gboolean
gst_soup_http_src_add_range_header (GstSoupHTTPSrc * src, guint64 offset)
{
  gchar buf[64];

  gint rc;

  soup_message_headers_remove (src->msg->request_headers, "Range");
  if (offset) {
    rc = g_snprintf (buf, sizeof (buf), "bytes=%" G_GUINT64_FORMAT "-", offset);
    if (rc > sizeof (buf) || rc < 0)
      return FALSE;
    soup_message_headers_append (src->msg->request_headers, "Range", buf);
  }
  src->read_position = offset;
  return TRUE;
}
示例#14
0
static void recv_headers(SoupMessage *from, gpointer data)
{
	SoupMessage *to = ((struct destination_info *) data)->msg;
	SoupServer *server = ((struct destination_info *) data)->server;

	g_print("[%p] HTTP/1.%d %d %s\n", to,
		soup_message_get_http_version(from),
		from->status_code, from->reason_phrase);

	soup_message_set_status_full(to,
		from->status_code, from->reason_phrase);

	soup_message_headers_foreach(from->response_headers,
		copy_header, to->response_headers);
	/* we remove it, because libsoup appending at the end */
	soup_message_headers_remove(to->response_headers, "Content-Length");

	soup_server_unpause_message(server, to);
}
示例#15
0
// Called each time the message is going to be sent again except the first time.
// It's used mostly to let webkit know about redirects.
static void restartedCallback(SoupMessage* msg, gpointer data)
{
    ResourceHandle* handle = static_cast<ResourceHandle*>(data);
    if (!handle)
        return;
    ResourceHandleInternal* d = handle->getInternal();
    if (d->m_cancelled)
        return;

    char* uri = soup_uri_to_string(soup_message_get_uri(msg), false);
    String location = String(uri);
    g_free(uri);
    KURL newURL = KURL(handle->request().url(), location);

    ResourceRequest request = handle->request();
    ResourceResponse response;
    request.setURL(newURL);
    request.setHTTPMethod(msg->method);
    fillResponseFromMessage(msg, &response);

    // Should not set Referer after a redirect from a secure resource to non-secure one.
    if (!request.url().protocolIs("https") && protocolIs(request.httpReferrer(), "https")) {
        request.clearHTTPReferrer();
        soup_message_headers_remove(msg->request_headers, "Referer");
    }

    if (d->client())
        d->client()->willSendRequest(handle, request, response);

    if (d->m_cancelled)
        return;

#ifdef HAVE_LIBSOUP_2_29_90
    // Update the first party in case the base URL changed with the redirect
    String firstPartyString = request.firstPartyForCookies().string();
    if (!firstPartyString.isEmpty()) {
        GOwnPtr<SoupURI> firstParty(soup_uri_new(firstPartyString.utf8().data()));
        soup_message_set_first_party(d->m_msg, firstParty.get());
    }
#endif
}
示例#16
0
static void
request_started(SoupSessionFeature *feature, SoupSession *session,
        SoupMessage *msg, SoupSocket *socket)
{
    (void) session;
    (void) socket;
    SoupCookieJar *sj = SOUP_COOKIE_JAR(feature);
    SoupURI *uri = soup_message_get_uri(msg);
    lua_State *L = globalconf.L;

    /* give user a chance to add cookies from other instances into the jar */
    gchar *str = soup_uri_to_string(uri, FALSE);
    lua_pushstring(L, str);
    g_free(str);
    signal_object_emit(L, soupconf.signals, "request-started", 1, 0);

    /* generate cookie header */
    gchar *header = soup_cookie_jar_get_cookies(sj, uri, TRUE);
    if (header) {
        soup_message_headers_replace(msg->request_headers, "Cookie", header);
        g_free(header);
    } else
        soup_message_headers_remove(msg->request_headers, "Cookie");
}
示例#17
0
static void
forget_close (SoupMessage *msg, gpointer user_data)
{
	soup_message_headers_remove (msg->response_headers, "Connection");
}