How can static method access class variable in Python?
Question:
This is what my code looks like
class InviteManager():
ALREADY_INVITED_MESSAGE = "You are already on our invite list"
INVITE_MESSAGE = "Thank you! we will be in touch soon"
@staticmethod
@missing_input_not_allowed
def invite(email):
try:
db.session.add(Invite(email))
db.session.commit()
except IntegrityError:
return ALREADY_INVITED_MESSAGE
return INVITE_MESSAGE
When I run my tests, I see
NameError: global name 'INVITE_MESSAGE' is not defined
How can I access INVITE_MESSAGE
inside @staticmethod
?
Answers:
Try:
class InviteManager():
ALREADY_INVITED_MESSAGE = "You are already on our invite list"
INVITE_MESSAGE = "Thank you! we will be in touch soon"
@staticmethod
@missing_input_not_allowed
def invite(email):
try:
db.session.add(Invite(email))
db.session.commit()
except IntegrityError:
return InviteManager.ALREADY_INVITED_MESSAGE
return InviteManager.INVITE_MESSAGE
The InviteManager
is in the scope of it’s staticmethods.
Just realized, I needed @classmethod
class InviteManager():
ALREADY_INVITED_MESSAGE = "You are already on our invite list"
INVITE_MESSAGE = "Thank you! we will be in touch soon"
@classmethod
@missing_input_not_allowed
def invite(cls, email):
try:
db.session.add(Invite(email))
db.session.commit()
except IntegrityError:
return cls.ALREADY_INVITED_MESSAGE
return cls.INVITE_MESSAGE
You can read about it here
You can access it as InviteManager.INVITE_MESSAGE
, but a cleaner solution is to change the static method to a class method:
@classmethod
@missing_input_not_allowed
def invite(cls, email):
return cls.INVITE_MESSAGE
(Or, if your code is really as simple as it looks, you can replace the whole class with a bunch of functions and constants in a module. Modules are namespaces.)
You can access to yours attributes with InviteManager.INVITE_MESSAGE
and InviteManager.ALREADY_INVITED_MESSAGE
without changing anything in their declaration.
Simply, understand the concept of class level variables/methods and instance level variables/methods.
While working with static methods, you won’t use self keyword as self keyword is used to represent instance of the class or to use instance variables of the class. In fact one use class_name, see below example:
class Myclass():
msg = "Hello World!"
@staticmethod
def printMsg():
print(Myclass.msg)
Myclass.printMsg() #Hello World!
print(Myclass.msg) #Hello World!
Myclass.msg = "Hello Neeraj!"
Myclass.printMsg() #Hello Neeraj!
print(Myclass.msg) #Hello Neeraj!
It is much simpler than all of that:
Just added __class__
to the class variables.
Like so:
return __class__.ALREADY_INVITED_MESSAGE
return __class__.INVITE_MESSAGE
There is no need to mention the ClassName (InviteManager) and there is no need to use a classmethod
This is what my code looks like
class InviteManager():
ALREADY_INVITED_MESSAGE = "You are already on our invite list"
INVITE_MESSAGE = "Thank you! we will be in touch soon"
@staticmethod
@missing_input_not_allowed
def invite(email):
try:
db.session.add(Invite(email))
db.session.commit()
except IntegrityError:
return ALREADY_INVITED_MESSAGE
return INVITE_MESSAGE
When I run my tests, I see
NameError: global name 'INVITE_MESSAGE' is not defined
How can I access INVITE_MESSAGE
inside @staticmethod
?
Try:
class InviteManager():
ALREADY_INVITED_MESSAGE = "You are already on our invite list"
INVITE_MESSAGE = "Thank you! we will be in touch soon"
@staticmethod
@missing_input_not_allowed
def invite(email):
try:
db.session.add(Invite(email))
db.session.commit()
except IntegrityError:
return InviteManager.ALREADY_INVITED_MESSAGE
return InviteManager.INVITE_MESSAGE
The InviteManager
is in the scope of it’s staticmethods.
Just realized, I needed @classmethod
class InviteManager():
ALREADY_INVITED_MESSAGE = "You are already on our invite list"
INVITE_MESSAGE = "Thank you! we will be in touch soon"
@classmethod
@missing_input_not_allowed
def invite(cls, email):
try:
db.session.add(Invite(email))
db.session.commit()
except IntegrityError:
return cls.ALREADY_INVITED_MESSAGE
return cls.INVITE_MESSAGE
You can read about it here
You can access it as InviteManager.INVITE_MESSAGE
, but a cleaner solution is to change the static method to a class method:
@classmethod
@missing_input_not_allowed
def invite(cls, email):
return cls.INVITE_MESSAGE
(Or, if your code is really as simple as it looks, you can replace the whole class with a bunch of functions and constants in a module. Modules are namespaces.)
You can access to yours attributes with InviteManager.INVITE_MESSAGE
and InviteManager.ALREADY_INVITED_MESSAGE
without changing anything in their declaration.
Simply, understand the concept of class level variables/methods and instance level variables/methods.
While working with static methods, you won’t use self keyword as self keyword is used to represent instance of the class or to use instance variables of the class. In fact one use class_name, see below example:
class Myclass():
msg = "Hello World!"
@staticmethod
def printMsg():
print(Myclass.msg)
Myclass.printMsg() #Hello World!
print(Myclass.msg) #Hello World!
Myclass.msg = "Hello Neeraj!"
Myclass.printMsg() #Hello Neeraj!
print(Myclass.msg) #Hello Neeraj!
It is much simpler than all of that:
Just added __class__
to the class variables.
Like so:
return __class__.ALREADY_INVITED_MESSAGE
return __class__.INVITE_MESSAGE
There is no need to mention the ClassName (InviteManager) and there is no need to use a classmethod