diff --git a/src/JwtHandler.Tests/Properties/AssemblyInfo.cs b/src/JwtHandler.Tests/Properties/AssemblyInfo.cs
index 76a469a1d55daac9be0cedb41863e7d2584c4be9..e6a294ef7ab8873ff898068187accec1068d0bdc 100644
--- a/src/JwtHandler.Tests/Properties/AssemblyInfo.cs
+++ b/src/JwtHandler.Tests/Properties/AssemblyInfo.cs
@@ -1,36 +1,16 @@
-using System.Reflection;
-using System.Runtime.CompilerServices;
-using System.Runtime.InteropServices;
+//------------------------------------------------------------------------------
+// <auto-generated>
+//     This code was generated by Cake.
+// </auto-generated>
+//------------------------------------------------------------------------------
+using System.Reflection;
 
-// General Information about an assembly is controlled through the following
-// set of attributes. Change these attribute values to modify the information
-// associated with an assembly.
 [assembly: AssemblyTitle("JwtHandler.Tests")]
-[assembly: AssemblyDescription("")]
-[assembly: AssemblyConfiguration("")]
-[assembly: AssemblyCompany("")]
+[assembly: AssemblyDescription("JwtHandler.Tests is a part of the CoScInE group.")]
+[assembly: AssemblyCompany("IT Center, RWTH Aachen University")]
 [assembly: AssemblyProduct("JwtHandler.Tests")]
-[assembly: AssemblyCopyright("Copyright ©  2020")]
-[assembly: AssemblyTrademark("")]
-[assembly: AssemblyCulture("")]
+[assembly: AssemblyVersion("1.2.0")]
+[assembly: AssemblyFileVersion("1.2.0")]
+[assembly: AssemblyInformationalVersion("1.2.0-topic-1125-apito0005")]
+[assembly: AssemblyCopyright("2020 IT Center, RWTH Aachen University")]
 
-// Setting ComVisible to false makes the types in this assembly not visible
-// to COM components.  If you need to access a type in this assembly from
-// COM, set the ComVisible attribute to true on that type.
-[assembly: ComVisible(false)]
-
-// The following GUID is for the ID of the typelib if this project is exposed to COM
-[assembly: Guid("09823fa2-31b4-462b-b534-956c74b56db3")]
-
-// Version information for an assembly consists of the following four values:
-//
-//      Major Version
-//      Minor Version
-//      Build Number
-//      Revision
-//
-// You can specify all the values or you can default the Build and Revision Numbers
-// by using the '*' as shown below:
-// [assembly: AssemblyVersion("1.0.*")]
-[assembly: AssemblyVersion("1.0.0.0")]
-[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/src/JwtHandler/JwtHandler.cs b/src/JwtHandler/JwtHandler.cs
index eea1926c81bf61479382ce703dbaa060732bf36c..f4d8f18ca211e7293288679933bbb49260a631e3 100644
--- a/src/JwtHandler/JwtHandler.cs
+++ b/src/JwtHandler/JwtHandler.cs
@@ -14,12 +14,21 @@ namespace Coscine.JwtHandler
         public IConfiguration Configuration { get; set; }
         private readonly JwtSecurityTokenHandler _jwtSecurityTokenHandler;
         private readonly SymmetricSecurityKey _symmetricSecurityKey;
+        private readonly DateTime _centuryBegin;
+        // How long the default token is valid (in minutes).
+        private readonly double _defaultExpiration;
+        private readonly string _issuer;
+        private readonly string _audience;
 
         public JWTHandler(IConfiguration configuration)
         {
             Configuration = configuration;
             _jwtSecurityTokenHandler = new JwtSecurityTokenHandler();
             _symmetricSecurityKey = GetSecurityKey();
+            _centuryBegin = new DateTime(1970, 1, 1);
+            _defaultExpiration = 30;
+            _issuer = "https://coscine.rwth-aachen.de";
+            _audience = "https://coscine.rwth-aachen.de";
         }
 
         public SymmetricSecurityKey GetSecurityKey()
@@ -38,11 +47,12 @@ namespace Coscine.JwtHandler
         {
             var tokenValidationParameters = new TokenValidationParameters
             {
+                ValidAudience = _audience,
+                ValidIssuer = _issuer,
                 ValidateIssuerSigningKey = true,
                 IssuerSigningKey = _symmetricSecurityKey,
-                // TODO: Validate those two
-                ValidateAudience = false,
-                ValidateIssuer = false
+                ValidateIssuer = false,
+                ValidateAudience = false
             };
 
             _jwtSecurityTokenHandler.ValidateToken(token, tokenValidationParameters, out _);
@@ -55,6 +65,13 @@ namespace Coscine.JwtHandler
         }
 
         public string GenerateJwtToken(JwtPayload payload, string signatureAlgorithm = "HS256")
+        {
+            var issuedAt = DateTime.Now;
+            var expires = issuedAt.AddMinutes(_defaultExpiration);
+            return GenerateJwtToken(payload, _issuer, _audience, issuedAt, expires, signatureAlgorithm);
+        }
+
+        public string GenerateJwtToken(JwtPayload payload, string issuer, string audience, DateTime issuedAt, DateTime expires, string signatureAlgorithm = "HS256")
         {
             if (payload == null)
             {
@@ -63,13 +80,12 @@ namespace Coscine.JwtHandler
 
             var signingCredentials = new SigningCredentials(_symmetricSecurityKey, signatureAlgorithm);
 
-            var centuryBegin = new DateTime(1970, 1, 1);
-            var exp = new TimeSpan(DateTime.Now.AddMinutes(30).Ticks - centuryBegin.Ticks).TotalSeconds;
-            var now = new TimeSpan(DateTime.Now.Ticks - centuryBegin.Ticks).TotalSeconds;
+            var exp = (expires - _centuryBegin).TotalSeconds;
+            var iat = (issuedAt - _centuryBegin).TotalSeconds;
 
-            payload.Add("iss", "coscine");
-            payload.Add("aud", "coscine");
-            payload.Add("iat", (long)now);
+            payload.Add("iss", issuer);
+            payload.Add("aud", audience);
+            payload.Add("iat", (long)iat);
             payload.Add("exp", (long)exp);
 
             var header = new JwtHeader(signingCredentials);
@@ -85,5 +101,12 @@ namespace Coscine.JwtHandler
             return GenerateJwtToken(payload, signatureAlgorithm);
         }
 
+        public string GenerateJwtToken(IReadOnlyDictionary<string, string> payloadContents, string issuer, string audience, DateTime issuedAt, DateTime expires, string signatureAlgorithm = "HS256")
+        {
+            var payload = new JwtPayload(payloadContents.Select(c => new Claim(c.Key, c.Value)));
+
+            return GenerateJwtToken(payload, issuer, audience, issuedAt, expires, signatureAlgorithm);
+        }
+
     }
 }
