/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ /* vim: set ts=8 sts=2 et sw=2 tw=80: */ /* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
class FSURLEncoded : public EncodingFormSubmission { public: /** * @param aEncoding the character encoding of the form * @param aMethod the method of the submit (either NS_FORM_METHOD_GET or * NS_FORM_METHOD_POST).
*/
FSURLEncoded(nsIURI* aActionURL, const nsAString& aTarget,
NotNull<const Encoding*> aEncoding, int32_t aMethod,
Document* aDocument, Element* aSubmitter)
: EncodingFormSubmission(aActionURL, aTarget, aEncoding, aSubmitter),
mMethod(aMethod),
mDocument(aDocument),
mWarnedFileControl(false) {}
protected: /** * URL encode a Unicode string by encoding it to bytes, converting linebreaks * properly, and then escaping many bytes as %xx. * * @param aStr the string to encode * @param aEncoded the encoded string [OUT] * @throws NS_ERROR_OUT_OF_MEMORY if we run out of memory
*/
nsresult URLEncode(const nsAString& aStr, nsACString& aEncoded);
private: /** * The method of the submit (either NS_FORM_METHOD_GET or * NS_FORM_METHOD_POST).
*/
int32_t mMethod;
/** The query string so far (the part after the ?) */
nsCString mQueryString;
/** The document whose URI to use when reporting errors */
nsCOMPtr<Document> mDocument;
/** Whether or not we have warned about a file control not being submitted */ bool mWarnedFileControl;
};
nsresult FSURLEncoded::AddNameDirectoryPair(const nsAString& aName,
Directory* aDirectory) { // No warning about because Directory objects are never sent via form.
void HandleMailtoSubject(nsCString& aPath) { // Walk through the string and see if we have a subject already. bool hasSubject = false; bool hasParams = false;
int32_t paramSep = aPath.FindChar('?'); while (paramSep != kNotFound && paramSep < (int32_t)aPath.Length()) {
hasParams = true;
// Get the end of the name at the = op. If it is *after* the next &, // assume that someone made a parameter without an = in it
int32_t nameEnd = aPath.FindChar('=', paramSep + 1);
int32_t nextParamSep = aPath.FindChar('&', paramSep + 1); if (nextParamSep == kNotFound) {
nextParamSep = aPath.Length();
}
// If the = op is after the &, this parameter is a name without value. // If there is no = op, same thing. if (nameEnd == kNotFound || nextParamSep < nameEnd) {
nameEnd = nextParamSep;
}
// If there is no subject, append a preformed subject to the mailto line if (!hasSubject) { if (hasParams) {
aPath.Append('&');
} else {
aPath.Append('?');
}
// Get the default subject
nsAutoString brandName;
nsresult rv = nsContentUtils::GetLocalizedString(
nsContentUtils::eBRAND_PROPERTIES, "brandShortName", brandName); if (NS_FAILED(rv)) return;
nsAutoString subjectStr;
rv = nsContentUtils::FormatLocalizedString(
subjectStr, nsContentUtils::eFORMS_PROPERTIES, "DefaultFormSubject",
brandName); if (NS_FAILED(rv)) return;
aPath.AppendLiteral("subject=");
nsCString subjectStrEscaped;
rv = NS_EscapeURL(NS_ConvertUTF16toUTF8(subjectStr), esc_Query,
subjectStrEscaped, mozilla::fallible); if (NS_FAILED(rv)) return;
if (mMethod == NS_FORM_METHOD_POST) { if (aURI->SchemeIs("mailto")) {
nsAutoCString path;
rv = aURI->GetPathQueryRef(path);
NS_ENSURE_SUCCESS(rv, rv);
HandleMailtoSubject(path);
// Append the body to and force-plain-text args to the mailto line
nsAutoCString escapedBody; if (NS_WARN_IF(!NS_Escape(mQueryString, escapedBody, url_XAlphas))) { return NS_ERROR_OUT_OF_MEMORY;
}
} else { // Get the full query string if (aURI->SchemeIs("javascript")) { return NS_OK;
}
nsCOMPtr<nsIURL> url = do_QueryInterface(aURI); if (url) { // Make sure that we end up with a query component in the URL. If // mQueryString is empty, nsIURI::SetQuery() will remove the query // component, which is not what we want.
rv = NS_MutateURI(aURI)
.SetQuery(mQueryString.IsEmpty() ? "?"_ns : mQueryString)
.Finalize(aOutURI);
} else {
nsAutoCString path;
rv = aURI->GetPathQueryRef(path);
NS_ENSURE_SUCCESS(rv, rv); // Bug 42616: Trim off named anchor and save it to add later
int32_t namedAnchorPos = path.FindChar('#');
nsAutoCString namedAnchor; if (kNotFound != namedAnchorPos) {
path.Right(namedAnchor, (path.Length() - namedAnchorPos));
path.Truncate(namedAnchorPos);
}
// Chop off old query string (bug 25330, 57333) // Only do this for GET not POST (bug 41585)
int32_t queryStart = path.FindChar('?'); if (kNotFound != queryStart) {
path.Truncate(queryStart);
}
path.Append('?'); // Bug 42616: Add named anchor to end after query string
path.Append(mQueryString + namedAnchor);
// i18n helper routines
nsresult FSURLEncoded::URLEncode(const nsAString& aStr, nsACString& aEncoded) {
nsAutoCString encodedBuf; // We encode with eValueEncode because the urlencoded format needs the newline // normalizations but percent-escapes characters that eNameEncode doesn't, // so calling NS_Escape would still be needed.
nsresult rv = EncodeVal(aStr, encodedBuf, EncodeType::eValueEncode);
NS_ENSURE_SUCCESS(rv, rv);
if (NS_WARN_IF(!NS_Escape(encodedBuf, aEncoded, url_XPAlphas))) { return NS_ERROR_OUT_OF_MEMORY;
}
// Get content type
nsAutoString contentType16;
aBlob->GetType(contentType16); if (contentType16.IsEmpty()) {
contentType16.AssignLiteral("application/octet-stream");
}
// We should not try to append an invalid stream. That will happen for example // if we try to update a file that actually do not exist. if (aInputStream) { // We need to dump the data up to this point into the POST data stream // here, since we're about to add the file input stream
AddPostDataStream();
nsCOMPtr<nsIInputStream> postDataChunkStream;
rv = NS_NewCStringInputStream(getter_AddRefs(postDataChunkStream),
mPostDataChunk);
NS_ASSERTION(postDataChunkStream, "Could not open a stream for POST!"); if (postDataChunkStream) {
mPostData->AppendStream(postDataChunkStream);
mTotalLength += mPostDataChunk.Length();
}
nsresult FSTextPlain::AddNameValuePair(const nsAString& aName, const nsAString& aValue) { // XXX This won't work well with a name like "a=b" or "a\nb" but I suppose // text/plain doesn't care about that. Parsers aren't built for escaped // values so we'll have to live with it.
mBody.Append(aName + u"="_ns + aValue + NS_LITERAL_STRING_FROM_CSTRING(CRLF));
// XXX HACK We are using the standard URL mechanism to give the body to the // mailer instead of passing the post data stream to it, since that sounds // hard. if (aURI->SchemeIs("mailto")) {
nsAutoCString path;
rv = aURI->GetPathQueryRef(path);
NS_ENSURE_SUCCESS(rv, rv);
HandleMailtoSubject(path);
// Append the body to and force-plain-text args to the mailto line
nsAutoCString escapedBody; if (NS_WARN_IF(!NS_Escape(NS_ConvertUTF16toUTF8(mBody), escapedBody,
url_XAlphas))) { return NS_ERROR_OUT_OF_MEMORY;
}
rv = NS_MutateURI(aURI).SetPathQueryRef(path).Finalize(aOutURI);
} else { // Create data stream. // We use eValueEncode to send the data through the charset encoder and to // normalize linebreaks to use the "standard net" format (\r\n), but not // perform any other escaping. This means that names and values which // contain '=' or newlines are potentially ambiguously encoded, but that is // how text/plain is specced.
nsCString cbody;
EncodeVal(mBody, cbody, EncodeType::eValueEncode);
// Create mime stream with headers and such
nsCOMPtr<nsIMIMEInputStream> mimeStream =
do_CreateInstance("@mozilla.org/network/mime-input-stream;1", &rv);
NS_ENSURE_SUCCESS(rv, rv);
/* static */
nsresult HTMLFormSubmission::GetFromForm(HTMLFormElement* aForm,
nsGenericHTMLElement* aSubmitter,
NotNull<const Encoding*>& aEncoding,
HTMLFormSubmission** aFormSubmission) { // Get all the information necessary to encode the form data
NS_ASSERTION(aForm->GetComposedDoc(), "Should have doc if we're building submission!");
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung ist noch experimentell.