Ejemplo n.º 1
0
class Transaction(ObjectFieldGroupBase):

    public_interface = (
        IntField('reference_no'),
        StringField('public_code'),
        IntField('year'),
        IntField('month'),
        IntField('day'),
        ObjectReferenceField('counterparty'),
        PaymentMethodField('payment_method'),
        DescriptionField('description'),
        DecimalField('amount'),
        ObjectReferenceField('subject'),
        IncomeExpenditureField('income_expenditure'),
        StringField('FY'),  # TODO clean up old data and make this an int field
        ObjectReferenceField('fund'),
        DescriptionField('comments'))

    def __str__(self):
        return '{0.__class__.__name__}({0._reference_no}, {0._public_code}, {0.book_date}, {0._counterparty})'.format(
            self)

    @property
    def book_date(self):
        if all((self._year, self._month, self._day)):
            return date(self._year, self._month, self._day)
        else:
            None
Ejemplo n.º 2
0
class Envelope(ObjectFieldGroupBase):
    # Data usage
    #
    # Used to administer the Free-will envelope programme.
    # Records the envelope used by a person in a particular year
    #

    public_interface = (
        IntField('year'),
        ObjectReferenceField('counterparty'),
        ObjectReferenceField('person'),
        IntField('envelope_number'),
    )
Ejemplo n.º 3
0
    def _db_columns_from_model(self):
        # now that model class is connected to the DB expose a readonly property for the id
        id_field = IntField(ID_PROPERTY_NAME, is_mutable=False)
        id_field.create_property_on_class(self._model_class, ID_FIELDNAME)

        # map the id column
        columns = {
            ID_FIELDNAME: Column(ID_COLUMN_NAME, Integer, key=ID_FIELDNAME)
        }

        for source, dest in self._model_class.constructor_to_internal:
            columns[dest.name] = Column(source.name, self._db_column_type_map[type(dest)], key=dest.name)

        return columns
Ejemplo n.º 4
0
class AClass(ObjectFieldGroupBase):
    public_interface = (
        IntField('ref_no'),
        StringField('name'),
        BooleanField('is_running'),
        AClassStatusField('status'),
        DateField('date'),
    )
Ejemplo n.º 5
0
class Parishioner(ObjectFieldGroupBase):
    # Receives parishioner records from parish list

    public_interface = (
        IntField('reference_no', is_mutable=False),
        StringField('surname'),
        StringField('first_name'),
        StringField('title'),
        StringField('status'),
        StringField('main_contact'),
        IntField('household_ref_no'),
        StringField('mobile'),
        StringField('other'),
        StringField('email'),
        StringField('gdpr_response'),
        StringField('by_email'),
        StringField('by_phone'),
        StringField('by_post'),
        StringField('news'),
        StringField('finance'),
    )
Ejemplo n.º 6
0
class Household(ObjectFieldGroupBase):
    # Receives household records from parish list

    public_interface = (
        IntField('reference_no', is_mutable=False),
        StringField('address1', required=True),
        StringField('address2'),
        StringField('address3'),
        StringField('county'),
        StringField('eircode'),
        StringField('telephone'),
    )
Ejemplo n.º 7
0
def envelopes_from_gsheet(session, extract_from_detailed_ledger):

    gs_field_year = IntField('year')
    gs_field_counterparty = IntField('counterpartyid')
    gs_field_parishioner = IntField('parishionerid')
    gs_field_envelope_number = IntField('envelope number')

    envelope_gsheet = ListFieldGroup((
        gs_field_year,
        gs_field_counterparty,
        gs_field_parishioner,
        UnusedField('household id'),
        gs_field_envelope_number,
    ))

    field_mappings = tuple(
        zip((
            gs_field_year,
            gs_field_counterparty,
            gs_field_parishioner,
            gs_field_envelope_number,
        ), Envelope.constructor_parameters))

    field_casts = {
        'counterpartyid':
        CounterpartyQuery(session).instance_finder('reference_no', int),
        'parishionerid':
        PersonQuery(session).instance_finder('parishioner_reference_no', int),
    }
    envelope_mapping = Mapping(envelope_gsheet,
                               Envelope.constructor_parameters, field_mappings,
                               field_casts)
    envelopes = extract_from_detailed_ledger(
        'FWE records', 'A1', ('year', 'counterpartyid', 'parishionerid',
                              'household id', 'envelope number'))
    load_class(session, envelopes, envelope_mapping, Envelope)
