How do I send an accessCode to a recipient and override the email using a template via the DocuSignAPI? - templates

I have tried just about everything that I can think of and cannot get this to work.
I am trying to set an access code in my code and send it to a templateRole using the RequestSignatureFromTemplate call. Right now, all of my configuration info is in XML. I am NOT adverse to using JSON but not all of my developers know JSON.
Here is a snippet of my XML.
<envelopeDefinition xmlns=\"http://www.docusign.com/restapi\">
accountId>12345</accountId>
<status>sent</status>
<emailSubject>Test Form</emailSubject>
<emailBlurb>This is a template test.</emailBlurb>
<templateId>####-########</templateId>
<templateRoles>
<templateRole>
<accessCode>AccessCode124</accessCode>" +
<addAccessCodeToEmail>true</addAccessCodeToEmail>" +
<email>jevans#eclarifire.com</email>
<name>Test User</name>
<roleName>RoleOne</roleName>
<emailNotification>
<emailSubject>This is RoleOne's subject</emailSubject>
<emailBody>This is RoleOne's email.</emailBody>
<addAccessCodeToEmail>true</addAccessCodeToEmail>
</emailNotification>
</templateRole>
<templateRole>
<accessCode>AccessCode246</accessCode>
<email>jevans#eclarifire.com</email>
<name>Test User2</name>
<roleName>RoleTwo</roleName>
<emailNotification>
<emailBody>Your access code is 24680</emailBody>
</emailNotification>
</templateRole>
</templateRoles>
</envelopeDefinition>
You'll notice that I have two different implementations in the templateRole nodes. This is intentional since I'm trying everything that I can think of. In templateRole(1), I have added the addAccessCodeToEmail node in two different places and it doesn't work in either. I have also attempted to override the emailBlurb node in templateRole(1) and it doesn't work either.
I've been through the documentation and it says that you should be able to add anything that the Recipients format follows but I can't get it to work.
Any one got any ideas?

