Search code examples
pythondjangogeraldo

Python GeraldoReports - Format a summed value with commas


I'm using Geraldo Reports to create PDF reports for my Django project. I am stuck on how to format values that are summary values.
I have an ObjectValue with action=FIELD_ACTION_SUM in a report group. I can't figure out how to format the returned value as a number with commas to separate the thousands.

I tried the get_text argument, which is listed in Geraldo Reports documentation, but not documented well on how to use it.

My current ObjectValue:

ObjectValue(
  attribute_name='labor',
  action=FIELD_ACTION_SUM,
  left=7 * inch,
  width=.8 * inch,
  style={'alignment': TA_RIGHT},
  get_text=lambda instance, value: '{:,.2f}'.format(value),
  stores_text_in_cache=False
),

I haven't had any luck searching for solutions. Does anyone here know what I'm doing wrong, or what I should be doing instead?


Solution

  • I found an answer after much trial and error ! In my example I have a field in a queryset called 'jd_gross' which I want to total in my report....I finally abandoned the action=FIELD_ACTION_SUM section and rolled my own

    in my band_detail section I can display this field with commas with the following :

            ObjectValue(attribute_name='jd_gross', left=26.7*cm, width=1.7*cm, style={'alignment':TA_RIGHT}, get_value=lambda instance: intcomma(instance.jd_gross)),
    

    The answer that works for me for the summary section however is to add to the : def init(self, *args, **kwargs): section, after the : self.band_page_header.elements += [ I used the same concept to calculate my total, convert it to a formatted string and add a line as a System Field in to my summary section as follows :

        myset = self.queryset
        grosstotal = 0
        for myline in myset:
            if myline.jd_gross:
                grosstotal += myline.jd_gross
        ugrosstotal = intcomma(grosstotal)
        self.band_summary.elements += [
            SystemField(expression=ugrosstotal, top=1*cm, left=26.5*cm, width=1.9*cm, style={'alignment':TA_RIGHT}),
            ]
    

    so my complete inherited report is now as follows :

    class JobdetailsReport(DefaultReport): title = 'Job Details' page_size = landscape(A4)

    class band_detail(DetailBand):
        height=0.7*cm
        elements=[
            ObjectValue(attribute_name='jd_job', left=0.1*cm),
            ObjectValue(attribute_name='c_name', left=1.5*cm),
            ObjectValue(attribute_name='clientname', left=5.8*cm),
            ObjectValue(attribute_name='jd_return', left=10.1*cm),
            ObjectValue(attribute_name='jd_delivery', left=12.6*cm),
            ObjectValue(attribute_name='get_j_status1_display', left=15.1*cm),
            ObjectValue(attribute_name='get_j_status2_display', left=17.6*cm),
            ObjectValue(attribute_name='jd_prodref', left=20.1*cm),
            ObjectValue(attribute_name='userformalname', left=23*cm),
            ObjectValue(attribute_name='jd_gross', left=26.7*cm, width=1.7*cm, style={'alignment':TA_RIGHT}, get_value=lambda instance: intcomma(instance.jd_gross)),
            ]
        borders = {'bottom': True}
    
    class band_summary(ReportBand):
        height = 1.7*cm
        elements = [
            Label(text='Records printed:', top=1*cm, left=0.5*cm),
            ObjectValue(expression='count(jd_job)', top=1*cm, left=5.6*cm),
            Label(text="Total Value:", top=1*cm, left=22*cm),
            ]
        borders = {'top': True}
    
    def __init__(self, *args, **kwargs):
        super(JobdetailsReport, self).__init__(*args, **kwargs)
    
        self.band_page_header.elements += [
            Label(text="Job No.", top=0.8*cm, left=0.1*cm),
            Label(text="Client", top=0.8*cm, left=1.5*cm),
            Label(text="Delivery", top=0.8*cm, left=5.8*cm),
            Label(text="Return", top=0.8*cm, left=10.1*cm),
            Label(text="Delivery", top=0.8*cm, left=12.6*cm),
            Label(text="Physical Status", top=0.8*cm, left=15.1*cm),
            Label(text="Accts Status", top=0.8*cm, left=17.6*cm),
            Label(text="Reference", top=0.8*cm, left=20.1*cm),
            Label(text="Our Contact", top=0.8*cm, left=23*cm),
            Label(text="Gross", top=0.8*cm, left=27*cm),
            ]
    
        myset = self.queryset
        grosstotal = 0
        for myline in myset:
            if myline.jd_gross:
                grosstotal += myline.jd_gross
        ugrosstotal = intcomma(grosstotal)
        self.band_summary.elements += [
            SystemField(expression=ugrosstotal, top=1*cm, left=26.5*cm, width=1.9*cm, style={'alignment':TA_RIGHT}),
            ]
    

    Hope that helps you ! It only took me several hours to get it to work......