Trading account is not authorized, openApiPy, how to solve?

Created at 22 Feb 2022, 11:22
How’s your experience with the cTrader Platform?
Your feedback is crucial to cTrader's development. Please take a few seconds to share your opinion and help us improve your trading experience. Thanks!
PR

prenven570

Joined 24.12.2021

Trading account is not authorized, openApiPy, how to solve?
22 Feb 2022, 11:22


I'm trying to open positions usnig openApiPy, but I get this erorr:

Connected
Message received: 
 ctidTraderAccountId: 23606106
errorCode: "INVALID_REQUEST"
description: "Trading account is not authorized"

API Application authorized

Please use setAccount command to set the authorized account before sending any other command, try help for more detail

To get account IDs use ProtoOAGetAccountListByAccessTokenReq command
Account 23606106 has been authorized

This acccount will be used for all future requests

You can change the account by using setAccount command


Command (ex help): 

 

Command Input Timeout

 

So, how can I authorize my trading account? I'm currently using demo account

This is the code i'm trying to run:

from ctrader_open_api import Client, Protobuf, TcpProtocol, Auth, EndPoints
from ctrader_open_api.messages.OpenApiCommonMessages_pb2 import *
from ctrader_open_api.messages.OpenApiCommonMessages_pb2 import *
from ctrader_open_api.messages.OpenApiMessages_pb2 import *
from ctrader_open_api.messages.OpenApiModelMessages_pb2 import *
from twisted.internet import reactor
from inputimeout import inputimeout, TimeoutOccurred
import json
import datetime


credentialsFile = open("credentials.json")
credentials = json.load(credentialsFile)

