Skip to content

Instantly share code, notes, and snippets.

@asafb-wix
Last active September 12, 2017 17:32
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save asafb-wix/826d124d8cb5e4c8875f16195590a463 to your computer and use it in GitHub Desktop.
Save asafb-wix/826d124d8cb5e4c8875f16195590a463 to your computer and use it in GitHub Desktop.
Answers SSO java example
package test;
import com.google.common.io.BaseEncoding;
import javax.crypto.Cipher;
import javax.crypto.spec.SecretKeySpec;
import java.io.UnsupportedEncodingException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Arrays;
public class CryptographyUtil {
public static String encrypt(String secret, String data) {
try {
SecretKeySpec secretKey = getKey(secret, "SHA");
Cipher cipher = Cipher.getInstance("AES/ECB/PKCS5Padding");
cipher.init(Cipher.ENCRYPT_MODE, secretKey);
return BaseEncoding.base64Url().omitPadding().encode(cipher.doFinal(data.getBytes("UTF-8")));
} catch (Exception ignored) {
}
return null;
}
private static SecretKeySpec getKey(String secret, String algorithm) {
try {
byte[] key = secret.getBytes("UTF-8");
key = Arrays.copyOf(MessageDigest.getInstance(algorithm).digest(key), 16);
return new SecretKeySpec(key, "AES");
} catch (NoSuchAlgorithmException | UnsupportedEncodingException e) {
e.printStackTrace();
}
return null;
}
}
package test;
import org.joda.time.DateTime;
import org.joda.time.DateTimeZone;
/**
* @author asafb
* @since 08/06/2016
*
* The SSO login flow is as follows:
*
* 1. The tenant generates an api key and secret in his Wix Answers account settings - the secret will be used to encrypt the sso token by the
* the tenants' user system. The tenant then configures in his Wix Answers account settings his sso form url and sso logout url.
*
* 2. When a user clicks on the login button in Wix Answers, he is redirected to the tenants' login page (sso form url).
* Before performing the redirect to the the tenants' login form, Wix Answers appends a redirectUrl parameter to the request - this is the
* Wix Answers callback url the tenant's user system should redirect back after the user is authenticated.
*
* 3. After the user is authenticated by the tenants' user system, the tenants' user system should create an encrypted sso token for
* that user using his api secret (see example code below), append the encrypted token parameter to the Wix Answers call back url and
* the key id attached to the secret used for the token encryption and redirect back to Wix Answers.
*
* 4. The SSO token is an encrypted json string (see SSOParams.java) containing the authenticated user data.
*
* The required fields in the json are:
*
* id - the user id in the tenants' user system
*
* email - the user email
*
* timestamp - current timestamp (UTC) in milliseconds (Unix/Epoch time)
*
* Optional fields in the json are:
*
* firstName
* lastName
* displayName
* profileImage - full url to the users' profile image
*
*
* e.g.:
*
* The tenants' user system login page configured in Wix Answers is: https://labworm.com/login
*
* Answers will redirect the user to https://labworm.com/login?redirectUrl=<answers-sso-callback-url>
*
* After user is authenticated by tenants' user system, the tenants' user system builds the encrypted sso token for the authenticated user
* and redirects the user back to Wix Answers with the token and key id appended to the callback url (answers-sso-callback-url):
*
* <answers-sso-callback-url>?token=<encrypted sso token>&key=<api key id>
*
*/
public class Main {
private static String KEY_ID = "<your api key id>";
private static String SECRET = "<your api key secret>";
public static void main(String[] args) {
SSOParams params = new SSOParams();
params.setDisplayName("<the user name>");
// set the users' external user id from tenants external user system
params.setId("<the user id in tenants' user system>");
params.setEmail("<the user email>");
params.setTimestamp(new DateTime().withZone(DateTimeZone.UTC).getMillis());
// this token should be sent as a request parameter back to Wix Answers after user is authenticated along with the
// api key id: token=<encrypted sso token>&key=KEY_ID
String ssoToken = getSSOToken(params);
}
private static String getSSOToken(SSOParams params) {
// create json string from params object
String serializedParams = toJson(params);
return CryptographyUtil.encrypt(SECRET, serializedParams);
}
private static String toJson(SSOParams params) {
String json = null;
// json = .... serialize params to json string
return json;
}
}
package test;
import javax.validation.constraints.NotNull;
/**
* @author asafb
* @since 6/22/15
*
* This class represents the generic json for sso sign in.
*/
public class SSOParams {
@NotNull
private String id;
@NotNull
private String email;
@NotNull
private Long timestamp;
private String firstName;
private String lastName;
private String displayName;
private String profileImage;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public Long getTimestamp() {
return timestamp;
}
public void setTimestamp(Long timestamp) {
this.timestamp = timestamp;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getDisplayName() {
return displayName;
}
public void setDisplayName(String displayName) {
this.displayName = displayName;
}
public String getProfileImage() {
return profileImage;
}
public void setProfileImage(String profileImage) {
this.profileImage = profileImage;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment