Create A FIX Message using Quickfix Python - python

I am a very new user to Quickfix Python. I want to send a QuoteRequest. My function to create a new quote request message is as below:
import quickfix as fix
def create_quote_request():
message = fix.Message()
header = message.getHeader()
header.setField(fix.MsgType(fix.MsgType_QuoteRequest))
gp = fix.Group()
gp.setField(fix.Symbol("GBPUSD"))
gp.setField(fix.Side(fix.Side_BUY))
gp.setField(fix.Account("TestAcc"))
gp.setField(fix.Currency("GBP"))
message.addGroup(gp)
fix.Session.sendToTarget(message, self.sessionID)
When I execute the code, I am getting error as below:
NotImplementedError: Wrong number r type of arguments for overloaded function 'new_group'.
Possible C/C++ prototypes are:
FIX::Group::Group(int, int)
FIX::Group::Group(int, int, int const[])
FIX::Group::Group(int, int, message_order const &)
FIX::Group::Group(FIX::Group const &)
I did read the documentation and found that the Group object requires arguments
Group(int field, int delim)
Not sure what to pass the values for field and delim. Appreciate your response and help.

not sure I´m on time to help. But I will try. I think #JimmyNJ is giving you proper answer.
According to official doc you can easily do it, but you don´t have to use a generic group, you have to use specific group available to your kind of message.
As far as I know, you should program something like this.
from quickfix44 import QuoteRequest
import quickfix as fix
message = QuoteRequest()
group = QuoteRequest.NoRelatedSym()
group.setField(fix.Symbol("GBPUSD"))
group.setField(fix.Side(fix.Side_BUY))
group.setField(fix.Account("TestAcc"))
group.setField(fix.Currency("GBP"))
message.addGroup(group)
I´m assuming you want to add these 4 tags into NoRelatedSym group, based in their tag numbers. I´ve also used FIX 44 version, maybe you are using a different version, but main idea is the same.

Related

How to build CDK Assembly using Python aws_cdk.cx_api

I'm desperate so any help is appreciated.
I'm trying to modify my current CDK out using cloud assembly in Python.
I can't find any examples, nor proper documentation for python, only reference guide.
This is my code:
import os
import subprocess
import aws_cdk.cx_api as cxapi
import aws_cdk.cloud_assembly_schema as cxschema
class my_class():
def synth():
ASSEMBLY_PATH = 'igor_cdk'
result = subprocess.run(['cdk', 'synth', '-o', ASSEMBLY_PATH], stdout=subprocess.PIPE)
my_stuff = result.stdout.decode('utf-8')
new_stack_name = original_stack_name+TEMP_OUT
print(new_stack_name)
cloud_assembly = cxapi.CloudAssembly(ASSEMBLY_PATH);
orig_stack_assembly = cloud_assembly.get_stack_by_name(original_stack_name)
logical_Ids = orig_stack_assembly.find_metadata_by_type("aws:cdk:logicalId")
cab = cxapi.CloudAssemblyBuilder(ASSEMBLY_PATH)
cab.add_artifact(new_stack_name, type = cxschema.ArtifactType.ASSET_MANIFEST, properties = orig_stack_assembly.manifest)
Then, In my dummy test, I call this:
print(stack_info.synth("Test", "Targeta"))
And that's executed with pytest.
Just for comparison, I got it working in Typescript:
const cab: CloudAssemblyBuilder = new CloudAssemblyBuilder(ASSEMBLY_PATH);
cab.addArtifact(new_stack_name, stack.manifest);
cab.buildAssembly();
I expected similar/same behavior, but I just can't figure out how to do it in python, and since my whole code base is in python, I'd just love to have it all done in one place, rather than reworking the whole thing in TS.
Edit:
If I pass the stack.manifest, I'm getting the following error:
jsii.errors.JSIIError: Value did not match any type in union:
Wire struct type '#aws-cdk/cloud-assembly-schema.ArtifactManifest' does not match expected '#aws-cdk/cloud-assembly-schema.AwsCloudFormationStackProperties', Wire struct type '#aws-cdk/cloud-assembly-schema.ArtifactManifest' does not match expected '#aws-cdk/cloud-assembly-schema.AssetManifestProperties',
Wire struct type '#aws-cdk/cloud-assembly-schema.ArtifactManifest' does not match expected '#aws-cdk/cloud-assembly-schema.TreeArtifactProperties',
Wire struct type '#aws-cdk/cloud-assembly-schema.ArtifactManifest' does not match expected '#aws-cdk/cloud-assembly-schema.NestedCloudAssemblyProperties'
And if I pass the whole stack assembly object, I run in even weirder problem:
jsii.errors.JavaScriptError:
RangeError: Maximum call stack size exceeded
at /private/var/folders/z6/c91mcs6j4g93t2856_p_51nr0000gn/T/jsii-kernel-35iS5M/node_modules/#aws-cdk/cx-api/lib/cloud-assembly.js:307:53