if __name__ == "__main__":
    currentAccountId = None
    hostType = input("Host (Live/Demo): ")
    hostType = hostType.lower()

    while hostType != "live" and  hostType != "demo":
        print(f"{hostType} is not a valid host type.")
        hostType = input("Host (Live/Demo): ")

    appClientId = credentials["ClientId"]
    appClientSecret = credentials["Secret"]
    isTokenAvailable = credentials["AccessToken"]

    accessToken = None
    if isTokenAvailable == False:
        appRedirectUri = input("App Redirect URI: ")
        auth = Auth(appClientId, appClientSecret, appRedirectUri)
        authUri = auth.getAuthUri()
        print(f"Please continue the authentication on your browser:\n {authUri}")
        webbrowser.open_new(authUri)
        print("\nThen enter the auth code that is appended to redirect URI immediatly (the code is after ?code= in URI)")
        authCode = input("Auth Code: ")
        token = auth.getToken(authCode)
        if "accessToken" not in token:
            raise KeyError(token)
        print("Token: \n", token)
        accessToken = token["accessToken"]
    else:
        accessToken = credentials["AccessToken"]
        
    client = Client(EndPoints.PROTOBUF_LIVE_HOST if hostType.lower() == "live" else EndPoints.PROTOBUF_DEMO_HOST, EndPoints.PROTOBUF_PORT, TcpProtocol)
 
    def setAccount(accountId):
        global currentAccountId
        if currentAccountId is not None:
            sendProtoOAAccountLogoutReq()
        currentAccountId = int(accountId)
        sendProtoOAAccountAuthReq()
        
        
    def sendProtoOAAccountAuthReq(clientMsgId = None):
        request = ProtoOAAccountAuthReq()
        request.ctidTraderAccountId = currentAccountId
        request.accessToken = accessToken
        deferred = client.send(request, clientMsgId = clientMsgId)
        deferred.addErrback(onError)     
        
        
    
    def connected(client): # Callback for client connection
        print("\nConnected")
        request = ProtoOAApplicationAuthReq()
        request.clientId = appClientId
        request.clientSecret = appClientSecret
        deferred = client.send(request)
        deferred.addErrback(onError)
    
    def disconnected(client, reason): # Callback for client disconnection
        print("\nDisconnected: ", reason)
    
    def onMessageReceived(client, message): # Callback for receiving all messages
        if message.payloadType in [ProtoOASubscribeSpotsRes().payloadType, ProtoOAAccountLogoutRes().payloadType, ProtoHeartbeatEvent().payloadType]:
            return
        elif message.payloadType == ProtoOAApplicationAuthRes().payloadType:
            print("API Application authorized\n")
            print("Please use setAccount command to set the authorized account before sending any other command, try help for more detail\n")
            print("To get account IDs use ProtoOAGetAccountListByAccessTokenReq command")
            if currentAccountId is not None:
                sendProtoOAAccountAuthReq()
                return
        elif message.payloadType == ProtoOAAccountAuthRes().payloadType:
            protoOAAccountAuthRes = Protobuf.extract(message)
            print(f"Account {protoOAAccountAuthRes.ctidTraderAccountId} has been authorized\n")
            print("This acccount will be used for all future requests\n")
            print("You can change the account by using setAccount command")
        else:
            print("Message received: \n", Protobuf.extract(message))
        reactor.callLater(3, callable=executeUserCommand)
    
    def onError(failure): # Call back for errors
        print("Message Error: ", failure)
        reactor.callLater(3, callable=executeUserCommand)
        
        
        
    def executeUserCommand():
        try:
            print("\n")
            userInput = inputimeout("Command (ex help): ", timeout=18)
        except TimeoutOccurred:
            print("Command Input Timeout")
            reactor.callLater(3, callable=executeUserCommand)
            return
        userInputSplit = userInput.split(" ")
        if not userInputSplit:
            print("Command split error: ", userInput)
            reactor.callLater(3, callable=executeUserCommand)
            return
        command = userInputSplit[0]
        try:
            parameters = [parameter if parameter[0] != "*" else parameter[1:] for parameter in userInputSplit[1:]]
        except:
            print("Invalid parameters: ", userInput)
            reactor.callLater(3, callable=executeUserCommand)
        if command in commands:
            commands[command](*parameters)
        else:
            print("Invalid Command: ", userInput)
            reactor.callLater(3, callable=executeUserCommand)
        
        
    def sendProtoOAGetAccountListByAccessTokenReq(clientMsgId = None):
        request = ProtoOAGetAccountListByAccessTokenReq()
        request.accessToken = credentials["AccessToken"]
        deferred = client.send(request, clientMsgId = clientMsgId)
        deferred.addErrback(onError)
        
    def sendProtoOAAssetListReq(clientMsgId = None):
        request = ProtoOAAssetListReq()
        request.ctidTraderAccountId = currentAccountId
        deferred = client.send(request, clientMsgId = clientMsgId)
        deferred.addErrback(onError)
        
    def sendProtoOANewOrderReq(symbolId, orderType, tradeSide, volume, price = None, clientMsgId = None):
        request = ProtoOANewOrderReq()
        request.ctidTraderAccountId = currentAccountId
        request.symbolId = int(symbolId)
        request.orderType = ProtoOAOrderType.Value(orderType.upper())
        request.tradeSide = ProtoOATradeSide.Value(tradeSide.upper())
        request.volume = int(volume) * 100
        if request.orderType == ProtoOAOrderType.LIMIT:
            request.limitPrice = float(price)
        elif request.orderType == ProtoOAOrderType.STOP:
            request.stopPrice = float(price)
        deferred = client.send(request, clientMsgId = clientMsgId)
        deferred.addErrback(onError)    
        
        
        
        
    def sendNewMarketOrder(symbolId, tradeSide, volume, clientMsgId = None):
        sendProtoOANewOrderReq(symbolId, "MARKET", tradeSide, volume, clientMsgId = clientMsgId)
        
    
    # Setting optional client callbacks
    client.setConnectedCallback(connected)
    client.setDisconnectedCallback(disconnected)
    client.setMessageReceivedCallback(onMessageReceived)
    
    
    accountId = credentials["AccountId"]
    setAccount(accountId)

symbolId = 22395
tradeSide ="BUY"
orderType = "MARKET"
volume = 1
sendProtoOANewOrderReq(symbolId, orderType, tradeSide, volume, price = None, clientMsgId = None)