diff --git a/src/JwtHandler/JwtHandler.csproj b/src/JwtHandler/JwtHandler.csproj
index 3751c4164b1254831d1d96c504284cfa06ebe5bd..fa2a53b4d5e9d032742f48e13bda61c312ca957c 100644
--- a/src/JwtHandler/JwtHandler.csproj
+++ b/src/JwtHandler/JwtHandler.csproj
@@ -30,6 +30,12 @@
     <ErrorReport>prompt</ErrorReport>
     <WarningLevel>4</WarningLevel>
   </PropertyGroup>
+  <PropertyGroup>
+    <SignAssembly>true</SignAssembly>
+  </PropertyGroup>
+  <PropertyGroup>
+    <AssemblyOriginatorKeyFile>key.snk</AssemblyOriginatorKeyFile>
+  </PropertyGroup>
   <ItemGroup>
     <Reference Include="Consul, Version=0.7.2.6, Culture=neutral, PublicKeyToken=20a6ad9a81df1d95, processorArchitecture=MSIL">
       <HintPath>..\packages\Consul.0.7.2.6\lib\net45\Consul.dll</HintPath>
@@ -64,6 +70,7 @@
     <Compile Include="Properties\AssemblyInfo.cs" />
   </ItemGroup>
   <ItemGroup>
+    <None Include="key.snk" />
     <None Include="packages.config" />
   </ItemGroup>
   <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
diff --git a/src/JwtHandler/Properties/AssemblyInfo.cs b/src/JwtHandler/Properties/AssemblyInfo.cs
index edc1e9a2e4ba049a1306d275b8ac105581f7126e..ea462807fcf61e5f29e69a7edeae2312499e2fe6 100644
--- a/src/JwtHandler/Properties/AssemblyInfo.cs
+++ b/src/JwtHandler/Properties/AssemblyInfo.cs
@@ -1,36 +1,16 @@
-using System.Reflection;
-using System.Runtime.CompilerServices;
-using System.Runtime.InteropServices;
+//------------------------------------------------------------------------------
+// <auto-generated>
+//     This code was generated by Cake.
+// </auto-generated>
+//------------------------------------------------------------------------------
+using System.Reflection;
 
-// General Information about an assembly is controlled through the following
-// set of attributes. Change these attribute values to modify the information
-// associated with an assembly.
 [assembly: AssemblyTitle("JwtHandler")]
-[assembly: AssemblyDescription("")]
-[assembly: AssemblyConfiguration("")]
-[assembly: AssemblyCompany("")]
+[assembly: AssemblyDescription("JwtHandler is a part of the CoScInE group.")]
+[assembly: AssemblyCompany("IT Center, RWTH Aachen University")]
 [assembly: AssemblyProduct("JwtHandler")]
-[assembly: AssemblyCopyright("Copyright ©  2020")]
-[assembly: AssemblyTrademark("")]
-[assembly: AssemblyCulture("")]
+[assembly: AssemblyVersion("1.2.0")]
+[assembly: AssemblyFileVersion("1.2.0")]
+[assembly: AssemblyInformationalVersion("1.2.0-topic-1125-apito0005")]
+[assembly: AssemblyCopyright("2020 IT Center, RWTH Aachen University")]
 
-// Setting ComVisible to false makes the types in this assembly not visible
-// to COM components.  If you need to access a type in this assembly from
-// COM, set the ComVisible attribute to true on that type.
-[assembly: ComVisible(false)]
-
-// The following GUID is for the ID of the typelib if this project is exposed to COM
-[assembly: Guid("f17cf42d-af36-45a4-9a81-1804e27857bd")]
-
-// Version information for an assembly consists of the following four values:
-//
-//      Major Version
-//      Minor Version
-//      Build Number
-//      Revision
-//
-// You can specify all the values or you can default the Build and Revision Numbers
-// by using the '*' as shown below:
-// [assembly: AssemblyVersion("1.0.*")]
-[assembly: AssemblyVersion("1.0.0.0")]
-[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/src/JwtHandler/key.snk b/src/JwtHandler/key.snk
new file mode 100644
index 0000000000000000000000000000000000000000..9bfa9ea084bf1e67d86c956dab9705b051ba4bbf
Binary files /dev/null and b/src/JwtHandler/key.snk differ