Convert MXKey to kotlin

This commit is contained in:
Benoit Marty 2019-07-03 16:45:08 +02:00
parent 7d5c31c510
commit 0ca9a5f68b
4 changed files with 142 additions and 151 deletions

View File

@ -24,7 +24,6 @@ import im.vector.matrix.android.internal.crypto.model.MXKey
import im.vector.matrix.android.internal.crypto.model.MXOlmSessionResult
import im.vector.matrix.android.internal.crypto.model.MXUsersDevicesMap
import im.vector.matrix.android.internal.crypto.tasks.ClaimOneTimeKeysForUsersDeviceTask
import im.vector.matrix.android.internal.session.SessionScope
import timber.log.Timber
import java.util.*
import javax.inject.Inject
@ -126,11 +125,13 @@ internal class EnsureOlmSessionsForDevicesAction @Inject constructor(private val
var isVerified = false
var errorMessage: String? = null

try {
olmDevice.verifySignature(deviceInfo.fingerprint()!!, oneTimeKey.signalableJSONDictionary(), signature)
isVerified = true
} catch (e: Exception) {
errorMessage = e.message
if (signature != null) {
try {
olmDevice.verifySignature(deviceInfo.fingerprint()!!, oneTimeKey.signalableJSONDictionary(), signature)
isVerified = true
} catch (e: Exception) {
errorMessage = e.message
}
}

// Check one-time key signature

View File

@ -1,139 +0,0 @@
/*
* Copyright 2016 OpenMarket Ltd
* Copyright 2018 New Vector Ltd
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package im.vector.matrix.android.internal.crypto.model;

import android.text.TextUtils;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import timber.log.Timber;

public class MXKey implements Serializable {
/**
* Key types.
*/
public static final String KEY_CURVE_25519_TYPE = "curve25519";
public static final String KEY_SIGNED_CURVE_25519_TYPE = "signed_curve25519";
//public static final String KEY_ED_25519_TYPE = "ed25519";

/**
* The type of the key.
*/
public String type;

/**
* The id of the key.
*/
public String keyId;

/**
* The key.
*/
public String value;

/**
* signature user Id to [deviceid][signature]
*/
public Map<String, Map<String, String>> signatures;

/**
* Default constructor
*/
public MXKey() {
}

/**
* Convert a map to a MXKey
*
* @param map the map to convert
*/
public MXKey(Map<String, Map<String, Object>> map) {
if ((null != map) && (map.size() > 0)) {
List<String> mapKeys = new ArrayList<>(map.keySet());

String firstEntry = mapKeys.get(0);
setKeyFullId(firstEntry);

Map<String, Object> params = map.get(firstEntry);
value = (String) params.get("key");
signatures = (Map<String, Map<String, String>>) params.get("signatures");
}
}

/**
* @return the key full id
*/
public String getKeyFullId() {
return type + ":" + keyId;
}

/**
* Update the key fields with a key full id
*
* @param keyFullId the key full id
*/
private void setKeyFullId(String keyFullId) {
if (!TextUtils.isEmpty(keyFullId)) {
try {
String[] components = keyFullId.split(":");

if (components.length == 2) {
type = components[0];
keyId = components[1];
}
} catch (Exception e) {
Timber.e(e, "## setKeyFullId() failed");
}
}
}

/**
* @return the signed data map
*/
public Map<String, Object> signalableJSONDictionary() {
Map<String, Object> map = new HashMap<>();

if (null != value) {
map.put("key", value);
}

return map;
}

/**
* Returns a signature for an user Id and a signkey
*
* @param userId the user id
* @param signkey the sign key
* @return the signature
*/
public String signatureForUserId(String userId, String signkey) {
// sanity checks
if (!TextUtils.isEmpty(userId) && !TextUtils.isEmpty(signkey)) {
if ((null != signatures) && signatures.containsKey(userId)) {
return signatures.get(userId).get(signkey);
}
}

return null;
}
}

View File

@ -0,0 +1,129 @@
/*
* Copyright 2019 New Vector Ltd
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package im.vector.matrix.android.internal.crypto.model

import im.vector.matrix.android.api.util.JsonDict
import timber.log.Timber
import java.util.*

data class MXKey(
/**
* The type of the key (in the example: "signed_curve25519").
*/
val type: String,

/**
* The id of the key (in the example: "AAAAFw").
*/
private val keyId: String,

/**
* The key (in the example: "IjwIcskng7YjYcn0tS8TUOT2OHHtBSfMpcfIczCgXj4").
*/
val value: String,

/**
* signature user Id to [deviceid][signature]
*/
private val signatures: Map<String, Map<String, String>>
) {

/**
* @return the signed data map
*/
fun signalableJSONDictionary(): Map<String, Any> {
val map = HashMap<String, Any>()

map["key"] = value

return map
}

/**
* Returns a signature for an user Id and a signkey
*
* @param userId the user id
* @param signkey the sign key
* @return the signature
*/
fun signatureForUserId(userId: String, signkey: String): String? {
// sanity checks
if (userId.isNotBlank() && signkey.isNotBlank()) {
if (signatures.containsKey(userId)) {
return signatures[userId]?.get(signkey)
}
}

return null
}


companion object {
/**
* Key types.
*/
const val KEY_CURVE_25519_TYPE = "curve25519"
const val KEY_SIGNED_CURVE_25519_TYPE = "signed_curve25519"
// const val KEY_ED_25519_TYPE = "ed25519"

/**
* Convert a map to a MXKey
*
* @param map the map to convert
*
* Json Example:
*
* <pre>
* "signed_curve25519:AAAAFw": {
* "key": "IjwIcskng7YjYcn0tS8TUOT2OHHtBSfMpcfIczCgXj4",
* "signatures": {
* "@userId:matrix.org": {
* "ed25519:GMJRREOASV": "EUjp6pXzK9u3SDFR\/qLbzpOi3bEREeI6qMnKzXu992HsfuDDZftfJfiUXv9b\/Hqq1og4qM\/vCQJGTHAWMmgkCg"
* }
* }
* }
* </pre>
*
* into several val members
*/
fun from(map: Map<String, JsonDict>?): MXKey? {
if (map?.isNotEmpty() == true) {
val firstKey = map.keys.first()

val components = firstKey.split(":").dropLastWhile { it.isEmpty() }

if (components.size == 2) {
val params = map[firstKey]
if (params != null) {
if (params["key"] is String) {
return MXKey(
type = components[0],
keyId = components[1],
value = params["key"] as String,
signatures = params["signatures"] as Map<String, Map<String, String>>
)
}
}
}
}

// Error case
Timber.e("## Unable to parse map")
return null
}
}
}

View File

@ -23,7 +23,6 @@ import im.vector.matrix.android.internal.crypto.model.MXUsersDevicesMap
import im.vector.matrix.android.internal.crypto.model.rest.KeysClaimBody
import im.vector.matrix.android.internal.crypto.model.rest.KeysClaimResponse
import im.vector.matrix.android.internal.network.executeRequest
import im.vector.matrix.android.internal.session.SessionScope
import im.vector.matrix.android.internal.task.Task
import timber.log.Timber
import java.util.*
@ -55,12 +54,13 @@ internal class DefaultClaimOneTimeKeysForUsersDevice @Inject constructor(private
val keysMap = HashMap<String, MXKey>()

for (deviceId in mapByUserId!!.keys) {
try {
keysMap[deviceId] = MXKey(mapByUserId[deviceId])
} catch (e: Exception) {
Timber.e(e, "## claimOneTimeKeysForUsersDevices : fail to create a MXKey ")
}
val mxKey = MXKey.from(mapByUserId[deviceId])

if (mxKey != null) {
keysMap[deviceId] = mxKey
} else {
Timber.e("## claimOneTimeKeysForUsersDevices : fail to create a MXKey")
}
}

if (keysMap.size != 0) {