private void ProgressHandler(IUploadProgress obj, VideosResource.InsertMediaUpload video) { if (obj.Status == UploadStatus.Failed) { MessageBox.Show(obj.Exception.Message); foreach (var help in obj.Exception.Data.Values) { MessageBox.Show(help.ToString()); } } if (obj.Status == UploadStatus.Uploading) { Dispatcher.BeginInvoke( new Action(() => { for (int i = 0; i < UploadQueue.Items.Count; i++) { System.Windows.Controls.Border UploadEntry = UploadQueue.Items.GetItemAt(i) as System.Windows.Controls.Border; if (UploadEntry.FindChild <TextBlock>("Stats").Text.Contains(video.Body.Snippet.Title)) { UploadEntry.FindChild <ProgressBar>("Progress").Value = obj.BytesSent / filesize; string[] Stats = UploadEntry.FindChild <TextBlock>("Stats").Text.Split('\n'); DateTime StartTime = DateTime.Parse(Stats[2].Substring(12)); TimeSpan ElapsedTime = DateTime.Now - StartTime; TimeSpan RemainingTime = TimeSpan.FromTicks((long)(ElapsedTime.Ticks * (100 - (obj.BytesSent / filesize) * 100))); UploadEntry.FindChild <TextBlock>("Stats").Text = Stats[0] + "\n" + Math.Round(obj.BytesSent / filesize, 3) + "%\n" + Stats[2] + "\nFinished in:\t" + RemainingTime.ToString(@"dd\.hh\:mm\:ss"); } } }) ); } }
/// <summary> /// Execute the upload of one file to YouTube. /// </summary> private static async Task ExecuteUploadProcess() { const int HTTP_CLIENT_TIMEOUT_MINUTES = 2; UserCredential OAUth2Credential = null; YouTubeService YouTube = null; bool OKtoContinue = true; try { OAUth2Credential = await GetCredential(); if (OAUth2Credential != null && OAUth2Credential.Token != null) { Console.WriteLine("Token Issued: {0}", OAUth2Credential.Token.Issued); } else { OKtoContinue = false; } } catch (Exception ex) { Console.WriteLine("Google Authorization: {0}", ex.Message); OKtoContinue = false; } if (OKtoContinue) { try { YouTube = new YouTubeService(new BaseClientService.Initializer { HttpClientInitializer = OAUth2Credential, GZipEnabled = true, ApplicationName = Assembly.GetExecutingAssembly().GetName().Name }); // // Default Timeout is 1 minute 40 seconds. // The following changes it to 2 minutes. YouTube.HttpClient.Timeout = TimeSpan.FromMinutes(HTTP_CLIENT_TIMEOUT_MINUTES); } catch (Exception ex) { Console.WriteLine(String.Format("YouTubeService error: {0}", ex.Message)); OKtoContinue = false; } if (OKtoContinue) { Video VideoResource = CreateVideoResource(); using (FileStream VideoFileStream = new FileStream(VIDEOFULLPATHFILENAME, FileMode.Open, FileAccess.Read, FileShare.Read)) { VideoInsertRequest = YouTube.Videos.Insert(VideoResource, "snippet,status,recordingDetails", VideoFileStream, "video/*"); await PerformUpload(); VideoFileStream.Close(); } } } }
internal YouTubeUploadRequest(string FileName, YouTubeService YouTubeService, Video Video) { _dataStream = new FileStream(FileName, FileMode.Open); _videoInsertRequest = YouTubeService.Videos.Insert(Video, "snippet,status", _dataStream, "video/*"); _videoInsertRequest.ProgressChanged += VideosInsertRequest_ProgressChanged; _videoInsertRequest.ResponseReceived += VideosInsertRequest_ResponseReceived; }
public void StatusReset() { mediaStream.Dispose(); mediaStream = null; Progress = 0; UploadingStatus = UploadingStatus.Queued; changedThumbnail = true; videoInsertRequest = null; }
private async void UploadToYouTube(StorageFile file) { ProgressRing.Visibility = Visibility.Visible; ProgressRing.IsActive = true; var clientSecretFile = new Uri("ms-appx:///client_id.json"); UserCredential credential = await GoogleWebAuthorizationBroker.AuthorizeAsync( clientSecretFile, // This OAuth 2.0 access scope allows an application to upload files to the // authenticated user's YouTube channel, but doesn't allow other types of access. new[] { YouTubeService.Scope.YoutubeUpload }, "*****@*****.**", CancellationToken.None ); var youtubeService = new YouTubeService(new BaseClientService.Initializer { HttpClientInitializer = credential, ApplicationName = "Lineage Suncasts" }); var video = new Video { Snippet = new VideoSnippet { Title = $"{file.Name}", Description = "A test recording made by the Suncasts app.", // Tags = new string[] {"tag1", "tag2"}, CategoryId = "22" }, Status = new VideoStatus { PrivacyStatus = "unlisted" } }; // See https://developers.google.com/youtube/v3/docs/videoCategories/list // or "private" or "public" Stream fs = (await file.OpenReadAsync()).AsStreamForRead(); VideosResource.InsertMediaUpload videosInsertRequest = youtubeService.Videos.Insert(video, "snippet,status", fs, "video/*"); videosInsertRequest.ProgressChanged += OnVideoInsertProgressChanged; videosInsertRequest.ResponseReceived += OnVideosInsertRequestResponseReceived; videosInsertRequest.ChunkSize = videosInsertRequest.ChunkSize; await videosInsertRequest.UploadAsync(); ProgressRing.IsActive = false; ProgressRing.Visibility = Visibility.Collapsed; }
public async Task AddVideoAsync(VideoModel videoModel, IProgress <UploadStatusModel> progress, CancellationToken cancellationToken) { _logger.LogTrace($"{GetType()} - BEGIN {nameof(AddVideoAsync)}"); try { YouTubeService ytService = await _ytServiceProvider.CreateServiceAsync(cancellationToken); IEnumerable <VideoCategory> categories = await GetCategoriesAsync(cancellationToken); VideoCategory category = categories.FirstOrDefault(c => c.Snippet.Title == videoModel.Metadata.Category); Video video = new Video(); video.HydrateFromVideoModel(videoModel.Metadata); video.Snippet.CategoryId = category.Id; long videoBytesLength = videoModel.VideoStream.Length; VideosResource.InsertMediaUpload req = ytService.Videos.Insert( video, new string[] { "snippet", "status" }, videoModel.VideoStream, "application/octet-stream" ); req.NotifySubscribers = true; req.ProgressChanged += ((uProgress) => { UploadStatusModel status = new UploadStatusModel(videoModel.Metadata); status.IsComplete = false; status.IsSuccess = false; status.StatusText = $"{uProgress.Status} ({uProgress.BytesSent} bytes sent)"; status.CompletionRate = (uProgress.BytesSent * 100) / videoBytesLength; progress.Report(status); _logger.LogInformation($"Upload of video : {uProgress.BytesSent} bytes sent"); }); req.ResponseReceived += ((video) => { _logger.LogInformation($"Upload of video is complete : {video.Id}"); UploadStatusModel status = new UploadStatusModel(videoModel.Metadata); status.IsComplete = true; videoModel.Metadata.VideoUrl = BuildVideoUrl(video.Id); if (!string.IsNullOrEmpty(video.ProcessingDetails?.ProcessingFailureReason)) { _logger.LogError($"Error while processing video upload : {video.ProcessingDetails.ProcessingFailureReason}"); _logger.LogError($"{video.ProcessingDetails.ProcessingIssuesAvailability ?? "No reason"}"); progress.Report(status); } else { status.IsSuccess = true; status.CompletionRate = 100; progress.Report(status); } }); IUploadProgress res = await req.UploadAsync(cancellationToken); videoModel.VideoStream.Close(); } catch (Exception e) { _logger.LogError("An error occurred while uploading video", e); videoModel.VideoStream.Close(); throw; } }
internal async Task AddVideo() { Console.WriteLine("Logging in."); UserCredential credential; try { using (FileStream stream = new FileStream(Path.GetFullPath(AppDomain.CurrentDomain.BaseDirectory + @"\client_secrets.json"), FileMode.Open, FileAccess.Read)) { credential = await GoogleWebAuthorizationBroker.AuthorizeAsync( GoogleClientSecrets.Load(stream).Secrets, new[] { YouTubeService.Scope.Youtube, YouTubeService.Scope.YoutubeUpload }, "user", CancellationToken.None ); stream.Close(); stream.Dispose(); } } catch (Exception e) { Console.Error.WriteLine("Error: " + e.Message); throw new Exception("Error: " + e.Message); } Console.WriteLine("Login OK."); YouTubeService youtubeService = new YouTubeService(new BaseClientService.Initializer() { HttpClientInitializer = credential, ApplicationName = "Google.Apis.Auth" }); string Parts = "snippet"; Video video = new Video(); video.Snippet = new VideoSnippet(); video.Snippet.Title = Configuration[FSM_ArgParser.Title] as string; if (Configuration.ContainsKey(FSM_ArgParser.Description)) { video.Snippet.Description = Configuration[FSM_ArgParser.Description] as string; } if (Configuration.ContainsKey(FSM_ArgParser.Tags)) { video.Snippet.Tags = Configuration[FSM_ArgParser.Tags] as List <string>; } video.Snippet.CategoryId = Configuration[FSM_ArgParser.CategoryID] as string; if (Configuration.ContainsKey(FSM_ArgParser.PrivacyStatus) || Configuration.ContainsKey(FSM_ArgParser.PublicStatsViewable)) { Parts += ",status"; video.Status = new VideoStatus(); if (Configuration.ContainsKey(FSM_ArgParser.PrivacyStatus)) { video.Status.PrivacyStatus = Configuration[FSM_ArgParser.PrivacyStatus] as string; } if (Configuration.ContainsKey(FSM_ArgParser.PublicStatsViewable)) { video.Status.PublicStatsViewable = (bool)Configuration[FSM_ArgParser.PublicStatsViewable]; } } if (Configuration.ContainsKey(FSM_ArgParser.Dimension) || Configuration.ContainsKey(FSM_ArgParser.Definition)) { Parts += ",contentDetails"; video.ContentDetails = new VideoContentDetails(); if (Configuration.ContainsKey(FSM_ArgParser.Dimension)) { video.ContentDetails.Dimension = Configuration[FSM_ArgParser.Dimension] as string; } if (Configuration.ContainsKey(FSM_ArgParser.Definition)) { video.ContentDetails.Definition = Configuration[FSM_ArgParser.Definition] as string; } } if (Configuration.ContainsKey(FSM_ArgParser.LocationDescription) || Configuration.ContainsKey(FSM_ArgParser.Location_Latitude) || Configuration.ContainsKey(FSM_ArgParser.Location_Longitude) || Configuration.ContainsKey(FSM_ArgParser.RecordingDate)) { Parts += ",recordingDetails"; video.RecordingDetails = new VideoRecordingDetails(); if (Configuration.ContainsKey(FSM_ArgParser.LocationDescription)) { video.RecordingDetails.LocationDescription = Configuration[FSM_ArgParser.LocationDescription] as string; } if (Configuration.ContainsKey(FSM_ArgParser.RecordingDate)) { video.RecordingDetails.RecordingDate = (DateTime)Configuration[FSM_ArgParser.RecordingDate]; } if (Configuration.ContainsKey(FSM_ArgParser.Location_Latitude) || Configuration.ContainsKey(FSM_ArgParser.Location_Longitude)) { video.RecordingDetails.Location = new GeoPoint(); if (Configuration.ContainsKey(FSM_ArgParser.Location_Latitude)) { video.RecordingDetails.Location.Latitude = (double)Configuration[FSM_ArgParser.Location_Latitude]; } if (Configuration.ContainsKey(FSM_ArgParser.Location_Longitude)) { video.RecordingDetails.Location.Longitude = (double)Configuration[FSM_ArgParser.Location_Longitude]; } } } string filePath = Configuration[FSM_ArgParser.File] as string; Console.WriteLine("Selected file: {0} ", filePath); Console.WriteLine("File size: {0} ", FileSize); int Chunksize = (int)((FileSize / 100) / ResumableUpload <Video> .MinimumChunkSize) * ResumableUpload <Video> .MinimumChunkSize; if (FileSize < ResumableUpload <Video> .MinimumChunkSize) { Chunksize = ResumableUpload <Video> .MinimumChunkSize; } else if (FileSize > (ResumableUpload <Video> .MinimumChunkSize * 4 * 40)) { Chunksize = ResumableUpload <Video> .MinimumChunkSize * 4 * 40; } using (FileStream fileStream = new FileStream(filePath, FileMode.Open, FileAccess.Read, FileShare.Read, Chunksize / 8)) { Console.WriteLine("Starting upload."); VideosResource.InsertMediaUpload videosInsertRequest = youtubeService.Videos.Insert(video, Parts, fileStream, "video/*"); videosInsertRequest.ChunkSize = Chunksize; videosInsertRequest.ProgressChanged += videosInsertRequest_ProgressChanged; TimeMbps = DateTime.Now; DataMbps = 0; try { videosInsertRequest.Upload(); } catch { } const int max_resumes = 25; int resumes = 0; while ((videosInsertRequest.GetProgress().Status != UploadStatus.Completed) && resumes < max_resumes) { resumes++; try { videosInsertRequest.Resume(); } catch { } } VideoID = videosInsertRequest.ResponseBody.Id; if (videosInsertRequest.GetProgress().Status != UploadStatus.Completed) { Console.Error.Write("Upload failed."); throw new Exception("Upload failed."); } fileStream.Close(); fileStream.Dispose(); } if (Configuration.ContainsKey(FSM_ArgParser.DisableComment) || Configuration.ContainsKey(FSM_ArgParser.DisableRating) || Configuration.ContainsKey(FSM_ArgParser.DisableVideoRespond)) { Console.WriteLine( "Warning: DisableComment, DisableRating and DisableVideoRespond are no longer functional due to the decrepation of the YouTube v2 API.\n" + "Google refuses to include these options into the YouTube v3 API.\n" + "Please use the YouTube web UI to manipulate these options." ); } }
private async Task Run(string title, string description, string[] tags, PrivacyStatus privacyStatus, IFormFile file) { UserCredential userCredential; GoogleAuthorizationCodeFlow.Initializer initializer = new GoogleAuthorizationCodeFlow.Initializer(); initializer.ClientSecrets = new ClientSecrets() { ClientId = _youtubeClientSecret.client_id, ClientSecret = _youtubeClientSecret.client_secret }; initializer.Scopes = new string[1] { YouTubeService.Scope.YoutubeUpload }; //var token = new TokenResponse { RefreshToken = _youtubeClientSecret.token_uri }; //userCredential = new UserCredential(new GoogleAuthorizationCodeFlow( // new GoogleAuthorizationCodeFlow.Initializer // { // ClientSecrets = initializer.ClientSecrets // }), // "user", // token); string token = await GenerateTokenAsync(); if (token != "") { userCredential = new UserCredential(new GoogleAuthorizationCodeFlow(initializer), "me", new TokenResponse() { RefreshToken = token, TokenType = "Bearer", ExpiresInSeconds = new long?(3599L), AccessToken = token }); YouTubeService youtubeService = new YouTubeService(new BaseClientService.Initializer() { HttpClientInitializer = userCredential, ApplicationName = Assembly.GetExecutingAssembly().GetName().Name }); Video video = new Video() { Snippet = new VideoSnippet() }; video.Snippet.Title = title; video.Snippet.Tags = tags; video.Snippet.Description = description; video.Snippet.CategoryId = ""; video.Status = new VideoStatus { PrivacyStatus = privacyStatus.ToString() }; await Task.Run(() => { VideosResource.InsertMediaUpload insertMediaUpload = youtubeService.Videos.Insert(video, "snippet,status", file.OpenReadStream(), "video/*"); insertMediaUpload.ProgressChanged += videosInsertRequest_ProgressChanged; insertMediaUpload.ResponseReceived += VideosInsertRequest_ResponseReceived; insertMediaUpload.UploadAsync().Wait(); }); } else { return; } }
private async Task <string> RunPostAsync(string title, string description, string[] tags, PrivacyStatus privacyStatus, IFormFile file) { try { var retryCount = 0; GoogleAuthorizationCodeFlow.Initializer initializer = new GoogleAuthorizationCodeFlow.Initializer { ClientSecrets = new ClientSecrets() { ClientId = _youtubeClientSecret.client_id, ClientSecret = _youtubeClientSecret.client_secret }, Scopes = new string[1] { YouTubeService.Scope.YoutubeUpload } }; ReGenerateToken: if (retryCount > 3) { return(""); } var token = await GenerateTokenAsync(); if (token == "") { retryCount += 1; goto ReGenerateToken; } var userCredential = new UserCredential(new GoogleAuthorizationCodeFlow(initializer), "me", new TokenResponse() { RefreshToken = token, TokenType = "Bearer", ExpiresInSeconds = new long?(3599L), AccessToken = token }); YouTubeService youtubeService = new YouTubeService(new BaseClientService.Initializer() { HttpClientInitializer = userCredential, ApplicationName = Assembly.GetExecutingAssembly().GetName().Name }); Video video = new Video() { Snippet = new VideoSnippet() }; video.Snippet.Title = title; video.Snippet.Tags = tags; video.Snippet.Description = description; video.Snippet.CategoryId = ""; video.Status = new VideoStatus { PrivacyStatus = privacyStatus.ToString() }; VideosResource.InsertMediaUpload insertMediaUpload = youtubeService.Videos.Insert(video, "snippet,status", file.OpenReadStream(), "video/*"); // insertMediaUpload.ProgressChanged += PostVideosInsertRequest_ProgressChanged; // insertMediaUpload.ResponseReceived += PostVideosInsertRequest_ResponseReceived; await insertMediaUpload.UploadAsync(); return(insertMediaUpload.ResponseBody?.Id); } catch (Exception e) { return(""); } }
private async Task Run() { UserCredential credential; string clientSecretsPath = CredentialsManager.GetClientSecretsLocation(); using (FileStream stream = new FileStream(clientSecretsPath, FileMode.Open, FileAccess.Read)) { credential = await GoogleWebAuthorizationBroker.AuthorizeAsync( GoogleClientSecrets.Load(stream).Secrets, // This OAuth 2.0 access scope allows an application to upload files to the // authenticated user's YouTube channel, but doesn't allow other types of access. new[] { YouTubeService.Scope.YoutubeUpload }, "user", CancellationToken.None ); } YouTubeService youtubeService = new YouTubeService(new BaseClientService.Initializer() { HttpClientInitializer = credential, ApplicationName = Assembly.GetExecutingAssembly().GetName().Name }); Video video = new Video { Snippet = new VideoSnippet { Title = "Default Video Title", Description = "Default Video Description", Tags = new[] { "tag1", "tag2" }, CategoryId = "22" } }; // See https://developers.google.com/youtube/v3/docs/videoCategories/list video.Status = new VideoStatus { PrivacyStatus = "unlisted" }; // or "private" or "public" string filePath = AssetsManager.GetSampleVideoPath(); // Replace with path to actual movie file. using (FileStream fileStream = new FileStream(filePath, FileMode.Open)) { VideosResource.InsertMediaUpload videosInsertRequest = youtubeService.Videos.Insert(video, "snippet,status", fileStream, "video/*"); videosInsertRequest.ProgressChanged += VideosInsertRequestProgressChanged; videosInsertRequest.ResponseReceived += VideosInsertRequestResponseReceived; await videosInsertRequest.UploadAsync(); } void VideosInsertRequestProgressChanged(IUploadProgress progress) { switch (progress.Status) { case UploadStatus.Uploading: Console.WriteLine("{0} bytes sent.", progress.BytesSent); break; case UploadStatus.Failed: Console.WriteLine("An error prevented the upload from completing.\n{0}", progress.Exception); break; } } void VideosInsertRequestResponseReceived(Video videoParam) { Console.WriteLine("Video id '{0}' was successfully uploaded.", videoParam.Id); } }
public async Task <UploadResult> UploadStart(DataChunkSize dataChunkSize = DataChunkSize.ChunkSize_10MB) { youtubeSession.TryGetTarget(out YouTubeSession session); if (UploadingStatus == UploadingStatus.UploadCanceled) { UploadingStatus = UploadingStatus.Queued; video.Id = null; if (mediaStream != null) { mediaStream.Dispose(); } mediaStream = null; Progress = 0; TotalUploaded = 0; TimeRemaining = new TimeSpan(); videoInsertRequest = null; IsManuallyPaused = false; } if (video.Id != null && ( UploadingStatus == UploadingStatus.UploadFailed || UploadingStatus == UploadingStatus.UploadCompleted || UploadingStatus == UploadingStatus.UpdateFailed || UploadingStatus == UploadingStatus.UpdateComplete )) { UploadingStatus = UploadingStatus.UpdateStart; await UploadThumbnail(video.Id); var videoUpdateRequest = session.YouTubeService.Videos.Update(video, "snippet,status"); var result = await videoUpdateRequest.ExecuteAsync(); if (result != null) { UploadingStatus = UploadingStatus.UpdateComplete; PC(nameof(UploadingStatus)); Completed?.Invoke(this, EventArgs.Empty); return(UploadResult.Succeed); } else { UploadingStatus = UploadingStatus.UpdateFailed; PC(nameof(UploadingStatus)); Failed?.Invoke(this, EventArgs.Empty); return(UploadResult.Succeed); } } if (!(UploadingStatus == UploadingStatus.Queued || UploadingStatus == UploadingStatus.UploadFailed)) { return(UploadResult.AlreadyUploading); } UploadingStatus = UploadingStatus.PrepareUpload; bool virIsNull = videoInsertRequest == null; if (virIsNull) { videoInsertRequest = session.YouTubeService.Videos.Insert(video, "snippet,status", mediaStream, "video/*"); if (videoInsertRequest == null) { UploadingStatus = UploadingStatus.UploadFailed; return(UploadResult.FailedUploadRequest); } DataChunkSize = dataChunkSize; videoInsertRequest.ProgressChanged += (uploadProgress) => { TotalUploaded = uploadProgress.BytesSent; Progress = uploadProgress.BytesSent / ( double )mediaStream.Length; double percentage = (uploadProgress.BytesSent - lastSentBytes) / ( double )mediaStream.Length; lastSentBytes = uploadProgress.BytesSent; double totalSeconds = (DateTime.Now.TimeOfDay - startTime).TotalSeconds; TimeRemaining = Progress != 0 ? TimeSpan.FromSeconds((totalSeconds / Progress) * (1 - Progress)) : TimeSpan.FromDays(999); switch (uploadProgress.Status) { case UploadStatus.Starting: startTime = DateTime.Now.TimeOfDay; UploadingStatus = UploadingStatus.UploadStart; Started?.Invoke(this, EventArgs.Empty); break; case UploadStatus.Uploading: UploadingStatus = UploadingStatus.Uploading; Uploading?.Invoke(this, EventArgs.Empty); break; case UploadStatus.Failed: UploadingStatus = UploadingStatus.UploadFailed; Failed?.Invoke(this, EventArgs.Empty); break; case UploadStatus.Completed: UploadingStatus = UploadingStatus.UploadCompleted; Uploading?.Invoke(this, EventArgs.Empty); Completed?.Invoke(this, EventArgs.Empty); mediaStream.Dispose(); mediaStream = null; break; } PC(nameof(Progress)); PC(nameof(UploadingStatus)); PC(nameof(TotalUploaded)); PC(nameof(TimeRemaining)); }; videoInsertRequest.ResponseReceived += async(video) => { await UploadThumbnail(video.Id); foreach (var playlist in Playlists) { playlist.AddVideo(video.Id); } }; } try { startTime = DateTime.Now.TimeOfDay; cancellationTokenSource = new CancellationTokenSource(); var uploadStatus = virIsNull ? await videoInsertRequest.UploadAsync(cancellationTokenSource.Token) : await videoInsertRequest.ResumeAsync(cancellationTokenSource.Token); cancellationTokenSource.Dispose(); video = videoInsertRequest.ResponseBody ?? video; if (uploadStatus.Status == UploadStatus.NotStarted) { UploadingStatus = UploadingStatus.UploadFailed; return(UploadResult.CannotStartUpload); } } catch { UploadingStatus = UploadingStatus.UploadFailed; return(UploadResult.UploadCanceled); } return(UploadResult.Succeed); }