Ejemplo n.º 8
0
class Account(ObjectFieldGroupBase):

    public_interface = (
        IntField('reference_no', is_mutable=False),
        StringField('purpose'),
        AccountStatusField('status'),
        StringField('name'),
        StringField('institution'),
        StringField('sort_code'),
        StringField('account_no'),
        StringField('BIC'),
        StringField('IBAN'),
    )

    def __str__(self):
        return '{0.__class__.__name__}({0._reference_no}, {0._account_no})'.format(
            self)
Ejemplo n.º 9
0
def tax_rebates_from_gsheet(session, extract_from_detailed_ledger):

    gs_field_parishioner_id = IntField('id')
    gs_field_status = StringField('status')
    gs_field_2015_rebate = StringField('2015 rebate')
    gs_field_2016_rebate = StringField('2016 rebate')
    gs_field_2017_rebate = StringField('2017 rebate')
    gs_field_2018_rebate = StringField('2018 rebate')

    tax_rebate_gsheet = ListFieldGroup(
        (
            gs_field_parishioner_id,
            UnusedField('household id'),
            UnusedField('new pps'),
            gs_field_status,
            gs_field_2015_rebate,
            gs_field_2016_rebate,
            gs_field_2017_rebate,
            gs_field_2018_rebate,
        )
    )

    field_mappings = tuple(zip(
        (
            gs_field_parishioner_id,
            gs_field_status,
            gs_field_2015_rebate,
            gs_field_2016_rebate,
            gs_field_2017_rebate,
            gs_field_2018_rebate,
        ),
        TaxRebate.constructor_parameters
    ))

    field_casts = {
        'id': PersonQuery(session).instance_finder('parishioner_reference_no', int),
    }
    tax_rebate_mapping = Mapping(tax_rebate_gsheet, TaxRebate.constructor_parameters, field_mappings, field_casts)
    tax_rebates = extract_from_detailed_ledger(
        'tax rebate responses',
        'A1',
        ('id', 'household id', 'new pps', 'status', '2015 rebate', '2016 rebate', '2017 rebate', '2018 rebate')
    )
    load_class(session, tax_rebates, tax_rebate_mapping, TaxRebate)
Ejemplo n.º 10
0
class PPS(ObjectFieldGroupBase):
    # Data usage
    #
    # Records PPS number for an individual in order that a tax rebate may be claimed
    # on funds donated to the parish.

    public_interface = (
        ObjectReferenceField('person', required=True),
        PPSStatusField(
            'status',
            required=True,
            default=PPSStatus.Requested,
            description='Has the parishioner responded to a request for a PPS?'
        ),
        StringField('pps'),
        StringField('name_override'),
        IntField('chy3_valid_year', description='The first financial year the most recent CHY3 form is valid from'),
        DescriptionField('notes')
    )
Ejemplo n.º 11
0
def tax_rebate_submissions_from_gsheet(session, extract_from_tax_rebates):

    gs_field_status = StringField('status')
    gs_field_year = IntField('year')
    gs_field_cal_rebate = StringField('calculated rebate')
    gs_field_filing_date = StringField('filing date')
    gs_field_est_rebate = StringField('estimated rebate from CDS1')
    gs_field_notice_no = StringField('notice number')
    gs_field_notes = StringField('notes')

    tax_rebates_gsheet = ListFieldGroup(
        (gs_field_status, gs_field_year, UnusedField('parishoner count'),
         UnusedField('donor count'), UnusedField('donations'),
         gs_field_cal_rebate, gs_field_filing_date, gs_field_est_rebate,
         gs_field_notice_no, gs_field_notes))

    field_mappings = tuple(
        zip((gs_field_status, gs_field_year, gs_field_cal_rebate,
             gs_field_filing_date, gs_field_est_rebate, gs_field_notice_no,
             gs_field_notes), TaxRebateSubmission.constructor_parameters))

    field_casts = {
        'status':
        lambda v, _: SubmissionStatus.Posted
        if v == 'posted' else SubmissionStatus.Revoked,
        'calculated rebate':
        strip_commas,
        'filing date':
        cast_dmy_date_from_string,
        'estimated rebate from CDS1':
        strip_commas
    }
    tax_rebates_mapping = Mapping(tax_rebates_gsheet,
                                  TaxRebateSubmission.constructor_parameters,
                                  field_mappings, field_casts)
    tax_rebate_submissions = extract_from_tax_rebates(
        'records', 'B1',
        ('status', 'year', 'parishoner count', 'donor count', 'donations',
         'calculated rebate', 'filing date', 'estimated rebate from CDS1',
         'notice number', 'notes'))
    load_class(session, tax_rebate_submissions, tax_rebates_mapping,
               TaxRebateSubmission)
