Skip to content

Commit af2e35d

Browse files
authored
feat(formatjs): Support sha1 hashing option (#431)
1 parent 48bb908 commit af2e35d

File tree

6 files changed

+45
-3
lines changed

6 files changed

+45
-3
lines changed

.changeset/legal-breads-sink.md

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
"@swc/plugin-formatjs": minor
3+
---
4+
5+
Add support for sha1 hash_type in idInterpolationPattern

Cargo.lock

+2
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

+2
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ cipher = "0.4.4"
2424
clap = "4.5.4"
2525
convert_case = "0.6.0"
2626
default-from-serde = "0.1"
27+
digest = "0.10"
2728
handlebars = "5.1.2"
2829
hex = "0.4.3"
2930
langtag = "0.3.2"
@@ -39,6 +40,7 @@ regex = { version = "1.10.4", default-features = false }
3940
serde = "1.0.203"
4041
serde_json = "1.0.117"
4142
serde_repr = "0.1"
43+
sha1 = "0.10"
4244
sha2 = "0.10"
4345
similar-asserts = "1.4.2"
4446
sourcemap = "9.0.0"

packages/formatjs/__tests__/wasm.test.ts

+26
Original file line numberDiff line numberDiff line change
@@ -178,4 +178,30 @@ describe("formatjs swc plugin", () => {
178178
expect(output).toMatch(/defaultMessage: "Hello, \{name\}!"/);
179179
expect(output).not.toMatch(/description/);
180180
});
181+
182+
it("should be able to use sha1 and sha512 hashing in interpolation", async () => {
183+
const input = `
184+
import { FormattedMessage } from 'react-intl';
185+
186+
export function Greeting() {
187+
return (
188+
<FormattedMessage
189+
defaultMessage="Hello!"
190+
description="Greeting message"
191+
/>
192+
);
193+
}
194+
`;
195+
196+
const sha1output = await transformCode(input, {
197+
idInterpolationPattern: "[sha1:contenthash:base64:6]",
198+
});
199+
const sha512output = await transformCode(input, {
200+
idInterpolationPattern: "[sha512:contenthash:base64:6]",
201+
});
202+
203+
expect(sha1output).toMatch(/id: "[a-zA-Z0-9]{6}"/);
204+
expect(sha512output).toMatch(/id: "[a-zA-Z0-9]{6}"/);
205+
expect(sha1output).not.toMatch(sha512output);
206+
});
181207
});

packages/formatjs/transform/Cargo.toml

+2
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,12 @@ custom_transform = []
1515

1616
[dependencies]
1717
base64ct = { workspace = true, features = ["alloc"] }
18+
digest = { workspace = true }
1819
once_cell = { workspace = true }
1920
regex = { workspace = true }
2021
serde = { workspace = true, features = ["derive"] }
2122
serde_json = { workspace = true }
23+
sha1 = { workspace = true }
2224
sha2 = { workspace = true }
2325
swc_core = { workspace = true, features = ["common", "ecma_visit", "ecma_ast"] }
2426

packages/formatjs/transform/src/lib.rs

+8-3
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,11 @@ use std::{
55
};
66

77
use base64ct::{Base64, Encoding};
8+
use digest::DynDigest;
89
use once_cell::sync::Lazy;
910
use regex::{Captures, Regex as Regexp};
1011
use serde::{ser::SerializeMap, Deserialize, Serialize};
12+
use sha1::Sha1;
1113
use sha2::{Digest, Sha512};
1214
use swc_core::{
1315
common::{
@@ -494,12 +496,15 @@ fn interpolate_name(filename: &str, interpolate_pattern: &str, content: &str) ->
494496

495497
url = r
496498
.replace(url.as_str(), |cap: &Captures| {
497-
// let hash_type = cap.get(1);
499+
let hash_type = cap.get(1);
498500
// let digest_type = cap.get(2);
499501
let max_length = cap.get(3);
500502

501-
// TODO: support hashtype
502-
let mut hasher = Sha512::new();
503+
// TODO: support more hash_types than sha1 and sha512
504+
let mut hasher: Box<dyn DynDigest> = match hash_type {
505+
Some(hash_type) if hash_type.as_str() == "sha1" => Box::new(Sha1::new()),
506+
_ => Box::new(Sha512::new()),
507+
};
503508
hasher.update(content.as_bytes());
504509
let hash = hasher.finalize();
505510
let base64_hash = Base64::encode_string(&hash);

0 commit comments

Comments
 (0)