# Starting the client service
client.startService()
reactor.run()

 


@prenven570
Replies

prenven570
22 Feb 2022, 12:37 ( Updated at: 22 Feb 2022, 12:44 )

RE:

 

Edit:

i solved  the problem of the unauthorized trading account, but the second question remains: How to open a position? 

 


@prenven570

amusleh
23 Feb 2022, 09:15

Hi,

To open a position or send any other request you have to first authorize your trading account on your connection session by sending a ProtoOAAccountAuthReq message.

After your account got authorized and you received the ProtoOAAccountAuthRes response message you can start sending trading requests or getting account related data.

To open a new order you have to send a ProtoOANewOrderReq request, this request is used for both pending and market (position) orders.

Now regarding OpenApiPy package, once you received the ProtoOAAccountAuthRes message via MessageReceivedCallback or your Twisted deferred then you can send a ProtoOANewOrderReq.

In your posted code I see you call the sendProtoOANewOrderReq method before you start the client service and connection, that will not work, because there is no connection between you and API yet let alone the app and account authorization.

Please check my added comments at onMessageReceived method:

from ctrader_open_api import Client, Protobuf, TcpProtocol, Auth, EndPoints
from ctrader_open_api.messages.OpenApiCommonMessages_pb2 import *
from ctrader_open_api.messages.OpenApiCommonMessages_pb2 import *
from ctrader_open_api.messages.OpenApiMessages_pb2 import *
from ctrader_open_api.messages.OpenApiModelMessages_pb2 import *
from twisted.internet import reactor
from inputimeout import inputimeout, TimeoutOccurred
import json
import datetime


credentialsFile = open("credentials.json")
credentials = json.load(credentialsFile)

