Clients initializing access to the market center

Once you establish a web socket connection, your client has 30 seconds to complete the login process. Otherwise, the socket will be closed.

The Standard Login authentication sequence is as follows:

  • Connect to Web Socket
  • Open message is sent to client
  • Client sends Challenge message with challenge KEY
  • Client uses challenge KEY to encrypt the User's password
  • Client sends Logon with encrypted password

Note
Symbridge will send current open orders and position information upon a successful login

Challenge


Request

Key

Type

Value

Required

type

string

challenge

Yes

Response

Key

Type

Value

type

string

challenge

key

string, base64

Base64 encoded public key that is used to encrypt username's password in Login message

Login


Request

Key

Type

Value

Required

type

string

login

Yes

userid

string

The userid of the user

Yes

pass

string, base64

User's Base64 password encrypted from the key provided in the challenge

Yes

Response

Key

Type

Value

type

string

login

result

string

"OK" if successful. If not successful, this field will contain the reject reason.

firm

string

The firm account associated with the login user

need2FA

boolean

Whether or not the user is required to use 2FA at login

roles

string

The role string associated with the login user

active

string

Whether the user is active or not.

secondary_account

string

The secondary account name

attr

json

Contains user level attributes.

use2fa

boolean

userid

string

The userid associated with the login user.

# Request
{
   "type":"login",
   "userid":"[email protected]",
   "pass":"s7UW26iGE/iVfk2ihPFIcyzRqZRi/Ztb23UNMomf3xrBzGKUHKzfNwZe5PIR/0zvfevYvkJnKLQVhR4U9/kObD/Ir0z6mBfLLgFwEcRm08jYI/nk7lDU+W32PqduTOCThlkXYueQslK54vR9rKvMs="
}

# Response
{
   "result":"OK",
   "firm":"SYMB",
   "need2FA":true,
   "roles":"OOOOO",
   "active":"Y",
   "secondary_account":"FKE3DF342",
   "type":"login",
   "use2fa":"Y",
   "userid":"[email protected]",
   "attr":{
      "country":"",
      "tax_code":"US",
      "last_name":"Doe",
      "first_name":"John ",
      "email":"[email protected]"
     }
}

Code Sample

The sample code below is a java-based example of how to recreate a public key using key value from the challenge response and using that public key to encrypt a password (“test123”).

The output binary array is then be translated into base64 string output, which is used in the “pass” field for the login message.

import java.security.*;
import java.security.spec.*;

String myPassword = "test123";

byte[] decBase64Key = javax.xml.bind.DatatypeConverter.parseBase64Binary(keyFromChallenge);
KeyFactorykf = KeyFactory.getInstance(“RSA”);
publicKey = kf.generatePublic(new X509EncodedKeySpec(decBase64Key));

Cipher cipher = Cipher.getInstance(“RSA”);
cipher.init(Cipher.ENCRYPT_MODE, publicKey);

byte[] result = cipher.doFinal (myPassword.getBytes(“UTF-8”));
String output = javax.xml.bind.DatatypeConverter.printBase64Binary(result);
def start_ws(self):
  self.ws = websocket.WebSocketApp(self.wss_url,
        on_open    = lambda ws: self.on_open(ws),
        on_message = lambda ws,message: self.on_message(ws, message),
        on_error   = lambda ws,message: self.on_error(ws, message))                 
  self.ws.run_forever(sslopt={"cert_reqs": ssl.CERT_NONE})

def on_message(self, message)
  json_message = json.loads(message)
  
  if json_message['type'] == 'challenge':
    print("Challenge received, sending logon")
    self.public_key = json_message['key']
    self.logon_message()
          
def encrypt(self, publickey, password):
  pubkey = f'-----BEGIN PUBLIC KEY-----\n'+publickey+'\n-----END PUBLIC KEY-----'
  
  text = password.encode('utf-8')
  pub_bio = BIO.MemoryBuffer(pubkey.encode('utf-8'))
  pub_rsa = RSA.load_pub_key_bio(pub_bio)
  
  secret = pub_rsa.public_encrypt(text, RSA.pkcs1_padding)
  sign = base64.b64encode(secret)
  ciphertext = sign.decode("utf-8")
  
  return ciphertext

def logon_message(self):
  message = {"type":"login","userid":self.userID,"pass":self.encrypt(self.public_key,self.password)}
  return self.ws.send(json.dumps(message))