bingads V13 report request fails in python sdk

I try to download a bingads report using python SDK, but I keep getting an error says: "Type not found: 'Aggregation'" after submitting a report request. I've tried all 4 options mentioned in the following link:
https://github.com/BingAds/BingAds-Python-SDK/blob/master/examples/v13/report_requests.py
Authentication process prior to request works just fine.
I execute the following:
report_request = get_report_request(authorization_data.account_id)
reporting_download_parameters = ReportingDownloadParameters(
report_request=report_request,
result_file_directory=FILE_DIRECTORY,
result_file_name=RESULT_FILE_NAME,
overwrite_result_file=True, # Set this value true if you want to overwrite the same file.
timeout_in_milliseconds=TIMEOUT_IN_MILLISECONDS
)
output_status_message("-----\nAwaiting download_report...")
download_report(reporting_download_parameters)
after a careful debugging, it seems that the program fails when trying to execute a command within "reporting_service_manager.py". Here is workflow:
download_report(self, download_parameters):
report_file_path = self.download_file(download_parameters)
then:
download_file(self, download_parameters):
operation = self.submit_download(download_parameters.report_request)
then:
submit_download(self, report_request):
self.normalize_request(report_request)
response = self.service_client.SubmitGenerateReport(report_request)
SubmitGenerateReport starts a sequence of events ending with a call to "_SeviceCall.init" function within "service_client.py", returning an exception "Type not found: 'Aggregation'"
try:
response = self.service_client.soap_client.service.__getattr__(self.name)(*args, **kwargs)
return response
except Exception as ex:
if need_to_refresh_token is False \
and self.service_client.refresh_oauth_tokens_automatically \
and self.service_client._is_expired_token_exception(ex):
need_to_refresh_token = True
else:
raise ex
Can anyone shed some light? .
Thanks
Please be sure to set Aggregation e.g., as shown here.
aggregation = 'Daily'
If the report type does not use aggregation, you can set Aggregation=None.
Does this help?
This may be a bit late 2 months after the fact but maybe this will help someone else. I had the same error (though I suppose it may not be the same issue). It does look like you did what I did (and I'm sure others will as well): copy-paste the Microsoft example code and tried to run it only to find that it didn't work.
I spent quite some time trying to debug the issue and it looked to me like the XML wasn't being searched correctly. I was using suds-py3 for the script at the time so I tried suds-community and everything just worked after that.
I also re-read the Bing Ads API walkthrough for getting started again and found that they recommend suds-jurko instead.
Long story short: If you want to use the bingads API don't use suds-py3, use either suds-community (which I can confirm works for everything I've used the API for) or suds-jurko (which is the one recommended by Microsoft).

How to change string into a QuickFix message?

I am trying to read my FIX logs and to parse them with the cracker that I wrote in python. However, this does not work because in my cracker I have calls like message.getHeader() which are QuickFix methods. They unsurprisingly return an error:
AttributeError: 'str' object has no attribute 'getHeader'
The logs are all strings, but the cracker is embedded within QuickFix and so uses QF methods. Is there any way to take the string and transform it into a QF message so I can just call crack(message) on it, or do I have to rewrite my cracker for this special case?
The following code should work.
import quickfix as qfix
import quickfix44 as q44
message = q44.ExecutionReport()
message.setString(input_string, True, qfix.DataDictionary('CustomDictionary.xml'))
'message' object will be updated in place and you should be able to use it as a quickfix Message object
The way that I do it in C# is to read tag 35 to see what message type I need to create. Then, I create that message type, and use the setString method to populate it. Something like this:
if (line.Contains("35=8"))
{
message = new QuickFix44.ExecutionReport();
}
else if(line.Contains("35=AS"))
{
message = new QuickFix44.AllocationReport();
}
. . . . and so on
message.setString(line, true, dictionary);
application.fromApp(message, sessionId); //The cracker takes care of it from here
where dictionary is my data dictionary. Is a similar method available in the Python bindings?
The following also works and doesn't require prior knowledge of message type.
import quickfix as fix
string = "8=FIX.4.49=24735=s34=549=sender52=20060319-09:08:20.88156=target22=840=244=948=ABC55=ABC60=20060319-09:08:19548=184214549=2550=0552=254=1453=2448=8447=D452=4448=AAA35777447=D452=338=954=2453=2448=8447=D452=4448=aaa447=D452=338=910=056"
data_dictionary = fix.DataDictionary("FIX44.xml")
message = fix.Message(string, data_dictionary, True)
print(message.toXML())

