001/* 002Copyright 2022 The OpenFunction Authors. 003 004Licensed under the Apache License, Version 2.0 (the "License"); 005you may not use this file except in compliance with the License. 006You may obtain a copy of the License at 007 008 http://www.apache.org/licenses/LICENSE-2.0 009 010Unless required by applicable law or agreed to in writing, software 011distributed under the License is distributed on an "AS IS" BASIS, 012WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013See the License for the specific language governing permissions and 014limitations under the License. 015*/ 016 017package dev.openfunction.functions; 018 019import java.util.List; 020import java.util.Map; 021import java.util.Optional; 022 023/** 024 * Represents the contents of an HTTP request that is being serviced by a Cloud Function. 025 */ 026public interface HttpRequest extends HttpMessage { 027 /** 028 * The HTTP method of this request, such as {@code "POST"} or {@code "GET"}. 029 * 030 * @return the HTTP method of this request. 031 */ 032 String getMethod(); 033 034 /** 035 * The full URI of this request as it arrived at the server. 036 * 037 * @return the full URI of this request. 038 */ 039 String getUri(); 040 041 /** 042 * The path part of the URI for this request, without any query. If the full URI is {@code 043 * http://foo.com/bar/baz?this=that}, then this method will return {@code /bar/baz}. 044 * 045 * @return the path part of the URI for this request. 046 */ 047 String getPath(); 048 049 /** 050 * The query part of the URI for this request. If the full URI is {@code 051 * http://foo.com/bar/baz?this=that}, then this method will return {@code this=that}. If there is 052 * no query part, the returned {@code Optional} is empty. 053 * 054 * @return the query part of the URI, if any. 055 */ 056 Optional<String> getQuery(); 057 058 /** 059 * The query parameters of this request. If the full URI is {@code 060 * http://foo.com/bar?thing=thing1&thing=thing2&cat=hat}, then the returned map will map {@code 061 * thing} to the list {@code ["thing1", "thing2"]} and {@code cat} to the list with the single 062 * element {@code "hat"}. 063 * 064 * @return a map where each key is the name of a query parameter and the corresponding {@code 065 * List} value indicates every value that was associated with that name. 066 */ 067 Map<String, List<String>> getQueryParameters(); 068 069 /** 070 * The first query parameter with the given name, if any. If the full URI is {@code 071 * http://foo.com/bar?thing=thing1&thing=thing2&cat=hat}, then {@code 072 * getFirstQueryParameter("thing")} will return {@code Optional.of("thing1")} and {@code 073 * getFirstQueryParameter("something")} will return {@code Optional.empty()}. This is a more 074 * convenient alternative to {@link #getQueryParameters}. 075 * 076 * @param name a query parameter name. 077 * @return the first query parameter value with the given name, if any. 078 */ 079 default Optional<String> getFirstQueryParameter(String name) { 080 List<String> parameters = getQueryParameters().get(name); 081 if (parameters == null || parameters.isEmpty()) { 082 return Optional.empty(); 083 } 084 return Optional.of(parameters.get(0)); 085 } 086 087 /** 088 * Represents one part inside a multipart ({@code multipart/form-data}) HTTP request. Each such 089 * part can have its own HTTP headers, which can be retrieved with the methods inherited from 090 * {@link HttpMessage}. 091 */ 092 interface HttpPart extends HttpMessage { 093 /** 094 * Returns the filename associated with this part, if any. 095 * 096 * @return the filename associated with this part, if any. 097 */ 098 Optional<String> getFileName(); 099 } 100 101 /** 102 * Returns the parts inside this multipart ({@code multipart/form-data}) HTTP request. Each entry 103 * in the returned map has the name of the part as its key and the contents as the associated 104 * value. 105 * 106 * @return a map from part names to part contents. 107 * @throws IllegalStateException if the {@link #getContentType() content type} is not {@code 108 * multipart/form-data}. 109 */ 110 Map<String, HttpPart> getParts(); 111}