Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(243)

Unified Diff: third_party/WebKit/Source/core/origin_trials/OriginTrialContext.cpp

Issue 1802773002: Support loading trial tokens from HTTP headers. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Don't use //net for parsing headers Created 4 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: third_party/WebKit/Source/core/origin_trials/OriginTrialContext.cpp
diff --git a/third_party/WebKit/Source/core/origin_trials/OriginTrialContext.cpp b/third_party/WebKit/Source/core/origin_trials/OriginTrialContext.cpp
index 1bae6e6b34edaaddee0088a05dd94140ad3f86bc..4b4096531dd2ae4b498a6d91a7494dfc0fc86778 100644
--- a/third_party/WebKit/Source/core/origin_trials/OriginTrialContext.cpp
+++ b/third_party/WebKit/Source/core/origin_trials/OriginTrialContext.cpp
@@ -10,6 +10,7 @@
#include "public/platform/Platform.h"
#include "public/platform/WebSecurityOrigin.h"
#include "public/platform/WebTrialTokenValidator.h"
+#include "wtf/text/StringBuilder.h"
namespace blink {
@@ -25,6 +26,54 @@ String getInvalidTokenMessage(const String& featureName)
return "The provided token(s) are not valid for the '" + featureName + "' feature.";
}
+bool isWhitespace(UChar chr)
+{
+ return (chr == ' ') || (chr == '\t');
+}
+
+bool skipWhiteSpace(const String& str, unsigned& pos)
+{
+ unsigned len = str.length();
+ while (pos < len && isWhitespace(str[pos]))
+ ++pos;
+ return pos < len;
+}
+
+// Extracts a quoted or unquoted token from an HTTP header. If the token was a
+// quoted string, this also removes the quotes and unescapes any escaped
+// characters. Also skips all whitespace before and after the token.
+String extractTokenOrQuotedString(const String& headerValue, unsigned& pos)
+{
+ unsigned len = headerValue.length();
+ String result;
+ if (!skipWhiteSpace(headerValue, pos))
+ return String();
+
+ if (headerValue[pos] == '\'' || headerValue[pos] == '"') {
+ StringBuilder out;
+ // Quoted string, append characters until matching quote is found,
+ // unescaping as we go.
+ UChar quote = headerValue[pos++];
+ while (pos < len && headerValue[pos] != quote) {
+ if (headerValue[pos] == '\\')
+ pos++;
+ if (pos < len)
+ out.append(headerValue[pos++]);
+ }
+ if (pos < len)
+ pos++;
+ result = out.toString();
+ } else {
+ // Unquoted token. Consume all characters until whitespace or comma.
+ int startPos = pos;
+ while (pos < len && !isWhitespace(headerValue[pos]) && headerValue[pos] != ',')
+ pos++;
+ result = headerValue.substring(startPos, pos - startPos);
+ }
+ skipWhiteSpace(headerValue, pos);
+ return result;
+}
+
} // namespace
OriginTrialContext::OriginTrialContext(ExecutionContext* host) : m_host(host)
@@ -48,6 +97,35 @@ OriginTrialContext* OriginTrialContext::from(ExecutionContext* host)
return originTrials;
}
+// static
+PassOwnPtr<Vector<String>> OriginTrialContext::parseHeaderValue(const String& headerValue)
+{
+ if (headerValue.isEmpty())
+ return nullptr;
chasej 2016/04/21 18:24:29 The comment for this method says it returns null i
Marijn Kruisselbrink 2016/04/21 20:27:09 Maybe it's more consistent to not special case emp
+ OwnPtr<Vector<String>> tokens(adoptPtr(new Vector<String>));
+ unsigned pos = 0;
+ unsigned len = headerValue.length();
+ while (pos < len) {
+ tokens->append(extractTokenOrQuotedString(headerValue, pos));
chasej 2016/04/21 18:24:29 The extractTokenOrQuotedString() method can return
Marijn Kruisselbrink 2016/04/21 20:27:09 Done
+ // Make sure tokens are comma-separated.
+ if (pos < len && headerValue[pos++] != ',')
+ return nullptr;
+ }
+ return tokens.release();
+}
+
+// static
+void OriginTrialContext::addTokensFromHeader(ExecutionContext* host, const String& headerValue)
+{
+ OwnPtr<Vector<String>> tokens = parseHeaderValue(headerValue);
+ if (!tokens)
+ return;
+ OriginTrialContext* context = from(host);
+ for (const String& token : *tokens) {
+ context->addToken(token);
+ }
+}
+
void OriginTrialContext::addToken(const String& token)
{
chasej 2016/04/21 18:24:30 As in the earlier comment, perhaps there should be
Marijn Kruisselbrink 2016/04/21 20:27:09 Done
m_tokens.append(token);

Powered by Google App Engine
This is Rietveld 408576698