}
dependencies {
- api("com.github.turasa:signal-service-java:2.15.3_unofficial_18")
+ api("com.github.turasa:signal-service-java:2.15.3_unofficial_19")
implementation("com.google.protobuf:protobuf-javalite:3.10.0")
implementation("org.bouncycastle:bcprov-jdk15on:1.68")
implementation("org.slf4j:slf4j-api:1.7.30")
import org.whispersystems.libsignal.IdentityKeyPair;
import org.whispersystems.libsignal.InvalidKeyException;
import org.whispersystems.libsignal.InvalidMessageException;
-import org.whispersystems.libsignal.InvalidVersionException;
import org.whispersystems.libsignal.ecc.ECPublicKey;
import org.whispersystems.libsignal.state.PreKeyRecord;
import org.whispersystems.libsignal.state.SignedPreKeyRecord;
new DynamicCredentialsProvider(account.getUuid(),
account.getUsername(),
account.getPassword(),
- account.getSignalingKey(),
account.getDeviceId()),
userAgent,
groupsV2Operations,
account.getUsername(),
account.getPassword(),
account.getDeviceId(),
- account.getSignalingKey(),
userAgent,
null,
timer,
}
public void updateAccountAttributes() throws IOException {
- accountManager.setAccountAttributes(account.getSignalingKey(),
+ accountManager.setAccountAttributes(null,
account.getSignalProtocolStore().getLocalRegistrationId(),
true,
// set legacy pin only if no KBS master key is set
} catch (TimeoutException e) {
if (returnOnTimeout) return;
continue;
- } catch (InvalidVersionException e) {
- logger.warn("Error while receiving messages, ignoring: {}", e.getMessage());
- continue;
}
if (envelope.hasSource()) {
groupsV2Operations = null;
}
accountManager = new SignalServiceAccountManager(serviceEnvironmentConfig.getSignalServiceConfiguration(),
- new DynamicCredentialsProvider(null, null, password, null, SignalServiceAddress.DEFAULT_DEVICE_ID),
+ new DynamicCredentialsProvider(null, null, password, SignalServiceAddress.DEFAULT_DEVICE_ID),
userAgent,
groupsV2Operations,
ServiceConfig.AUTOMATIC_NETWORK_RETRY,
}
public String finishDeviceLink(String deviceName) throws IOException, InvalidKeyException, TimeoutException, UserAlreadyExists {
- String signalingKey = KeyUtils.createSignalingKey();
SignalServiceAccountManager.NewDeviceRegistrationReturn ret = accountManager.finishNewDeviceRegistration(
identityKey,
- signalingKey,
false,
true,
registrationId,
ret.getDeviceId(),
ret.getIdentity(),
registrationId,
- signalingKey,
profileKey)) {
account.save();
this.accountManager = new SignalServiceAccountManager(serviceEnvironmentConfig.getSignalServiceConfiguration(),
new DynamicCredentialsProvider(
// Using empty UUID, because registering doesn't work otherwise
- null,
- account.getUsername(),
- account.getPassword(),
- account.getSignalingKey(),
- SignalServiceAddress.DEFAULT_DEVICE_ID),
+ null, account.getUsername(), account.getPassword(), SignalServiceAddress.DEFAULT_DEVICE_ID),
userAgent,
groupsV2Operations,
ServiceConfig.AUTOMATIC_NETWORK_RETRY,
String verificationCode, String pin
) throws IOException, KeyBackupSystemNoDataException, KeyBackupServicePinException {
verificationCode = verificationCode.replace("-", "");
- if (account.getSignalingKey() == null) {
- account.setSignalingKey(KeyUtils.createSignalingKey());
- }
VerifyAccountResponse response;
try {
response = verifyAccountWithCode(verificationCode, pin, null);
account.setRegistered(true);
account.setUuid(UuidUtil.parseOrNull(response.getUuid()));
account.setRegistrationLockPin(pin);
+ account.getSignalProtocolStore().archiveAllSessions();
account.getSignalProtocolStore()
.saveIdentity(account.getSelfAddress(),
account.getSignalProtocolStore().getIdentityKeyPair().getPublicKey(),
final String verificationCode, final String legacyPin, final String registrationLock
) throws IOException {
return accountManager.verifyAccountWithCode(verificationCode,
- account.getSignalingKey(),
+ null,
account.getSignalProtocolStore().getLocalRegistrationId(),
true,
legacyPin,
import org.whispersystems.signalservice.internal.configuration.SignalCdnUrl;
import org.whispersystems.signalservice.internal.configuration.SignalContactDiscoveryUrl;
import org.whispersystems.signalservice.internal.configuration.SignalKeyBackupServiceUrl;
+import org.whispersystems.signalservice.internal.configuration.SignalProxy;
import org.whispersystems.signalservice.internal.configuration.SignalServiceConfiguration;
import org.whispersystems.signalservice.internal.configuration.SignalServiceUrl;
import org.whispersystems.signalservice.internal.configuration.SignalStorageUrl;
private final static TrustStore TRUST_STORE = new WhisperTrustStore();
private final static Optional<Dns> dns = Optional.absent();
+ private final static Optional<SignalProxy> proxy = Optional.absent();
private final static byte[] zkGroupServerPublicParams = Base64.getDecoder()
.decode("AMhf5ywVwITZMsff/eCyudZx9JDmkkkbV6PInzG4p8x3VqVJSFiMvnvlEKWuRob/1eaIetR31IYeAbm0NdOuHH8Qi+Rexi1wLlpzIo1gstHWBfZzy1+qHRV5A4TqPp15YzBPm0WSggW6PbSn+F4lf57VCnHF7p8SvzAA2ZZJPYJURt8X7bbg+H3i+PEjH9DXItNEqs2sNcug37xZQDLm7X0=");
new SignalStorageUrl[]{new SignalStorageUrl(STORAGE_URL, TRUST_STORE)},
interceptors,
dns,
+ proxy,
zkGroupServerPublicParams);
}
import org.whispersystems.signalservice.internal.configuration.SignalCdnUrl;
import org.whispersystems.signalservice.internal.configuration.SignalContactDiscoveryUrl;
import org.whispersystems.signalservice.internal.configuration.SignalKeyBackupServiceUrl;
+import org.whispersystems.signalservice.internal.configuration.SignalProxy;
import org.whispersystems.signalservice.internal.configuration.SignalServiceConfiguration;
import org.whispersystems.signalservice.internal.configuration.SignalServiceUrl;
import org.whispersystems.signalservice.internal.configuration.SignalStorageUrl;
private final static TrustStore TRUST_STORE = new WhisperTrustStore();
private final static Optional<Dns> dns = Optional.absent();
+ private final static Optional<SignalProxy> proxy = Optional.absent();
private final static byte[] zkGroupServerPublicParams = Base64.getDecoder()
.decode("ABSY21VckQcbSXVNCGRYJcfWHiAMZmpTtTELcDmxgdFbtp/bWsSxZdMKzfCp8rvIs8ocCU3B37fT3r4Mi5qAemeGeR2X+/YmOGR5ofui7tD5mDQfstAI9i+4WpMtIe8KC3wU5w3Inq3uNWVmoGtpKndsNfwJrCg0Hd9zmObhypUnSkfYn2ooMOOnBpfdanRtrvetZUayDMSC5iSRcXKpdls=");
new SignalStorageUrl[]{new SignalStorageUrl(STORAGE_URL, TRUST_STORE)},
interceptors,
dns,
+ proxy,
zkGroupServerPublicParams);
}
private String registrationLockPin;
private MasterKey pinMasterKey;
private StorageKey storageKey;
- private String signalingKey;
private ProfileKey profileKey;
private int preKeyIdOffset;
private int nextSignedPreKeyId;
int deviceId,
IdentityKeyPair identityKey,
int registrationId,
- String signalingKey,
ProfileKey profileKey
) throws IOException {
IOUtils.createPrivateDirectories(dataPath);
account.password = password;
account.profileKey = profileKey;
account.deviceId = deviceId;
- account.signalingKey = signalingKey;
account.signalProtocolStore = new JsonSignalProtocolStore(identityKey, registrationId);
account.groupStore = new JsonGroupStore(getGroupCachePath(dataPath, username));
account.contactStore = new JsonContactsStore();
if (rootNode.hasNonNull("storageKey")) {
storageKey = new StorageKey(Base64.getDecoder().decode(rootNode.get("storageKey").asText()));
}
- if (rootNode.hasNonNull("signalingKey")) {
- signalingKey = rootNode.get("signalingKey").asText();
- if (signalingKey.equals("null")) {
- // Workaround for load bug in older versions
- signalingKey = null;
- }
- }
if (rootNode.hasNonNull("preKeyIdOffset")) {
preKeyIdOffset = rootNode.get("preKeyIdOffset").asInt(0);
} else {
pinMasterKey == null ? null : Base64.getEncoder().encodeToString(pinMasterKey.serialize()))
.put("storageKey",
storageKey == null ? null : Base64.getEncoder().encodeToString(storageKey.serialize()))
- .put("signalingKey", signalingKey)
.put("preKeyIdOffset", preKeyIdOffset)
.put("nextSignedPreKeyId", nextSignedPreKeyId)
.put("profileKey", Base64.getEncoder().encodeToString(profileKey.serialize()))
this.storageKey = storageKey;
}
- public String getSignalingKey() {
- return signalingKey;
- }
-
- public void setSignalingKey(final String signalingKey) {
- this.signalingKey = signalingKey;
- }
-
public ProfileKey getProfileKey() {
return profileKey;
}
import org.slf4j.LoggerFactory;
import org.whispersystems.libsignal.SignalProtocolAddress;
import org.whispersystems.libsignal.state.SessionRecord;
-import org.whispersystems.libsignal.state.SessionStore;
+import org.whispersystems.signalservice.api.SignalServiceSessionStore;
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
import org.whispersystems.signalservice.api.util.UuidUtil;
import java.util.List;
import java.util.UUID;
-class JsonSessionStore implements SessionStore {
+class JsonSessionStore implements SignalServiceSessionStore {
private final static Logger logger = LoggerFactory.getLogger(JsonSessionStore.class);
sessions.removeIf(info -> info.address.matches(serviceAddress));
}
+ @Override
+ public void archiveSession(final SignalProtocolAddress address) {
+ final SessionRecord sessionRecord = loadSession(address);
+ if (sessionRecord == null) {
+ return;
+ }
+ sessionRecord.archiveCurrentState();
+ storeSession(address, sessionRecord);
+ }
+
+ public void archiveAllSessions() {
+ for (SessionInfo info : sessions) {
+ try {
+ final SessionRecord sessionRecord = new SessionRecord(info.sessionRecord);
+ sessionRecord.archiveCurrentState();
+ info.sessionRecord = sessionRecord.serialize();
+ } catch (IOException ignored) {
+ }
+ }
+ }
+
public static class JsonSessionStoreDeserializer extends JsonDeserializer<JsonSessionStore> {
@Override
import org.whispersystems.libsignal.SignalProtocolAddress;
import org.whispersystems.libsignal.state.PreKeyRecord;
import org.whispersystems.libsignal.state.SessionRecord;
-import org.whispersystems.libsignal.state.SignalProtocolStore;
import org.whispersystems.libsignal.state.SignedPreKeyRecord;
+import org.whispersystems.signalservice.api.SignalServiceProtocolStore;
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
import java.util.List;
-public class JsonSignalProtocolStore implements SignalProtocolStore {
+public class JsonSignalProtocolStore implements SignalServiceProtocolStore {
@JsonProperty("preKeys")
@JsonDeserialize(using = JsonPreKeyStore.JsonPreKeyStoreDeserializer.class)
sessionStore.deleteAllSessions(serviceAddress);
}
+ @Override
+ public void archiveSession(final SignalProtocolAddress address) {
+ sessionStore.archiveSession(address);
+ }
+
+ public void archiveAllSessions() {
+ sessionStore.archiveAllSessions();
+ }
+
@Override
public SignedPreKeyRecord loadSignedPreKey(int signedPreKeyId) throws InvalidKeyIdException {
return signedPreKeyStore.loadSignedPreKey(signedPreKeyId);