wxPython: Execute an event function automatically at program startup - python

There's a combobox event in my code:
self.combobox1.Bind(wx.EVT_COMBOBOX, self.onActionCombobox1)
It executes the function
def onActionCombobox1(self, event):
Is there a way to execute this function automatically everytime when I start my program?
I tried it like this:
self.onActionCombobox1(event)
but it says Undefined variable: event

if you do not make use of the event variable you want to do:
self.onActionCombobox1(None)
This, set in the __init__ method of your class, will execute the method at class instantiation (not necessarily equivalent to program startup as in wxPython you can have windows/widgets that can be created dynamically at run time. You could call the method from the class before instantiating it but then method actions have not to be related with any widget state or behavior as they do not exist yet. Anyway, in that case maybe the method should be written better as an independent function).

Related

In Python 2 do we need a self keyword for a function even if the function isn't part of a class?

So I'm looking through some old python 2 code and I see this function
def manage_addMapSamlPlugin(self, id, title='', delegate_path='', REQUEST=None):
""" Factory method to instantiate a MapSamlPlugin """
# Make sure we really are working in our container (the
# PluggableAuthService object)
self = self.this()
# Instantiate the adapter object
lmp = MapSamlPlugin(id, title=title, delegate_path=delegate_path )
self._setObject(id, lmp)
if REQUEST is not None:
REQUEST.RESPONSE.redirect('%s/manage_main' % self.absolute_url())
Now this function is outside of a class, the code compiles and doesn't give any errors. My understanding is that the self keyword in this case is just anything that gets passed in, but self.this() and self._setObject(id, lmp) that shouldn't be a thing right? Shouldn't the compiler throw an error? The code is run on a terminal in a ssh server I don't know what compiler it uses.
At the end of the file this is where the function gets called.
def initialize(context):
registerMultiPlugin(MapSamlPlugin.meta_type)
context.registerClass(
MapSamlPlugin,
constructors=(manage_addMapSamlPluginForm, manage_addMapSamlPlugin),
permission=ManageUsers,
icon=os.path.join(mgr_dir, "saml_icon.png"),
visibility=None,
)
And this is also a standalone function "context" isn't derived from any imports or class.
The comment is an important clue:
def manage_addMapSamlPlugin(self, id, title='', delegate_path='', REQUEST=None):
""" Factory method to instantiate a MapSamlPlugin """
# Make sure we really are working in our container (the
# PluggableAuthService object)
self = self.this()
self is expected to be an object which has a this() method -- it sounds like that method returns a PluggableAuthService object. If you grep the rest of the code for def this you'll probably find it. Looking for class PluggableAuthService might also shed some light.
If you call this function and pass it a self that doesn't implement the expected interface, you'll get an AttributeError at runtime. Since there are no type annotations here, there's not really a way to catch errors statically (at "compile time" -- although typically compiling Python doesn't in itself enforce any static type checks).
My suspicion is that this function was originally a method of that class, and got refactored out of it for some reason (maybe as the first step in some larger refactor that was never finished). A class method works just fine if you yank it out of a class, provided that you explicitly provide the self parameter when you call it.

Python UiPath - How to use Classes with UiPath.Python.Activities