I've never used the addAccessCodeToEmail property in a "Create/Send Envelope" API request, because including the Access Code in the email that the recipient receives entirely nullifies the effect of using Access Code for authentication in the first place. i.e., the entire point of requiring the Recipient to enter an Access Code is to add another layer of assurance -- beyond the fact that someone merely has access to an email inbox -- before granting access to the envelope. If you're going to include the access code in the email that the Recipient receives, then using Access Code as the form of authentication isn't providing any additional security benefit whatsoever -- whoever has access to that email inbox will be able to easily access the envelope (same result as if you don't use Access Code at all).
That being said, there is a property that (for whatever reason) should allow you to have Access Code included in the email that the recipient receives -- I can't get this to work either. Maybe a bug, but someone at DocuSign will need to confirm. According to the documentation, this should result in the email containing the access code:
POST https://{{env}}.docusign.net/restapi/{{version}}/accounts/{{acctId}}/envelopes
{
"status" : "sent",
"emailBlurb" : "please sign",
"emailSubject" : "Please sign your document",
"templateId" : "TEMPLATE_ID",
"templateRoles" : [{
"name" : "John Doe",
"email" : "JohnsEmail#outlook.com",
"roleName" : "Signer1",
"accessCode" : "1234",
"addAccessCodeToEmail": "true"
}]
}
This request results in the recipient being required to enter an Access Code before he can access the Envelope, but the addAccessCodeToEmail property isn't having the expected effect, as the Access Code doesn't appear anywhere in the email that the recipient receives.
Alternative Approach (Best Practice):
Instead of adding the plain-text access code to the email, best practice when using the API to create/send an Envelope and require Access Code as the form of recipient authentication would be to do the following:
Programmatically set accessCode using a piece of data that your application knows about the recipient.
Set the "Email Blurb" (i.e., body of the email) to provide a hint as to the Access Code.
For example, let's say your application knows the Recipient's social security number. When you make the "Create Envelope" API request:
Set the value of accessCode to the last 4 digits of the Recipient's SSN.
Set the value of emailBlurb to include the messaging "Your access code is the last 4 digits of your SSN."
Doing things this way is much more secure than simply including the Access Code (in plain text) in the Email itself.
Finally, regarding your question about overriding the email subject & body for recipients -- see definition of emailNotification property on page 290-291 of the REST API guide (http://www.docusign.com/sites/default/files/REST_API_Guide_v2.pdf):
IMPORTANT: If this is enabled for one recipient, it overrides the Envelope Subject and EmailBlurb. Also, you must enable emailNotification for all recipients.
Sounds like you need to set emailNotification for each and every recipient if you want it to have any effect.

Here are a couple of examples that use "Composite Templates" in the Create Envelope API request to create an envelope with either ID Check or Phone Authentication as the method of recipient authentication.
Recipient Authentication = ID Check
POST https://{{env}}.docusign.net/restapi/{{version}}/accounts/{{acctId}}/envelopes
{
"emailSubject": "Please sign",
"emailBlurb": "Please sign...thanks!",
"status": "sent",
"compositeTemplates": [
{
"serverTemplates": [
{
"sequence" : 1,
"templateId": "TEMPLATE_ID"
}],
"inlineTemplates": [
{
"sequence" : 2,
"recipients": {
"signers" : [{
"email": "SallysEmail#outlook.com",
"name": "Sally Adamson",
"recipientId": "1",
"roleName": "ROLE_NAME",
"requireIdLookup": "true",
"idCheckConfigurationName": "ID Check $"
}]
}
}]
}]
}
Recipient Authentication = Phone Auth
POST https://{{env}}.docusign.net/restapi/{{version}}/accounts/{{acctId}}/envelopes
{
"emailSubject": "Please sign",
"emailBlurb": "Please sign...thanks!",
"status": "sent",
"compositeTemplates": [
{
"serverTemplates": [
{
"sequence" : 1,
"templateId": "TEMPLATE_ID"
}],
"inlineTemplates": [
{
"sequence" : 2,
"recipients": {
"signers" : [{
"email": "SallysEmail#outlook.com",
"name": "Sally Adamson",
"recipientId": "1",
"roleName": "ROLE_NAME",
"requireIdLookup": "true",
"idCheckConfigurationName": "Phone Auth $",
"phoneAuthentication": {
"recipMayProvideNumber": "false",
"senderProvidedNumbers": ["206-444-5555"]
}
}]
}
}]
}]
}

Related

How to get list of meaningful name upon fetching minted NFTs list from Alchemy Api?

I am new to block chain and I am using Alchemy and my NFTs and NFT Meta Data is on "Pinata". When I fetch my minted NFTs from Alchemy API, in response I get list of "contract addresses" and "Token Ids". Is there any way to get list of meaningful names of my minted NFTs instead of ids (without using loops). OR is there a way to store a meaningful name upon minting . Any help will be appreciated.
response upon calling API :
{"balance": "1", "contract": {"address": "0xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"}, "id": {"tokenId": "0x0000000000000000000000000000000000000000000000000000000000000000"}}]```
Is there any way to get list of meaningful names of my minted NFTs instead of ids (without using loops).
Yes! As of July 12th, 2022 (current time) -- the getNFTs endpoint includes a withMetadata query param option that defaults to true (see docs).
That means that the response should include the info you might want, including:
title: name of the NFT asset
description: brief human-readable description
media.gateway: public gateway uri for the raw asset
etc.
See full documentation here: https://docs.alchemy.com/alchemy/enhanced-apis/nft-api/getnfts
An example response might look like this:
{
"ownedNfts": [
{
"contract": {
"address": "0x0beed7099af7514ccedf642cfea435731176fb02"
},
"id": {
"tokenId": "28",
"tokenMetadata": {
"tokenType": "ERC721"
}
},
"title": "DuskBreaker #28",
"description": "Breakers have the honor of serving humanity through their work on The Dusk. They are part of a select squad of 10,000 recruits who spend their days exploring a mysterious alien spaceship filled with friends, foes, and otherworldly technology.",
"tokenUri": {
"raw": "https://duskbreakers.gg/api/breakers/28",
"gateway": "https://duskbreakers.gg/api/breakers/28"
},
"media": [
{
"raw": "https://duskbreakers.gg/breaker_images/28.png",
"gateway": "https://duskbreakers.gg/breaker_images/28.png"
}
],
"metadata": {
...
}
},
...
]
...
}
You should then be able to do something like this to get your names:
const names = ownedNfts.map((nft) => nft.title};
Use the getNFTMetadata method to get information on each NFT.

Docusign Create Envelope ENVELOPE_IS_INCOMPLETE using templateId

The Envelope is not Complete. A Complete Envelope Requires Documents, Recipients, Tabs, and a Subject Line.
I am trying to create an envelope using the REST Api from docusign and got this error. This was working a few weeks ago and now, I suddenly got this error. Below is my json body for the request.
{
"status": "sent",
"emailSubject": "Company Contract: Signature Required",
"templateId": "310439de-819e-404b-90d6-a468bc0e4e12",
"templateRoles": [
{
"email": "sample1#gmail.com",
"name": "Buyer Buy",
"roleName": "BUYER_PROFILE"
},
{
"email": "sample#gmail.com",
"name": "First Floor",
"roleName": "SELLER_PROFILE"
}
]
}
I also tried this request via postman and I still have the same error. I hope anyone can help. Thanks
It seems you have not added any DS Tabs for all the signers in your DS template "templateId": "310439de-819e-404b-90d6-a468bc0e4e12". A signer in an envelope always needs at least on DS Tab on the document. So update your template to add atleast one tab for every Signer role and it should fix your error.

AWS Kinesis: user address in event encoded / encrypted

In my React Native mobile app, I use AWS Amplify to send info about user actions (screen views, button taps, swipes, etc.) by means of Analytics.record(...) to AWS Pinpoint which in turn feeds them into a AWS Kinesis Data Stream. I have created an AWS Lambda Python 3 function that listens to events in this data stream.
Setup has been a breeze, thanks to outstanding documentation and everything works fine - except for one thing:
When a user logs in, I update the Pinpoint Endpoint with the user ID, email address and some more attributes using Analytics.updateEndpoint(...). In the lambda function, I base64-decode the event payload as shown in this sample code and a sample event payload looks roughly like this:
{
"event_type": "_session.start",
"event_timestamp": 1572345161558,
"application": {
"app_id": "<some app ID>",
"cognito_identity_pool_id": "us-east-1:<some pool ID>",
"sdk": {},
"version_name": "<the app version I put in using updateEndpoint(...)>"
... <snipped for brevity> ...
},
"attributes": {},
"endpoint": {
"ChannelType": "APNS",
"Address": "=ABAQRuUDJD ... <some longish binary value> j0eL+69lsY=",
"EndpointStatus": "ACTIVE",
"Location": {
"Country": "US"
},
"Demographic": {
"Make": "iPhone",
"Model": "iPhone X",
"ModelVersion": "13.1.3",
...
"Platform": "ios"
},
"User": {
"UserId": "us-east-1:<Cognito ID of the user that logged in>",
"UserAttributes": {}
},
... <snipped for brevity> ...
},
"awsAccountId": "<my account ID>"
}
The user email address in the "Address" field above is not contained in the Kinesis Data Stream event as plain text, but encoded (or encrypted ?) somehow.
My question: Can anybody tell me how it is encoded / encrypted ? And, ideally, how to get the plain text address ?
I tried to base64-decode it or decrypt it using my default AWS KMS key (and a combination thereof), but no luck.
Alternatively, I could use the (plain text) user ID to look up the email address in the AWS Cognito user pool used to manage auth & auth, but getting it from the event directly would obviously be a lot simpler...
I have searched the web up and down, asked in the AWS-Amplify channel on gitter, but that Address encoding / encryption just does not seem to be documented anywhere...

How to get user attributes (username, email, etc.) using cognito identity id

I have AWS Cognito Identity Pool that is configured with Cognito User Pool as an authentication provider.
Assume I have identity ID of an identity in Cognito Identity Pool (e.g. us-east-1:XXaXcXXa-XXXX-XXXX-XXX-XXXXXXXXXXXX) where this identity has a linked login to a user in Cognito User Pool.
Using identity ID, how can I get the linked user details (email, phone, username)?
The ID Token that you exchange with Cognito federated identity service to get the identity id and credentials already has all user attributes. You do not need an extra call to any service.
It is a JWT token and you can use any library on the client to decode the values. You can read this guide for more information about the tokens vended by Cognito user pools.
Alternatively, you can also use the Access Token to call GetUser API which will return all the user information.
Using REST API
AccessToken
Thought that this could be very helpful to someone as I've spent a lot of time trying to figure out how to get UserAttributes with only accessToken and region ( Similar to this but with REST API ( Without using aws-sdk )
You can get UserAttributes with accessToken using this HTTP request. ( GetUser )
Method: POST
Endpoint: https://cognito-idp.{REGION}.amazonaws.com/
Content-Type: application/x-amz-json-1.1
Content-Length: 1162 // Access Token bytes length
X-Amz-Target: AWSCognitoIdentityProviderService.GetUser
Body: {"AccessToken":"ACCESS_TOKEN"}
And if the accessToken is valid, you should receive example response like the following
{
"UserAttributes": [
{
"Name": "sub",
"Value": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxx"
},
{
"Name": "email_verified",
"Value": "true"
},
{
"Name": "name",
"Value": "Jason"
},
{
"Name": "phone_number_verified",
"Value": "true"
},
{
"Name": "phone_number",
"Value": "+xxxxxxxxxxx"
},
{
"Name": "email",
"Value": "xxxx#gmail.com"
}
],
"Username": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxx"
}
AWS cognito-idp list-users has a filter option that allows you to filter based on attribute. 'sub' is the attribute that matches the identity id you are describing.
e.g. at the command line:
aws cognito-idp list-users --user-pool-id us-east-1_abcdFghjI --filter "sub=\":XXaXcXXa-XXXX-XXXX-XXX-XXXXXXXXXXXX\""
This also requires the user-pool-id, which I suspect you have. Additionally, I have no idea how this is implemented or how it performances when filtering a large number of users, but I take custom attributes not being usable in filters as a hint that there is some form of indexing behind the curtain.
I faced the similar issue and after too much of scratching i was not able to find the exact way of pulling out the details. My usecase was to get the details in android APP.
After looking into their AWSMobile client API code. I found below and it is working from me.
Log.i(TAG, "User Details"+ AWSMobileClient.getInstance().getUserAttributes().toString());
Recommendation - Try use AWSMobileclient incase you are using it for Android Development as this is new library that is recommended for development.
Just struggled with this for a while, and the way I got the user name, using Java API is:
identityManager.login(this, new DefaultSignInResultHandler() {
#Override
public void onSuccess(Activity activity, IdentityProvider identityProvider) {
...
String userName = ((CognitoUserPoolsSignInProvider) identityProvider).getCognitoUserPool().getCurrentUser().getUserId();
There is a listener we can initialize that will listen to changes in our authentication state and allow us to have access to the type of authentication event that happened and update the application state based on that data.
With Amplify, the Hub module allows us to do this pretty easily:
import { Hub } from 'aws-amplify';
Hub.listen('auth', (data) => {
const {payload} = data;
if (payload.event === 'signOut') {
console.log('signOut');
} else if (payload.event === 'signIn') {
console.log('A new auth event has happened: ', data.payload.data.username + ' has ' + data.payload.event);
}
});
For those who are looking how to get the value of email parameter in Java programmatically
I assume you have already figured out how to get the needed / all users from the pool.
Say I have ListUsersResult with my all users and say I want to check the email value of the first user:
ListUsersResult allUsers = getAllUsers();
UserType userType = allUsers.getUsers().get(0);
First I can get user's all attributes:
List<AttributeType> attributes = userType.getAttributes();
Then loop through the attributes looking for the one we're interested in (our case email):
for (AttributeType att : attributes) {
if (att.getName().equals("email")) {
// do whatever you want
}
}
Remember that printing in to the console will most probably not work since it is sensitive data. But you can compare it like this:
att.getValue().equals("mymail#mail")
Use this piece of code
GetDetailsHandler detailsHandler = new GetDetailsHandler() {
#Override
public void onSuccess(CognitoUserDetails cognitoUserDetails) {
CognitoUserAttributes cognitoUserAttributes=cognitoUserDetails.getAttributes();
stringStringHashMap=new HashMap<>();
stringStringHashMap =cognitoUserAttributes.getAttributes();
userNumber=stringStringHashMap.get("phone_number");
e1.setText(userNumber);
Log.d("Response"," Inside DEATILS HANDLER");
// Store details in the AppHandler
AppHelper.setUserDetails(cognitoUserDetails);
// Trusted devices?
handleTrustedDevice();
// e1.setText(input.getText().toString());
}
#Override
public void onFailure(Exception exception) {
closeWaitDialog();
showDialogMessage("Could not fetch user details!", AppHelper.formatException(exception), true);
}
};
private void getDetails() {
AppHelper.getPool().getUser(username).getDetailsInBackground(detailsHandler);
}
console.log('username is ' + cognitoUser.getUsername());

Reset password of a user in Google Apps

How to reset password of a Google App user using Google App script/Python/Java script.
I know it can be done using GAM, I want to know if its possible through above languages.
https://developers.google.com/admin-sdk/directory/v1/reference/users/update#request
You can do it when you update your user account.
Here is some code when you create user account.
{
"primaryEmail": "liz#example.com",
"name": {
"givenName": "Elizabeth",
"familyName": "Smith"
},
"suspended": false,
"password": "new user password",
"hashFunction": "SHA-1",
"changePasswordAtNextLogin": false,
"ipWhitelisted": false,
"ims": [
{
To change the password just update your user account.
{
"primaryEmail": "liz#example.com",
"name": {
"givenName": "Liz",
"familyName": "Smith"
},
"suspended": false,
"password": "updated password",
"hashFunction": "SHA-1",
"changePasswordAtNextLogin": true,
"ipWhitelisted": false,
"ims": [
{
You need to set the "changePasswordAtNextLogin": true, in order to change the password.
NOTE: A password is required for new user accounts. If a hashFunction
is specified, the password must be a valid hash key.
The previous answer, while actually partially true, contains some wrong assumptions and uses plain old SHA1, which is actually discouraged now in 2022, and since my edits were rejected as too substantial and the question doesn't have a proper answer yet, I'll write my own answer.
You can use patch semantics for exactly what you're trying to do - you don't need to provide a fully-populated User object for that, just the fields you actually change - in your case, only the new password details, omitting any user fields you aren't changing in the process.
For instance, this would be the correct payload if you want to change a password to Testpassw0rd1 (assuming your app will use a salt string of Usesomesalthere1 and SHA-256 based password hashing, which is considered a safe algorithm):
{
"password": "$5$Usesomesalthere1$F8UxCaJUKHYgoZUY01YRiogSXXRquSmFuTHcpFOVrD7",
"hashFunction": "crypt"
}
(Yes, that's the entire payload you'd want to send to the patch method endpoint for your desired user.)
A proper password value for any string you want you can obtain from libc crypt() function, using $5$your_salt_value$ as the second parameter (replace your_salt_value with whatever you use in your app - you just need to have it consistent with the value used in password JSON parameter, can't have it different in both places or the resulting password won't work at all).