When dynamically creating and generating Model class, modify some
properties, fill in the information required by the sub-table, the
first time can return the normal result, the second result error,
after the analysis of the second result field to retain the first
table name:
class Object:
def __init__(self, **kwargs):
self.__dict__.update(kwargs)
def _model_new(cls, *args, **kwargs):
return cls(*args, **kwargs)enter code here
class ShardModel(object):
_shard_db_models = {}
temp_class = []
def __new__(cls, *args, **kwargs):
shard_key = kwargs.pop('shard_key', 0) % cls.Config.table_num
model_name = cls.__name__
model_name += '_%s' % shard_key
model_class = cls._shard_db_models.get(model_name)
if model_class is not None:
return model_class
# Deep copy attrs
attrs = dict()
attrs.update(cls.__dict__)
if 'objects' in attrs:
attrs['objects'] = attrs['objects'].__class__()
# Set table name with shard_key
meta = Object(**cls.Meta.__dict__)
meta.db_table = meta.db_table % shard_key
meta.abstract = False
attrs['Meta'] = meta
attrs['new'] = classmethod(_model_new)
attrs['__module__'] = cls.__name__
cursor = connection.cursor()
tables = [table_info.name for table_info in connection.introspection.get_table_list(cursor)]
# Create model class dynamically
model_class = type(model_name, tuple([models.Model] + list(cls.__bases__[1:])), attrs)
print(model_class)
if meta.db_table not in tables:
for cmd in ('makemigrations', 'migrate'):
exec_command(cmd, meta.app_label)
cls._shard_db_models[model_name] = model_class
return model_class
this is my model
class Nice(ShardModel):
user_id = models.IntegerField()
user_name = models.CharField(max_length=256)
password = models.CharField(max_length=256)
class Config:
table_num = 3
class Meta:
app_label = 'Test'
db_table = 'test_%s'
abstract = True
this my view
def NiceView(request):
user_id = int(request.GET.get('user_id'))
user = Nice(shard_key=user_id).objects.get(user_id=user_id)
return HttpResponse(json.dumps(model_to_dict(user)))
Here are the two times test results
url:http://127.0.0.1:8000/test?user_id=7
results:{"id": 2, "user_id": 7, "user_name": "ni", "password": "hao"};url:http://127.0.0.1:8000/test?user_id=5;error:(1054, "Unknown column 'test_1.user_id' in 'field list'")
I have two methods inside a class (mask_im and save_im) that I must include in several other classes in separate modules. How can I create a class with those two methods without copying and paste 10 lines of code, or at least reduce it to two lines of code? I want to have like a class template or something that I can reuse easily.
class MaskFromImages:
def __init__(self, im_to_mask, m_rules, val_assign=None):
im_mem = ReadMap(im_to_mask, mem=True)
self.reference = im_mem.reference
if im_mem.no_data is None:
self.out_no_data = 255
else:
self.out_no_data = im_mem.no_data
out_array = im_mem.array
out_mem = im_mem.osgeodata
for i in m_rules:
out_array = MaskCls(out_mem, i[0], i[1], val_assign).array
out_mem = save_map(out_array, "", im_mem.d_type, self.reference, format_out="MEM")
out_array = out_array.astype("int16")
self.array = out_array
def mask_im(self, mask_aoi, mask_aoi_vl, replace_im=None, reverse=False):
map_mem = save_map(self.array, "", gdal.GDT_UInt16, self.reference, format_out="MEM")
im_masked = MaskAOI(map_mem, mask_aoi, mask_aoi_vl, self.out_no_data,
replace_im=replace_im, reverse=reverse)
return im_masked
def save_im(self, output, format_out="GTiff"):
ds_out = save_map(self.array, output, gdal.GDT_UInt16, self.reference, out_no_data=self.out_no_data,
format_out=format_out)
if format_out == 'MEM':
return ds_out
This is the way I solved it using inheritance:
class Template:
def __init__(self):
self.array = None
self.reference = None
self.out_no_data = None
self.data_type = None
def mask(self, mask_aoi, mask_aoi_vl, replace_im=None, reverse=False):
map_mem = save_map(self.array, "", self.data_type, self.reference, format_out="MEM")
im_masked = MaskAOI(map_mem, mask_aoi, mask_aoi_vl, self.out_no_data,
replace_im=replace_im, reverse=reverse)
return im_masked
def save(self, output, format_out="GTiff"):
ds_out = save_map(self.array, output, self.data_type, self.reference, out_no_data=self.out_no_data,
format_out=format_out)
if format_out == 'MEM':
return ds_out
class MergeClasses(Template):
def __init__(self, input_data, m_classes, other_cls_val=None):
class_map1 = ReadMap(input_data)
self.reference = class_map1.reference
class_map1_array = class_map1.array
if class_map1.no_data is None:
self.out_no_data = 255
else:
self.out_no_data = class_map1.no_data
array_class = merge_cls(class_map1_array, m_classes, other_cls_val)
class_map_f = array_class.astype("int16")
self.array = class_map_f
self.data_type = gdal.GDT_UInt16
I am working on an ecommerce project but my OrderManager() class does not saving the instance(i think)
When i am clicking on BOOK button i am getting this error which is defined in my view
order_amount = order_obj.total * 100
AttributeError: 'NoneType' object has no attribute 'total'
But when i refresh the page error goes way and order_obj.total * 100 is calculated, But my question is why i need to refresh the page again and again when i create a new order.
Here is my models.py
class OrderQuerySet(models.query.QuerySet):
def not_created(self):
return self.exclude(status='created')
class OrderManager(models.Manager):
def get_queryset(self):
return OrderQuerySet(self.model, using=self.db)
def create_or_get_order(self, product):
created = None
obj = None
qs = self.get_queryset().filter(product=product, active=True, status='created')
if qs.count() == 1:
obj = qs.first()
else:
self.model.objects.create(product=product)
created = True
return obj, created
class Order(models.Model):
order_id = models.CharField(max_length=120, blank=True)
product = models.ForeignKey(Product, on_delete=models.CASCADE)
total = models.PositiveIntegerField()
active = models.BooleanField(default=True)
objects = OrderManager()
class Meta:
ordering = ['-ordered_on', '-updated']
def __str__(self):
return self.order_id
def check_done(self): # check everything is correct before final checkout
order_id = self.order_id
total = self.total
if order_id and total > 0:
return True
return False
def mark_paid(self):
if self.check_done():
self.status = 'paid'
self.save()
return self.status
def pre_save_create_order_id(sender, instance, *args, **kwargs):
if not instance.order_id:
instance.order_id = unique_order_id_generator(instance)
pre_save.connect(pre_save_create_order_id, sender=Order)
def pre_save_order_total(sender, instance, *args, **kwargs):
"""calculate the product total while clicking on Book Button
(Still booking is not done you just clicked on Book button)"""
instance.total = instance.product.price
pre_save.connect(pre_save_order_total, sender=Order)
Views.py
def checkout_home_view(request, *args, **kwargs):
order_obj = None
order_amount = None
order_currency = None
order_id = None
slug = kwargs['slug']
product = Product.objects.get(slug=slug)
if product is not None:
# ****************** Here is problem ******************************
order_obj, order_create = Order.objects.create_or_get_order(product)
''' HERE I AM GETTING order_obj as None BUT WHEN I REFRESH ERROR GOES WAY '''
print('order_obj', order_obj) # printing None initally
order_amount = order_obj.total * 100
order_currency = 'INR'
order_id = order_obj.order_id
if request.method == 'POST':
'check that booking is done'
is_prepared = order_obj.check_done() # check_done() defined in Order model
if is_prepared:
client = razorpay.Client(auth=("xxx", "xxx"))
payment = client.order.create(dict(amount=order_amount, currency=order_currency))
if payment:
order_obj.mark_paid() # mark_paid() defined in Order model
order_obj.save()
class OrderManager(models.Manager):
...
def create_or_get_order(self, product):
created = None
obj = None
qs = self.get_queryset().filter(product=product, active=True, status='created')
if qs.count() == 1:
obj = qs.first()
else:
# -------------- catch the returned obj and return --------------
obj = self.model.objects.create(product=product)
created = True
return obj, created
fix: I moved an invoke of a Radiobutton from the init of my view to the controller like this:
class Controller(object):
def __init__(self):
self.model = Model()
print('start init of View')
self.view = View(self.importieren, self.exportieren, self.beenden, self.J5, self.J6, self.J7, self.J8, self.J9,
self.J10, self.J11, self.J12, self.JA, self.tabelle_sorti, self.hinzufugen, self.zuordnen,
self.ande, self.JA, self.model.ausgabe('projekte'), self.tabelle_update, self.a1, self.a2, self.a3,
self.a4, self.a5, self.a6, self.a7)
print('done init')
self.wahlen = ('sErst', 'sZweit', 'sDritt')
self.delimiter = {'imp_s': None, 'imp_p': None, 'exp': None}
self.dchosen = None
self.slcsv = 'schuelerliste.csv'
self.plcsv = 'projektliste.csv'
self.double = False
self.andernx = ""
self.view.radios['jahrg-Alle'].invoke()
self.tabelle()
self.view.table['main'].bind('<Double-Button-1>', self.treevent)
# Erstimportierung
if self.model.ausgabe('schueler'):
self.importieren(True)
self.view.mainloop()
def tabelle_update(self, fetchshlr=None, fetchprj=None):
print('start update')
if fetchshlr is None:
fetchshlr = self.model.ausgabe('schueler')
if fetchprj is None:
fetchprj = self.model.ausgabe('projekte')
self.view.tableup(fetchshlr, fetchprj)
This invoke called the function, before View was ready and so caused the error. Thanks for the Help
I tried to not ask a question hear, but after hours of searching I have to.
I am currently working on a programm and recently splitted the main file in three in style of the MVC-Scheme. And I have one function to update a Treeview working as a table. But this function (and only that one!), says:
Exception in Tkinter callback\
Traceback (most recent call last):\
File "C:\Users\...\Python38\lib\tkinter\__init__.py", line 1883, in __call__\
return self.func(*args)\
File "C:/Users/.../Controller.py", line 184, in tabelle_update\
self.view.table['main'].tag_configure(i[0], background='white')\
AttributeError: 'Controller' object has no attribute 'view'
I already tried to use lambda (and if you ask why, because someone said it in the internet) and it just prevented the function to work at all. Also I think it has something todo with this:
{'model': <Model.Model object at 0x0000018CA8068160>, 'view': <View.View object .>, ...}
this is an extract of the attributes ditionary and I think it has something to do with the missing at 0x... part in 'view' as seen in 'model'
Please Help me to get this up and running
And here are my important code parts (if you need more, pls write)
note that the diffrent classes are in diffrent files and are properly imported
Major Changes in programmcode under tabelle_update and under the View class tableup
I tried to move the View heavy parts to View, didn't fix anything.
class Controller(object):
def __init__(self):
self.model = Model()
self.view = View(self.importieren, self.exportieren, self.beenden, self.J5, self.J6, self.J7, self.J8, self.J9,
self.J10, self.J11, self.J12, self.tabelle_update, self.tabelle_sorti, self.hinzufugen,
self.zuordnen, self.ande, self.tabelle_update, self.model.ausgabe('projekte'),
self.tabelle_update, self.a1, self.a2, self.a3, self.a4, self.a5, self.a6, self.a7)
self.wahlen = ('sErst', 'sZweit', 'sDritt')
self.delimiter = {'imp_s': None, 'imp_p': None, 'exp': None}
self.dchosen = None
self.slcsv = 'schuelerliste.csv'
self.plcsv = 'projektliste.csv'
self.double = False
self.andernx = ""
self.tabelle()
self.view.table['main'].bind('<Double-Button-1>', self.treevent)
# Erstimportierung
if self.model.ausgabe('schueler'):
self.importieren(True)
print(self.__dict__)
self.view.mainloop()
def tabelle(self):
fetch = self.model.ausgabe('schueler')
self.view.shlr_tabelle(fetch)
def tabelle_update(self, fetchshlr=None, fetchprj=None):
print('start update')
if fetchshlr is None:
fetchshlr = self.model.ausgabe('schueler')
if fetchprj is None:
fetchprj = self.model.ausgabe('projekte')
self.view.tableup(fetchshlr, fetchprj)
class View(ttkthemes.ThemedTk):
def __init__(self, imp, exp, bee, j5, j6, j7, j8, j9, j10, j11, j12, ja, tabsort, hin, zord, ande, scht,
prjt, aktutable, a1, a2, a3, a4, a5, a6, a7):
# print(ttkthemes.THEMES) # zum Ausgeben der verfügbaren Themes
ttkthemes.ThemedTk.__init__(self, theme='breeze')
self.title("Projektwochenverwaltungsprogramm")
self.geometry('800x300')
self.minsize(800, 300)
self.resizable(width=True, height=True)
# bestimmen der Callbacks
self.callback_imp = imp
self.callback_exp = exp
self.callback_bee = bee
self.radiocom = {'jahrg': [j5, j6, j7, j8, j9, j10, j11, j12, ja], 'ande': [a1, a2, a3, a4, a5, a6, a7]}
self.tabelle_sorti = tabsort
self.callback_aktut = aktutable
self.callback_zord = zord
self.callback_hin = hin
self.callback_ande = ande
self.callback_scht = scht
self.callback_prjt = prjt
# Tabelle
self.scrollbars = {'main': Scrollbar(self.rahmen[2], orient="vertical")}
self.table = {'main': Treeview(self.rahmen[2], yscrollcommand=self.scrollbars['main'].set, height=200)}
self.scrollbars['main'].pack(side=RIGHT, fill=BOTH)
self.rahmen[1].pack()
self.rahmen['popup_pro'].pack(fill=X)
self.rahmen[2].pack(fill=BOTH, expand=True)
def shlr_tabelle(self, fetch):
ml = ['ID']
for name in self.names['schueler']:
ml.append(name)
ml.append('Zugeordned zu')
self.table['main']['columns'] = ml
self.table['main']['show'] = 'headings'
for i in range(len(ml)):
self.table['main'].column(ml[i], width=self.width['schueler'][i], minwidth=self.width['schueler'][i])
for i in range(len(ml)):
self.table['main'].heading(ml[i], text=ml[i], command=lambda col=i: self.tabelle_sorti(col, False, 'main'))
for t in fetch:
self.table['main'].insert('', t[0], t[0], values=t) # , tags=t[0]
self.scrollbars['main'].config(command=self.table['main'].yview)
self.table['main'].pack(fill=BOTH)
def prj_tabelle(self, fetch):
self.top['prjt'] = Toplevel()
self.top['prjt'].title('Projekte Liste')
self.top['prjt'].geometry('800x300')
self.top['prjt'].minsize(800, 300)
self.scrollbars['prj'] = Scrollbar(self.top['prjt'], orient="vertical")
self.table['prj'] = Treeview(self.top['prjt'], yscrollcommand=self.scrollbars['prj'].set, height=200)
ml = ['ID']
for name in self.names['projekte']:
ml.append(name)
self.table['prj']['columns'] = ml
self.table['prj']['show'] = 'headings'
for i in range(len(ml)):
self.table['prj'].column(ml[i], width=self.width['projekte'][i], minwidth=self.width['projekte'][i])
for i in range(len(ml)):
self.table['prj'].heading(ml[i], text=ml[i], command=lambda col=i: self.tabelle_sorti(col, False, 'prj'))
for t in fetch:
self.table['prj'].insert('', t[0], t[0], values=t) # , tags=t[0]
self.scrollbars['prj'].config(command=self.table['prj'].yview)
self.scrollbars['prj'].pack(side=RIGHT, fill=BOTH)
self.table['prj'].pack(fill=BOTH)
def tableup(self, fetchshlr, fetchprj):
print('läuft')
for i in fetchshlr:
self.view.table['main'].tag_configure(i[0], background='white')
self.view.table['main'].delete(*self.view.table['main'].get_children())
for t in fetchshlr:
self.view.table['main'].insert('', t[0], t[0], values=t) # , tags=t[0]
for ele in fetchshlr:
if ele[8] is None:
self.view.table['main'].tag_configure(ele[0], background='#fa6150')
try:
for i in fetchprj:
self.view.table['prj'].tag_configure(i[0], background='white')
self.view.table['prj'].delete(*self.view.table['prj'].get_children())
for t in fetchprj:
self.view.table['prj'].insert('', t[0], t[0], values=t) # , tags=t[0]
failed = self.model.prj_aktu()
for prj in failed:
self.view.table['prj'].tag_configure(prj, background='#fa6150')
except KeyError:
pass
You have to ask yourself when self.view is fully initialized, and when you're trying to access self.view. The error is telling you that you're trying to access it before you define it.
You should be able to visualize this by adding print statements like so:
print("before self.view is defined")
self.view = View(...)
print("after self.view is defined")
and then:
print("using self.view...")
self.view.table['main'].tag_configure(i[0], background='white')
I have the following code snippet:
class BaseUserAccount(object):
def __init__(self):
accountRefNo = "RefHDFC001"
FIType = "DEPOSIT"
pan = "AFF34964FFF"
mobile = "9822289017"
email = "manoja#cookiejar.co.in"
aadhar = "5555530495555"
class TestUserSavingsAccount(BaseUserAccount):
def __init__(self):
super().__init__()
accountNo = "HDFC111111111111"
accountTypeEnum = "SAVINGS"
def test_create_account(self):
request_body = """\
<UserAccountInfo>
<UserAccount accountRefNo="{}" accountNo="{}"
accountTypeEnum="{}" FIType="{}">
<Identifiers pan="{}" mobile="{}" email="{}" aadhar="{}"></Identifiers>
</UserAccount>
</UserAccountInfo>
""".format(self.accountRefNo, self.accountNo, self.accountTypeEnum,
self.FIType, self.pan, self.mobile, self.email, self.aadhar)
If I run this code in the interactive shell:
>>> t = TestUserSavingsAccount()
>>> t.accountRefNo
AttributeError: 'TestUserSavingsAccount' object has no attribute 'accountRefNo'
>>> t.accountNo
AttributeError: 'TestUserSavingsAccount' object has no attribute 'accountNo'
Seeing the above behavior, it seems like the super is neither setting up values from the base class and neither the attributes of the child (accountNo, accountTypeEnum) are being set.
The way you wrote only assign those values to local variables. You need to initialize attributes of the self object instead:
class BaseUserAccount(object):
def __init__(self):
self.accountRefNo = "RefHDFC001"
self.FIType = "DEPOSIT"
self.pan = "AFF34964FFF"
self.mobile = "9822289017"
self.email = "manoja#cookiejar.co.in"
self.aadhar = "5555530495555"
class TestUserSavingsAccount(BaseUserAccount):
def __init__(self):
super().__init__()
self.accountNo = "HDFC111111111111"
self.accountTypeEnum = "SAVINGS"