Ejemplo n.º 12
0
class TaxRebateSubmission(ObjectFieldGroupBase):
    # Data usage
    #
    # Record of the years in which a person's PPS was submitted in a rebate claim

    public_interface = (
        SubmissionStatusField(
            'status',
            required=True,
            default=SubmissionStatus.Preparing,
            description=
            'Records what stage in its lifecycle the submission is at.'),
        IntField('FY', required=True),
        DecimalField('calculated_rebate'),
        DateField('filing_date'),
        DecimalField('estimated_rebate',
                     description='Estimated rebate from CDS1 form.'),
        StringField('notice_number'),
        DescriptionField('notes'),
    )
Ejemplo n.º 13
0
class Organisation(ObjectFieldGroupBase):
    # Data usage
    #
    # Represents a household or other organisation
    # People belong to an organisation
    #

    public_interface = (
        StringField('name', required=True),
        OrganisationCategoryField('category', required=True),
        OrganisationStatusField('status',
                                required=True,
                                default=OrganisationStatus.Active),
        IntField(
            'reference_no',
            required=True,
            is_mutable=False,
            description=
            'Internal use. Refers to identity in source data. Required for initial data load.'
        ),
    )
Ejemplo n.º 14
0
class Counterparty(ObjectFieldGroupBase):
    # Data usage
    #
    # Associates an identifiable person with their financial activity
    #

    public_interface = (
        IntField('reference_no'),
        StringField(
            'bank_text',
            description='Used to identify donors from bank statements'),
        ObjectReferenceField('person'),
        ObjectReferenceField('organisation'),
        StringField('name_override'),
        StringField(
            'method',
            description=
            'Method whereby funds are received or dispersed. Used to aid reconciliation.'
        ),  # TODO enum?
        BooleanField(
            'has_SO_card',
            description='Has donor requested a standing order donor card.'),
        BooleanField(
            'by_email',
            'Has the donor agreed to receive communications by email?'),
        DescriptionField('notes',
                         'Free text record of unusual circumstances.'),
    )

    def __str__(self):
        return '{0.__class__.__name__}({0._reference_no}, {0.name}, {0._bank_text})'.format(
            self)

    @property
    def name(self):
        return self._name_override if self._name_override else self._person.name

    @property
    def lookup_name(self):
        return self.name.lower()
Ejemplo n.º 15
0
def counterparty_from_gsheet(session, extract_from_detailed_ledger):

    gs_field_id = IntField('id')
    gs_field_bank_text = StringField('bank text')
    gs_field_person = IntField('parishoner id')
    gs_field_organisation = IntField('household id')
    gs_field_name_override = StringField('name override')
    gs_field_method = StringField('method')
    gs_field_so_card = StringField('SO card?')
    gs_field_by_email = StringField('by email')
    gs_field_notes = StringField('notes')

    counterparty_gsheet = ListFieldGroup((
        gs_field_id,
        gs_field_bank_text,
        gs_field_person,
        gs_field_organisation,
        UnusedField('main contact'),
        UnusedField('.'),
        gs_field_name_override,
        UnusedField('name'),
        UnusedField('_'),
        UnusedField('reverse lookup parishoner id'),
        UnusedField('reverse lookup cp id'),
        UnusedField('__'),
        UnusedField('___'),
        UnusedField('____'),
        UnusedField('_____'),
        UnusedField('______'),
        gs_field_method,
        gs_field_so_card,
        gs_field_by_email,
        gs_field_notes,
    ))

    field_mappings = tuple(
        zip((
            gs_field_id,
            gs_field_bank_text,
            gs_field_person,
            gs_field_organisation,
            gs_field_name_override,
            gs_field_method,
            gs_field_so_card,
            gs_field_by_email,
            gs_field_notes,
        ), Counterparty.constructor_parameters))

    field_casts = {
        'parishoner id':
        PersonQuery(session).instance_finder('parishioner_reference_no', int),
        'household id':
        OrganisationQuery(session).instance_finder('reference_no', int),
        'SO card?':
        cast_yes_no,
        'by email':
        cast_yes_no,
    }

    counterparty_mapping = Mapping(counterparty_gsheet,
                                   Counterparty.constructor_parameters,
                                   field_mappings, field_casts)
    counterparties = extract_from_detailed_ledger(
        'counterparties', 'A1',
        ('id', 'bank text', 'parishoner id', 'household id', 'main contact',
         '.', 'name override', 'name', '_', 'reverse lookup parishoner id',
         'reverse lookup cp id', '__', '___', '____', '_____', '______',
         'method', 'SO card?', 'by email', 'notes'))
    load_class(session, counterparties, counterparty_mapping, Counterparty)