Here is an image showing Python scope activity (version 3.6 and target x64):
Python Scope
The main problem is the relation between both invoke python methods, the first one is used to start the class object, and the second one to access a method of that class. Here is an image of the first invoke python properties:
Invoke Python init method
And the getNumberPlusOne activity call:
Invoke Python getNumberPlusOne method
The python code being executed:
class ExampleClass:
def __init__(self,t,n):
self.text = t
self.number = n
def getNumberPlusOne(self):
return (self.number+1)
And finally, the error when executing the second Invoke Python Method:
An ExceptionDetail, likely created by IncludeExceptionDetailInFaults=true, whose value is:
System.InvalidOperationException: Error invoking Python method ----> System.Runtime.Serialization.InvalidDataContractException: Type 'UiPath.Python.PythonObject' cannot be serialized. Consider marking it with the DataContractAttribute attribute, and marking all of its members you want serialized with the DataMemberAttribute attribute. If the type is a collection, consider marking it with the CollectionDataContractAttribute. See the Microsoft .NET Framework documentation for other supported types.
Any idea about where is the mistake and how to interact with the output object created in the init method?
I believe that this activity was designed with simple scripts in mind, not with entire classes. Here's an article on their Community Forum where user Sergiu.Wittenberger goes into more details.
Let's start with the Load Python Script activity:
In my case the local variable "pyScript" is a pointer to the python object, i.e. an instance of ExampleClass.
Now, there is the Invoke Python Method activity - this one allows us to call a method by name. It seems however that methods on the class are inaccessible to UiPath - you can't just type pyScript.MethodName().
So it seems that we can't access class methods (please proof me wrong here!), but there's a workaround as shown by Sergio. In your case, you would add another method outside your class in order to access or manipulate your object:
class ExampleClass:
def __init__(self,t,n):
self.text = t
self.number = n
def getNumberPlusOne(self):
return (self.number+1)
foo = ExampleClass("bar", 42)
def get_number_plus_one():
return foo.getNumberPlusOne()
Note that this also means that the object is instantiated within the very same file: foo. At this point this seems to be the only option to interact with an object -- again, I'd hope somebody can prove me wrong.
For the sake of completeness, here's the result:
I would like to add to what the above user said that you have to make sure that the imports you use are in the global site-packages, and not in a venv as Studio doesn't have access to that.
Moreoever, always add this:
import os
import sys
sys.path.append(os.path.dirname(os.path.realpath(__file__)))
to the beginning of your code. Again, a limitation of the implementation. (docs here: https://docs.uipath.com/activities/docs/load-script)
Doing this you might be able to do more complicated structures I think, but I haven't tested this out.

Circular dependencies python for functions in same file

I have code structure something like this:-
def send_message(msg):
print msg + "\n"
x.new_message("You",msg)
class GUI(Frame):
def createWidgets(self):
self.input.bind('<Key-Return>',self.send)
def send(self, event):
send_message(self.contents.get())
self.contents.set("")
def new_message(self,sender, msg):
line = sender+": "+msg+"\n"
self.chat.contents.set(self.chat.contents.get()+line)
def __init__(self):
self.createWidgets()
x = GUI()
As you can see, this has some circular dependancies. Function send_message requires instance x as well as new_message method of GUI. GUI definition needs send_message. Thus it is not possible to satisfy all the constraints. What to do?
In the complete code you showed in die comments we can see that you call self.mainloop() in GUI.__init__. This will start the event handling of the gui and will probably not terminate until the program in finished. Only then the assignment x = GUI() will finish and x will be available.
To circumvent this you have multiple options. Generally doing an endless loop in __init__ is probably a bad idea. Instead call mainloop() after the GUI is instantiated.
def __init__(self):
# only do init
x = GUI()
x.mainloop()
As jasonharper said in python variables in functions are only looked up when you execute that function, not when defining them. Thus circular dependencies in runtime are most of the time not a problem in python.
Names within Python functions are not required to refer to anything at the time the function is defined - they're only looked up when the function is actually called. So, your send_message() is perfectly fine as it is (although it would probably be better to make x a parameter rather than a global variable).
Your GUI class is going to fail to instantiate as shown, due to references to widgets you didn't show the creation of - self.input for example. I cannot tell how much of that is due to you stripping the code down for posting.

Sublime Editor Plugin remember variable

I am writing a sublime editor 2 plugin, and would like it to remember a variable for the duration of the session. I do not want it to save the variable as a file (it is a password), but would like to be able to run a command repeatedly, and the variable to be accessible.
I want my plugin to work something like this...
import commands, subprocess
class MyCommand(sublime_plugin.TextCommand):
def run(self, edit, command = "ls"):
try:
thevariable
except NameError:
# should run the first time only
thevariable = "A VALUE"
else:
# should run subsequent times
print thevariable
One way to achieve this would be to make it a global variable. This will allow you to access that variable from any function. Here is a stack question to consider.
Another option would be to add it to the instance of the class. This is commonly done in the __init__() method of the class. This method is run as soon as the class object is instantiated. For more information on self and __init__() consult this stack discussion. Here is a basic example.
class MyCommand(sublime_plugin.TextCommand):
def __init__(self, view):
self.view = view # EDIT
self.thevariable = 'YOUR VALUE'
This will allow you to access this variable from a class object after it has been created. Something like this MyCommandObject.thevariable. These types of variables will last until the window in which the method was called from is closed.

Object cannot be created globally but can locally python

I am defining two classes in the same module and want to use the second one in the first one (as a global variable):
class Class1(object):
global_c2 = Class2()
def foo(self):
local_c2 = Class2()
class Class2(object):
pass
global_c2 gets an error but local_c2 doesn't. This makes sense because when the compiler looks through this file it won't know that Class2 is going to exist. Also if I switch the class around so that Class2 is defined first it works.
However I was wondering if there is another way to get around this. Maybe I can somehow tell python that Class2 is going to exist so don't worry about it, or do I just have to put them in the right order?
The compiler doesn't do anything here. In both cases, exactly the same bytecode sequence is generated to look up the class at runtime and instanciate it.
What makes the difference is when the statements are run. All code in a Python module is executed top from bottom -- there is no such thing as a declaration, everything's a definition and every binding is dynamic. Code in a class definition is run when the class definition is encountered (and therefore before the second class is brought into existence and bound to the name Class2). Code in a function runs when the function is called, and because you don't call the function before the definition of the second class, it's available by the time you call that function.
That's basically what every solution boils down to: Delay binding until whatever you're binding to exists.
You can do the following (i.e. backfill the contents of Class1 once Class2 has been declared.
class Class1(object):
pass
class Class2(object):
pass
Class1.global_c2 = Class2()

Categories

Resources