mirror of
				https://github.com/caddyserver/caddy.git
				synced 2025-10-31 02:27:19 -04:00 
			
		
		
		
	
						commit
						a14fce0b1e
					
				| @ -1,6 +1,7 @@ | |||||||
| package middleware | package middleware | ||||||
| 
 | 
 | ||||||
| import ( | import ( | ||||||
|  | 	"fmt" | ||||||
| 	"net/http" | 	"net/http" | ||||||
| 	"os" | 	"os" | ||||||
| 	"path" | 	"path" | ||||||
| @ -128,6 +129,10 @@ func (fh *fileHandler) serveFile(w http.ResponseWriter, r *http.Request, name st | |||||||
| 		return http.StatusNotFound, nil | 		return http.StatusNotFound, nil | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
|  | 	// Add ETag header | ||||||
|  | 	e := fmt.Sprintf(`W/"%x-%x"`, d.ModTime().Unix(), d.Size()) | ||||||
|  | 	w.Header().Set("ETag", e) | ||||||
|  | 
 | ||||||
| 	// Note: Errors generated by ServeContent are written immediately | 	// Note: Errors generated by ServeContent are written immediately | ||||||
| 	// to the response. This usually only happens if seeking fails (rare). | 	// to the response. This usually only happens if seeking fails (rare). | ||||||
| 	http.ServeContent(w, r, d.Name(), d.ModTime(), f) | 	http.ServeContent(w, r, d.Name(), d.ModTime(), f) | ||||||
|  | |||||||
| @ -8,6 +8,7 @@ import ( | |||||||
| 	"path/filepath" | 	"path/filepath" | ||||||
| 	"strings" | 	"strings" | ||||||
| 	"testing" | 	"testing" | ||||||
|  | 	"time" | ||||||
| ) | ) | ||||||
| 
 | 
 | ||||||
| var testDir = filepath.Join(os.TempDir(), "caddy_testdir") | var testDir = filepath.Join(os.TempDir(), "caddy_testdir") | ||||||
| @ -44,6 +45,7 @@ func TestServeHTTP(t *testing.T) { | |||||||
| 
 | 
 | ||||||
| 		expectedStatus      int | 		expectedStatus      int | ||||||
| 		expectedBodyContent string | 		expectedBodyContent string | ||||||
|  | 		expectedEtag        string | ||||||
| 	}{ | 	}{ | ||||||
| 		// Test 0 - access without any path | 		// Test 0 - access without any path | ||||||
| 		{ | 		{ | ||||||
| @ -60,12 +62,14 @@ func TestServeHTTP(t *testing.T) { | |||||||
| 			url:                 "https://foo/file1.html", | 			url:                 "https://foo/file1.html", | ||||||
| 			expectedStatus:      http.StatusOK, | 			expectedStatus:      http.StatusOK, | ||||||
| 			expectedBodyContent: testFiles["file1.html"], | 			expectedBodyContent: testFiles["file1.html"], | ||||||
|  | 			expectedEtag:        `W/"1e240-13"`, | ||||||
| 		}, | 		}, | ||||||
| 		// Test 3 - access folder with index file with trailing slash | 		// Test 3 - access folder with index file with trailing slash | ||||||
| 		{ | 		{ | ||||||
| 			url:                 "https://foo/dirwithindex/", | 			url:                 "https://foo/dirwithindex/", | ||||||
| 			expectedStatus:      http.StatusOK, | 			expectedStatus:      http.StatusOK, | ||||||
| 			expectedBodyContent: testFiles[filepath.Join("dirwithindex", "index.html")], | 			expectedBodyContent: testFiles[filepath.Join("dirwithindex", "index.html")], | ||||||
|  | 			expectedEtag:        `W/"1e240-20"`, | ||||||
| 		}, | 		}, | ||||||
| 		// Test 4 - access folder with index file without trailing slash | 		// Test 4 - access folder with index file without trailing slash | ||||||
| 		{ | 		{ | ||||||
| @ -105,6 +109,7 @@ func TestServeHTTP(t *testing.T) { | |||||||
| 			url:                 "https://foo/dirwithindex/index.html", | 			url:                 "https://foo/dirwithindex/index.html", | ||||||
| 			expectedStatus:      http.StatusOK, | 			expectedStatus:      http.StatusOK, | ||||||
| 			expectedBodyContent: testFiles[filepath.Join("dirwithindex", "index.html")], | 			expectedBodyContent: testFiles[filepath.Join("dirwithindex", "index.html")], | ||||||
|  | 			expectedEtag:        `W/"1e240-20"`, | ||||||
| 		}, | 		}, | ||||||
| 		// Test 11 - send a request with query params | 		// Test 11 - send a request with query params | ||||||
| 		{ | 		{ | ||||||
| @ -143,6 +148,7 @@ func TestServeHTTP(t *testing.T) { | |||||||
| 		responseRecorder := httptest.NewRecorder() | 		responseRecorder := httptest.NewRecorder() | ||||||
| 		request, err := http.NewRequest("GET", test.url, strings.NewReader("")) | 		request, err := http.NewRequest("GET", test.url, strings.NewReader("")) | ||||||
| 		status, err := fileserver.ServeHTTP(responseRecorder, request) | 		status, err := fileserver.ServeHTTP(responseRecorder, request) | ||||||
|  | 		etag := responseRecorder.Header().Get("Etag") | ||||||
| 
 | 
 | ||||||
| 		// check if error matches expectations | 		// check if error matches expectations | ||||||
| 		if err != nil { | 		if err != nil { | ||||||
| @ -154,6 +160,11 @@ func TestServeHTTP(t *testing.T) { | |||||||
| 			t.Errorf(getTestPrefix(i)+"Expected status %d, found %d", test.expectedStatus, status) | 			t.Errorf(getTestPrefix(i)+"Expected status %d, found %d", test.expectedStatus, status) | ||||||
| 		} | 		} | ||||||
| 
 | 
 | ||||||
|  | 		// check etag | ||||||
|  | 		if test.expectedEtag != etag { | ||||||
|  | 			t.Errorf(getTestPrefix(i)+"Expected Etag header %d, found %d", test.expectedEtag, etag) | ||||||
|  | 		} | ||||||
|  | 
 | ||||||
| 		// check body content | 		// check body content | ||||||
| 		if !strings.Contains(responseRecorder.Body.String(), test.expectedBodyContent) { | 		if !strings.Contains(responseRecorder.Body.String(), test.expectedBodyContent) { | ||||||
| 			t.Errorf(getTestPrefix(i)+"Expected body to contain %q, found %q", test.expectedBodyContent, responseRecorder.Body.String()) | 			t.Errorf(getTestPrefix(i)+"Expected body to contain %q, found %q", test.expectedBodyContent, responseRecorder.Body.String()) | ||||||
| @ -173,6 +184,8 @@ func beforeServeHTTPTest(t *testing.T) { | |||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
|  | 	fixedTime := time.Unix(123456, 0) | ||||||
|  | 
 | ||||||
| 	for relFile, fileContent := range testFiles { | 	for relFile, fileContent := range testFiles { | ||||||
| 		absFile := filepath.Join(testDir, relFile) | 		absFile := filepath.Join(testDir, relFile) | ||||||
| 
 | 
 | ||||||
| @ -197,6 +210,12 @@ func beforeServeHTTPTest(t *testing.T) { | |||||||
| 			return | 			return | ||||||
| 		} | 		} | ||||||
| 		f.Close() | 		f.Close() | ||||||
|  | 
 | ||||||
|  | 		// and set the last modified time | ||||||
|  | 		err = os.Chtimes(absFile, fixedTime, fixedTime) | ||||||
|  | 		if err != nil { | ||||||
|  | 			t.Fatalf("Failed to set file time to %s. Error was: %v", fixedTime, err) | ||||||
|  | 		} | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
| } | } | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user