diff options
-rw-r--r-- | src/deno_dir.rs | 165 | ||||
-rw-r--r-- | tests/subdir/mismatch_ext.ts | 1 | ||||
-rw-r--r-- | tests/subdir/no_ext | 1 | ||||
-rw-r--r-- | tests/subdir/unknown_ext.deno | 1 | ||||
-rwxr-xr-x | tools/http_server.py | 6 |
5 files changed, 164 insertions, 10 deletions
diff --git a/src/deno_dir.rs b/src/deno_dir.rs index b5fd7cb0a..1af5daa3f 100644 --- a/src/deno_dir.rs +++ b/src/deno_dir.rs @@ -28,6 +28,16 @@ pub struct CodeFetchOutput { pub maybe_source_map: Option<Vec<u8>>, } +/// Gets corresponding MediaType given extension +fn extmap(ext: &str) -> msg::MediaType { + match ext { + "ts" => msg::MediaType::TypeScript, + "js" => msg::MediaType::JavaScript, + "json" => msg::MediaType::Json, + _ => msg::MediaType::Unknown, + } +} + pub struct DenoDir { // Example: /Users/rld/.deno/ pub root: PathBuf, @@ -156,7 +166,21 @@ impl DenoDir { None => Ok(()), }?; deno_fs::write_file(&p, &source, 0o666)?; - deno_fs::write_file(&mt, content_type.as_bytes(), 0o666)?; + // Remove possibly existing stale .mime file + // may not exist. DON'T unwrap + let _ = std::fs::remove_file(&media_type_filename); + // Create .mime file only when content type different from extension + let resolved_content_type = map_content_type(&p, Some(&content_type)); + let ext = p + .extension() + .map(|x| x.to_str().unwrap_or("")) + .unwrap_or(""); + let media_type = extmap(&ext); + if media_type == msg::MediaType::Unknown + || media_type != resolved_content_type + { + deno_fs::write_file(&mt, content_type.as_bytes(), 0o666)? + } return Ok(Some(CodeFetchOutput { module_name: module_name.to_string(), filename: filename.to_string(), @@ -614,7 +638,7 @@ mod tests { } #[test] - fn test_get_source_code() { + fn test_get_source_code_1() { let (temp_dir, deno_dir) = test_setup(); // http_util::fetch_sync_string requires tokio tokio_util::init(|| { @@ -635,10 +659,8 @@ mod tests { b"export { printHello } from \"./print_hello.ts\";\n"; assert_eq!(r.source_code, expected); assert_eq!(&(r.media_type), &msg::MediaType::TypeScript); - assert_eq!( - fs::read_to_string(&mime_file_name).unwrap(), - "application/typescript" - ); + // Should not create .mime file due to matching ext + assert!(fs::read_to_string(&mime_file_name).is_err()); // Modify .mime let _ = fs::write(&mime_file_name, "text/javascript"); @@ -665,12 +687,68 @@ mod tests { let expected3: &[u8] = b"export { printHello } from \"./print_hello.ts\";\n"; assert_eq!(r3.source_code, expected3); - // Now the .mime file should be overwritten back to TypeScript! - // (due to http fetch) + // Now the old .mime file should have gone! Resolved back to TypeScript assert_eq!(&(r3.media_type), &msg::MediaType::TypeScript); + assert!(fs::read_to_string(&mime_file_name).is_err()); + }); + } + + #[test] + fn test_get_source_code_2() { + let (temp_dir, deno_dir) = test_setup(); + // http_util::fetch_sync_string requires tokio + tokio_util::init(|| { + let module_name = "http://localhost:4545/tests/subdir/mismatch_ext.ts"; + let filename = deno_fs::normalize_path( + deno_dir + .deps_http + .join("localhost_PORT4545/tests/subdir/mismatch_ext.ts") + .as_ref(), + ); + let mime_file_name = format!("{}.mime", &filename); + + let result = deno_dir.get_source_code(module_name, &filename); + println!("module_name {} filename {}", module_name, filename); + assert!(result.is_ok()); + let r = result.unwrap(); + let expected: &[u8] = b"export const loaded = true;\n"; + assert_eq!(r.source_code, expected); + // Mismatch ext with content type, create .mime + assert_eq!(&(r.media_type), &msg::MediaType::JavaScript); assert_eq!( fs::read_to_string(&mime_file_name).unwrap(), - "application/typescript" + "text/javascript" + ); + + // Modify .mime + let _ = fs::write(&mime_file_name, "text/typescript"); + let result2 = deno_dir.get_source_code(module_name, &filename); + assert!(result2.is_ok()); + let r2 = result2.unwrap(); + let expected2: &[u8] = b"export const loaded = true;\n"; + assert_eq!(r2.source_code, expected2); + // If get_source_code does not call remote, this should be TypeScript + // as we modified before! (we do not overwrite .mime due to no http fetch) + assert_eq!(&(r2.media_type), &msg::MediaType::TypeScript); + assert_eq!( + fs::read_to_string(&mime_file_name).unwrap(), + "text/typescript" + ); + + // Force self.reload + let deno_dir = DenoDir::new(true, Some(temp_dir.path().to_path_buf())) + .expect("setup fail"); + let result3 = deno_dir.get_source_code(module_name, &filename); + assert!(result3.is_ok()); + let r3 = result3.unwrap(); + let expected3: &[u8] = b"export const loaded = true;\n"; + assert_eq!(r3.source_code, expected3); + // Now the old .mime file should be overwritten back to JavaScript! + // (due to http fetch) + assert_eq!(&(r3.media_type), &msg::MediaType::JavaScript); + assert_eq!( + fs::read_to_string(&mime_file_name).unwrap(), + "text/javascript" ); }); } @@ -696,7 +774,8 @@ mod tests { let r = result.unwrap().unwrap(); assert_eq!(&(r.source_code), b"export const loaded = true;\n"); assert_eq!(&(r.media_type), &msg::MediaType::TypeScript); - assert_eq!(fs::read_to_string(&mime_file_name).unwrap(), "video/mp2t"); + // matching ext, no .mime file created + assert!(fs::read_to_string(&mime_file_name).is_err()); // Modify .mime, make sure read from local let _ = fs::write(&mime_file_name, "text/javascript"); @@ -711,6 +790,72 @@ mod tests { #[test] fn test_fetch_source_2() { + use tokio_util; + // http_util::fetch_sync_string requires tokio + tokio_util::init(|| { + let (_temp_dir, deno_dir) = test_setup(); + let module_name = "http://localhost:4545/tests/subdir/no_ext"; + let filename = deno_fs::normalize_path( + deno_dir + .deps_http + .join("localhost_PORT4545/tests/subdir/no_ext") + .as_ref(), + ); + let mime_file_name = format!("{}.mime", &filename); + let result = deno_dir.fetch_remote_source(module_name, &filename); + assert!(result.is_ok()); + let r = result.unwrap().unwrap(); + assert_eq!(&(r.source_code), b"export const loaded = true;\n"); + assert_eq!(&(r.media_type), &msg::MediaType::TypeScript); + // no ext, should create .mime file + assert_eq!( + fs::read_to_string(&mime_file_name).unwrap(), + "text/typescript" + ); + + let module_name_2 = "http://localhost:4545/tests/subdir/mismatch_ext.ts"; + let filename_2 = deno_fs::normalize_path( + deno_dir + .deps_http + .join("localhost_PORT4545/tests/subdir/mismatch_ext.ts") + .as_ref(), + ); + let mime_file_name_2 = format!("{}.mime", &filename_2); + let result_2 = deno_dir.fetch_remote_source(module_name_2, &filename_2); + assert!(result_2.is_ok()); + let r2 = result_2.unwrap().unwrap(); + assert_eq!(&(r2.source_code), b"export const loaded = true;\n"); + assert_eq!(&(r2.media_type), &msg::MediaType::JavaScript); + // mismatch ext, should create .mime file + assert_eq!( + fs::read_to_string(&mime_file_name_2).unwrap(), + "text/javascript" + ); + + // test unknown extension + let module_name_3 = "http://localhost:4545/tests/subdir/unknown_ext.deno"; + let filename_3 = deno_fs::normalize_path( + deno_dir + .deps_http + .join("localhost_PORT4545/tests/subdir/unknown_ext.deno") + .as_ref(), + ); + let mime_file_name_3 = format!("{}.mime", &filename_3); + let result_3 = deno_dir.fetch_remote_source(module_name_3, &filename_3); + assert!(result_3.is_ok()); + let r3 = result_3.unwrap().unwrap(); + assert_eq!(&(r3.source_code), b"export const loaded = true;\n"); + assert_eq!(&(r3.media_type), &msg::MediaType::TypeScript); + // unknown ext, should create .mime file + assert_eq!( + fs::read_to_string(&mime_file_name_3).unwrap(), + "text/typescript" + ); + }); + } + + #[test] + fn test_fetch_source_3() { // only local, no http_util::fetch_sync_string called let (_temp_dir, deno_dir) = test_setup(); let cwd = std::env::current_dir().unwrap(); diff --git a/tests/subdir/mismatch_ext.ts b/tests/subdir/mismatch_ext.ts new file mode 100644 index 000000000..e67d2a017 --- /dev/null +++ b/tests/subdir/mismatch_ext.ts @@ -0,0 +1 @@ +export const loaded = true; diff --git a/tests/subdir/no_ext b/tests/subdir/no_ext new file mode 100644 index 000000000..e67d2a017 --- /dev/null +++ b/tests/subdir/no_ext @@ -0,0 +1 @@ +export const loaded = true; diff --git a/tests/subdir/unknown_ext.deno b/tests/subdir/unknown_ext.deno new file mode 100644 index 000000000..e67d2a017 --- /dev/null +++ b/tests/subdir/unknown_ext.deno @@ -0,0 +1 @@ +export const loaded = true; diff --git a/tools/http_server.py b/tools/http_server.py index 6cf997b86..7c4b1fe25 100755 --- a/tools/http_server.py +++ b/tools/http_server.py @@ -58,6 +58,12 @@ class ContentTypeHandler(SimpleHTTPServer.SimpleHTTPRequestHandler): return "application/x-javascript" if "form_urlencoded" in path: return "application/x-www-form-urlencoded" + if "no_ext" in path: + return "text/typescript" + if "unknown_ext" in path: + return "text/typescript" + if "mismatch_ext" in path: + return "text/javascript" return SimpleHTTPServer.SimpleHTTPRequestHandler.guess_type(self, path) |