Esempio n. 1
0
def test_get_by_toptier():
    """Test Agency lookup by toptier CGAC code."""
    toptier = mommy.make('references.ToptierAgency',
                         cgac_code='xyz',
                         name='yo')
    subtier = mommy.make('references.SubtierAgency',
                         subtier_code='abc',
                         name='yo')
    mommy.make('references.Agency',
               toptier_agency=toptier,
               subtier_agency=subtier)
    mommy.make('references.Agency',
               toptier_agency=toptier,
               subtier_agency=mommy.make('references.SubtierAgency',
                                         subtier_code='abc',
                                         name='no'),
               update_date=datetime.date(2017, 10, 10))
    agency1 = mommy.make('references.Agency',
                         toptier_agency=toptier,
                         subtier_agency=subtier)

    # lookup should return agency w/ most recent update_date that
    # matches the cgac code
    assert Agency.get_by_toptier('xyz') == agency1
    # If there's no match, we should get none
    assert Agency.get_by_toptier('nope') is None
Esempio n. 2
0
def test_get_by_toptier():
    """Test Agency lookup by toptier CGAC code."""
    toptier = mommy.make("references.ToptierAgency",
                         toptier_code="xyz",
                         name="yo")
    subtier = mommy.make("references.SubtierAgency",
                         subtier_code="abc",
                         name="yo")

    mommy.make(
        "references.Agency",
        toptier_agency=toptier,
        subtier_agency=mommy.make("references.SubtierAgency",
                                  subtier_code="bbb",
                                  name="no"),
        update_date=datetime.date(2017, 10, 10),
    )
    agency1 = mommy.make("references.Agency",
                         toptier_agency=toptier,
                         subtier_agency=subtier)

    # lookup should return agency w/ most recent update_date that
    # matches the cgac code
    assert Agency.get_by_toptier("xyz") == agency1
    # If there's no match, we should get none
    assert Agency.get_by_toptier("nope") is None
def get_awarding_agency(row):
    if row.txn:
        # We found a matching transaction, so grab its awarding agency info and pass it get_or_create_summary_award
        return Agency.objects.get(id=int(row.txn))
    else:
        # No matching transaction found, so find/create Award by using toptier agency only, since CGAC code is the only
        # piece of awarding agency info that we have.
        return Agency.get_by_toptier(row.agency_identifier)
def get_valid_awarding_agency(row):
    agency_subtier_code = row['awarding_sub_tier_agency_c']
    agency_toptier_code = row['awarding_agency_code']
    valid_subtier_code = (agency_subtier_code and len(agency_subtier_code) > 0)
    valid_toptier_code = (agency_toptier_code and len(agency_toptier_code) > 0)

    if not valid_toptier_code and not valid_subtier_code:
        return None

    agency = None
    # Get the awarding agency
    if valid_subtier_code and valid_toptier_code:
        agency = Agency.get_by_toptier_subtier(row['awarding_agency_code'], row['awarding_sub_tier_agency_c'])

    if not agency and valid_subtier_code:
        agency = Agency.get_by_subtier(row['awarding_sub_tier_agency_c'])

    if not agency and valid_toptier_code:
        agency = Agency.get_by_toptier(row['awarding_agency_code'])

    return agency
def get_valid_awarding_agency(row):
    agency_subtier_code = row['awarding_sub_tier_agency_c']
    agency_toptier_code = row['awarding_agency_code']
    valid_subtier_code = (agency_subtier_code and len(agency_subtier_code) > 0)
    valid_toptier_code = (agency_toptier_code and len(agency_toptier_code) > 0)

    if not valid_toptier_code and not valid_subtier_code:
        return None

    agency = None
    # Get the awarding agency
    if valid_subtier_code and valid_toptier_code:
        agency = Agency.get_by_toptier_subtier(
            row['awarding_agency_code'], row['awarding_sub_tier_agency_c'])

    if not agency and valid_subtier_code:
        agency = Agency.get_by_subtier(row['awarding_sub_tier_agency_c'])

    if not agency and valid_toptier_code:
        agency = Agency.get_by_toptier(row['awarding_agency_code'])

    return agency
