コード例 #1
0
        public static async Task <IActionResult> Run(
            [HttpTrigger(AuthorizationLevel.Anonymous, "post", "options", Route = null)] HttpRequest req,
            [StorageAccount("StorageConnectionString")] CloudStorageAccount storageAccount,
            TraceWriter log
            )
        {
            var email = req.Query["email"].FirstOrDefault()?.ToLower();

            if (string.IsNullOrWhiteSpace(email))
            {
                return(new BadRequestObjectResult("The query parameter \"email\" is empty or missing"));
            }

            log.Info($"E-mail verification request received for {email}");
            var client          = storageAccount.CreateCloudTableClient();
            var throttleService = new ThrottleService(client, log);
            var throttled       = (await throttleService.ThrottleOrIncrement(email)) || (await throttleService.ThrottleOrIncrement(IpUtility.GetClientIp(req)));

            if (throttled)
            {
                return(new StatusCodeResult(429));
            }

            var code  = $"{new Random().Next(100, 999)}{new Random().Next(100, 999)}{new Random().Next(100, 999)}";
            var token = Guid.NewGuid().ToString().Replace("-", "");
            var auth  = new EmailAuthToken(email, token, code)
            {
                Expiration = DateTimeOffset.UtcNow.AddHours(4),
            };

            var secret = Environment.GetEnvironmentVariable("email-secret", EnvironmentVariableTarget.Process);

            if (Upload(log, "http://grimdawn.dreamcrash.org/ia/backup/auth.php", $"token={secret}&target={email}&code={code}"))
            {
                var table = client.GetTableReference(EmailAuthToken.TableName);
                await table.CreateIfNotExistsAsync();

                await table.ExecuteAsync(TableOperation.Insert(auth));

                log.Info($"Successfully posted email for {email}");
            }

            return(new OkObjectResult(new ResponseDto {
                Token = token
            }));
        }
コード例 #2
0
        public static async Task <IActionResult> Run(
            [HttpTrigger(AuthorizationLevel.Anonymous, "post", "options", Route = null)] HttpRequest req,
            [StorageAccount("StorageConnectionString")] CloudStorageAccount storageAccount,
            TraceWriter log
            )
        {
            var token  = req.Query["token"];
            var code   = req.Query["code"];
            var client = storageAccount.CreateCloudTableClient();

            if (string.IsNullOrWhiteSpace(token))
            {
                return(new BadRequestObjectResult("The query parameter \"token\" is empty or missing"));
            }
            else if (string.IsNullOrWhiteSpace(code))
            {
                return(new BadRequestObjectResult("The query parameter \"code\" is empty or missing"));
            }

            log.Info($"E-mail verification request received for {token}");

            // Throttling required for verification as well, to prevent infinite attempts on a token.
            var throttleService = new ThrottleService(storageAccount.CreateCloudTableClient(), log);
            var throttled       = (await throttleService.ThrottleOrIncrement("attempt-" + token)) || (await throttleService.ThrottleOrIncrement("attempt-" + IpUtility.GetClientIp(req)));

            if (throttled)
            {
                return(new StatusCodeResult(429));
            }

            var table = client.GetTableReference(EmailAuthToken.TableName);
            await table.CreateIfNotExistsAsync();

            var query = TableQuery.CombineFilters(
                TableQuery.GenerateFilterCondition("PartitionKey", QueryComparisons.Equal, token),
                TableOperators.And,
                TableQuery.GenerateFilterCondition("RowKey", QueryComparisons.Equal, code)
                );
            var exQuery = new TableQuery <EmailAuthToken>().Where(query);

            var entry = await QueryHelper.Get(table, exQuery);

            if (entry != null)
            {
                if (DateTimeOffset.UtcNow < entry.Expiration)
                {
                    log.Info($"Authentication successful for {entry.Email}");

                    var auth = new Authentication {
                        PartitionKey = Authentication.PartitionName,
                        RowKey       = (Guid.NewGuid().ToString() + Guid.NewGuid().ToString()).Replace("-", ""),
                        Identity     = entry.Email
                    };

                    var authTable = client.GetTableReference(Authentication.TableName);
                    await authTable.CreateIfNotExistsAsync();

                    await authTable.ExecuteAsync(TableOperation.Insert(auth));

                    return(new OkObjectResult(new VerifyEmailTokenResponseDto {
                        Success = true,
                        Token = auth.RowKey
                    }));
                }
                else
                {
                    log.Info($"Authentication token {token} for {entry.Email} has already expired, expiration {entry.Expiration}");

                    return(new OkObjectResult(new VerifyEmailTokenResponseDto {
                        Success = false
                    }));
                }
            }
            else
            {
                log.Info("No entry found");
                return(new OkObjectResult(new VerifyEmailTokenResponseDto {
                    Success = false
                }));
            }
        }