Maxscript Python addModifier

I'm writing maxscript in python and the following code throws a type error:
import MaxPlus
res = MaxPlus.Core.GetRootNode()
#This is just as example that I use the first child.
child = MaxPlus.INode.GetChild(res,0)
morpherFP = MaxPlus.FPValue()
MaxPlus.Core.EvalMAXScript("Morpher()", morpherFP)
morpher = MaxPlus.FPValue.Get(morpherFP)
MaxPlus.INode.AddModifier(child, morpher)
And from the MaxScript Listener I always receive the following error:
type 'exceptions.TypeError' in method 'INode_AddModifier', argument 2 of type 'Autodesk::Max::Modifier'"
while the type of morpher is Animatable(Morpher) and Animatable is a subclass of Modifier. Could someone help me with this?
Thank you in advance
I think I found a possible solution (The only thing I know is that the MaxScript Listener doesn't throw an error):
import MaxPlus
res = MaxPlus.Core.GetRootNode()
#I use the first child as example
child = MaxPlus.INode.GetChild(res,0)
morpher = MaxPlus.Factory.CreateObjectModifier(MaxPlus.ClassIds.Morpher)
MaxPlus.INode.AddModifier(child, morpher)
# the following also seems to work aka it does not throw any errors
child.InsertModifier(morpher,1)
Let me know if it is not correct or there is an easier or more understandable way.

Python c_types .dll functions (pari library)

Alright, so a couple days ago I decided to try and write a primitive wrapper for the PARI library. Ever since then I've been playing with ctypes library in loading the dll and accessing the functions contained using code similar to the following:
from ctypes import *
libcyg=CDLL("<path/cygwin1.dll") #It needs cygwin to be loaded. Not sure why.
pari=CDLL("<path>/libpari-gmp-2.4.dll")
print pari.fibo #fibonacci function
#prints something like "<_FuncPtr object at 0x00BA5828>"
So the functions are there and they can potentially be accessed, but I always receive an access violation no matter what I try. For example:
pari.fibo(5) #access violation
pari.fibo(c_int(5)) #access violation
pari.fibo.argtypes = [c_long] #setting arguments manually
pari.fibo.restype = long #set the return type
pari.fibo(byref(c_int(5))) #access violation reading 0x04 consistently
and any variation on that, including setting argtypes to receive pointers.
The Pari .dll is written in C and the fibonacci function's syntax within the library is GEN fibo(long x).
Could it be the return type that's causing these errors, as it is not a standard int or long but a GEN type, which is unique to the PARI library? Any help would be appreciated. If anyone is able to successfully load the library and use ANY function from within python, please tell; I've been at this for hours now.
EDIT: Seems as though I was simply forgetting to initialize the library. After a quick pari.pari_init(4000000,500000) it stopped erroring. Now my problem lies in the in the fact that it returns a GEN object; which is fine, but whenever I try to reference the address to which it points, it's always 33554435, which I presume is still an address. I'm trying further commands and I'll update if I succeed in getting the correct value of something.
You have two problems here, one give fibo the correct return type and two convert the GEN return type to the value you are looking for.
Poking around the source code a bit, you'll find that GEN is defined as a pointer to a long. Also, at looks like the library provides some converting/printing GENs. I focused in on GENtostr since it would probably be safer for all the pari functions.
import cytpes
pari = ctypes.CDLL("./libpari.so.2.3.5") #I did this under linux
pari.fibo.restype = ctypes.POINTER(ctypes.c_long)
pari.GENtostr.restype = ctypes.POINTER(ctypes.c_char)
pari.pari_init(4000000,500000)
x = pari.fibo(100)
y = pari.GENtostr(x)
ctypes.string_at(y)
Results in:
'354224848179261915075'

Categories

Resources