Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 12 additions & 4 deletions java-spiffe-core/src/main/java/io/spiffe/spiffeid/SpiffeId.java
Original file line number Diff line number Diff line change
Expand Up @@ -72,18 +72,25 @@ public static SpiffeId parse(final String id) {
throw new IllegalArgumentException(EMPTY);
}

if (!id.startsWith(SCHEME_PREFIX)) {
int schemeSeparatorIndex = id.indexOf("://");
if (schemeSeparatorIndex <= 0) {
throw new InvalidSpiffeIdException(WRONG_SCHEME);
}

String rest = id.substring(SCHEME_PREFIX.length());
String scheme = id.substring(0, schemeSeparatorIndex);
if (!SPIFFE_SCHEME.equalsIgnoreCase(scheme)) {
throw new InvalidSpiffeIdException(WRONG_SCHEME);
}

String rest = id.substring(schemeSeparatorIndex + 3);

int i = 0;
for (char c : rest.toCharArray()) {
if (c == '/') {
break;
}
if (!isValidTrustDomainChar(c)) {
char normalized = Character.toLowerCase(c);
if (!isValidTrustDomainChar(normalized)) {
throw new InvalidSpiffeIdException(BAD_TRUST_DOMAIN_CHAR);
}
i++;
Expand All @@ -100,7 +107,8 @@ public static SpiffeId parse(final String id) {
validatePath(path);
}

return new SpiffeId(new TrustDomain(td), path);
String normalizedTrustDomain = td.toLowerCase();
return new SpiffeId(new TrustDomain(normalizedTrustDomain), path);
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,9 @@ public static TrustDomain parse(String idOrName) {
return SpiffeId.parse(idOrName).getTrustDomain();
}

validateTrustDomainName(idOrName);
return new TrustDomain(idOrName);
String normalizedName = idOrName.toLowerCase();
validateTrustDomainName(normalizedName);
return new TrustDomain(normalizedName);
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,9 @@ static Stream<Arguments> provideTestValidSpiffeIds() {
Arguments.of("spiffe://trustdomain/path", TrustDomain.parse("trustdomain"), "/path"),
Arguments.of("spiffe://trustdomain/path1/path2", TrustDomain.parse("trustdomain"), "/path1/path2"),
Arguments.of("spiffe://trustdomain/PATH1/PATH2", TrustDomain.parse("trustdomain"), "/PATH1/PATH2"),
Arguments.of("spiffe://trustdomain/9eebccd2-12bf-40a6-b262-65fe0487d453", TrustDomain.parse("trustdomain"), "/9eebccd2-12bf-40a6-b262-65fe0487d453")
Arguments.of("spiffe://trustdomain/9eebccd2-12bf-40a6-b262-65fe0487d453", TrustDomain.parse("trustdomain"), "/9eebccd2-12bf-40a6-b262-65fe0487d453"),
Arguments.of("SPIFFE://trustdomain/path", TrustDomain.parse("trustdomain"), "/path"),
Arguments.of("SpIfFe://TrUsTdOmAiN/Workload", TrustDomain.parse("trustdomain"), "/Workload")
);
}

Expand Down Expand Up @@ -92,7 +94,7 @@ static Stream<Arguments> provideInvalidSpiffeIds() {
Arguments.of("spiffe://user:password@test.org/path/element", "Trust domain characters are limited to lowercase letters, numbers, dots, dashes, and underscores"),
Arguments.of("spiffe:path/element", "Scheme is missing or invalid"),
Arguments.of("spiffe:/path/element", "Scheme is missing or invalid"),
Arguments.of("SPIFFE://path/element", "Scheme is missing or invalid"),
Arguments.of("spiffe://", "Trust domain is missing"),
Arguments.of("spiffe://domain.test/path/elem%5uent", "Path segment characters are limited to letters, numbers, dots, dashes, and underscores"),
Arguments.of("spiffe://trustdomain/path//", "Path cannot contain empty segments"),
Arguments.of("spiffe://trustdomain/./other", "Path cannot contain dot segments"),
Expand Down Expand Up @@ -173,9 +175,10 @@ void testParseWithAllChars() {

String td = "spiffe://trustdomain" + c;

if (TD_CHARS.contains(c)) {
char normalizedTdChar = Character.toLowerCase(c);
if (TrustDomain.isValidTrustDomainChar(normalizedTdChar)) {
SpiffeId spiffeId = SpiffeId.parse(td);
assertEquals(spiffeId.toString(), td);
assertEquals("spiffe://trustdomain" + normalizedTdChar, spiffeId.toString());
} else {
try {
SpiffeId.parse(td);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,6 @@
import org.junit.jupiter.params.provider.MethodSource;

import java.util.stream.Stream;

import static io.spiffe.spiffeid.SpiffeIdTest.TD_CHARS;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.fail;
Expand All @@ -22,6 +20,12 @@ void testTrustDomainFromName() {
assertEquals("trustdomain", trustDomain.getName());
}

@Test
void testTrustDomainFromNameMixedCase_isNormalizedToLowercase() {
TrustDomain trustDomain = TrustDomain.parse("TrUsTdOmAiN");
assertEquals("trustdomain", trustDomain.getName());
}

@Test
void testFromIdStringWithoutPath() {
TrustDomain trustDomain = TrustDomain.parse("spiffe://trustdomain");
Expand All @@ -41,9 +45,10 @@ void testAllChars() {
char c = (char) i;
String td = "trustdomain" + c;

if (TD_CHARS.contains(c)) {
char normalizedTdChar = Character.toLowerCase(c);
if (TrustDomain.isValidTrustDomainChar(normalizedTdChar)) {
TrustDomain trustDomain = TrustDomain.parse(td);
assertEquals(td, trustDomain.getName());
assertEquals("trustdomain" + normalizedTdChar, trustDomain.getName());
} else {
try {
TrustDomain.parse(td);
Expand All @@ -70,8 +75,8 @@ static Stream<Arguments> provideInvalidTrustDomain() {
Arguments.of("", "Trust domain is missing"),
Arguments.of("spiffe://", "Trust domain is missing"),
Arguments.of(null, "idOrName must not be null"),
Arguments.of("Trustdomain", "Trust domain characters are limited to lowercase letters, numbers, dots, dashes, and underscores"),
Arguments.of("spiffe://Domain.test", "Trust domain characters are limited to lowercase letters, numbers, dots, dashes, and underscores"),
Arguments.of("trustdomain!", "Trust domain characters are limited to lowercase letters, numbers, dots, dashes, and underscores"),
Arguments.of("spiffe://domain!.test", "Trust domain characters are limited to lowercase letters, numbers, dots, dashes, and underscores"),
Arguments.of("spiffe://domain.test/spiffe://domain.test/path/element", "Path segment characters are limited to letters, numbers, dots, dashes, and underscores"),
Arguments.of("http://domain.test", "Scheme is missing or invalid"),
Arguments.of("spiffe:// domain.test ", "Trust domain characters are limited to lowercase letters, numbers, dots, dashes, and underscores"),
Expand Down Expand Up @@ -112,6 +117,12 @@ void testParseFromSpiffeIdWithPath_extractsTrustDomain() {
assertEquals("example.org", trustDomain.getName());
}

@Test
void testParseFromSpiffeIdWithPath_mixedCaseSchemeAndTrustDomain_normalizesTrustDomain() {
TrustDomain trustDomain = TrustDomain.parse("SpIfFe://ExAmPlE.OrG/foo");
assertEquals("example.org", trustDomain.getName());
}

@Test
void testParseInvalidScheme_spiffeWithSingleSlash_throwsInvalidScheme() {
assertThrows(InvalidSpiffeIdException.class,
Expand Down