Skip to content

Commit

Permalink
Merge pull request #51 from chaoxinhu/feature/modify-context
Browse files Browse the repository at this point in the history
Modify @context field and add Credential Serialization
  • Loading branch information
chenhaozx committed Mar 20, 2019
2 parents 037753c + ec38b9b commit a6fab0b
Show file tree
Hide file tree
Showing 7 changed files with 225 additions and 16 deletions.
43 changes: 43 additions & 0 deletions src/main/java/com/webank/weid/constant/CredentialConstant.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
/*
* Copyright© (2018-2019) WeBank Co., Ltd.
*
* This file is part of weidentity-java-sdk.
*
* weidentity-java-sdk is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* weidentity-java-sdk is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with weidentity-java-sdk. If not, see <https://www.gnu.org/licenses/>.
*/

package com.webank.weid.constant;

/**
* The Class CredentialConstant.
*
* @author chaoxinhu
*/

public final class CredentialConstant {

/**
* The Constant default Credential Context.
*/
public static final String DEFAULT_CREDENTIAL_CONTEXT =
"https://www.w3.org/2018/credentials/v1";
/**
* The Constant default Credential Context field name.
*/
public static final String CREDENTIAL_CONTEXT_FIELD = "\"context\"";
/**
* The Constant default Credential Context field name in Credential Json String.
*/
public static final String CREDENTIAL_CONTEXT_PORTABLE_JSON_FIELD = "\"@context\"";
}
12 changes: 6 additions & 6 deletions src/main/java/com/webank/weid/constant/WeIdConstant.java
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ public final class WeIdConstant {
* The Constant WeIdentity DID Document Protocol Version.
*/
public static final String WEID_DOC_PROTOCOL_VERSION =
"\"@context\": \"https://weidentity.webank.com/did/v1\",";
"\"@context\" : \"https://w3id.org/did/v1\",";

/**
* The Constant GAS_PRICE.
Expand Down Expand Up @@ -114,11 +114,6 @@ public final class WeIdConstant {
*/
public static final String PIPELINE = "|";

/**
* The Constant default Certificate Context.
*/
public static final String DEFAULT_CERTIFICATE_CONTEXT = "v1";

/**
* The Constant Max authority issuer name length in Chars.
*/
Expand Down Expand Up @@ -154,6 +149,11 @@ public final class WeIdConstant {
*/
public static final String UUID_SEPARATOR = "-";

/**
* Quote.
*/
public static final String DOUBLE_QUOTE = "\"";

/**
* UUID Pattern.
*/
Expand Down
22 changes: 14 additions & 8 deletions src/main/java/com/webank/weid/rpc/CredentialService.java
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,9 @@ public interface CredentialService {
/**
* Generate a credential with selected data.
*
* @param credential the credential.
* @param credential the credential
* @param disclosure the setting of disclosure, such as: {@code{"name":1,"gender":0,"age":1}},
* which means you WILL disclose "name" and "age", and "gender" WILL NOT be disclosed
* to others.
* @return CredentialWrapper
*/
ResponseData<CredentialWrapper> createSelectiveCredential(
Expand All @@ -59,7 +58,6 @@ ResponseData<CredentialWrapper> createSelectiveCredential(
*
* @param credential the credential
* @return the verification result. True if yes, false otherwise with exact verify error codes
* in ResponseData
*/
ResponseData<Boolean> verify(Credential credential);

Expand All @@ -74,9 +72,8 @@ ResponseData<CredentialWrapper> createSelectiveCredential(
/**
* Verify the validity of a credential. Public key must be provided.
*
* @param credentialWrapper the credential wrapper.
* @param weIdPublicKey the specified public key which used to verify signature of the
* credential.
* @param credentialWrapper the credential wrapper
* @param weIdPublicKey the specified public key which used to verify credential signature
* @return the verification result. True if yes, false otherwise with exact verify error codes
*/
ResponseData<Boolean> verifyCredentialWithSpecifiedPubKey(
Expand All @@ -88,8 +85,17 @@ ResponseData<Boolean> verifyCredentialWithSpecifiedPubKey(
* Get the full hash value of a Credential. All fields in the Credential will be included. This
* method should be called when creating and verifying the Credential Evidence.
*
* @param args the args
* @param credential the args
* @return the Credential Hash value in byte array, fixed to be 32 Bytes length
*/
ResponseData<String> getCredentialHash(Credential args);
ResponseData<String> getCredentialHash(Credential credential);

/**
* Get the Json String of a Credential. All fields in the Credential will be included. This
* also supports the selectively disclosed Credential.
*
* @param credential the credential
* @return the Credential Json value in String
*/
ResponseData<String> getCredentialJson(Credential credential);
}
Original file line number Diff line number Diff line change
Expand Up @@ -26,15 +26,19 @@
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
import java.util.regex.Pattern;

import com.fasterxml.jackson.databind.ObjectMapper;
import org.apache.commons.lang3.StringUtils;
import org.bcos.web3j.crypto.Sign;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

import com.webank.weid.constant.CredentialConstant;
import com.webank.weid.constant.CredentialFieldDisclosureValue;
import com.webank.weid.constant.ErrorCode;
import com.webank.weid.constant.WeIdConstant;
import com.webank.weid.protocol.base.Cpt;
import com.webank.weid.protocol.base.Credential;
import com.webank.weid.protocol.base.CredentialWrapper;
Expand Down Expand Up @@ -392,4 +396,62 @@ public ResponseData<CredentialWrapper> createSelectiveCredential(
return new ResponseData<>(credentialResult, ErrorCode.SUCCESS);
}

/**
* Get the Json String of a Credential. All fields in the Credential will be included. This also
* supports the selectively disclosed Credential.
*
* @param credential the credential wrapper
* @return the Credential Json value in String
*/
@Override
public ResponseData<String> getCredentialJson(Credential credential) {
ErrorCode errorCode = CredentialUtils.isCredentialValid(credential);
if (errorCode.getCode() != ErrorCode.SUCCESS.getCode()) {
return new ResponseData<>(
StringUtils.EMPTY,
ErrorCode.getTypeByErrorCode(errorCode.getCode())
);
}

ObjectMapper mapper = new ObjectMapper();
String credentialString = StringUtils.EMPTY;
try {
credentialString = mapper.writerWithDefaultPrettyPrinter()
.writeValueAsString(credential);
} catch (Exception e) {
logger.error("Error occurred in getCredentialJson: ", e);
return new ResponseData<>(StringUtils.EMPTY, ErrorCode.CREDENTIAL_ERROR);
}

// Convert timestamp into UTC timezone
try {
String issueranceDate = new StringBuilder()
.append(WeIdConstant.DOUBLE_QUOTE)
.append(DateUtils.convertTimestampToUtc(credential.getIssuranceDate()))
.append(WeIdConstant.DOUBLE_QUOTE)
.toString();
String expirationDate = new StringBuilder()
.append(WeIdConstant.DOUBLE_QUOTE)
.append(DateUtils.convertTimestampToUtc(credential.getExpirationDate()))
.append(WeIdConstant.DOUBLE_QUOTE)
.toString();
credentialString = credentialString
.replace(credential.getIssuranceDate().toString(), issueranceDate);
credentialString = credentialString
.replace(credential.getExpirationDate().toString(), expirationDate);
// Convert context into "@context"
credentialString = credentialString.replaceFirst(
Pattern.quote(CredentialConstant.CREDENTIAL_CONTEXT_FIELD),
CredentialConstant.CREDENTIAL_CONTEXT_PORTABLE_JSON_FIELD
);
} catch (Exception e) {
logger.error("Date conversion failed in getCredentialJson: ", e);
return new ResponseData<>(StringUtils.EMPTY, ErrorCode.CREDENTIAL_ERROR);
}

ResponseData<String> credentialResult = new ResponseData<>();
credentialResult.setResult(credentialString);
credentialResult.setErrorCode(errorCode);
return credentialResult;
}
}
3 changes: 2 additions & 1 deletion src/main/java/com/webank/weid/util/CredentialUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@
import org.apache.commons.lang3.StringUtils;
import org.bcos.web3j.abi.datatypes.generated.Bytes32;

import com.webank.weid.constant.CredentialConstant;
import com.webank.weid.constant.CredentialFieldDisclosureValue;
import com.webank.weid.constant.ErrorCode;
import com.webank.weid.constant.WeIdConstant;
Expand Down Expand Up @@ -158,7 +159,7 @@ public static String concatCredentialMetadata(Credential arg) {
* @return Context value in String.
*/
public static String getDefaultCredentialContext() {
return WeIdConstant.DEFAULT_CERTIFICATE_CONTEXT;
return CredentialConstant.DEFAULT_CREDENTIAL_CONTEXT;
}

/**
Expand Down
14 changes: 13 additions & 1 deletion src/main/java/com/webank/weid/util/DateUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -119,6 +119,18 @@ public static boolean isValidDateString(String dateString) {
}
}

/**
* Check the timestamp date to UTC date string.
*
* @param timestamp the date string
* @return UTC formatted date string
*/
public static String convertTimestampToUtc(Long timestamp) {
DateFormat df = getDefaultDateFormat();
df.setLenient(false);
return df.format(new Date(timestamp));
}

/**
* Get current timestamp in Int256 type.
*
Expand All @@ -138,7 +150,7 @@ public static String getCurrentTimeStampString() {
}

/**
* Get current timestamp in String type.
* Get current timestamp in String type.
*
* @return the current time stamp long
*/
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
/*
* Copyright© (2018-2019) WeBank Co., Ltd.
*
* This file is part of weidentity-java-sdk.
*
* weidentity-java-sdk is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* weidentity-java-sdk is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with weidentity-java-sdk. If not, see <https://www.gnu.org/licenses/>.
*/

package com.webank.weid.full.credential;

import java.util.HashMap;
import java.util.UUID;

import org.apache.commons.lang3.StringUtils;
import org.junit.Assert;
import org.junit.Test;

import com.webank.weid.constant.CredentialConstant;
import com.webank.weid.constant.ErrorCode;
import com.webank.weid.full.TestBaseServcie;
import com.webank.weid.protocol.base.Credential;
import com.webank.weid.protocol.response.ResponseData;

/**
* Testing getCredentialJson method.
*
* @author chaoxinhu
*/
public class TestGetCredentialJson extends TestBaseServcie {

@Test
public void testGetCredentialJsonCase1() {
Credential credential = buildCredential();
ResponseData<String> response1 = credentialService.getCredentialJson(credential);
Assert.assertEquals(ErrorCode.SUCCESS.getCode(), response1.getErrorCode().intValue());
Assert.assertNotNull(response1.getResult());
Assert.assertTrue(
response1
.getResult()
.contains(CredentialConstant.CREDENTIAL_CONTEXT_PORTABLE_JSON_FIELD));
Assert.assertTrue(
response1
.getResult()
.contains(CredentialConstant.DEFAULT_CREDENTIAL_CONTEXT));

credential = buildCredential();
credential.setIssuer("xxxxxxxxx");
response1 = credentialService.getCredentialHash(credential);
Assert.assertNotEquals(ErrorCode.SUCCESS.getCode(), response1.getErrorCode().intValue());
Assert.assertEquals(StringUtils.EMPTY, response1.getResult());
}

@Test
public void testGetCredentialJsonCase2() {
ResponseData<String> response1 = credentialService.getCredentialJson(null);
Assert.assertNotEquals(ErrorCode.SUCCESS.getCode(), response1.getErrorCode().intValue());
Assert.assertEquals(StringUtils.EMPTY, response1.getResult());
}

private Credential buildCredential() {
Credential credential = new Credential();
HashMap<String, Object> claim = new HashMap<>();
claim.put("xxxxxxxxxxxxx", "xxxxxxxxxxxxx");
credential.setClaim(claim);
credential.setContext(CredentialConstant.DEFAULT_CREDENTIAL_CONTEXT);
credential.setCptId(Integer.valueOf(1002));
credential.setExpirationDate(System.currentTimeMillis() + 10000L);
credential.setId(UUID.randomUUID().toString());
credential.setIssuer("did:weid:0x0000000000000001");
credential.setIssuranceDate(System.currentTimeMillis());
credential.setSignature("xxxxxxxxxxxx");
return credential;
}
}

0 comments on commit a6fab0b

Please sign in to comment.