summaryrefslogtreecommitdiffstats
path: root/src/DotNetOpenAuth.OAuth2/OAuth2/AccessToken.cs
diff options
context:
space:
mode:
authorAndrew Arnott <andrewarnott@gmail.com>2012-04-01 15:36:22 -0700
committerAndrew Arnott <andrewarnott@gmail.com>2012-04-01 15:36:22 -0700
commit0c8a4a3a33e840e7c449388f078155efaf1854c7 (patch)
treea2737354658f5bb6699197e615e84182a48a6f0d /src/DotNetOpenAuth.OAuth2/OAuth2/AccessToken.cs
parent4fcf484a281697630698c12f81fdcf7306346366 (diff)
downloadDotNetOpenAuth-0c8a4a3a33e840e7c449388f078155efaf1854c7.zip
DotNetOpenAuth-0c8a4a3a33e840e7c449388f078155efaf1854c7.tar.gz
DotNetOpenAuth-0c8a4a3a33e840e7c449388f078155efaf1854c7.tar.bz2
AccessToken is now a public class.
Resource Servers can now handle access tokens that are issued for a client's data (not a 3rd party resource owner's). Client Identifiers are no longer included in access tokens for unauthenticated clients. More work needed on IAccessTokenAnalyzer and the access token formatter. We need to generalize the serialization itself so folks can use JWT, etc. We also still need access token to have a host-defined map of claims. Fixes #104 Fixes #102
Diffstat (limited to 'src/DotNetOpenAuth.OAuth2/OAuth2/AccessToken.cs')
-rw-r--r--src/DotNetOpenAuth.OAuth2/OAuth2/AccessToken.cs104
1 files changed, 104 insertions, 0 deletions
diff --git a/src/DotNetOpenAuth.OAuth2/OAuth2/AccessToken.cs b/src/DotNetOpenAuth.OAuth2/OAuth2/AccessToken.cs
new file mode 100644
index 0000000..1aeeea7
--- /dev/null
+++ b/src/DotNetOpenAuth.OAuth2/OAuth2/AccessToken.cs
@@ -0,0 +1,104 @@
+//-----------------------------------------------------------------------
+// <copyright file="AccessToken.cs" company="Outercurve Foundation">
+// Copyright (c) Outercurve Foundation. All rights reserved.
+// </copyright>
+//-----------------------------------------------------------------------
+
+namespace DotNetOpenAuth.OAuth2 {
+ using System;
+ using System.Collections.Generic;
+ using System.Diagnostics.Contracts;
+ using System.Security.Cryptography;
+ using DotNetOpenAuth.Messaging;
+ using DotNetOpenAuth.Messaging.Bindings;
+ using DotNetOpenAuth.OAuth2.ChannelElements;
+
+ /// <summary>
+ /// A short-lived token that accompanies HTTP requests to protected data to authorize the request.
+ /// </summary>
+ public class AccessToken : AuthorizationDataBag {
+ /// <summary>
+ /// Initializes a new instance of the <see cref="AccessToken"/> class.
+ /// </summary>
+ public AccessToken() {
+ }
+
+ /// <summary>
+ /// Initializes a new instance of the <see cref="AccessToken"/> class.
+ /// </summary>
+ /// <param name="authorization">The authorization to be described by the access token.</param>
+ /// <param name="lifetime">The lifetime of the access token.</param>
+ internal AccessToken(IAuthorizationDescription authorization, TimeSpan? lifetime) {
+ Requires.NotNull(authorization, "authorization");
+
+ this.ClientIdentifier = authorization.ClientIdentifier;
+ this.UtcCreationDate = authorization.UtcIssued;
+ this.User = authorization.User;
+ this.Scope.ResetContents(authorization.Scope);
+ this.Lifetime = lifetime;
+ }
+
+ /// <summary>
+ /// Initializes a new instance of the <see cref="AccessToken"/> class.
+ /// </summary>
+ /// <param name="scopes">The scopes.</param>
+ /// <param name="username">The username of the account that authorized this token.</param>
+ /// <param name="lifetime">The lifetime for this access token.</param>
+ /// <remarks>
+ /// The <see cref="ClientIdentifier.ClientIdentifier"/> is left <c>null</c> in this case because this constructor
+ /// is invoked in the case where the client is <em>not</em> authenticated, and therefore no
+ /// trust in the client_id is appropriate.
+ /// </remarks>
+ internal AccessToken(IEnumerable<string> scopes, string username, TimeSpan? lifetime) {
+ this.Scope.ResetContents(scopes);
+ this.User = username;
+ this.Lifetime = lifetime;
+ this.UtcCreationDate = DateTime.UtcNow;
+ }
+
+ /// <summary>
+ /// Gets or sets the lifetime of the access token.
+ /// </summary>
+ /// <value>The lifetime.</value>
+ [MessagePart(Encoder = typeof(TimespanSecondsEncoder))]
+ public TimeSpan? Lifetime { get; set; }
+
+ /// <summary>
+ /// Creates a formatter capable of serializing/deserializing an access token.
+ /// </summary>
+ /// <param name="signingKey">The crypto service provider with the authorization server's private key used to asymmetrically sign the access token.</param>
+ /// <param name="encryptingKey">The crypto service provider with the resource server's public key used to encrypt the access token.</param>
+ /// <returns>An access token serializer.</returns>
+ internal static IDataBagFormatter<AccessToken> CreateFormatter(RSACryptoServiceProvider signingKey, RSACryptoServiceProvider encryptingKey) {
+ Contract.Requires(signingKey != null || !signingKey.PublicOnly);
+ Contract.Requires(encryptingKey != null);
+ Contract.Ensures(Contract.Result<IDataBagFormatter<AccessToken>>() != null);
+
+ return new UriStyleMessageFormatter<AccessToken>(signingKey, encryptingKey);
+ }
+
+ /// <summary>
+ /// Checks the message state for conformity to the protocol specification
+ /// and throws an exception if the message is invalid.
+ /// </summary>
+ /// <remarks>
+ /// <para>Some messages have required fields, or combinations of fields that must relate to each other
+ /// in specialized ways. After deserializing a message, this method checks the state of the
+ /// message to see if it conforms to the protocol.</para>
+ /// <para>Note that this property should <i>not</i> check signatures or perform any state checks
+ /// outside this scope of this particular message.</para>
+ /// </remarks>
+ /// <exception cref="ProtocolException">Thrown if the message is invalid.</exception>
+ protected override void EnsureValidMessage() {
+ base.EnsureValidMessage();
+
+ // Has this token expired?
+ if (this.Lifetime.HasValue) {
+ DateTime expirationDate = this.UtcCreationDate + this.Lifetime.Value;
+ if (expirationDate < DateTime.UtcNow) {
+ throw new ExpiredMessageException(expirationDate, this.ContainingMessage);
+ }
+ }
+ }
+ }
+}