if __name__ == "__main__":
    currentAccountId = None
    hostType = input("Host (Live/Demo): ")
    hostType = hostType.lower()

    while hostType != "live" and  hostType != "demo":
        print(f"{hostType} is not a valid host type.")
        hostType = input("Host (Live/Demo): ")

    appClientId = credentials["ClientId"]
    appClientSecret = credentials["Secret"]
    isTokenAvailable = credentials["AccessToken"]

    accessToken = None
    if isTokenAvailable == False:
        appRedirectUri = input("App Redirect URI: ")
        auth = Auth(appClientId, appClientSecret, appRedirectUri)
        authUri = auth.getAuthUri()
        print(f"Please continue the authentication on your browser:\n {authUri}")
        webbrowser.open_new(authUri)
        print("\nThen enter the auth code that is appended to redirect URI immediatly (the code is after ?code= in URI)")
        authCode = input("Auth Code: ")
        token = auth.getToken(authCode)
        if "accessToken" not in token:
            raise KeyError(token)
        print("Token: \n", token)
        accessToken = token["accessToken"]
    else:
        accessToken = credentials["AccessToken"]
        
    client = Client(EndPoints.PROTOBUF_LIVE_HOST if hostType.lower() == "live" else EndPoints.PROTOBUF_DEMO_HOST, EndPoints.PROTOBUF_PORT, TcpProtocol)
 
    def setAccount(accountId):
        global currentAccountId
        if currentAccountId is not None:
            sendProtoOAAccountLogoutReq()
        currentAccountId = int(accountId)
        sendProtoOAAccountAuthReq()
        
        
    def sendProtoOAAccountAuthReq(clientMsgId = None):
        request = ProtoOAAccountAuthReq()
        request.ctidTraderAccountId = currentAccountId
        request.accessToken = accessToken
        deferred = client.send(request, clientMsgId = clientMsgId)
        deferred.addErrback(onError)     
        
        
    
    def connected(client): # Callback for client connection
        print("\nConnected")
        request = ProtoOAApplicationAuthReq()
        request.clientId = appClientId
        request.clientSecret = appClientSecret
        deferred = client.send(request)
        deferred.addErrback(onError)
    
    def disconnected(client, reason): # Callback for client disconnection
        print("\nDisconnected: ", reason)
    
    def onMessageReceived(client, message): # Callback for receiving all messages
        if message.payloadType in [ProtoOASubscribeSpotsRes().payloadType, ProtoOAAccountLogoutRes().payloadType, ProtoHeartbeatEvent().payloadType]:
            return
        elif message.payloadType == ProtoOAApplicationAuthRes().payloadType:
            print("API Application authorized\n")
            print("Please use setAccount command to set the authorized account before sending any other command, try help for more detail\n")
            print("To get account IDs use ProtoOAGetAccountListByAccessTokenReq command")
            if currentAccountId is not None:
                sendProtoOAAccountAuthReq()
                return
        elif message.payloadType == ProtoOAAccountAuthRes().payloadType:
            protoOAAccountAuthRes = Protobuf.extract(message)
            print(f"Account {protoOAAccountAuthRes.ctidTraderAccountId} has been authorized\n")
            print("This acccount will be used for all future requests\n")
            print("You can change the account by using setAccount command")
            # This is where you can send a new order request
            # This is the place that your account authorization
            # response message is received
        else:
            print("Message received: \n", Protobuf.extract(message))
        reactor.callLater(3, callable=executeUserCommand)
    
    def onError(failure): # Call back for errors
        print("Message Error: ", failure)
        reactor.callLater(3, callable=executeUserCommand)
        
        
        
    def executeUserCommand():
        try:
            print("\n")
            userInput = inputimeout("Command (ex help): ", timeout=18)
        except TimeoutOccurred:
            print("Command Input Timeout")
            reactor.callLater(3, callable=executeUserCommand)
            return
        userInputSplit = userInput.split(" ")
        if not userInputSplit:
            print("Command split error: ", userInput)
            reactor.callLater(3, callable=executeUserCommand)
            return
        command = userInputSplit[0]
        try:
            parameters = [parameter if parameter[0] != "*" else parameter[1:] for parameter in userInputSplit[1:]]
        except:
            print("Invalid parameters: ", userInput)
            reactor.callLater(3, callable=executeUserCommand)
        if command in commands:
            commands[command](*parameters)
        else:
            print("Invalid Command: ", userInput)
            reactor.callLater(3, callable=executeUserCommand)
        
        
    def sendProtoOAGetAccountListByAccessTokenReq(clientMsgId = None):
        request = ProtoOAGetAccountListByAccessTokenReq()
        request.accessToken = credentials["AccessToken"]
        deferred = client.send(request, clientMsgId = clientMsgId)
        deferred.addErrback(onError)
        
    def sendProtoOAAssetListReq(clientMsgId = None):
        request = ProtoOAAssetListReq()
        request.ctidTraderAccountId = currentAccountId
        deferred = client.send(request, clientMsgId = clientMsgId)
        deferred.addErrback(onError)
        
    def sendProtoOANewOrderReq(symbolId, orderType, tradeSide, volume, price = None, clientMsgId = None):
        request = ProtoOANewOrderReq()
        request.ctidTraderAccountId = currentAccountId
        request.symbolId = int(symbolId)
        request.orderType = ProtoOAOrderType.Value(orderType.upper())
        request.tradeSide = ProtoOATradeSide.Value(tradeSide.upper())
        request.volume = int(volume) * 100
        if request.orderType == ProtoOAOrderType.LIMIT:
            request.limitPrice = float(price)
        elif request.orderType == ProtoOAOrderType.STOP:
            request.stopPrice = float(price)
        deferred = client.send(request, clientMsgId = clientMsgId)
        deferred.addErrback(onError)    
        
        
        
        
    def sendNewMarketOrder(symbolId, tradeSide, volume, clientMsgId = None):
        sendProtoOANewOrderReq(symbolId, "MARKET", tradeSide, volume, clientMsgId = clientMsgId)
        
    
    # Setting optional client callbacks
    client.setConnectedCallback(connected)
    client.setDisconnectedCallback(disconnected)
    client.setMessageReceivedCallback(onMessageReceived)

    # Starting the client service
    client.startService()
    reactor.run()

 


@amusleh

william@hallsdesign.co.uk
03 Mar 2022, 18:12

RE: RE:

prenven570 said:

 

Edit:

i solved  the problem of the unauthorized trading account, but the second question remains: How to open a position? 

 

Hi, how did you solve the unauthorised trading account bit? I have this same issue and I am unsure how to solve. ( just changed my accountID to xxxxxxxx ).

 

Message received: 
 ctidTraderAccountId: xxxxxxxx
errorCode: "ACCOUNT_NOT_AUTHORIZED"
description: "Account is not authorized"

Any help is greatly appreciated.


@william@hallsdesign.co.uk

amusleh
04 Mar 2022, 07:22

RE: RE: RE:

william@hallsdesign.co.uk said:

prenven570 said:

 

Edit:

i solved  the problem of the unauthorized trading account, but the second question remains: How to open a position? 

 

Hi, how did you solve the unauthorised trading account bit? I have this same issue and I am unsure how to solve. ( just changed my accountID to xxxxxxxx ).

 

Message received: 
 ctidTraderAccountId: xxxxxxxx
errorCode: "ACCOUNT_NOT_AUTHORIZED"
description: "Account is not authorized"

Any help is greatly appreciated.

Hi,

You have to send a ProtoOAAccountAuthReq before sending any other request for an account.

After you received the ProtoOAAccountAuthRes then you can start sending other types of requests for that account.

Please check console sample setAccount command code.


@amusleh

prenven570
04 Mar 2022, 09:18

RE: RE: RE:

william@hallsdesign.co.uk said:

prenven570 said:

 

Edit:

i solved  the problem of the unauthorized trading account, but the second question remains: How to open a position? 

 

Hi, how did you solve the unauthorised trading account bit? I have this same issue and I am unsure how to solve. ( just changed my accountID to xxxxxxxx ).

 

Message received: 
 ctidTraderAccountId: xxxxxxxx
errorCode: "ACCOUNT_NOT_AUTHORIZED"
description: "Account is not authorized"

Any help is greatly appreciated.

I solved by using this code:


 
from ctrader_open_api import Client, Protobuf, TcpProtocol, Auth, EndPoints
from ctrader_open_api.messages.OpenApiCommonMessages_pb2 import *
from ctrader_open_api.messages.OpenApiCommonMessages_pb2 import *
from ctrader_open_api.messages.OpenApiMessages_pb2 import *
from ctrader_open_api.messages.OpenApiModelMessages_pb2 import *
from twisted.internet import reactor
import json
import datetime

#you create a .json file with credentials ther's a sample on the github repository (jupyter sample)


credentialsFile = open("credentials-dev.json") credentials = json.load(credentialsFile)

host = EndPoints.PROTOBUF_LIVE_HOST if credentials["HostType"].lower() == "live" else EndPoints.PROTOBUF_DEMO_HOST
client = Client(host, EndPoints.PROTOBUF_PORT, TcpProtocol)

 

def accountAuthResponseCallback(result):
    print("\nAccount authenticated")
    request = ProtoOASymbolsListReq()
    request.ctidTraderAccountId = credentials["AccountId"]
    request.includeArchivedSymbols = False
    deferred = client.send(request)
    
def applicationAuthResponseCallback(result):
    print("\nApplication authenticated")
    request = ProtoOAAccountAuthReq()
    request.ctidTraderAccountId = credentials["AccountId"]
    request.accessToken = credentials["AccessToken"]
    deferred = client.send(request)
    deferred.addCallbacks(accountAuthResponseCallback, onError)

def onError(client, failure): # Call back for errors
    print("\nMessage Error: ", failure)

def disconnected(client, reason): # Callback for client disconnection
    print("\nDisconnected: ", reason)

def onMessageReceived(client, message): # Callback for receiving all messages
    if message.payloadType in [ProtoHeartbeatEvent().payloadType, ProtoOAAccountAuthRes().payloadType, ProtoOAApplicationAuthRes().payloadType, ProtoOASymbolsListRes().payloadType, ProtoOAGetTrendbarsRes().payloadType]:
        return
    print("\nMessage received: \n", Protobuf.extract(message))
    
