MD Luffy
MD Luffy

Reputation: 556

Get the field name of a class without hardcoding

I have a Pydantic model class like this

class User(BaseModel):
   username: str
   firstname: str
   lastname: str

Now, I want to be able to reference "username" without hardcoding (like how I was able to reference the class name)

setup_index(User.__name__, "username") 

Is there any way without going through the code generation route ?

Upvotes: 6

Views: 8410

Answers (3)

luksfarris
luksfarris

Reputation: 1551

I know this question is old, but you could also do either one of the following (with some negligible performance sacrifice):

user = User(username="JohnAppleseed", firstname="John", lastname="Appleseed")

# method one, pydantic not used
username = user.__dict__.get('username')

# method two, no encoders called
username = user.dict().get('username')

# method three, encoders called
import json
username = json.loads(user.json()).get('username')

This avoids the call to getattr, which in my opinion is not very elegant

Upvotes: 0

maestro.inc
maestro.inc

Reputation: 815

You can make use of the getattr and the setattr function to directly access attributes from classes

 user = User('Vegeta') #initializing a class instance with username 'Vegeta'
 new_username = getattr(user, 'username') #getting the attribute and assigning it

 setup_index(User.__name__, new_username) 

Upvotes: 4

  1. If the client knows the name of the member, then getattr(user, 'username') can be used (as mentioned by @michael-butscher).
  2. If the client does not know the name of the member, then a getter function can be created via name_getter = operator.attrgetter('username') and provided to the client to be used as name_getter(user). The same effect can be achieved by defining a getter method in User and providing a reference to this method. Either ways, if username is an implementation detail, then this approach helps hide such details from the client.

Upvotes: 3

Related Questions