github.com/ncw/rclone@v1.48.1-0.20190724201158-a35aa1360e3e/backend/drive/drive_internal_test.go (about)

     1  package drive
     2  
     3  import (
     4  	"bytes"
     5  	"context"
     6  	"encoding/json"
     7  	"io"
     8  	"io/ioutil"
     9  	"mime"
    10  	"path/filepath"
    11  	"strings"
    12  	"testing"
    13  
    14  	_ "github.com/ncw/rclone/backend/local"
    15  	"github.com/ncw/rclone/fs"
    16  	"github.com/ncw/rclone/fs/operations"
    17  	"github.com/ncw/rclone/fstest/fstests"
    18  	"github.com/pkg/errors"
    19  	"github.com/stretchr/testify/assert"
    20  	"github.com/stretchr/testify/require"
    21  	"google.golang.org/api/drive/v3"
    22  )
    23  
    24  func TestDriveScopes(t *testing.T) {
    25  	for _, test := range []struct {
    26  		in       string
    27  		want     []string
    28  		wantFlag bool
    29  	}{
    30  		{"", []string{
    31  			"https://www.googleapis.com/auth/drive",
    32  		}, false},
    33  		{" drive.file , drive.readonly", []string{
    34  			"https://www.googleapis.com/auth/drive.file",
    35  			"https://www.googleapis.com/auth/drive.readonly",
    36  		}, false},
    37  		{" drive.file , drive.appfolder", []string{
    38  			"https://www.googleapis.com/auth/drive.file",
    39  			"https://www.googleapis.com/auth/drive.appfolder",
    40  		}, true},
    41  	} {
    42  		got := driveScopes(test.in)
    43  		assert.Equal(t, test.want, got, test.in)
    44  		gotFlag := driveScopesContainsAppFolder(got)
    45  		assert.Equal(t, test.wantFlag, gotFlag, test.in)
    46  	}
    47  }
    48  
    49  /*
    50  var additionalMimeTypes = map[string]string{
    51  	"application/vnd.ms-excel.sheet.macroenabled.12":                          ".xlsm",
    52  	"application/vnd.ms-excel.template.macroenabled.12":                       ".xltm",
    53  	"application/vnd.ms-powerpoint.presentation.macroenabled.12":              ".pptm",
    54  	"application/vnd.ms-powerpoint.slideshow.macroenabled.12":                 ".ppsm",
    55  	"application/vnd.ms-powerpoint.template.macroenabled.12":                  ".potm",
    56  	"application/vnd.ms-powerpoint":                                           ".ppt",
    57  	"application/vnd.ms-word.document.macroenabled.12":                        ".docm",
    58  	"application/vnd.ms-word.template.macroenabled.12":                        ".dotm",
    59  	"application/vnd.openxmlformats-officedocument.presentationml.template":   ".potx",
    60  	"application/vnd.openxmlformats-officedocument.spreadsheetml.template":    ".xltx",
    61  	"application/vnd.openxmlformats-officedocument.wordprocessingml.template": ".dotx",
    62  	"application/vnd.sun.xml.writer":                                          ".sxw",
    63  	"text/richtext":                                                           ".rtf",
    64  }
    65  */
    66  
    67  // Load the example export formats into exportFormats for testing
    68  func TestInternalLoadExampleFormats(t *testing.T) {
    69  	fetchFormatsOnce.Do(func() {})
    70  	buf, err := ioutil.ReadFile(filepath.FromSlash("test/about.json"))
    71  	var about struct {
    72  		ExportFormats map[string][]string `json:"exportFormats,omitempty"`
    73  		ImportFormats map[string][]string `json:"importFormats,omitempty"`
    74  	}
    75  	require.NoError(t, err)
    76  	require.NoError(t, json.Unmarshal(buf, &about))
    77  	_exportFormats = fixMimeTypeMap(about.ExportFormats)
    78  	_importFormats = fixMimeTypeMap(about.ImportFormats)
    79  }
    80  
    81  func TestInternalParseExtensions(t *testing.T) {
    82  	for _, test := range []struct {
    83  		in      string
    84  		want    []string
    85  		wantErr error
    86  	}{
    87  		{"doc", []string{".doc"}, nil},
    88  		{" docx ,XLSX, 	pptx,svg", []string{".docx", ".xlsx", ".pptx", ".svg"}, nil},
    89  		{"docx,svg,Docx", []string{".docx", ".svg"}, nil},
    90  		{"docx,potato,docx", []string{".docx"}, errors.New(`couldn't find MIME type for extension ".potato"`)},
    91  	} {
    92  		extensions, _, gotErr := parseExtensions(test.in)
    93  		if test.wantErr == nil {
    94  			assert.NoError(t, gotErr)
    95  		} else {
    96  			assert.EqualError(t, gotErr, test.wantErr.Error())
    97  		}
    98  		assert.Equal(t, test.want, extensions)
    99  	}
   100  
   101  	// Test it is appending
   102  	extensions, _, gotErr := parseExtensions("docx,svg", "docx,svg,xlsx")
   103  	assert.NoError(t, gotErr)
   104  	assert.Equal(t, []string{".docx", ".svg", ".xlsx"}, extensions)
   105  }
   106  
   107  func TestInternalFindExportFormat(t *testing.T) {
   108  	item := &drive.File{
   109  		Name:     "file",
   110  		MimeType: "application/vnd.google-apps.document",
   111  	}
   112  	for _, test := range []struct {
   113  		extensions    []string
   114  		wantExtension string
   115  		wantMimeType  string
   116  	}{
   117  		{[]string{}, "", ""},
   118  		{[]string{".pdf"}, ".pdf", "application/pdf"},
   119  		{[]string{".pdf", ".rtf", ".xls"}, ".pdf", "application/pdf"},
   120  		{[]string{".xls", ".rtf", ".pdf"}, ".rtf", "application/rtf"},
   121  		{[]string{".xls", ".csv", ".svg"}, "", ""},
   122  	} {
   123  		f := new(Fs)
   124  		f.exportExtensions = test.extensions
   125  		gotExtension, gotFilename, gotMimeType, gotIsDocument := f.findExportFormat(item)
   126  		assert.Equal(t, test.wantExtension, gotExtension)
   127  		if test.wantExtension != "" {
   128  			assert.Equal(t, item.Name+gotExtension, gotFilename)
   129  		} else {
   130  			assert.Equal(t, "", gotFilename)
   131  		}
   132  		assert.Equal(t, test.wantMimeType, gotMimeType)
   133  		assert.Equal(t, true, gotIsDocument)
   134  	}
   135  }
   136  
   137  func TestMimeTypesToExtension(t *testing.T) {
   138  	for mimeType, extension := range _mimeTypeToExtension {
   139  		extensions, err := mime.ExtensionsByType(mimeType)
   140  		assert.NoError(t, err)
   141  		assert.Contains(t, extensions, extension)
   142  	}
   143  }
   144  
   145  func TestExtensionToMimeType(t *testing.T) {
   146  	for mimeType, extension := range _mimeTypeToExtension {
   147  		gotMimeType := mime.TypeByExtension(extension)
   148  		mediatype, _, err := mime.ParseMediaType(gotMimeType)
   149  		assert.NoError(t, err)
   150  		assert.Equal(t, mimeType, mediatype)
   151  	}
   152  }
   153  
   154  func TestExtensionsForExportFormats(t *testing.T) {
   155  	if _exportFormats == nil {
   156  		t.Error("exportFormats == nil")
   157  	}
   158  	for fromMT, toMTs := range _exportFormats {
   159  		for _, toMT := range toMTs {
   160  			if !isInternalMimeType(toMT) {
   161  				extensions, err := mime.ExtensionsByType(toMT)
   162  				assert.NoError(t, err, "invalid MIME type %q", toMT)
   163  				assert.NotEmpty(t, extensions, "No extension found for %q (from: %q)", fromMT, toMT)
   164  			}
   165  		}
   166  	}
   167  }
   168  
   169  func TestExtensionsForImportFormats(t *testing.T) {
   170  	t.Skip()
   171  	if _importFormats == nil {
   172  		t.Error("_importFormats == nil")
   173  	}
   174  	for fromMT := range _importFormats {
   175  		if !isInternalMimeType(fromMT) {
   176  			extensions, err := mime.ExtensionsByType(fromMT)
   177  			assert.NoError(t, err, "invalid MIME type %q", fromMT)
   178  			assert.NotEmpty(t, extensions, "No extension found for %q", fromMT)
   179  		}
   180  	}
   181  }
   182  
   183  func (f *Fs) InternalTestDocumentImport(t *testing.T) {
   184  	oldAllow := f.opt.AllowImportNameChange
   185  	f.opt.AllowImportNameChange = true
   186  	defer func() {
   187  		f.opt.AllowImportNameChange = oldAllow
   188  	}()
   189  
   190  	testFilesPath, err := filepath.Abs(filepath.FromSlash("test/files"))
   191  	require.NoError(t, err)
   192  
   193  	testFilesFs, err := fs.NewFs(testFilesPath)
   194  	require.NoError(t, err)
   195  
   196  	_, f.importMimeTypes, err = parseExtensions("odt,ods,doc")
   197  	require.NoError(t, err)
   198  
   199  	err = operations.CopyFile(context.Background(), f, testFilesFs, "example2.doc", "example2.doc")
   200  	require.NoError(t, err)
   201  }
   202  
   203  func (f *Fs) InternalTestDocumentUpdate(t *testing.T) {
   204  	testFilesPath, err := filepath.Abs(filepath.FromSlash("test/files"))
   205  	require.NoError(t, err)
   206  
   207  	testFilesFs, err := fs.NewFs(testFilesPath)
   208  	require.NoError(t, err)
   209  
   210  	_, f.importMimeTypes, err = parseExtensions("odt,ods,doc")
   211  	require.NoError(t, err)
   212  
   213  	err = operations.CopyFile(context.Background(), f, testFilesFs, "example2.xlsx", "example1.ods")
   214  	require.NoError(t, err)
   215  }
   216  
   217  func (f *Fs) InternalTestDocumentExport(t *testing.T) {
   218  	var buf bytes.Buffer
   219  	var err error
   220  
   221  	f.exportExtensions, _, err = parseExtensions("txt")
   222  	require.NoError(t, err)
   223  
   224  	obj, err := f.NewObject(context.Background(), "example2.txt")
   225  	require.NoError(t, err)
   226  
   227  	rc, err := obj.Open(context.Background())
   228  	require.NoError(t, err)
   229  	defer func() { require.NoError(t, rc.Close()) }()
   230  
   231  	_, err = io.Copy(&buf, rc)
   232  	require.NoError(t, err)
   233  	text := buf.String()
   234  
   235  	for _, excerpt := range []string{
   236  		"Lorem ipsum dolor sit amet, consectetur",
   237  		"porta at ultrices in, consectetur at augue.",
   238  	} {
   239  		require.Contains(t, text, excerpt)
   240  	}
   241  }
   242  
   243  func (f *Fs) InternalTestDocumentLink(t *testing.T) {
   244  	var buf bytes.Buffer
   245  	var err error
   246  
   247  	f.exportExtensions, _, err = parseExtensions("link.html")
   248  	require.NoError(t, err)
   249  
   250  	obj, err := f.NewObject(context.Background(), "example2.link.html")
   251  	require.NoError(t, err)
   252  
   253  	rc, err := obj.Open(context.Background())
   254  	require.NoError(t, err)
   255  	defer func() { require.NoError(t, rc.Close()) }()
   256  
   257  	_, err = io.Copy(&buf, rc)
   258  	require.NoError(t, err)
   259  	text := buf.String()
   260  
   261  	require.True(t, strings.HasPrefix(text, "<html>"))
   262  	require.True(t, strings.HasSuffix(text, "</html>\n"))
   263  	for _, excerpt := range []string{
   264  		`<meta http-equiv="refresh"`,
   265  		`Loading <a href="`,
   266  	} {
   267  		require.Contains(t, text, excerpt)
   268  	}
   269  }
   270  
   271  func (f *Fs) InternalTest(t *testing.T) {
   272  	// These tests all depend on each other so run them as nested tests
   273  	t.Run("DocumentImport", func(t *testing.T) {
   274  		f.InternalTestDocumentImport(t)
   275  		t.Run("DocumentUpdate", func(t *testing.T) {
   276  			f.InternalTestDocumentUpdate(t)
   277  			t.Run("DocumentExport", func(t *testing.T) {
   278  				f.InternalTestDocumentExport(t)
   279  				t.Run("DocumentLink", func(t *testing.T) {
   280  					f.InternalTestDocumentLink(t)
   281  				})
   282  			})
   283  		})
   284  	})
   285  }
   286  
   287  var _ fstests.InternalTester = (*Fs)(nil)