From 53da5c81b07bd47aff70061acbaa774b8c71d205 Mon Sep 17 00:00:00 2001 From: Sriram Bhargav Date: Thu, 7 Dec 2023 17:24:13 +0530 Subject: [PATCH] TP-48508 | Adding helper to download files form a google drive directory (#305) * TP-48508 | Adding helper to download files form a google drive directory --- Makefile | 2 +- common/util/common_util.go | 8 + common/util/constant.go | 8 +- common/util/file_util.go | 21 ++ pkg/google/googleDrive/drive_actions.go | 25 ++- pkg/google/googleDrive/drive_interface.go | 8 +- service/google/drive_service.go | 88 +++++++-- service/google/drive_service_test.go | 186 +++++++++++++++++- .../monitoring_service_client_test.go | 7 +- 9 files changed, 315 insertions(+), 38 deletions(-) diff --git a/Makefile b/Makefile index af9833a..fbe7ac7 100644 --- a/Makefile +++ b/Makefile @@ -33,7 +33,7 @@ generatemocks: @rm -rf $(CURDIR)/mocks @echo "Generating mocks..." @mkdir "mocks" - cd $(CURDIR)/pkg/google/googleDrive && minimock -i GoogleDriveActions -s _mock.go -o $(CURDIR)/mocks + cd $(CURDIR)/pkg/google/googleDrive && minimock -i DriveActions -s _mock.go -o $(CURDIR)/mocks cd $(CURDIR)/pkg/conference && minimock -i ICalendarActions -s _mock.go -o $(CURDIR)/mocks cd $(CURDIR)/pkg/rest/ && minimock -i HttpRestClient -s _mock.go -o $(CURDIR)/mocks cd $(CURDIR)/pkg/atlassian/ && minimock -i JiraClient -s _mock.go -o $(CURDIR)/mocks diff --git a/common/util/common_util.go b/common/util/common_util.go index b1f6d75..cca9fc9 100644 --- a/common/util/common_util.go +++ b/common/util/common_util.go @@ -276,3 +276,11 @@ func IsBlank(input string) bool { trimmedInput := strings.TrimSpace(input) return trimmedInput == "" } + +func GetFileExtensionFromMimeType(mimeType ContentType) string { + switch mimeType { + case ContentTypeTextHTML: + return ".html" + } + return "" +} diff --git a/common/util/constant.go b/common/util/constant.go index d9eb787..e389491 100644 --- a/common/util/constant.go +++ b/common/util/constant.go @@ -52,9 +52,7 @@ const ( SessionTokenHeader = "X-Session-Token" ) -const ( - GoogleDriveFileMimeType = "application/vnd.google-apps.folder" -) +const () const ( ConferenceMessage = "To discuss, use this *<%s|Meet link>*" @@ -63,7 +61,9 @@ const ( type ContentType string const ( - ContentTypeJSON = "application/json" + ContentTypeJSON = "application/json" + ContentTypeTextHTML = "text/html" + GoogleDriveFileMimeType = "application/vnd.google-apps.folder" ) const ( diff --git a/common/util/file_util.go b/common/util/file_util.go index d98dc6a..4f7ec1c 100644 --- a/common/util/file_util.go +++ b/common/util/file_util.go @@ -117,3 +117,24 @@ func CloseFile(file *os.File) { logger.Error(fmt.Sprintf("Error while closing file: %v", err)) } } + +func WriteToFile(fileLocation string, fileName string, contentReader io.ReadCloser) error { + file, err := os.Create(fileLocation + "/" + fileName) + if err != nil { + logger.Error(fmt.Sprintf("Error creating file with name %v : %v", fileName, err)) + return err + } + _, err = io.Copy(file, contentReader) + if err != nil { + logger.Error(fmt.Sprintf("Error copying file with name %v : %v", fileName, err)) + return err + } + return nil +} + +func DeleteDirectory(directoryPath string) { + err := os.RemoveAll(directoryPath) + if err != nil { + logger.Error(fmt.Sprintf("Error while deleting directory: %v", err)) + } +} diff --git a/pkg/google/googleDrive/drive_actions.go b/pkg/google/googleDrive/drive_actions.go index f44308f..db02ec6 100644 --- a/pkg/google/googleDrive/drive_actions.go +++ b/pkg/google/googleDrive/drive_actions.go @@ -4,14 +4,16 @@ import ( "context" "google.golang.org/api/drive/v3" "houston/common/util" + "net/http" "time" ) -type GoogleDriveActionsImpl struct { +type ActionsImpl struct { filesService *drive.FilesService } -func (driveActions *GoogleDriveActionsImpl) SearchInDrive(timeout time.Duration, query string) (*drive.FileList, error) { +func (driveActions *ActionsImpl) SearchInDrive(timeout time.Duration, query string) (*drive.FileList, + error) { driveContext, cancelFunc := context.WithTimeout(context.Background(), timeout) defer cancelFunc() fileList, err := driveActions.filesService.List().Q(query).Context(driveContext).Do() @@ -21,7 +23,8 @@ func (driveActions *GoogleDriveActionsImpl) SearchInDrive(timeout time.Duration, return fileList, nil } -func (driveActions *GoogleDriveActionsImpl) CreateDirectory(timeout time.Duration, directoryName string) (*drive.File, error) { +func (driveActions *ActionsImpl) CreateDirectory(timeout time.Duration, + directoryName string) (*drive.File, error) { driveContext, cancelFunc := context.WithTimeout(context.Background(), timeout) defer cancelFunc() directory := &drive.File{MimeType: util.GoogleDriveFileMimeType, Name: directoryName} @@ -32,7 +35,7 @@ func (driveActions *GoogleDriveActionsImpl) CreateDirectory(timeout time.Duratio return file, nil } -func (driveActions *GoogleDriveActionsImpl) DeleteFile(timeout time.Duration, fileId string) error { +func (driveActions *ActionsImpl) DeleteFile(timeout time.Duration, fileId string) error { driveContext, cancelFunc := context.WithTimeout(context.Background(), timeout) defer cancelFunc() err := driveActions.filesService.Delete(fileId).Context(driveContext).Do() @@ -42,7 +45,8 @@ func (driveActions *GoogleDriveActionsImpl) DeleteFile(timeout time.Duration, fi return nil } -func (driveActions *GoogleDriveActionsImpl) CopyFile(timeout time.Duration, fileId string, directoryId string) (*drive.File, error) { +func (driveActions *ActionsImpl) CopyFile(timeout time.Duration, fileId string, + directoryId string) (*drive.File, error) { driveContext, cancelFunc := context.WithTimeout(context.Background(), timeout) defer cancelFunc() copyFile := &drive.File{Parents: []string{directoryId}} @@ -52,3 +56,14 @@ func (driveActions *GoogleDriveActionsImpl) CopyFile(timeout time.Duration, file } return file, nil } + +func (driveActions *ActionsImpl) ExportFile(timeout time.Duration, fileId string, + mimeType string) (*http.Response, error) { + driveContext, cancelFunc := context.WithTimeout(context.Background(), timeout) + defer cancelFunc() + download, err := driveActions.filesService.Export(fileId, mimeType).Context(driveContext).Download() + if err != nil { + return nil, err + } + return download, nil +} diff --git a/pkg/google/googleDrive/drive_interface.go b/pkg/google/googleDrive/drive_interface.go index 56d6e07..f510fed 100644 --- a/pkg/google/googleDrive/drive_interface.go +++ b/pkg/google/googleDrive/drive_interface.go @@ -7,21 +7,23 @@ import ( "google.golang.org/api/option" "houston/internal/clients" "houston/logger" + "net/http" "time" ) -type GoogleDriveActions interface { +type DriveActions interface { SearchInDrive(timeout time.Duration, query string) (*drive.FileList, error) CreateDirectory(timeout time.Duration, directoryName string) (*drive.File, error) DeleteFile(timeout time.Duration, fileId string) error CopyFile(timeout time.Duration, fileId string, directoryId string) (*drive.File, error) + ExportFile(timeout time.Duration, fileId string, mimeType string) (*http.Response, error) } -func NewGoogleDriveActions() (*GoogleDriveActionsImpl, error) { +func NewGoogleDriveActions() (*ActionsImpl, error) { driveService, err := drive.NewService(context.Background(), option.WithTokenSource(clients.GetGoogleTokenSource())) if err != nil { logger.Error("Unable to retrieve Drive client", zap.Error(err)) return nil, err } - return &GoogleDriveActionsImpl{filesService: driveService.Files}, nil + return &ActionsImpl{filesService: driveService.Files}, nil } diff --git a/service/google/drive_service.go b/service/google/drive_service.go index eb5ec8d..d659fab 100644 --- a/service/google/drive_service.go +++ b/service/google/drive_service.go @@ -1,22 +1,26 @@ package google import ( + "errors" "fmt" "github.com/spf13/viper" + "go.uber.org/zap" "google.golang.org/api/drive/v3" "houston/common/util" - houstonLogger "houston/logger" + "houston/logger" "houston/pkg/google/googleDrive" + "net/http" + "os" "sort" "time" ) type Service struct { - driveActions googleDrive.GoogleDriveActions + driveActions googleDrive.DriveActions driveActionTimeOut time.Duration } -func NewDriveService(driveActions googleDrive.GoogleDriveActions) *Service { +func NewDriveService(driveActions googleDrive.DriveActions) *Service { return &Service{driveActions: driveActions, driveActionTimeOut: viper.GetDuration("google.api.timeout")} } @@ -24,7 +28,7 @@ func (driveService *Service) createDirectory(directoryName string) (*drive.File, query := fmt.Sprintf("name = '%s' and mimeType = '%v'", directoryName, util.GoogleDriveFileMimeType) directoryList, err := driveService.driveActions.SearchInDrive(driveService.driveActionTimeOut, query) if err != nil { - houstonLogger.Error(fmt.Sprintf("Error searching for directory %v: %v", directoryName, err)) + logger.Error(fmt.Sprintf("Error searching for directory %v: %v", directoryName, err)) return nil, err } if len(directoryList.Files) > 0 { @@ -43,13 +47,13 @@ func (driveService *Service) moveFilesToDirectory(fileList *drive.FileList, dire // Create a copy of the file in the new directory. _, err := driveService.driveActions.CopyFile(driveService.driveActionTimeOut, file.Id, directory.Id) if err != nil { - houstonLogger.Error(fmt.Sprintf("Error copying file %v to directory %v: %v", file.Name, directory.Name, err)) + logger.Error(fmt.Sprintf("Error copying file %v to directory %v: %v", file.Name, directory.Name, err)) return nil, err } // Delete the original file. err = driveService.driveActions.DeleteFile(driveService.driveActionTimeOut, file.Id) if err != nil { - houstonLogger.Error(fmt.Sprintf("Error deleting file %v: %v", file.Name, err)) + logger.Error(fmt.Sprintf("Error deleting file %v: %v", file.Name, err)) return nil, err } } @@ -60,13 +64,13 @@ func (driveService *Service) CollectTranscripts(fileName string) error { query := fmt.Sprintf("name contains '%s' and mimeType != '%s'", fileName, util.GoogleDriveFileMimeType) fileList, err := driveService.driveActions.SearchInDrive(driveService.driveActionTimeOut, query) if err != nil { - houstonLogger.Error(fmt.Sprintf("Error searching for files named %v: %v", fileName, err)) + logger.Error(fmt.Sprintf("Error searching for files named %v: %v", fileName, err)) return err } if len(fileList.Files) == 0 { - houstonLogger.Info(fmt.Sprintf("No files found named: %v", fileName)) - return nil + logger.Info(fmt.Sprintf("No files found named: %v", fileName)) + return errors.New(fmt.Sprintf("No files found named: %v", fileName)) } // Check and create a directory with the specified fileName. directory, err := driveService.createDirectory(fileName) @@ -90,11 +94,11 @@ func (driveService *Service) CollectTranscripts(fileName string) error { // Handle any parsing errors here if necessary. if err1 != nil { - houstonLogger.Error(fmt.Sprintf("Error parsing time for object %s: %v", fileList.Files[index1].Name, err1)) + logger.Error(fmt.Sprintf("Error parsing time for object %s: %v", fileList.Files[index1].Name, err1)) return false } if err2 != nil { - houstonLogger.Error(fmt.Sprintf("Error parsing time for object %s: %v", fileList.Files[index2].Name, err2)) + logger.Error(fmt.Sprintf("Error parsing time for object %s: %v", fileList.Files[index2].Name, err2)) return false } @@ -104,9 +108,67 @@ func (driveService *Service) CollectTranscripts(fileName string) error { // Move files to the new directory. responseMessages, err := driveService.moveFilesToDirectory(fileList, directory) if err != nil { - houstonLogger.Error(fmt.Sprintf("Error moving files to directory %v: %v", directory.Name, err)) + logger.Error(fmt.Sprintf("Error moving files to directory %v: %v", directory.Name, err)) return err } - houstonLogger.Info(fmt.Sprintf("Response messages: %v", responseMessages)) + logger.Info(fmt.Sprintf("Response messages: %v", responseMessages)) return nil } + +func (driveService *Service) DownloadTranscripts(directory *drive.File, mimeType util.ContentType) (string, error) { + if directory.MimeType != util.GoogleDriveFileMimeType { + logger.Error(fmt.Sprintf("Error: %v is not a directory", directory.Name)) + return "", errors.New(fmt.Sprintf("Error: %v is not a directory", directory.Name)) + } + currentDirectory, _ := os.Getwd() + downloadDirectory := currentDirectory + "/" + directory.Name + err := util.CheckAndCreateDirectory(downloadDirectory) + if err != nil { + logger.Error(fmt.Sprintf("Error creating directory %v: %v", downloadDirectory, err)) + return "", err + } + + query := fmt.Sprintf("name contains '%s' and mimeType != '%s'", directory.Name, util.GoogleDriveFileMimeType) + fileList, err := driveService.driveActions.SearchInDrive(driveService.driveActionTimeOut, query) + if err != nil { + logger.Error(fmt.Sprintf("Error searching for files in directory %v: %v", directory.Name, err)) + return "", err + } + for _, driveFile := range fileList.Files { + exportResponse, err := driveService.DownloadFile(driveFile, mimeType) + if err != nil { + logger.Error(fmt.Sprintf("Error downloading file %v: %v", driveFile.Name, err)) + return "", err + } + err = util.WriteToFile(downloadDirectory, driveFile.Name+util.GetFileExtensionFromMimeType(mimeType), + exportResponse.Body) + if err != nil { + logger.Error(fmt.Sprintf("Error writing file %v to directory %v: %v", driveFile.Name, downloadDirectory, + zap.Error(err))) + return "", err + } + err = exportResponse.Body.Close() + if err != nil { + logger.Error(fmt.Sprintf("Error closing response body: %v", err)) + return "", err + } + } + return downloadDirectory, nil +} + +func (driveService *Service) DownloadFile(file *drive.File, mimeType util.ContentType) (*http.Response, error) { + exportFileResponse, err := driveService.driveActions.ExportFile(driveService.driveActionTimeOut, file.Id, + string(mimeType)) + if err != nil { + return nil, err + } + if exportFileResponse.Body == nil || exportFileResponse.StatusCode == 0 { + logger.Error(fmt.Sprintf("Error downloading file %v: %v", file.Name, err)) + return nil, errors.New("export file response is nil") + } + if exportFileResponse.StatusCode != http.StatusOK { + logger.Error(fmt.Sprintf("Error downloading file %v: %v", file.Name, err)) + return nil, err + } + return exportFileResponse, nil +} diff --git a/service/google/drive_service_test.go b/service/google/drive_service_test.go index 12e66dd..02557ed 100644 --- a/service/google/drive_service_test.go +++ b/service/google/drive_service_test.go @@ -2,13 +2,18 @@ package google import ( "errors" + "fmt" "github.com/gojuno/minimock/v3" + "github.com/google/uuid" "github.com/magiconair/properties/assert" "github.com/spf13/viper" "github.com/stretchr/testify/suite" "google.golang.org/api/drive/v3" + "houston/common/util" "houston/logger" "houston/mocks" + "net/http" + "os" "testing" "time" ) @@ -27,7 +32,7 @@ func (suite *DriveServiceSuite) SetupSuite() { func (suite *DriveServiceSuite) Test_CollectTranscripts_FileNotFound() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'directoryName' and mimeType != 'application/vnd."+ "google-apps.folder'").Then(nil, errors.New("file not found")) @@ -40,7 +45,7 @@ func (suite *DriveServiceSuite) Test_CollectTranscripts_SuccessCase() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'fileName' and mimeType != 'application/vnd.google-apps."+ "folder'").Then(&drive.FileList{ @@ -76,7 +81,7 @@ func (suite *DriveServiceSuite) Test_CollectTranscripts_SuccessCase() { func (suite *DriveServiceSuite) Test_CollectTranscripts_CreateDirectoryError() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'fileName' and mimeType != 'application/vnd.google-apps."+ "folder'").Then(&drive.FileList{ Files: []*drive.File{ @@ -98,7 +103,7 @@ func (suite *DriveServiceSuite) Test_CollectTranscripts_CreateDirectoryError() { func (suite *DriveServiceSuite) Test_CollectTranscripts_CopyFileError() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'fileName' and mimeType != 'application/vnd.google-apps."+ "folder'").Then(&drive.FileList{ Files: []*drive.File{ @@ -126,7 +131,7 @@ func (suite *DriveServiceSuite) Test_CollectTranscripts_CopyFileError() { func (suite *DriveServiceSuite) Test_CollectTranscripts_SearchFileError() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'fileName' and mimeType != 'application/vnd.google-apps."+ "folder'").Then(nil, errors.New("error searching for files")) driveService := NewDriveService(driveActions) @@ -137,7 +142,7 @@ func (suite *DriveServiceSuite) Test_CollectTranscripts_SearchFileError() { func (suite *DriveServiceSuite) Test_SearchInDrive_TimeOut() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'fileName' and mimeType != 'application/vnd.google-apps."+"folder'").Then(nil, errors.New("google drive api timedout")) driveService := NewDriveService(driveActions) err := driveService.CollectTranscripts("fileName") @@ -147,7 +152,7 @@ func (suite *DriveServiceSuite) Test_SearchInDrive_TimeOut() { func (suite *DriveServiceSuite) Test_CreateDirectory_TimeOut() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'fileName' and mimeType != 'application/vnd.google-apps."+ "folder'").Then(&drive.FileList{ Files: []*drive.File{ @@ -169,7 +174,7 @@ func (suite *DriveServiceSuite) Test_CreateDirectory_TimeOut() { func (suite *DriveServiceSuite) Test_CopyFile_TimeOut() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'fileName' and mimeType != 'application/vnd.google-apps."+ "folder'").Then(&drive.FileList{ Files: []*drive.File{ @@ -197,7 +202,7 @@ func (suite *DriveServiceSuite) Test_CopyFile_TimeOut() { func (suite *DriveServiceSuite) Test_DeleteFile_TimeOut() { controller := minimock.NewController(suite.T()) suite.T().Cleanup(controller.Finish) - driveActions := mocks.NewGoogleDriveActionsMock(controller) + driveActions := mocks.NewDriveActionsMock(controller) driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, "name contains 'fileName' and mimeType != 'application/vnd.google-apps."+ "folder'").Then(&drive.FileList{ Files: []*drive.File{ @@ -227,6 +232,169 @@ func (suite *DriveServiceSuite) Test_DeleteFile_TimeOut() { assert.Equal(suite.T(), err.Error(), "google drive api timedout") } +func (suite *DriveServiceSuite) Test_DownloadFile_TimeOut() { + driveFile := &drive.File{ + Id: uuid.New().String(), + Name: "fileName", + MimeType: "application/vnd.google-apps.document", + } + controller := minimock.NewController(suite.T()) + suite.T().Cleanup(controller.Finish) + driveActions := mocks.NewDriveActionsMock(controller) + driveService := NewDriveService(driveActions) + driveActions.ExportFileMock.When(suite.driveActionTimeOut, driveFile.Id, util.ContentTypeTextHTML). + Then(nil, errors.New("google drive api timed out")) + response, err := driveService.DownloadFile(driveFile, util.ContentTypeTextHTML) + suite.Assert().True(response == nil) + suite.Assert().Equal(err.Error(), "google drive api timed out") +} + +func (suite *DriveServiceSuite) Test_DownloadFile_EmptyResponse() { + driveFile := &drive.File{ + Id: uuid.New().String(), + Name: "fileName", + MimeType: "application/vnd.google-apps.document", + } + exportResponse := &http.Response{} + controller := minimock.NewController(suite.T()) + suite.T().Cleanup(controller.Finish) + driveActions := mocks.NewDriveActionsMock(controller) + driveService := NewDriveService(driveActions) + driveActions.ExportFileMock.When(suite.driveActionTimeOut, driveFile.Id, util.ContentTypeTextHTML). + Then(exportResponse, nil) + response, err := driveService.DownloadFile(driveFile, util.ContentTypeTextHTML) + suite.Assert().True(response == nil) + suite.Assert().True(err.Error() == "export file response is nil") +} + +func (suite *DriveServiceSuite) Test_DownloadFile_Success() { + testFile := createTestFile() + driveFile := &drive.File{ + Id: uuid.New().String(), + Name: "fileName", + MimeType: "application/vnd.google-apps.document", + } + exportResponse := &http.Response{ + StatusCode: http.StatusOK, + Body: testFile, + } + controller := minimock.NewController(suite.T()) + suite.T().Cleanup(controller.Finish) + driveActions := mocks.NewDriveActionsMock(controller) + driveService := NewDriveService(driveActions) + driveActions.ExportFileMock.When(suite.driveActionTimeOut, driveFile.Id, util.ContentTypeTextHTML). + Then(exportResponse, nil) + response, err := driveService.DownloadFile(driveFile, util.ContentTypeTextHTML) + suite.Assert().True(response != nil) + suite.Assert().True(err == nil) +} + +func (suite *DriveServiceSuite) Test_DownloadTranscripts_MimeTypeCheck() { + controller := minimock.NewController(suite.T()) + suite.T().Cleanup(controller.Finish) + driveActions := mocks.NewDriveActionsMock(controller) + driveService := NewDriveService(driveActions) + directoryPath, err := driveService.DownloadTranscripts(&drive.File{ + Id: "fileId", + Name: "fileName", + MimeType: "application/vnd.google-apps.document", + }, util.ContentTypeTextHTML) + suite.Assert().Equal(err.Error(), fmt.Sprintf("Error: %v is not a directory", "fileName")) + suite.Assert().Equal(directoryPath, "") +} + +func (suite *DriveServiceSuite) Test_DownloadTranscripts_SearchError() { + controller := minimock.NewController(suite.T()) + suite.T().Cleanup(controller.Finish) + + inputFile := &drive.File{ + Id: "fileId", + Name: "directory", + MimeType: "application/vnd.google-apps.folder", + } + driveActions := mocks.NewDriveActionsMock(controller) + driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, + fmt.Sprintf("name contains '%s' and mimeType != '%s'", inputFile.Name, util.GoogleDriveFileMimeType)).Then(nil, + errors.New("error exporting file")) + driveService := NewDriveService(driveActions) + directoryPath, err := driveService.DownloadTranscripts(inputFile, util.ContentTypeTextHTML) + suite.Assert().Equal(err.Error(), "error exporting file") + suite.Assert().Equal(directoryPath, "") +} + +func (suite *DriveServiceSuite) Test_DownloadTranscripts_ExportFileError() { + controller := minimock.NewController(suite.T()) + suite.T().Cleanup(controller.Finish) + + inputFile := &drive.File{ + Id: "fileId", + Name: "directory", + MimeType: "application/vnd.google-apps.folder", + } + + searchResponseFile := &drive.File{ + Id: "fileId", + Name: "fileName", + MimeType: "application/vnd.google-apps.document", + } + driveActions := mocks.NewDriveActionsMock(controller) + driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, + fmt.Sprintf("name contains '%s' and mimeType != '%s'", inputFile.Name, util.GoogleDriveFileMimeType)).Then(&drive.FileList{ + Files: []*drive.File{searchResponseFile}, + }, nil) + driveActions.ExportFileMock.When(suite.driveActionTimeOut, inputFile.Id, util.ContentTypeTextHTML).Then(nil, errors.New("error exporting file")) + driveService := NewDriveService(driveActions) + directoryPath, err := driveService.DownloadTranscripts(inputFile, util.ContentTypeTextHTML) + suite.Assert().Equal(err.Error(), "error exporting file") + suite.Assert().Equal(directoryPath, "") +} + +func (suite *DriveServiceSuite) Test_DownloadTranscripts_SuccessCase() { + controller := minimock.NewController(suite.T()) + suite.T().Cleanup(controller.Finish) + testFile := createTestFile() + inputFile := &drive.File{ + Id: "fileId", + Name: "directory", + MimeType: "application/vnd.google-apps.folder", + } + + searchResponseFile := &drive.File{ + Id: "fileId", + Name: "fileName", + MimeType: "application/vnd.google-apps.document", + } + exportResponse := &http.Response{ + StatusCode: http.StatusOK, + Body: testFile, + } + driveActions := mocks.NewDriveActionsMock(controller) + driveActions.SearchInDriveMock.When(suite.driveActionTimeOut, + fmt.Sprintf("name contains '%s' and mimeType != '%s'", inputFile.Name, util.GoogleDriveFileMimeType)).Then(&drive.FileList{ + Files: []*drive.File{searchResponseFile}, + }, nil) + driveActions.ExportFileMock.When(suite.driveActionTimeOut, inputFile.Id, util.ContentTypeTextHTML).Then(exportResponse, nil) + driveService := NewDriveService(driveActions) + directoryPath, err := driveService.DownloadTranscripts(inputFile, util.ContentTypeTextHTML) + suite.Assert().Equal(err, nil) + suite.Assert().NotNil(directoryPath) + util.DeleteDirectory(directoryPath) + os.Remove(testFile.Name()) +} + func TestDriveService(t *testing.T) { suite.Run(t, new(DriveServiceSuite)) } + +func createTestFile() *os.File { + file, err := os.Create("test.txt") + content := uuid.NewString() + if err != nil { + logger.Error(fmt.Sprintf("Error creating test file: %v", err)) + } + err = os.WriteFile(file.Name(), []byte(content), 0644) + if err != nil { + logger.Error(fmt.Sprintf("Error writing to test file: %v", err)) + } + return file +} diff --git a/service/monitoringService/monitoring_service_client_test.go b/service/monitoringService/monitoring_service_client_test.go index 7d8377a..2481e83 100644 --- a/service/monitoringService/monitoring_service_client_test.go +++ b/service/monitoringService/monitoring_service_client_test.go @@ -9,6 +9,7 @@ import ( "github.com/spf13/viper" "github.com/stretchr/testify/suite" "go.uber.org/zap" + "houston/common/util" "houston/logger" "houston/mocks" "houston/model" @@ -48,7 +49,7 @@ func (suite *MonitoringServiceSuite) Test_GetGrafanaImages_500Case() { } payload, _ := json.Marshal(getGrafanaImagesRequestBody) requestHeaders := map[string]string{ - "Content-Type": "application/json", + "Content-Type": util.ContentTypeJSON, "CORRELATION_ID": requestId, } response := &http.Response{ @@ -89,7 +90,7 @@ func (suite *MonitoringServiceSuite) Test_GetGrafanaImages_ErrorResponseCase() { } payload, _ := json.Marshal(getGrafanaImagesRequestBody) requestHeaders := map[string]string{ - "Content-Type": "application/json", + "Content-Type": util.ContentTypeJSON, "CORRELATION_ID": requestId, } @@ -126,7 +127,7 @@ func (suite *MonitoringServiceSuite) Test_GetGrafanaImages_EmptyResponseBodyCase } payload, _ := json.Marshal(getGrafanaImagesRequestBody) requestHeaders := map[string]string{ - "Content-Type": "application/json", + "Content-Type": util.ContentTypeJSON, "CORRELATION_ID": requestId, } response := &http.Response{