public async Task <Mosaic> CreateMosaic(string userId, string galleryId, string name, Stream stream)
        {
            var tempFile = Path.GetTempFileName();

            try
            {
                var mosaicId = name + "-" + Guid.NewGuid().ToString();
                using (var fileStream = File.OpenWrite(tempFile))
                {
                    Utilities.CopyStream(stream, fileStream);
                }

                var putRequest = new PutObjectRequest
                {
                    BucketName = this._appOptions.MosaicStorageBucket,
                    Key        = S3KeyManager.DetermineS3Key(userId, mosaicId, S3KeyManager.ImageType.Original),
                    FilePath   = tempFile
                };
                await this._s3Client.PutObjectAsync(putRequest).ConfigureAwait(false);

                var mosaic = new Mosaic
                {
                    UserId     = userId,
                    MosaicId   = mosaicId,
                    CreateDate = DateTime.UtcNow,
                    Name       = name,
                    Status     = Mosaic.Statuses.Creating
                };

                var input = new ExecutionInput
                {
                    TableGalleryItems = this._appOptions.TableGalleryItems,
                    TableMosaic       = this._appOptions.TableMosaic,
                    Bucket            = this._appOptions.MosaicStorageBucket,
                    SourceKey         = putRequest.Key,
                    GalleryId         = galleryId,
                    MosaicId          = mosaicId,
                    UserId            = userId
                };

                var stepResponse = await this._stepClient.StartExecutionAsync(new StartExecutionRequest
                {
                    StateMachineArn = this._appOptions.StateMachineArn,
                    Name            = $"{Utilities.MakeSafeName(putRequest.Key, 80)}",
                    Input           = JsonConvert.SerializeObject(input)
                }).ConfigureAwait(false);

                mosaic.ExecutionArn = stepResponse.ExecutionArn;
                await this._ddbContext.SaveAsync(mosaic).ConfigureAwait(false);

                return(mosaic);
            }
            finally
            {
                if (File.Exists(tempFile))
                {
                    File.Delete(tempFile);
                }
            }
        }
        public async Task OnGet()
        {
            var search = this._ddbContext.QueryAsync <Mosaic>(this.HttpContext.User.Identity.Name);

            this.Mosaics = new List <MosaicSummary>();
            foreach (var item in (await search.GetRemainingAsync()).OrderByDescending(x => x.CreateDate))
            {
                var summary = new MosaicSummary(item)
                {
                    MosaicFullUrl = this._s3Client.GetPreSignedURL(new GetPreSignedUrlRequest
                    {
                        BucketName = _appOptions.MosaicStorageBucket,
                        Key        = S3KeyManager.DetermineS3Key(this.HttpContext.User.Identity.Name, item.MosaicId, S3KeyManager.ImageType.FullMosaic),
                        Expires    = DateTime.UtcNow.AddHours(1)
                    }),
                    MosaicThumbnailUrl = this._s3Client.GetPreSignedURL(new GetPreSignedUrlRequest
                    {
                        BucketName = _appOptions.MosaicStorageBucket,
                        Key        = S3KeyManager.DetermineS3Key(this.HttpContext.User.Identity.Name, item.MosaicId, S3KeyManager.ImageType.ThumbnailMosaic),
                        Expires    = DateTime.UtcNow.AddHours(1)
                    })
                };

                this.Mosaics.Add(summary);
            }
        }
        public async Task StartGalleryImport(string userId, string galleryId, Stream stream)
        {
            var tempFile = Path.GetTempFileName();

            try
            {
                using (var fileStream = File.OpenWrite(tempFile))
                {
                    Utilities.CopyStream(stream, fileStream);
                }

                var transferRequest = new TransferUtilityUploadRequest
                {
                    BucketName = this._appOptions.MosaicStorageBucket,
                    Key        = S3KeyManager.DetermineS3Key(userId, galleryId, S3KeyManager.ImageType.TileGallerySource),
                    FilePath   = tempFile
                };
                await this._s3TransferUtility.UploadAsync(transferRequest).ConfigureAwait(false);

                // Default verb is GET, and 60min validity should be more than sufficient!
                var importUrl = this._s3Client.GetPreSignedURL(new GetPreSignedUrlRequest
                {
                    BucketName = transferRequest.BucketName,
                    Key        = transferRequest.Key,
                    Expires    = DateTime.Now.AddHours(1)
                });

                var submitRequest = new SubmitJobRequest
                {
                    JobQueue           = this._appOptions.JobQueueArn,
                    JobDefinition      = this._appOptions.JobDefinitionArn,
                    JobName            = $"{Utilities.MakeSafeName(galleryId, 128)}",
                    ContainerOverrides = new ContainerOverrides
                    {
                        Environment = new List <Amazon.Batch.Model.KeyValuePair>
                        {
                            new Amazon.Batch.Model.KeyValuePair {
                                Name = Constants.ZIP_EXPANDER_BUCKET, Value = this._appOptions.MosaicStorageBucket
                            },
                            new Amazon.Batch.Model.KeyValuePair {
                                Name = Constants.ZIP_EXPANDER_DDB_TABLE, Value = this._appOptions.TableGallery
                            },
                            new Amazon.Batch.Model.KeyValuePair {
                                Name = Constants.ZIP_EXPANDER_USER_ID, Value = userId
                            },
                            new Amazon.Batch.Model.KeyValuePair {
                                Name = Constants.ZIP_EXPANDER_GALLERY_ID, Value = galleryId
                            },
                            new Amazon.Batch.Model.KeyValuePair {
                                Name = Constants.ZIP_EXPANDER_IMPORT_URL, Value = importUrl
                            }
                        }
                    }
                };

                await this._batchClient.SubmitJobAsync(submitRequest).ConfigureAwait(false);
            }
            finally
            {
                if (File.Exists(tempFile))
                {
                    File.Delete(tempFile);
                }
            }
        }