Esempio n. 6
0
    def get_or_create_summary_award(awarding_agency=None,
                                    piid=None,
                                    fain=None,
                                    uri=None,
                                    parent_award_id=None,
                                    use_cache=False):
        """
        Given a set of award identifiers and awarding agency information,
        find a corresponding Award record. If we can't find one, create it.

        Returns:
            created: a list of new awards created (or that need to be created
                if using cache), used to enable bulk insert
            summary_award: the summary award that the calling process can map to
        """
        # If an award transaction's ID is a piid, it's contract data
        # If the ID is fain or a uri, it's financial assistance. If the award transaction
        # has both a fain and a uri, fain takes precedence.
        q_kwargs = {}
        for i in [(piid, "piid"), (fain, "fain"), (uri, "uri")]:
            if i[0]:
                q_kwargs[i[1]] = i[0]
                if parent_award_id:
                    q_kwargs["parent_award__" + i[1]] = parent_award_id
                    # parent_award__piid, parent_award__fain, parent_award__uri
                else:
                    q_kwargs["parent_award"] = None

                # Now search for it
                # Do we want to log something if the the query below turns up
                # more than one award record?
                if use_cache:
                    q_kwargs_fixed = list(q_kwargs.items()) + [
                        ('awarding_agency', awarding_agency),
                    ]
                    q_kwargs_fixed.sort()
                    summary_award = awards_cache.get(q_kwargs_fixed)
                    if summary_award:
                        return [], summary_award

                # Look for an existing award record
                summary_award = Award.objects \
                    .filter(Q(**q_kwargs)) \
                    .filter(awarding_agency=awarding_agency) \
                    .first()
                if (summary_award is None and awarding_agency is not None
                        and awarding_agency.toptier_agency.name !=
                        awarding_agency.subtier_agency.name):
                    # No award match found when searching by award id info +
                    # awarding subtier agency. Relax the awarding agency
                    # critera to just the toptier agency instead of the subtier
                    # agency and try the search again.
                    awarding_agency_toptier = Agency.get_by_toptier(
                        awarding_agency.toptier_agency.cgac_code)
                    summary_award = Award.objects \
                        .filter(Q(**q_kwargs)) \
                        .filter(awarding_agency=awarding_agency_toptier) \
                        .first()

                if summary_award:
                    if use_cache:
                        awards_cache.set(q_kwargs_fixed, summary_award)
                    return [], summary_award

                # We weren't able to match, so create a new award record.
                if parent_award_id:
                    # If parent award id was supplied, recursively get/create
                    # an award record for it
                    parent_created, parent_award = Award.get_or_create_summary_award(
                        use_cache=use_cache,
                        **{
                            i[1]: parent_award_id,
                            'awarding_agency': awarding_agency
                        })
                else:
                    parent_created, parent_award = [], None

                # Now create the award record for this award transaction
                summary_award = Award(
                    **{
                        i[1]: i[0],
                        "parent_award": parent_award,
                        "awarding_agency": awarding_agency
                    })
                created = [
                    summary_award,
                ]
                created.extend(parent_created)

                if use_cache:
                    awards_cache.set(q_kwargs_fixed, summary_award)
                else:
                    summary_award.save()
                return created, summary_award

        raise ValueError(
            'Unable to find or create an award with the provided information: '
            'piid={}, fain={}, uri={}, parent_id={}, awarding_agency={}'.
            format(piid, fain, uri, parent_award_id, awarding_agency))
def load_file_c(submission_attributes, award_financial_data, db_cursor):
    """
    Process and load file C broker data.
    Note: this should run AFTER the D1 and D2 files are loaded because we try
    to join to those records to retrieve some additional information
    about the awarding sub-tier agency.
    """
    # this matches the file b reverse directive, but am repeating it here
    # to ensure that we don't overwrite it as we change up the order of
    # file loading
    reverse = re.compile(r'(_(cpe|fyb)$)|^transaction_obligated_amount$')

    for row in award_financial_data:
        # Check and see if there is an entry for this TAS
        treasury_account = get_treasury_appropriation_account_tas_lookup(
            row.get('tas_id'), db_cursor)
        if treasury_account is None:
            raise Exception('Could not find appropriation account for TAS: ' +
                            row['tas'])

        # Find a matching transaction record, so we can use its
        # subtier agency information to match to (or create) an Award record
        awarding_cgac = row.get('agency_identifier')  # cgac from record's TAS
        txn = get_award_financial_transaction(
            awarding_cgac,
            piid=row.get('piid'),
            parent_award_id=row.get('parent_award_id'),
            fain=row.get('fain'),
            uri=row.get('uri'))
        if txn is not None:
            # We found a matching transaction, so grab its awarding agency
            # info and pass it get_or_create_summary_award
            awarding_agency = txn.awarding_agency
        else:
            # No matching transaction found, so find/create Award by using
            # topiter agency only, since CGAC code is the only piece of
            # awarding agency info that we have.
            awarding_agency = Agency.get_by_toptier(awarding_cgac)

        # Find the award that this award transaction belongs to. If it doesn't exist, create it.
        created, award = Award.get_or_create_summary_award(
            awarding_agency=awarding_agency,
            piid=row.get('piid'),
            fain=row.get('fain'),
            uri=row.get('uri'),
            parent_award_id=row.get('parent_award_id'),
            use_cache=False)

        award_financial_data = FinancialAccountsByAwards()

        value_map = {
            'award':
            award,
            'submission':
            submission_attributes,
            'reporting_period_start':
            submission_attributes.reporting_period_start,
            'reporting_period_end':
            submission_attributes.reporting_period_end,
            'treasury_account':
            treasury_account,
            'object_class':
            get_or_create_object_class(row['object_class'],
                                       row['by_direct_reimbursable_fun'],
                                       logger),
            'program_activity':
            get_or_create_program_activity(row, submission_attributes)
        }

        # Still using the cpe|fyb regex compiled above for reverse
        afd = load_data_into_model(award_financial_data,
                                   row,
                                   value_map=value_map,
                                   save=True,
                                   reverse=reverse)

    awards_cache.clear()