def connected(client): # Callback for client connection
    print("\nConnected")
    request = ProtoOAApplicationAuthReq()
    request.clientId = credentials["ClientId"]
    request.clientSecret = credentials["Secret"]
    deferred = client.send(request)
    deferred.addCallbacks(applicationAuthResponseCallback, onError)
    
# Setting optional client callbacks
client.setConnectedCallback(connected)
client.setDisconnectedCallback(disconnected)
client.setMessageReceivedCallback(onMessageReceived)

# Starting the client service
client.startService()
# Run Twisted reactor, we imported it earlier
reactor.run()


@prenven570

william@hallsdesign.co.uk
10 Mar 2022, 18:28

RE: RE: RE: RE:

Thanks for the help with this, think I have solved it too now. :) 

 

prenven570 said:

william@hallsdesign.co.uk said:

prenven570 said:

 

Edit:

i solved  the problem of the unauthorized trading account, but the second question remains: How to open a position? 

 

Hi, how did you solve the unauthorised trading account bit? I have this same issue and I am unsure how to solve. ( just changed my accountID to xxxxxxxx ).

 

Message received: 
 ctidTraderAccountId: xxxxxxxx
errorCode: "ACCOUNT_NOT_AUTHORIZED"
description: "Account is not authorized"

Any help is greatly appreciated.

I solved by using this code:


 
from ctrader_open_api import Client, Protobuf, TcpProtocol, Auth, EndPoints
from ctrader_open_api.messages.OpenApiCommonMessages_pb2 import *
from ctrader_open_api.messages.OpenApiCommonMessages_pb2 import *
from ctrader_open_api.messages.OpenApiMessages_pb2 import *
from ctrader_open_api.messages.OpenApiModelMessages_pb2 import *
from twisted.internet import reactor
import json
import datetime

#you create a .json file with credentials ther's a sample on the github repository (jupyter sample)


credentialsFile = open("credentials-dev.json") credentials = json.load(credentialsFile)

host = EndPoints.PROTOBUF_LIVE_HOST if credentials["HostType"].lower() == "live" else EndPoints.PROTOBUF_DEMO_HOST
client = Client(host, EndPoints.PROTOBUF_PORT, TcpProtocol)

 

def accountAuthResponseCallback(result):
    print("\nAccount authenticated")
    request = ProtoOASymbolsListReq()
    request.ctidTraderAccountId = credentials["AccountId"]
    request.includeArchivedSymbols = False
    deferred = client.send(request)
    
def applicationAuthResponseCallback(result):
    print("\nApplication authenticated")
    request = ProtoOAAccountAuthReq()
    request.ctidTraderAccountId = credentials["AccountId"]
    request.accessToken = credentials["AccessToken"]
    deferred = client.send(request)
    deferred.addCallbacks(accountAuthResponseCallback, onError)

def onError(client, failure): # Call back for errors
    print("\nMessage Error: ", failure)

def disconnected(client, reason): # Callback for client disconnection
    print("\nDisconnected: ", reason)

def onMessageReceived(client, message): # Callback for receiving all messages
    if message.payloadType in [ProtoHeartbeatEvent().payloadType, ProtoOAAccountAuthRes().payloadType, ProtoOAApplicationAuthRes().payloadType, ProtoOASymbolsListRes().payloadType, ProtoOAGetTrendbarsRes().payloadType]:
        return
    print("\nMessage received: \n", Protobuf.extract(message))
    
def connected(client): # Callback for client connection
    print("\nConnected")
    request = ProtoOAApplicationAuthReq()
    request.clientId = credentials["ClientId"]
    request.clientSecret = credentials["Secret"]
    deferred = client.send(request)
    deferred.addCallbacks(applicationAuthResponseCallback, onError)
    
# Setting optional client callbacks
client.setConnectedCallback(connected)
client.setDisconnectedCallback(disconnected)
client.setMessageReceivedCallback(onMessageReceived)

# Starting the client service
client.startService()
# Run Twisted reactor, we imported it earlier
reactor.run()

 


@william@hallsdesign.co.uk