Skip to content

Commit

Permalink
Convert some fields on CreateProfileRequest and `VersionedProfileRe…
Browse files Browse the repository at this point in the history
…sponse` to byte arrays
  • Loading branch information
katherine-signal authored Sep 13, 2023
1 parent de41088 commit 2601d6e
Show file tree
Hide file tree
Showing 4 changed files with 86 additions and 69 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,6 @@
import javax.ws.rs.core.HttpHeaders;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import org.apache.commons.lang3.StringUtils;
import org.signal.libsignal.protocol.IdentityKey;
import org.signal.libsignal.protocol.ServiceId;
import org.signal.libsignal.zkgroup.InvalidInputException;
Expand All @@ -81,7 +80,6 @@
import org.whispersystems.textsecuregcm.entities.ProfileAvatarUploadAttributes;
import org.whispersystems.textsecuregcm.entities.UserCapabilities;
import org.whispersystems.textsecuregcm.entities.VersionedProfileResponse;
import org.whispersystems.textsecuregcm.util.ProfileHelper;
import org.whispersystems.textsecuregcm.identity.AciServiceIdentifier;
import org.whispersystems.textsecuregcm.identity.IdentityType;
import org.whispersystems.textsecuregcm.identity.PniServiceIdentifier;
Expand All @@ -97,6 +95,7 @@
import org.whispersystems.textsecuregcm.storage.ProfilesManager;
import org.whispersystems.textsecuregcm.storage.VersionedProfile;
import org.whispersystems.textsecuregcm.util.Pair;
import org.whispersystems.textsecuregcm.util.ProfileHelper;
import org.whispersystems.textsecuregcm.util.Util;
import software.amazon.awssdk.services.s3.S3Client;
import software.amazon.awssdk.services.s3.model.DeleteObjectRequest;
Expand Down Expand Up @@ -166,7 +165,7 @@ public Response setProfile(@Auth AuthenticatedAccount auth, @NotNull @Valid Crea
final Optional<VersionedProfile> currentProfile = profilesManager.get(auth.getAccount().getUuid(),
request.getVersion());

if (StringUtils.isNotBlank(request.getPaymentAddress())) {
if (request.getPaymentAddress() != null && request.getPaymentAddress().length != 0) {
final boolean hasDisallowedPrefix =
dynamicConfigurationManager.getConfiguration().getPaymentsConfiguration().getDisallowedPrefixes().stream()
.anyMatch(prefix -> auth.getAccount().getNumber().startsWith(prefix));
Expand All @@ -191,11 +190,11 @@ public Response setProfile(@Auth AuthenticatedAccount auth, @NotNull @Valid Crea
profilesManager.set(auth.getAccount().getUuid(),
new VersionedProfile(
request.getVersion(),
decodeFromBase64(request.getName()),
request.getName(),
avatar,
decodeFromBase64(request.getAboutEmoji()),
decodeFromBase64(request.getAbout()),
decodeFromBase64(request.getPaymentAddress()),
request.getAboutEmoji(),
request.getAbout(),
request.getPaymentAddress(),
request.getCommitment().serialize()));

if (request.getAvatarChange() != CreateProfileRequest.AvatarChange.UNCHANGED) {
Expand Down Expand Up @@ -408,17 +407,16 @@ private VersionedProfileResponse buildVersionedProfileResponse(final Account acc
VERSION_NOT_FOUND_COUNTER.increment();
}

final String name = maybeProfile.map(VersionedProfile::name).map(ProfileController::encodeToBase64).orElse(null);
final String about = maybeProfile.map(VersionedProfile::about).map(ProfileController::encodeToBase64).orElse(null);
final String aboutEmoji = maybeProfile.map(VersionedProfile::aboutEmoji).map(ProfileController::encodeToBase64).orElse(null);
final byte[] name = maybeProfile.map(VersionedProfile::name).orElse(null);
final byte[] about = maybeProfile.map(VersionedProfile::about).orElse(null);
final byte[] aboutEmoji = maybeProfile.map(VersionedProfile::aboutEmoji).orElse(null);
final String avatar = maybeProfile.map(VersionedProfile::avatar).orElse(null);

// Allow requests where either the version matches the latest version on Account or the latest version on Account
// is empty to read the payment address.
final String paymentAddress = maybeProfile
final byte[] paymentAddress = maybeProfile
.filter(p -> account.getCurrentProfileVersion().map(v -> v.equals(version)).orElse(true))
.map(VersionedProfile::paymentAddress)
.map(ProfileController::encodeToBase64)
.orElse(null);

return new VersionedProfileResponse(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,8 @@
import javax.annotation.Nullable;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import org.apache.commons.lang3.StringUtils;
import org.signal.libsignal.zkgroup.profiles.ProfileKeyCommitment;
import org.whispersystems.textsecuregcm.util.ByteArrayBase64WithPaddingAdapter;
import org.whispersystems.textsecuregcm.util.ExactlySize;

public class CreateProfileRequest {
Expand All @@ -24,8 +24,10 @@ public class CreateProfileRequest {
private String version;

@JsonProperty
@ExactlySize({108, 380})
private String name;
@JsonSerialize(using = ByteArrayBase64WithPaddingAdapter.Serializing.class)
@JsonDeserialize(using = ByteArrayBase64WithPaddingAdapter.Deserializing.class)
@ExactlySize({81, 285})
private byte[] name;

@JsonProperty
private boolean avatar;
Expand All @@ -34,16 +36,22 @@ public class CreateProfileRequest {
private boolean sameAvatar;

@JsonProperty
@ExactlySize({0, 80})
private String aboutEmoji;
@JsonSerialize(using = ByteArrayBase64WithPaddingAdapter.Serializing.class)
@JsonDeserialize(using = ByteArrayBase64WithPaddingAdapter.Deserializing.class)
@ExactlySize({0, 60})
private byte[] aboutEmoji;

@JsonProperty
@ExactlySize({0, 208, 376, 720})
private String about;
@JsonSerialize(using = ByteArrayBase64WithPaddingAdapter.Serializing.class)
@JsonDeserialize(using = ByteArrayBase64WithPaddingAdapter.Deserializing.class)
@ExactlySize({0, 156, 282, 540})
private byte[] about;

@JsonProperty
@ExactlySize({0, 776})
private String paymentAddress;
@JsonSerialize(using = ByteArrayBase64WithPaddingAdapter.Serializing.class)
@JsonDeserialize(using = ByteArrayBase64WithPaddingAdapter.Deserializing.class)
@ExactlySize({0, 582})
private byte[] paymentAddress;

@JsonProperty
@Nullable
Expand All @@ -59,8 +67,8 @@ public CreateProfileRequest() {
}

public CreateProfileRequest(
ProfileKeyCommitment commitment, String version, String name, String aboutEmoji, String about,
String paymentAddress, boolean wantsAvatar, boolean sameAvatar, List<String> badgeIds) {
final ProfileKeyCommitment commitment, final String version, final byte[] name, final byte[] aboutEmoji, final byte[] about,
final byte[] paymentAddress, final boolean wantsAvatar, final boolean sameAvatar, final List<String> badgeIds) {
this.commitment = commitment;
this.version = version;
this.name = name;
Expand All @@ -80,7 +88,7 @@ public String getVersion() {
return version;
}

public String getName() {
public byte[] getName() {
return name;
}

Expand All @@ -104,16 +112,16 @@ public AvatarChange getAvatarChange() {
return AvatarChange.UNCHANGED;
}

public String getAboutEmoji() {
return StringUtils.stripToNull(aboutEmoji);
public byte[] getAboutEmoji() {
return aboutEmoji;
}

public String getAbout() {
return StringUtils.stripToNull(about);
public byte[] getAbout() {
return about;
}

public String getPaymentAddress() {
return StringUtils.stripToNull(paymentAddress);
public byte[] getPaymentAddress() {
return paymentAddress;
}

public Optional<List<String>> getBadges() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,36 +7,47 @@

import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonUnwrapped;
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import org.whispersystems.textsecuregcm.util.ByteArrayBase64WithPaddingAdapter;

public class VersionedProfileResponse {

@JsonUnwrapped
private BaseProfileResponse baseProfileResponse;

@JsonProperty
private String name;
@JsonSerialize(using = ByteArrayBase64WithPaddingAdapter.Serializing.class)
@JsonDeserialize(using = ByteArrayBase64WithPaddingAdapter.Deserializing.class)
private byte[] name;

@JsonProperty
private String about;
@JsonSerialize(using = ByteArrayBase64WithPaddingAdapter.Serializing.class)
@JsonDeserialize(using = ByteArrayBase64WithPaddingAdapter.Deserializing.class)
private byte[] about;

@JsonProperty
private String aboutEmoji;
@JsonSerialize(using = ByteArrayBase64WithPaddingAdapter.Serializing.class)
@JsonDeserialize(using = ByteArrayBase64WithPaddingAdapter.Deserializing.class)
private byte[] aboutEmoji;

@JsonProperty
private String avatar;

@JsonProperty
private String paymentAddress;
@JsonSerialize(using = ByteArrayBase64WithPaddingAdapter.Serializing.class)
@JsonDeserialize(using = ByteArrayBase64WithPaddingAdapter.Deserializing.class)
private byte[] paymentAddress;

public VersionedProfileResponse() {
}

public VersionedProfileResponse(final BaseProfileResponse baseProfileResponse,
final String name,
final String about,
final String aboutEmoji,
final byte[] name,
final byte[] about,
final byte[] aboutEmoji,
final String avatar,
final String paymentAddress) {
final byte[] paymentAddress) {

this.baseProfileResponse = baseProfileResponse;
this.name = name;
Expand All @@ -50,23 +61,23 @@ public BaseProfileResponse getBaseProfileResponse() {
return baseProfileResponse;
}

public String getName() {
public byte[] getName() {
return name;
}

public String getAbout() {
public byte[] getAbout() {
return about;
}

public String getAboutEmoji() {
public byte[] getAboutEmoji() {
return aboutEmoji;
}

public String getAvatar() {
return avatar;
}

public String getPaymentAddress() {
public byte[] getPaymentAddress() {
return paymentAddress;
}
}
Loading

0 comments on commit 2601d6e

Please sign in to comment.