Esempio n. 4
0
        public async Task <State> FunctionHandler(State state, ILambdaContext context)
        {
            if (Directory.Exists(this.TileImageCacheDirectory))
            {
                Directory.Delete(this.TileImageCacheDirectory, true);
            }

            Directory.CreateDirectory(this.TileImageCacheDirectory);

            context.Logger.LogLine("Loading mosaic layout info");
            var mosaicLayoutInfo =
                await MosaicLayoutInfoManager.Load(this.S3Client, state.Bucket, state.MosaicLayoutInfoKey);

            var width  = mosaicLayoutInfo.ColorMap.GetLength(0) * state.TileSize;
            var height = mosaicLayoutInfo.ColorMap.GetLength(1) * state.TileSize;

            context.Logger.LogLine($"Creating pixel data array {width}x{height}");
            var pixalData = new Rgba32[width * height];

            for (int i = 0; i < pixalData.Length; i++)
            {
                pixalData[i] = Rgba32.Black;
            }

            context.Logger.LogLine($"Creating blank image");
            using (var rawImage = Image.LoadPixelData(pixalData, width, height))
            {
                context.Logger.LogLine($"Created blank image");
                for (int x = 0; x < mosaicLayoutInfo.ColorMap.GetLength(0); x++)
                {
                    int xoffset = x * state.TileSize;
                    context.Logger.LogLine($"Processing row {x}");
                    for (int y = 0; y < mosaicLayoutInfo.ColorMap.GetLength(1); y++)
                    {
                        int yoffset = y * state.TileSize;
                        var tileId  = mosaicLayoutInfo.TileMap[x, y];
                        var tileKey = mosaicLayoutInfo.IdToTileKey[tileId];

                        using (var tileImage = await LoadTile(state.Bucket, tileKey, context))
                        {
                            for (int x1 = 0; x1 < state.TileSize; x1++)
                            {
                                for (int y1 = 0; y1 < state.TileSize; y1++)
                                {
                                    rawImage[x1 + xoffset, y1 + yoffset] = tileImage[x1, y1];
                                }
                            }
                        }
                    }
                }

                // Write full mosaic to S3
                {
                    var finalOutputStream = new MemoryStream();
                    rawImage.Save(finalOutputStream, new SixLabors.ImageSharp.Formats.Jpeg.JpegEncoder());
                    finalOutputStream.Position = 0;

                    var destinationKey =
                        S3KeyManager.DetermineS3Key(state.UserId, state.MosaicId, S3KeyManager.ImageType.FullMosaic);
                    context.Logger.LogLine(
                        $"Saving full mosaic to {destinationKey} with size {finalOutputStream.Length}");
                    await this.S3Client.PutObjectAsync(new PutObjectRequest
                    {
                        BucketName  = state.Bucket,
                        Key         = destinationKey,
                        InputStream = finalOutputStream
                    });
                }

                // Write web size mosaic to S3
                await SaveResize(state, rawImage, Constants.IMAGE_WEB_WIDTH, Constants.IMAGE_WEB_HEIGHT,
                                 S3KeyManager.DetermineS3Key(state.UserId, state.MosaicId, S3KeyManager.ImageType.WebMosaic),
                                 context);

                // Write thumbnail mosaic to S3
                await SaveResize(state, rawImage, Constants.IMAGE_THUMBNAIL_WIDTH, Constants.IMAGE_THUMBNAIL_HEIGHT,
                                 S3KeyManager.DetermineS3Key(state.UserId, state.MosaicId, S3KeyManager.ImageType.ThumbnailMosaic),
                                 context);

                return(state);
            }
        }