Esempio n. 8
0
def get_or_create_summary_award(awarding_agency=None,
                                piid=None,
                                fain=None,
                                uri=None,
                                parent_award_id=None,
                                save=True):
    """
    Given a set of award identifiers and awarding agency information,
    find a corresponding Award record. If we can't find one, create it.

    Returns:
        created: a list of new awards created, used to enable bulk insert
        summary_award: the summary award that the calling process can map to
    """
    # If an award transaction's ID is a piid, it's contract data
    # If the ID is fain or a uri, it's financial assistance. If the award transaction
    # has both a fain and a uri, include both.
    try:
        # Look for an existing award record

        # Check individual FILE C D linkage first
        lookup_kwargs = {'recipient_id__isnull': False}
        if piid is not None:
            lookup_kwargs['piid'] = piid
        if parent_award_id is not None:
            lookup_kwargs['parent_award__piid'] = parent_award_id
        if fain is not None:
            lookup_kwargs['fain'] = fain
        if uri is not None:
            lookup_kwargs['uri'] = uri

        award_queryset = Award.objects.filter(**lookup_kwargs)[:2]

        award_count = len(award_queryset)

        if award_count == 1:
            summary_award = award_queryset[0]
            return [], summary_award

        # if nothing found revert to looking for an award that this record could've already created
        lookup_kwargs = {"awarding_agency": awarding_agency}
        for i in [(piid, "piid"), (fain, "fain"), (uri, "uri")]:
            lookup_kwargs[i[1]] = i[0]
            if parent_award_id:
                # parent_award__piid
                lookup_kwargs["parent_award_piid"] = parent_award_id

        # Look for an existing award record
        summary_award = Award.objects \
            .filter(Q(**lookup_kwargs)) \
            .filter(awarding_agency=awarding_agency) \
            .first()
        if (summary_award is None and awarding_agency is not None
                and awarding_agency.toptier_agency.name !=
                awarding_agency.subtier_agency.name):
            # No award match found when searching by award id info +
            # awarding subtier agency. Relax the awarding agency
            # critera to just the toptier agency instead of the subtier
            # agency and try the search again.
            awarding_agency_toptier = Agency.get_by_toptier(
                awarding_agency.toptier_agency.cgac_code)

            summary_award = Award.objects \
                .filter(Q(**lookup_kwargs)) \
                .filter(awarding_agency=awarding_agency_toptier) \
                .first()

        if summary_award:
            return [], summary_award

        parent_created, parent_award = [], None

        # Now create the award record for this award transaction
        create_kwargs = {
            "awarding_agency": awarding_agency,
            "parent_award": parent_award,
            "parent_award_piid": parent_award_id
        }
        for i in [(piid, "piid"), (fain, "fain"), (uri, "uri")]:
            create_kwargs[i[1]] = i[0]
        summary_award = Award(**create_kwargs)
        created = [
            summary_award,
        ]
        created.extend(parent_created)

        if save:
            summary_award.save()

        return created, summary_award

    # Do not use bare except
    except ValueError:
        raise ValueError(
            'Unable to find or create an award with the provided information: '
            'piid={}, fain={}, uri={}, parent_id={}, awarding_agency={}'.
            format(piid, fain, uri, parent_award_id, awarding_agency))