github.com/floatingorchard/grab/v3@v3.0.0-20240419111603-44e36a9c1818/util_test.go (about)

     1  package grab
     2  
     3  import (
     4  	"fmt"
     5  	"net/http"
     6  	"net/url"
     7  	"testing"
     8  )
     9  
    10  func TestURLFilenames(t *testing.T) {
    11  	t.Run("Valid", func(t *testing.T) {
    12  		expect := "filename"
    13  		testCases := []string{
    14  			"http://test.com/filename",
    15  			"http://test.com/path/filename",
    16  			"http://test.com/deep/path/filename",
    17  			"http://test.com/filename?with=args",
    18  			"http://test.com/filename#with-fragment",
    19  			"http://test.com/filename?with=args&and#with-fragment",
    20  		}
    21  
    22  		for _, tc := range testCases {
    23  			req, _ := http.NewRequest("GET", tc, nil)
    24  			resp := &http.Response{
    25  				Request: req,
    26  			}
    27  			actual, err := guessFilename(resp)
    28  			if err != nil {
    29  				t.Errorf("%v", err)
    30  			}
    31  
    32  			if actual != expect {
    33  				t.Errorf("expected '%v', got '%v'", expect, actual)
    34  			}
    35  		}
    36  	})
    37  
    38  	t.Run("Invalid", func(t *testing.T) {
    39  		testCases := []string{
    40  			"http://test.com",
    41  			"http://test.com/",
    42  			"http://test.com/filename/",
    43  			"http://test.com/filename/?with=args",
    44  			"http://test.com/filename/#with-fragment",
    45  			"http://test.com/filename\x00",
    46  		}
    47  
    48  		for _, tc := range testCases {
    49  			t.Run(tc, func(t *testing.T) {
    50  				req, err := http.NewRequest("GET", tc, nil)
    51  				if err != nil {
    52  					if tc == "http://test.com/filename\x00" {
    53  						// Since go1.12, urls with invalid control character return an error
    54  						// See https://github.com/golang/go/commit/829c5df58694b3345cb5ea41206783c8ccf5c3ca
    55  						t.Skip()
    56  					}
    57  				}
    58  				resp := &http.Response{
    59  					Request: req,
    60  				}
    61  
    62  				_, err = guessFilename(resp)
    63  				if err != ErrNoFilename {
    64  					t.Errorf("expected '%v', got '%v'", ErrNoFilename, err)
    65  				}
    66  			})
    67  		}
    68  	})
    69  }
    70  
    71  func TestHeaderFilenames(t *testing.T) {
    72  	u, _ := url.ParseRequestURI("http://test.com/badfilename")
    73  	resp := &http.Response{
    74  		Request: &http.Request{
    75  			URL: u,
    76  		},
    77  		Header: http.Header{},
    78  	}
    79  
    80  	setFilename := func(resp *http.Response, filename string) {
    81  		resp.Header.Set("Content-Disposition", fmt.Sprintf("attachment;filename=\"%s\"", filename))
    82  	}
    83  
    84  	t.Run("Valid", func(t *testing.T) {
    85  		expect := "filename"
    86  		testCases := []string{
    87  			"filename",
    88  			"path/filename",
    89  			"/path/filename",
    90  			"../../filename",
    91  			"/path/../../filename",
    92  			"/../../././///filename",
    93  		}
    94  
    95  		for _, tc := range testCases {
    96  			setFilename(resp, tc)
    97  			actual, err := guessFilename(resp)
    98  			if err != nil {
    99  				t.Errorf("error (%v): %v", tc, err)
   100  			}
   101  
   102  			if actual != expect {
   103  				t.Errorf("expected '%v' (%v), got '%v'", expect, tc, actual)
   104  			}
   105  		}
   106  	})
   107  
   108  	t.Run("Invalid", func(t *testing.T) {
   109  		testCases := []string{
   110  			"",
   111  			"/",
   112  			".",
   113  			"/.",
   114  			"/./",
   115  			"..",
   116  			"../",
   117  			"/../",
   118  			"/path/",
   119  			"../path/",
   120  			"filename\x00",
   121  			"filename/",
   122  			"filename//",
   123  			"filename/..",
   124  		}
   125  
   126  		for _, tc := range testCases {
   127  			setFilename(resp, tc)
   128  			if actual, err := guessFilename(resp); err != ErrNoFilename {
   129  				t.Errorf("expected: %v (%v), got: %v (%v)", ErrNoFilename, tc, err, actual)
   130  			}
   131  		}
   132  	})
   133  }
   134  
   135  func TestHeaderWithMissingDirective(t *testing.T) {
   136  	u, _ := url.ParseRequestURI("http://test.com/filename")
   137  	resp := &http.Response{
   138  		Request: &http.Request{
   139  			URL: u,
   140  		},
   141  		Header: http.Header{},
   142  	}
   143  
   144  	setHeader := func(resp *http.Response, value string) {
   145  		resp.Header.Set("Content-Disposition", value)
   146  	}
   147  
   148  	t.Run("Valid", func(t *testing.T) {
   149  		expect := "filename"
   150  		testCases := []string{
   151  			"inline",
   152  			"attachment",
   153  		}
   154  
   155  		for _, tc := range testCases {
   156  			setHeader(resp, tc)
   157  			actual, err := guessFilename(resp)
   158  			if err != nil {
   159  				t.Errorf("error (%v): %v", tc, err)
   160  			}
   161  
   162  			if actual != expect {
   163  				t.Errorf("expected '%v' (%v), got '%v'", expect, tc, actual)
   164  			}
   165  		}
   166  	})
   167  }