-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
18 changed files
with
896 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,4 @@ | ||
[run] | ||
branch = True | ||
source = uw_hrp/ | ||
include = uw_hrp/* |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
sudo: false | ||
language: python | ||
python: | ||
- '2.7' | ||
- '3.4' | ||
- '3.5' | ||
- '3.6' | ||
before_script: | ||
- pip install -e . | ||
- pip install pep8 | ||
- pip install nose2 | ||
- pip install coverage | ||
- pip install commonconf | ||
- pip install python-coveralls | ||
script: | ||
- pep8 uw_hrp/ --exclude=uw_hrp/tests | ||
- coverage run --source=uw_hrp uw_hrp/test.py -v | ||
after_script: | ||
- coveralls |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
include uw_hrp/VERSION | ||
recursive-include uw_hrp * |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,5 @@ | ||
[![Build Status](https://api.travis-ci.org/uw-it-aca/uw-restclients-hrp.svg?branch=master)](https://travis-ci.org/uw-it-aca/uw-restclients-hrp) | ||
[![Coverage Status](https://coveralls.io/repos/uw-it-aca/uw-restclients-hrp/badge.png?branch=master)](https://coveralls.io/r/uw-it-aca/uw-restclients-hrp?branch=master) | ||
|
||
# uw-restclients-hrp | ||
REST client for the UW HR/Payroll Web Service |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,40 @@ | ||
import os | ||
from setuptools import setup | ||
|
||
README = """ | ||
See the README on `GitHub | ||
<https://github.com/uw-it-aca/uw-restclients-hrp>`_. | ||
""" | ||
|
||
# The VERSION file is created by travis-ci, based on the tag name | ||
version_path = 'uw_hrp/VERSION' | ||
VERSION = open(os.path.join(os.path.dirname(__file__), version_path)).read() | ||
VERSION = VERSION.replace("\n", "") | ||
|
||
# allow setup.py to be run from any path | ||
os.chdir(os.path.normpath(os.path.join(os.path.abspath(__file__), os.pardir))) | ||
|
||
setup( | ||
name='UW-RestClients-HRP', | ||
version=VERSION, | ||
packages=['uw_hrp'], | ||
author="UW-IT AXDD", | ||
author_email="aca-it@uw.edu", | ||
include_package_data=True, | ||
install_requires=['UW-RestClients-Core>0.8,<1.0', | ||
'UW-RestClients-PWS>=0.1,<1.0', | ||
'simplejson', | ||
], | ||
license='Apache License, Version 2.0', | ||
description=('A library for connecting to the UW Human Resources API'), | ||
long_description=README, | ||
url="https://github.com/uw-it-aca/uw-restclients-hrp", | ||
classifiers=[ | ||
'Intended Audience :: Developers', | ||
'License :: OSI Approved :: Apache Software License', | ||
'Operating System :: OS Independent', | ||
'Programming Language :: Python', | ||
'Programming Language :: Python :: 2.7', | ||
'Programming Language :: Python :: 3.4', | ||
], | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
[HRP] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
0.1 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
""" | ||
This is the interface for interacting with | ||
the hrp web service. | ||
""" | ||
|
||
import logging | ||
import json | ||
from uw_hrp.dao import HRP_DAO | ||
from restclients_core.exceptions import DataFailureException | ||
|
||
|
||
logger = logging.getLogger(__name__) | ||
|
||
|
||
def get_resource(url): | ||
response = HRP_DAO().getURL(url, {'Accept': 'application/json'}) | ||
logger.info("%s ==status==> %s" % (url, response.status)) | ||
|
||
if response.status != 200: | ||
raise DataFailureException(url, response.status, response.data) | ||
|
||
logger.debug("%s ==data==> %s" % (url, response.data)) | ||
return response.data |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,93 @@ | ||
""" | ||
This is the interface for interacting with the HRP Web Service. | ||
""" | ||
|
||
from datetime import datetime | ||
import logging | ||
import simplejson as json | ||
from restclients_core.exceptions import InvalidRegID, InvalidNetID,\ | ||
InvalidEmployeeID | ||
from uw_pws import PWS | ||
from uw_hrp.models import Appointment, Appointee | ||
from uw_hrp import get_resource | ||
|
||
|
||
URL_PREFIX = "/hrp/v1/appointee/" | ||
logger = logging.getLogger(__name__) | ||
|
||
|
||
def get_appointee_by_eid(employee_id): | ||
if not PWS().valid_employee_id(employee_id): | ||
raise InvalidEmployeeID(employee_id) | ||
return _get_appointee(employee_id) | ||
|
||
|
||
def get_appointee_by_netid(netid): | ||
if not PWS().valid_uwnetid(netid): | ||
raise InvalidNetID(netid) | ||
return _get_appointee(netid) | ||
|
||
|
||
def get_appointee_by_regid(regid): | ||
if not PWS().valid_uwregid(regid): | ||
raise InvalidRegID(regid) | ||
return _get_appointee(regid) | ||
|
||
|
||
def _get_appointee(id): | ||
""" | ||
Return a restclients.models.hrp.AppointeePerson object | ||
""" | ||
url = "%s%s.json" % (URL_PREFIX, id) | ||
response = get_resource(url) | ||
return process_json(response) | ||
|
||
|
||
def process_json(response_body): | ||
json_data = json.loads(response_body) | ||
person_data = json_data.get("Person") | ||
if not person_data: | ||
return None | ||
|
||
appointee = create_appointee(person_data) | ||
|
||
if json_data.get("Appointments"): | ||
apps = [] | ||
for app in json_data.get("Appointments"): | ||
if float(app.get("PayRate")) > 0.000: | ||
# only those currently having a salary | ||
apps.append(create_appointment(app)) | ||
appointee.appointments = apps | ||
return appointee | ||
|
||
|
||
def create_appointee(person): | ||
ap = Appointee() | ||
ap.netid = person.get("UWNetID") | ||
ap.regid = person.get("UWRegID") | ||
ap.employee_id = person.get("EmployeeID") | ||
ap.status = person.get("EmploymentStatus") | ||
ap.status_desc = person.get("EmploymentStatusDescription") | ||
ap.home_dept_budget_number = person.get("HomeDepartmentBudgetNumber") | ||
ap.home_dept_budget_name = person.get("HomeDepartmentBudgetName") | ||
ap.home_dept_org_code = person.get("HomeDepartmentOrganizationCode") | ||
ap.home_dept_org_name = person.get("HomeDepartmentOrganizationName") | ||
ap.onoff_campus_code = person.get("OnOffCampusCode") | ||
ap.onoff_campus_code_desc = person.get("OnOffCampusCodeDescription") | ||
return ap | ||
|
||
|
||
def create_appointment(appointment): | ||
app = Appointment() | ||
app.app_number = int(appointment.get("AppointmentNumber")) | ||
app.app_state = appointment.get("AppointmentState") | ||
app.dept_budget_name = appointment.get("DepartmentBudgetName") | ||
app.dept_budget_number = appointment.get("DepartmentBudgetNumber") | ||
app.job_class_code = appointment.get("JobClassCode") | ||
app.job_class_title = appointment.get("JobClassTitle") | ||
app.org_code = appointment.get("OrganizationCode") | ||
app.org_name = appointment.get("OrganizationName") | ||
app.paid_app_code = appointment.get("PaidAppointmentCode") | ||
app.status = appointment.get("Status") | ||
app.status_desc = appointment.get("StatusDescription") | ||
return app |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
import logging | ||
import os | ||
from os.path import abspath, dirname | ||
from restclients_core.dao import DAO | ||
|
||
|
||
class HRP_DAO(DAO): | ||
def service_name(self): | ||
return 'hrpws' | ||
|
||
def service_mock_paths(self): | ||
return [abspath(os.path.join(dirname(__file__), "resources"))] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,169 @@ | ||
from restclients_core import models | ||
|
||
|
||
class Appointment(models.Model): | ||
CURRENT_STATE = 'CURRENT' | ||
ACTIVE_STATUS = 'A' | ||
|
||
app_number = models.PositiveSmallIntegerField() | ||
app_state = models.CharField(max_length=16) | ||
dept_budget_name = models.CharField(max_length=96) | ||
dept_budget_number = models.CharField(max_length=16) | ||
job_class_code = models.CharField(max_length=16) | ||
job_class_title = models.CharField(max_length=96) | ||
org_code = models.CharField(max_length=16) | ||
org_name = models.CharField(max_length=96) | ||
paid_app_code = models.CharField(max_length=8) | ||
status = models.CharField(max_length=8) | ||
status_desc = models.CharField(max_length=16) | ||
|
||
def __cmp__(self, other): | ||
if other is not None: | ||
return self.app_number.__cmp__(other.app_number) | ||
|
||
def __lt__(self, other): | ||
return self.app_number < other.app_number | ||
|
||
def is_active_app_status(self): | ||
return self.status == Appointment.ACTIVE_STATUS | ||
|
||
def is_current_app_state(self): | ||
return self.app_state.upper() == Appointment.CURRENT_STATE | ||
|
||
def json_data(self): | ||
return { | ||
'app_number': self.app_number, | ||
'app_state': self.app_state, | ||
'dept_budget_name': self.dept_budget_name, | ||
'dept_budget_number': self.dept_budget_number, | ||
'job_class_code': self.job_class_code, | ||
'job_class_title': self.job_class_title, | ||
'org_code': self.org_code, | ||
'org_name': self.org_name, | ||
'paid_app_code': self.paid_app_code, | ||
'status': self.status, | ||
'status_desc': self.status_desc, | ||
} | ||
|
||
def __str__(self): | ||
return ("{%s: %s, %s: %s, %s: %s, %s: %s," + | ||
" %s: %s, %s: %s, %s: %s, %s: %s," | ||
" %s: %s, %s: %s, %s: %s}") % ( | ||
'app_number', self.app_number, | ||
'app_state', self.app_state, | ||
'dept_budget_name', self.dept_budget_name, | ||
'dept_budget_number', self.dept_budget_number, | ||
'job_class_code', self.job_class_code, | ||
'job_class_title', self.job_class_title, | ||
'org_code', self.org_code, | ||
'org_name', self.org_name, | ||
'paid_app_code', self.paid_app_code, | ||
'status', self.status, | ||
'status_desc', self.status_desc | ||
) | ||
|
||
class Meta: | ||
db_table = 'restclients_hrp_appointment' | ||
|
||
|
||
class Appointee(models.Model): | ||
# employment status codes | ||
STATUS_ACTIVE = "A" | ||
STATUS_RETIREE = "R" | ||
STATUS_SEPARATED = "S" | ||
|
||
# On Off Campus codes | ||
ON_SEATTLE_CAMPUS = "1" | ||
JOINT_CENTER_FOR_GRADUATE_STUDY = "3" | ||
FRIDAY_HARBOR_LABORATORIES = "4" | ||
REGIONAL_MEDICAL_LIBRARY = "6" | ||
COMPOSITE_LOCATIONS = "7" | ||
HARBORVIEW_MEDICAL_CENTER = "A" | ||
VETERANS_HOSPITAL = "B" | ||
US_PUBLIC_HEALTH_SERVICE_HOSPITAL = "C" | ||
CHILDRENS_ORTHOPEDIC_MEDICAL_CENTER = "D" | ||
FIRCREST_LABORATORY = "E" | ||
PROVIDENCE_MEDICAL_CENTER = "F" | ||
APPLIED_PHYSIC_LABORATORY = "G" | ||
PRIMATE_CENTER_SPECIAL_LOCATION = "H" | ||
ON_SEATTLE_CAMPUS_OTHER = "N" | ||
TACOMA_CAMPUS = "T" | ||
BOTHELL_WOODINVILLE_CAMPUS = "W" | ||
OFF_CAMPUS_ASSIGNMENT = "Y" | ||
OFF_CAMPUS_OTHER = "Z" | ||
|
||
# home_dept_org_code 1st digit" | ||
UW_SEATTLE = "2" | ||
MEDICAL_HEALTH_SCIENCES = "3" | ||
ADMIN_MANAGEMENT = "4" | ||
UW_BOTHELL = "5" | ||
UW_TACOMA = "6" | ||
|
||
netid = models.SlugField(max_length=32, | ||
db_index=True, | ||
unique=True) | ||
regid = models.CharField(max_length=32, | ||
db_index=True, | ||
unique=True) | ||
employee_id = models.CharField(max_length=9, | ||
db_index=True, | ||
unique=True) | ||
status = models.CharField(max_length=2) | ||
status_desc = models.CharField(max_length=16) | ||
home_dept_budget_number = models.CharField(max_length=16) | ||
home_dept_budget_name = models.CharField(max_length=96, | ||
null=True) | ||
home_dept_org_code = models.CharField(max_length=16) | ||
home_dept_org_name = models.CharField(max_length=96, | ||
null=True) | ||
onoff_campus_code = models.CharField(max_length=2) | ||
onoff_campus_code_desc = models.CharField(max_length=32) | ||
|
||
def __init__(self): | ||
self.appointments = [] | ||
|
||
def is_active_emp_status(self): | ||
return self.status == Appointee.STATUS_ACTIVE | ||
|
||
def json_data(self): | ||
apps = [] | ||
for app in self.appointments: | ||
apps.append(app.json_data()) | ||
|
||
return { | ||
"netid": self.netid, | ||
'regid': self.regid, | ||
'employee_id': self.employee_id, | ||
'status': self.status, | ||
'is_active': self.is_active_emp_status(), | ||
'status_desc': self.status_desc, | ||
'home_dept_budget_number': self.home_dept_budget_number, | ||
'home_dept_budget_name': self.home_dept_budget_name, | ||
'home_dept_org_code': self.home_dept_org_code, | ||
'home_dept_org_name': self.home_dept_org_name, | ||
'onoff_campus_code': self.onoff_campus_code, | ||
'onoff_campus_code_desc': self.onoff_campus_code_desc, | ||
'appointments': apps | ||
} | ||
|
||
def __str__(self): | ||
return ("{%s: %s, %s: %s, %s: %s, %s: %s," + | ||
" %s: %s, %s: %s, %s: %s, %s: %s," | ||
" %s: %s, %s: %s, %s: %s, %s: %s, %s: [%s]}") % ( | ||
"netid", self.netid, | ||
'regid', self.regid, | ||
'employee_id', self.employee_id, | ||
'status', self.status, | ||
'is_active', self.is_active_emp_status(), | ||
'status_desc', self.status_desc, | ||
'home_dept_budget_number', self.home_dept_budget_number, | ||
'home_dept_budget_name', self.home_dept_budget_name, | ||
'home_dept_org_code', self.home_dept_org_code, | ||
'home_dept_org_name', self.home_dept_org_name, | ||
'onoff_campus_code', self.onoff_campus_code, | ||
'onoff_campus_code_desc', self.onoff_campus_code_desc, | ||
'appointments', ','.join(map(str, self.appointments)) | ||
) | ||
|
||
class Meta: | ||
db_table = 'restclients_hrp_appointee' |
Oops, something went wrong.