Ejemplo n.º 16
0
class ATypedClass(ObjectFieldGroupBase):
    public_interface = (
        StringField('name'),
        IntField('type'),
    )
Ejemplo n.º 17
0
class Person(ObjectFieldGroupBase):

    # May be a degenerate object which just refers to an Organisation

    public_interface = (
        ObjectReferenceField('organisation', required=True),
        StringField(
            'family_name',
            description=
            'Surname of individual. Used to correctly address communications to them.'
        ),
        StringField(
            'given_name',
            description=
            'First name of individual. Used to correctly address communications to them.'
        ),
        StringField(
            'title',
            description=
            'Honorific used in formal communications and when addressing letters.'
        ),
        PersonStatusField(
            'status',
            required=True,
            default=PersonStatus.Active,
            description=
            'Is the person living, deceased or has contact been lost with them.'
        ),
        StringField(
            'mobile',
            description=
            'In addition to facilitating voice communications may be used to supplement secure access to personal data.'
        ),
        StringField(
            'other_phone',
            description='Supplementary phone number e.g. work direct dial, fax.'
        ),
        StringField(
            'email',
            description=
            'Primary means of electronic communication and identity for maintaining personal information.'
        ),
        IntField(
            'parishioner_reference_no',
            is_mutable=False,
            description=
            'Internal use. Refers to identity in source data. Required for initial data load.'
        ),
    )

    def __str__(self):
        return '{0.__class__.__name__}({0._parishioner_reference_no}, {0.name})'.format(
            self)

    @property
    def name(self):
        if self._title:
            return '{0._title} {0._given_name} {0._family_name}'.format(self)
        else:
            return '{0._given_name} {0._family_name}'.format(self)

    @property
    def name_without_title(self):
        return '{0._given_name} {0._family_name}'.format(self)
Ejemplo n.º 18
0
def parishioners_from_gsheet(session, extract_from_parish_list):

    gs_field_id = IntField('id')
    gs_field_surname = StringField('SURNAME')
    gs_field_first_name = StringField('FIRST_NAME')
    gs_field_title = StringField('TITLE')
    gs_field_status = StringField('STATUS')
    gs_field_main_contact = StringField('main_contact')
    gs_field_household_ref_no = IntField('household_id')
    gs_field_mobile = StringField('mobile')
    gs_field_other_personal = StringField('other personal')
    gs_field_email = StringField('email')
    gs_field_gdpr_response = StringField('gdpr response?')
    gs_field_by_email = StringField('email?')
    gs_field_by_phone = StringField('phone?')
    gs_field_by_post = StringField('post?')
    gs_field_news = StringField('news?')
    gs_field_finance = StringField('finance?')

    parishioner_gsheet = ListFieldGroup((
        gs_field_id,
        gs_field_surname,
        gs_field_first_name,
        gs_field_title,
        gs_field_status,
        gs_field_main_contact,
        gs_field_household_ref_no,
        UnusedField('ADDRESS1'),
        UnusedField('ADDRESS2'),
        UnusedField('ADDRESS3'),
        UnusedField('County'),
        UnusedField('EIRCODE'),
        UnusedField('TELEPHONE'),
        gs_field_mobile,
        gs_field_other_personal,
        gs_field_email,
        gs_field_gdpr_response,
        gs_field_by_email,
        gs_field_by_phone,
        gs_field_by_post,
        gs_field_news,
        gs_field_finance,
    ))

    field_mappings = tuple(
        zip((
            gs_field_id,
            gs_field_surname,
            gs_field_first_name,
            gs_field_title,
            gs_field_status,
            gs_field_main_contact,
            gs_field_household_ref_no,
            gs_field_mobile,
            gs_field_other_personal,
            gs_field_email,
            gs_field_gdpr_response,
            gs_field_by_email,
            gs_field_by_phone,
            gs_field_by_post,
            gs_field_news,
            gs_field_finance,
        ), Parishioner.constructor_parameters))

    parishioner_mapping = Mapping(parishioner_gsheet,
                                  Parishioner.constructor_parameters,
                                  field_mappings)
    parishioner_rows = extract_from_parish_list(
        'parishioners', 'A1',
        ('id', 'SURNAME', 'FIRST_NAME', 'TITLE', 'STATUS', 'main contact?',
         'household id', 'ADDRESS1', 'ADDRESS2', 'ADDRESS3', 'County',
         'EIRCODE', 'landline', 'mobile', 'other personal', 'email',
         'gdpr response?', 'email?', 'phone?', 'post?', 'news?', 'finance?'))
    parishioners = list(
        model_instances(parishioner_rows, parishioner_mapping, Parishioner))
    session.add_all(parishioners)