mirror of
https://github.com/sartography/cr-connect-workflow.git
synced 2025-02-23 13:18:35 +00:00
commit
4c3b4db7b2
3
Pipfile
3
Pipfile
@ -39,13 +39,14 @@ requests = "*"
|
||||
sentry-sdk = {extras = ["flask"],version = "==0.14.4"}
|
||||
sphinx = "*"
|
||||
swagger-ui-bundle = "*"
|
||||
spiffworkflow = {git = "https://github.com/sartography/SpiffWorkflow.git", ref = "master"}
|
||||
spiffworkflow = {git = "https://github.com/sartography/SpiffWorkflow.git",ref = "master"}
|
||||
webtest = "*"
|
||||
werkzeug = "*"
|
||||
xlrd = "*"
|
||||
xlsxwriter = "*"
|
||||
pygithub = "*"
|
||||
python-box = "*"
|
||||
python-levenshtein = "*"
|
||||
|
||||
[requires]
|
||||
python_version = "3.8"
|
||||
|
9
Pipfile.lock
generated
9
Pipfile.lock
generated
@ -1,7 +1,7 @@
|
||||
{
|
||||
"_meta": {
|
||||
"hash": {
|
||||
"sha256": "81609b24d5be29db98b75d9d2597c20cee854a0ce6036fbd9b2dd58707852e3f"
|
||||
"sha256": "621d57ec513f24c665dd34e08ae5a19fc27784e87c55bb4d2a91a1d48a473081"
|
||||
},
|
||||
"pipfile-spec": 6,
|
||||
"requires": {
|
||||
@ -690,6 +690,13 @@
|
||||
],
|
||||
"version": "==1.0.4"
|
||||
},
|
||||
"python-levenshtein": {
|
||||
"hashes": [
|
||||
"sha256:033a11de5e3d19ea25c9302d11224e1a1898fe5abd23c61c7c360c25195e3eb1"
|
||||
],
|
||||
"index": "pypi",
|
||||
"version": "==0.12.0"
|
||||
},
|
||||
"pytz": {
|
||||
"hashes": [
|
||||
"sha256:a494d53b6d39c3c6e44c3bec237336e14305e4f29bbf800b599253057fbb79ed",
|
||||
|
@ -166,10 +166,12 @@ class LookupDataModel(db.Model):
|
||||
# query with:
|
||||
# search_results = LookupDataModel.query.filter(LookupDataModel.label.match("INTERNAL")).all()
|
||||
|
||||
__ts_vector__ = func.to_tsvector('simple', label)
|
||||
|
||||
__table_args__ = (
|
||||
Index(
|
||||
'ix_lookupdata_tsv',
|
||||
func.to_tsvector('simple', label), # Use simple, not english to keep stop words in place.
|
||||
__ts_vector__, # Use simple, not english to keep stop words in place.
|
||||
postgresql_using='gin'
|
||||
),
|
||||
)
|
||||
|
@ -1,19 +1,24 @@
|
||||
import copy
|
||||
|
||||
from flask import g
|
||||
|
||||
from crc import app
|
||||
from crc.api.common import ApiError
|
||||
from crc.scripts.script import Script
|
||||
from crc.services.ldap_service import LdapService
|
||||
from crc.services.user_service import UserService
|
||||
|
||||
|
||||
class Ldap(Script):
|
||||
"""This Script allows to be introduced as part of a workflow and called from there, taking
|
||||
a UID (or several) as input and looking it up through LDAP to return the person's details """
|
||||
a UID (or several) as input and looking it up through LDAP to return the person's details.
|
||||
If no user id is specified, returns information about the current user."""
|
||||
|
||||
def get_description(self):
|
||||
return """
|
||||
Attempts to create a dictionary with person details, using the
|
||||
provided argument (a UID) and look it up through LDAP.
|
||||
provided argument (a UID) and look it up through LDAP. If no UID is
|
||||
provided, then returns information about the current user.
|
||||
|
||||
Examples:
|
||||
supervisor_info = ldap(supervisor_uid) // Sets the supervisor information to ldap details for the given uid.
|
||||
@ -26,13 +31,15 @@ supervisor_info = ldap(supervisor_uid) // Sets the supervisor information to l
|
||||
return self.set_users_info_in_task(task, args)
|
||||
|
||||
def set_users_info_in_task(self, task, args):
|
||||
if len(args) != 1:
|
||||
raise ApiError(code="missing_argument",
|
||||
message="Ldap takes a single argument, the "
|
||||
"UID for the person we want to look up")
|
||||
uid = args[0]
|
||||
user_info_dict = {}
|
||||
|
||||
if len(args) > 1:
|
||||
raise ApiError(code="invalid_argument",
|
||||
message="Ldap takes at most one argument, the "
|
||||
"UID for the person we want to look up.")
|
||||
if len(args) < 1:
|
||||
if UserService.has_user():
|
||||
uid = UserService.current_user().uid
|
||||
else:
|
||||
uid = args[0]
|
||||
user_info = LdapService.user_info(uid)
|
||||
user_info_dict = {
|
||||
"display_name": user_info.display_name,
|
||||
|
@ -181,20 +181,22 @@ class LookupService(object):
|
||||
if len(query) > 0:
|
||||
if ' ' in query:
|
||||
terms = query.split(' ')
|
||||
new_terms = ["'%s'" % query]
|
||||
new_terms = []
|
||||
for t in terms:
|
||||
new_terms.append("%s:*" % t)
|
||||
new_query = ' | '.join(new_terms)
|
||||
new_query = ' & '.join(new_terms)
|
||||
new_query = "'%s' | %s" % (query, new_query)
|
||||
else:
|
||||
new_query = "%s:*" % query
|
||||
|
||||
# Run the full text query
|
||||
db_query = db_query.filter(LookupDataModel.label.match(new_query))
|
||||
# But hackishly order by like, which does a good job of
|
||||
# pulling more relevant matches to the top.
|
||||
db_query = db_query.filter(
|
||||
LookupDataModel.__ts_vector__.match(new_query, postgresql_regconfig='simple'))
|
||||
|
||||
# Hackishly order by like, which does a good job of pulling more relevant matches to the top.
|
||||
db_query = db_query.order_by(desc(LookupDataModel.label.like("%" + query + "%")))
|
||||
|
||||
logging.getLogger('sqlalchemy.engine').setLevel(logging.INFO)
|
||||
logging.info(db_query)
|
||||
result = db_query.limit(limit).all()
|
||||
logging.getLogger('sqlalchemy.engine').setLevel(logging.ERROR)
|
||||
return result
|
||||
|
@ -1,5 +1,5 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<bpmn:definitions xmlns:bpmn="http://www.omg.org/spec/BPMN/20100524/MODEL" xmlns:bpmndi="http://www.omg.org/spec/BPMN/20100524/DI" xmlns:dc="http://www.omg.org/spec/DD/20100524/DC" xmlns:camunda="http://camunda.org/schema/1.0/bpmn" xmlns:di="http://www.omg.org/spec/DD/20100524/DI" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" id="Definitions_06pyjz2" targetNamespace="http://bpmn.io/schema/bpmn" exporter="Camunda Modeler" exporterVersion="4.0.0">
|
||||
<bpmn:definitions xmlns:bpmn="http://www.omg.org/spec/BPMN/20100524/MODEL" xmlns:bpmndi="http://www.omg.org/spec/BPMN/20100524/DI" xmlns:dc="http://www.omg.org/spec/DD/20100524/DC" xmlns:camunda="http://camunda.org/schema/1.0/bpmn" xmlns:di="http://www.omg.org/spec/DD/20100524/DI" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" id="Definitions_06pyjz2" targetNamespace="http://bpmn.io/schema/bpmn" exporter="Camunda Modeler" exporterVersion="3.7.0">
|
||||
<bpmn:process id="Process_01143nb" isExecutable="true">
|
||||
<bpmn:startEvent id="StartEvent_1">
|
||||
<bpmn:outgoing>Flow_0kcrx5l</bpmn:outgoing>
|
||||
@ -27,7 +27,7 @@
|
||||
#### {{ pi.PI.display_name }}
|
||||
##### Title: {{ pi.PI.title }}
|
||||
|
||||
##### Department: {{ PI_department }}
|
||||
##### Department: {{ pi.PI.department }}
|
||||
##### Affiliation: {{ pi.PI.affiliation }}</bpmn:documentation>
|
||||
<bpmn:extensionElements>
|
||||
<camunda:formData>
|
||||
@ -43,23 +43,24 @@
|
||||
<camunda:property name="display_name" value="pi.PI.label" />
|
||||
</camunda:properties>
|
||||
</bpmn:extensionElements>
|
||||
<bpmn:incoming>Flow_07f7kkd</bpmn:incoming>
|
||||
<bpmn:incoming>Flow_147b9li</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_1mplloa</bpmn:outgoing>
|
||||
</bpmn:userTask>
|
||||
<bpmn:sequenceFlow id="Flow_0kcrx5l" sourceRef="StartEvent_1" targetRef="ScriptTask_LoadPersonnel" />
|
||||
<bpmn:sequenceFlow id="Flow_1mplloa" sourceRef="Activity_EditPI" targetRef="Activity_0r8pam5" />
|
||||
<bpmn:sequenceFlow id="Flow_1dcsioh" sourceRef="ScriptTask_LoadPersonnel" targetRef="Activity_0bg56lv" />
|
||||
<bpmn:sequenceFlow id="Flow_17uqguj" sourceRef="Activity_0bg56lv" targetRef="Gateway_CheckForPI" />
|
||||
<bpmn:scriptTask id="Activity_0bg56lv" name="Check for PI">
|
||||
<bpmn:incoming>Flow_1dcsioh</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_1vgepkq</bpmn:outgoing>
|
||||
<bpmn:outgoing>Flow_17uqguj</bpmn:outgoing>
|
||||
<bpmn:script>pi = {x:investigators[x] for x in investigators.keys() if x[:2] == 'PI'}</bpmn:script>
|
||||
</bpmn:scriptTask>
|
||||
<bpmn:exclusiveGateway id="Gateway_CheckForPI" name="PI Cnt">
|
||||
<bpmn:incoming>Flow_1vgepkq</bpmn:incoming>
|
||||
<bpmn:incoming>Flow_17uqguj</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_147b9li</bpmn:outgoing>
|
||||
<bpmn:outgoing>Flow_00prawo</bpmn:outgoing>
|
||||
</bpmn:exclusiveGateway>
|
||||
<bpmn:sequenceFlow id="Flow_147b9li" name="1 PI from PB" sourceRef="Gateway_CheckForPI" targetRef="Activity_DeterminePI_Department">
|
||||
<bpmn:sequenceFlow id="Flow_147b9li" name="1 PI from PB" sourceRef="Gateway_CheckForPI" targetRef="Activity_EditPI">
|
||||
<bpmn:conditionExpression xsi:type="bpmn:tFormalExpression">len(pi.keys()) == 1</bpmn:conditionExpression>
|
||||
</bpmn:sequenceFlow>
|
||||
<bpmn:sequenceFlow id="Flow_00prawo" name="No PI from PB" sourceRef="Gateway_CheckForPI" targetRef="Activity_1qwzwyi">
|
||||
@ -92,122 +93,80 @@
|
||||
##### Title: {{ sc.title }}
|
||||
|
||||
|
||||
|
||||
|
||||
##### Department: {{ sc.department }}
|
||||
##### Affiliation: {{ sc.affiliation }}</bpmn:documentation>
|
||||
<bpmn:extensionElements>
|
||||
<camunda:formData>
|
||||
<camunda:formField id="sc.access" label="Should this Study Coordinator have full editing access in the system?" type="boolean" defaultValue="true" />
|
||||
<camunda:formField id="sc.emails" label="Should this Study Coordinator receive automated email notifications?" type="boolean" defaultValue="true" />
|
||||
<camunda:formField id="sc.access" label="Should this Study Coordinator have full editing access in the system?" type="boolean" />
|
||||
<camunda:formField id="sc.emails" label="Should this Study Coordinator receive automated email notifications?" type="boolean" defaultValue="yes" />
|
||||
</camunda:formData>
|
||||
<camunda:properties>
|
||||
<camunda:property name="display_name" value="sc.label" />
|
||||
</camunda:properties>
|
||||
</bpmn:extensionElements>
|
||||
<bpmn:incoming>Flow_0xifvai</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_1n0k4pd</bpmn:outgoing>
|
||||
<bpmn:multiInstanceLoopCharacteristics isSequential="true" camunda:collection="scs" camunda:elementVariable="sc" />
|
||||
<bpmn:multiInstanceLoopCharacteristics camunda:collection="scs" camunda:elementVariable="sc" />
|
||||
</bpmn:userTask>
|
||||
<bpmn:sequenceFlow id="Flow_1oqem42" name="No Study Coordinators" sourceRef="Gateway_0jykh6r" targetRef="EndEvent_1qor16n">
|
||||
<bpmn:conditionExpression xsi:type="bpmn:tFormalExpression">len(scs.keys()) == 0</bpmn:conditionExpression>
|
||||
</bpmn:sequenceFlow>
|
||||
<bpmn:sequenceFlow id="Flow_14ti38o" sourceRef="Activity_1qwzwyi" targetRef="Activity_0r8pam5" />
|
||||
<bpmn:scriptTask id="Activity_DeterminePI_Department" name="Determine PI E0 Department">
|
||||
<bpmn:incoming>Flow_147b9li</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_1grahhv</bpmn:outgoing>
|
||||
<bpmn:script>LDAP_dept = pi.PI.department
|
||||
length_LDAP_dept = len(LDAP_dept)
|
||||
E0_start = LDAP_dept.find("E0:") + 3
|
||||
E0_slice = LDAP_dept[E0_start:length_LDAP_dept]
|
||||
E0_first_hyphen = E0_slice.find("-")
|
||||
E0_dept_start = E0_first_hyphen + 1
|
||||
E0_school = E0_slice[0:E0_first_hyphen]
|
||||
isSpace = " " in E0_slice
|
||||
E0_spec = ""
|
||||
E0_dept = ""
|
||||
|
||||
if isSpace:
|
||||
E0_first_space = E0_slice.find(" ")
|
||||
E0_spec_start = E0_first_space + 1
|
||||
E0_spec_end = len(E0_slice)
|
||||
E0_dept = E0_slice[E0_dept_start:E0_first_space]
|
||||
E0_spec = E0_slice[E0_spec_start:E0_spec_end]
|
||||
</bpmn:script>
|
||||
</bpmn:scriptTask>
|
||||
<bpmn:sequenceFlow id="Flow_1vgepkq" sourceRef="Activity_0bg56lv" targetRef="Gateway_CheckForPI" />
|
||||
<bpmn:sequenceFlow id="Flow_1grahhv" sourceRef="Activity_DeterminePI_Department" targetRef="Activity_1aeas6q" />
|
||||
<bpmn:sequenceFlow id="Flow_07f7kkd" sourceRef="Activity_1aeas6q" targetRef="Activity_EditPI" />
|
||||
<bpmn:businessRuleTask id="Activity_1aeas6q" name="Determine PI Department" camunda:decisionRef="Decision_PI_Dept">
|
||||
<bpmn:incoming>Flow_1grahhv</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_07f7kkd</bpmn:outgoing>
|
||||
</bpmn:businessRuleTask>
|
||||
</bpmn:process>
|
||||
<bpmndi:BPMNDiagram id="BPMNDiagram_1">
|
||||
<bpmndi:BPMNPlane id="BPMNPlane_1" bpmnElement="Process_01143nb">
|
||||
<bpmndi:BPMNEdge id="Flow_07f7kkd_di" bpmnElement="Flow_07f7kkd">
|
||||
<di:waypoint x="990" y="120" />
|
||||
<di:waypoint x="1130" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1grahhv_di" bpmnElement="Flow_1grahhv">
|
||||
<di:waypoint x="830" y="120" />
|
||||
<di:waypoint x="890" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1vgepkq_di" bpmnElement="Flow_1vgepkq">
|
||||
<di:waypoint x="500" y="120" />
|
||||
<di:waypoint x="565" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_14ti38o_di" bpmnElement="Flow_14ti38o">
|
||||
<di:waypoint x="1230" y="240" />
|
||||
<di:waypoint x="1340" y="240" />
|
||||
<di:waypoint x="1340" y="160" />
|
||||
<di:waypoint x="800" y="240" />
|
||||
<di:waypoint x="910" y="240" />
|
||||
<di:waypoint x="910" y="160" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1oqem42_di" bpmnElement="Flow_1oqem42">
|
||||
<di:waypoint x="1480" y="145" />
|
||||
<di:waypoint x="1480" y="270" />
|
||||
<di:waypoint x="1830" y="270" />
|
||||
<di:waypoint x="1830" y="138" />
|
||||
<di:waypoint x="1050" y="145" />
|
||||
<di:waypoint x="1050" y="270" />
|
||||
<di:waypoint x="1400" y="270" />
|
||||
<di:waypoint x="1400" y="138" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="1625" y="236" width="64" height="27" />
|
||||
<dc:Bounds x="1195" y="236" width="64" height="27" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1n0k4pd_di" bpmnElement="Flow_1n0k4pd">
|
||||
<di:waypoint x="1720" y="120" />
|
||||
<di:waypoint x="1812" y="120" />
|
||||
<di:waypoint x="1290" y="120" />
|
||||
<di:waypoint x="1382" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_0xifvai_di" bpmnElement="Flow_0xifvai">
|
||||
<di:waypoint x="1505" y="120" />
|
||||
<di:waypoint x="1620" y="120" />
|
||||
<di:waypoint x="1075" y="120" />
|
||||
<di:waypoint x="1190" y="120" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="1510" y="86" width="79" height="27" />
|
||||
<dc:Bounds x="1080" y="86" width="79" height="27" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_0elbjpd_di" bpmnElement="Flow_0elbjpd">
|
||||
<di:waypoint x="1390" y="120" />
|
||||
<di:waypoint x="1455" y="120" />
|
||||
<di:waypoint x="960" y="120" />
|
||||
<di:waypoint x="1025" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_00prawo_di" bpmnElement="Flow_00prawo">
|
||||
<di:waypoint x="590" y="145" />
|
||||
<di:waypoint x="590" y="240" />
|
||||
<di:waypoint x="1130" y="240" />
|
||||
<di:waypoint x="570" y="145" />
|
||||
<di:waypoint x="570" y="240" />
|
||||
<di:waypoint x="700" y="240" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="688" y="222" width="71" height="14" />
|
||||
<dc:Bounds x="590" y="222" width="71" height="14" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_147b9li_di" bpmnElement="Flow_147b9li">
|
||||
<di:waypoint x="615" y="120" />
|
||||
<di:waypoint x="730" y="120" />
|
||||
<di:waypoint x="595" y="120" />
|
||||
<di:waypoint x="700" y="120" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="615" y="103" width="63" height="14" />
|
||||
<dc:Bounds x="608" y="102" width="63" height="14" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_17uqguj_di" bpmnElement="Flow_17uqguj">
|
||||
<di:waypoint x="500" y="120" />
|
||||
<di:waypoint x="545" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1dcsioh_di" bpmnElement="Flow_1dcsioh">
|
||||
<di:waypoint x="350" y="120" />
|
||||
<di:waypoint x="400" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1mplloa_di" bpmnElement="Flow_1mplloa">
|
||||
<di:waypoint x="1230" y="120" />
|
||||
<di:waypoint x="1290" y="120" />
|
||||
<di:waypoint x="800" y="120" />
|
||||
<di:waypoint x="860" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_0kcrx5l_di" bpmnElement="Flow_0kcrx5l">
|
||||
<di:waypoint x="188" y="120" />
|
||||
@ -220,37 +179,31 @@ if isSpace:
|
||||
<dc:Bounds x="250" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="EndEvent_1qor16n_di" bpmnElement="EndEvent_1qor16n">
|
||||
<dc:Bounds x="1812" y="102" width="36" height="36" />
|
||||
<dc:Bounds x="1382" y="102" width="36" height="36" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_0d622qi_di" bpmnElement="Activity_EditPI">
|
||||
<dc:Bounds x="1130" y="80" width="100" height="80" />
|
||||
<dc:Bounds x="700" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_1dq6tzx_di" bpmnElement="Activity_0bg56lv">
|
||||
<dc:Bounds x="400" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Gateway_0qzf1r3_di" bpmnElement="Gateway_CheckForPI" isMarkerVisible="true">
|
||||
<dc:Bounds x="565" y="95" width="50" height="50" />
|
||||
<dc:Bounds x="545" y="95" width="50" height="50" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="574" y="71" width="31" height="14" />
|
||||
<dc:Bounds x="554" y="71" width="31" height="14" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_0neg931_di" bpmnElement="Activity_1qwzwyi">
|
||||
<dc:Bounds x="1130" y="200" width="100" height="80" />
|
||||
<dc:Bounds x="700" y="200" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_1ktvk27_di" bpmnElement="Activity_0r8pam5">
|
||||
<dc:Bounds x="1290" y="80" width="100" height="80" />
|
||||
<dc:Bounds x="860" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Gateway_0jykh6r_di" bpmnElement="Gateway_0jykh6r" isMarkerVisible="true">
|
||||
<dc:Bounds x="1455" y="95" width="50" height="50" />
|
||||
<dc:Bounds x="1025" y="95" width="50" height="50" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_1nz85vv_di" bpmnElement="Activity_1bcnjyq">
|
||||
<dc:Bounds x="1620" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_1z05bvn_di" bpmnElement="Activity_DeterminePI_Department">
|
||||
<dc:Bounds x="730" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_0uz6yhu_di" bpmnElement="Activity_1aeas6q">
|
||||
<dc:Bounds x="890" y="80" width="100" height="80" />
|
||||
<dc:Bounds x="1190" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
</bpmndi:BPMNPlane>
|
||||
</bpmndi:BPMNDiagram>
|
||||
|
Binary file not shown.
206
tests/data/irb_api_personnel/irb_api_personnel.bpmn
Normal file
206
tests/data/irb_api_personnel/irb_api_personnel.bpmn
Normal file
@ -0,0 +1,206 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<bpmn:definitions xmlns:bpmn="http://www.omg.org/spec/BPMN/20100524/MODEL" xmlns:bpmndi="http://www.omg.org/spec/BPMN/20100524/DI" xmlns:dc="http://www.omg.org/spec/DD/20100524/DC" xmlns:camunda="http://camunda.org/schema/1.0/bpmn" xmlns:di="http://www.omg.org/spec/DD/20100524/DI" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" id="Definitions_06pyjz2" targetNamespace="http://bpmn.io/schema/bpmn" exporter="Camunda Modeler" exporterVersion="3.7.0">
|
||||
<bpmn:process id="Process_01143nb" isExecutable="true">
|
||||
<bpmn:startEvent id="StartEvent_1">
|
||||
<bpmn:outgoing>Flow_0kcrx5l</bpmn:outgoing>
|
||||
</bpmn:startEvent>
|
||||
<bpmn:scriptTask id="ScriptTask_LoadPersonnel" name="Load IRB Personnel">
|
||||
<bpmn:incoming>Flow_0kcrx5l</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_1dcsioh</bpmn:outgoing>
|
||||
<bpmn:script>investigators = study_info('investigators')</bpmn:script>
|
||||
</bpmn:scriptTask>
|
||||
<bpmn:endEvent id="EndEvent_1qor16n">
|
||||
<bpmn:documentation>## The following information was gathered:
|
||||
{% if pi|length == 1 %}
|
||||
### PI: {{ pi.PI.display_name }}
|
||||
* Edit Acess? {{ pi.edit_access }}
|
||||
* Send Emails? {{ pi.emails }}
|
||||
* Experience: {{ pi.experience }}
|
||||
{% else %}
|
||||
### No PI in PB
|
||||
{% endif %}</bpmn:documentation>
|
||||
<bpmn:incoming>Flow_1n0k4pd</bpmn:incoming>
|
||||
<bpmn:incoming>Flow_1oqem42</bpmn:incoming>
|
||||
</bpmn:endEvent>
|
||||
<bpmn:userTask id="Activity_EditPI" name="Update PI Info" camunda:formKey="PI_AccessEmailsExperience">
|
||||
<bpmn:documentation>### Please provide supplemental information for:
|
||||
#### {{ pi.PI.display_name }}
|
||||
##### Title: {{ pi.PI.title }}
|
||||
|
||||
##### Department: {{ pi.PI.department }}
|
||||
##### Affiliation: {{ pi.PI.affiliation }}</bpmn:documentation>
|
||||
<bpmn:extensionElements>
|
||||
<camunda:formData>
|
||||
<camunda:formField id="pi.edit_access" label="Should the Principal Investigator have full editing access in the system?" type="boolean" defaultValue="true" />
|
||||
<camunda:formField id="pi.emails" label="Should the Principal Investigator receive automated email notifications?" type="boolean" defaultValue="true" />
|
||||
<camunda:formField id="pi.experience" label="Investigator's Experience" type="textarea">
|
||||
<camunda:properties>
|
||||
<camunda:property id="rows" value="5" />
|
||||
</camunda:properties>
|
||||
</camunda:formField>
|
||||
</camunda:formData>
|
||||
<camunda:properties>
|
||||
<camunda:property name="display_name" value="pi.PI.label" />
|
||||
</camunda:properties>
|
||||
</bpmn:extensionElements>
|
||||
<bpmn:incoming>Flow_147b9li</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_1mplloa</bpmn:outgoing>
|
||||
</bpmn:userTask>
|
||||
<bpmn:sequenceFlow id="Flow_0kcrx5l" sourceRef="StartEvent_1" targetRef="ScriptTask_LoadPersonnel" />
|
||||
<bpmn:sequenceFlow id="Flow_1mplloa" sourceRef="Activity_EditPI" targetRef="Activity_0r8pam5" />
|
||||
<bpmn:sequenceFlow id="Flow_1dcsioh" sourceRef="ScriptTask_LoadPersonnel" targetRef="Activity_0bg56lv" />
|
||||
<bpmn:sequenceFlow id="Flow_17uqguj" sourceRef="Activity_0bg56lv" targetRef="Gateway_CheckForPI" />
|
||||
<bpmn:scriptTask id="Activity_0bg56lv" name="Check for PI">
|
||||
<bpmn:incoming>Flow_1dcsioh</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_17uqguj</bpmn:outgoing>
|
||||
<bpmn:script>pi = {x:investigators[x] for x in investigators.keys() if x[:2] == 'PI'}</bpmn:script>
|
||||
</bpmn:scriptTask>
|
||||
<bpmn:exclusiveGateway id="Gateway_CheckForPI" name="PI Cnt" default="Flow_147b9li">
|
||||
<bpmn:incoming>Flow_17uqguj</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_147b9li</bpmn:outgoing>
|
||||
<bpmn:outgoing>Flow_00prawo</bpmn:outgoing>
|
||||
</bpmn:exclusiveGateway>
|
||||
<bpmn:sequenceFlow id="Flow_147b9li" name="1 PI from PB" sourceRef="Gateway_CheckForPI" targetRef="Activity_EditPI" />
|
||||
<bpmn:sequenceFlow id="Flow_00prawo" name="No PI from PB" sourceRef="Gateway_CheckForPI" targetRef="Activity_1qwzwyi">
|
||||
<bpmn:conditionExpression xsi:type="bpmn:tFormalExpression">len(pi.keys()) == 0</bpmn:conditionExpression>
|
||||
</bpmn:sequenceFlow>
|
||||
<bpmn:manualTask id="Activity_1qwzwyi" name="Show No PI">
|
||||
<bpmn:documentation>No PI entered in PB</bpmn:documentation>
|
||||
<bpmn:incoming>Flow_00prawo</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_14ti38o</bpmn:outgoing>
|
||||
</bpmn:manualTask>
|
||||
<bpmn:sequenceFlow id="Flow_0elbjpd" sourceRef="Activity_0r8pam5" targetRef="Gateway_0jykh6r" />
|
||||
<bpmn:scriptTask id="Activity_0r8pam5" name="Check for Study Coordinators">
|
||||
<bpmn:incoming>Flow_1mplloa</bpmn:incoming>
|
||||
<bpmn:incoming>Flow_14ti38o</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_0elbjpd</bpmn:outgoing>
|
||||
<bpmn:script>scs = {x:investigators[x] for x in investigators.keys() if x[:3] == 'SC_'}</bpmn:script>
|
||||
</bpmn:scriptTask>
|
||||
<bpmn:exclusiveGateway id="Gateway_0jykh6r" default="Flow_0xifvai">
|
||||
<bpmn:incoming>Flow_0elbjpd</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_0xifvai</bpmn:outgoing>
|
||||
<bpmn:outgoing>Flow_1oqem42</bpmn:outgoing>
|
||||
</bpmn:exclusiveGateway>
|
||||
<bpmn:sequenceFlow id="Flow_0xifvai" name="1 or more Study Coordinators" sourceRef="Gateway_0jykh6r" targetRef="Activity_1bcnjyq" />
|
||||
<bpmn:sequenceFlow id="Flow_1n0k4pd" sourceRef="Activity_1bcnjyq" targetRef="EndEvent_1qor16n" />
|
||||
<bpmn:userTask id="Activity_1bcnjyq" name="Update SC Info" camunda:formKey="SC_AccessEmails">
|
||||
<bpmn:documentation>### Please provide supplemental information for:
|
||||
#### {{ sc.display_name }}
|
||||
##### Title: {{ sc.title }}
|
||||
|
||||
|
||||
##### Department: {{ sc.department }}
|
||||
##### Affiliation: {{ sc.affiliation }}</bpmn:documentation>
|
||||
<bpmn:extensionElements>
|
||||
<camunda:formData>
|
||||
<camunda:formField id="sc.access" label="Should this Study Coordinator have full editing access in the system?" type="boolean" />
|
||||
<camunda:formField id="sc.emails" label="Should this Study Coordinator receive automated email notifications?" type="boolean" defaultValue="yes" />
|
||||
</camunda:formData>
|
||||
</bpmn:extensionElements>
|
||||
<bpmn:incoming>Flow_0xifvai</bpmn:incoming>
|
||||
<bpmn:outgoing>Flow_1n0k4pd</bpmn:outgoing>
|
||||
<bpmn:multiInstanceLoopCharacteristics camunda:collection="scs" camunda:elementVariable="sc" />
|
||||
</bpmn:userTask>
|
||||
<bpmn:sequenceFlow id="Flow_1oqem42" name="No Study Coordinators" sourceRef="Gateway_0jykh6r" targetRef="EndEvent_1qor16n">
|
||||
<bpmn:conditionExpression xsi:type="bpmn:tFormalExpression">len(scs.keys()) == 0</bpmn:conditionExpression>
|
||||
</bpmn:sequenceFlow>
|
||||
<bpmn:sequenceFlow id="Flow_14ti38o" sourceRef="Activity_1qwzwyi" targetRef="Activity_0r8pam5" />
|
||||
</bpmn:process>
|
||||
<bpmndi:BPMNDiagram id="BPMNDiagram_1">
|
||||
<bpmndi:BPMNPlane id="BPMNPlane_1" bpmnElement="Process_01143nb">
|
||||
<bpmndi:BPMNEdge id="Flow_14ti38o_di" bpmnElement="Flow_14ti38o">
|
||||
<di:waypoint x="800" y="240" />
|
||||
<di:waypoint x="910" y="240" />
|
||||
<di:waypoint x="910" y="160" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1oqem42_di" bpmnElement="Flow_1oqem42">
|
||||
<di:waypoint x="1050" y="145" />
|
||||
<di:waypoint x="1050" y="270" />
|
||||
<di:waypoint x="1400" y="270" />
|
||||
<di:waypoint x="1400" y="138" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="1195" y="236" width="64" height="27" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1n0k4pd_di" bpmnElement="Flow_1n0k4pd">
|
||||
<di:waypoint x="1290" y="120" />
|
||||
<di:waypoint x="1382" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_0xifvai_di" bpmnElement="Flow_0xifvai">
|
||||
<di:waypoint x="1075" y="120" />
|
||||
<di:waypoint x="1190" y="120" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="1080" y="86" width="79" height="27" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_0elbjpd_di" bpmnElement="Flow_0elbjpd">
|
||||
<di:waypoint x="960" y="120" />
|
||||
<di:waypoint x="1025" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_00prawo_di" bpmnElement="Flow_00prawo">
|
||||
<di:waypoint x="570" y="145" />
|
||||
<di:waypoint x="570" y="240" />
|
||||
<di:waypoint x="700" y="240" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="590" y="222" width="71" height="14" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_147b9li_di" bpmnElement="Flow_147b9li">
|
||||
<di:waypoint x="595" y="120" />
|
||||
<di:waypoint x="700" y="120" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="608" y="102" width="63" height="14" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_17uqguj_di" bpmnElement="Flow_17uqguj">
|
||||
<di:waypoint x="500" y="120" />
|
||||
<di:waypoint x="545" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1dcsioh_di" bpmnElement="Flow_1dcsioh">
|
||||
<di:waypoint x="350" y="120" />
|
||||
<di:waypoint x="400" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_1mplloa_di" bpmnElement="Flow_1mplloa">
|
||||
<di:waypoint x="800" y="120" />
|
||||
<di:waypoint x="860" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNEdge id="Flow_0kcrx5l_di" bpmnElement="Flow_0kcrx5l">
|
||||
<di:waypoint x="188" y="120" />
|
||||
<di:waypoint x="250" y="120" />
|
||||
</bpmndi:BPMNEdge>
|
||||
<bpmndi:BPMNShape id="_BPMNShape_StartEvent_2" bpmnElement="StartEvent_1">
|
||||
<dc:Bounds x="152" y="102" width="36" height="36" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="ScriptTask_0h49cmf_di" bpmnElement="ScriptTask_LoadPersonnel">
|
||||
<dc:Bounds x="250" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="EndEvent_1qor16n_di" bpmnElement="EndEvent_1qor16n">
|
||||
<dc:Bounds x="1382" y="102" width="36" height="36" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_0d622qi_di" bpmnElement="Activity_EditPI">
|
||||
<dc:Bounds x="700" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_1dq6tzx_di" bpmnElement="Activity_0bg56lv">
|
||||
<dc:Bounds x="400" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Gateway_0qzf1r3_di" bpmnElement="Gateway_CheckForPI" isMarkerVisible="true">
|
||||
<dc:Bounds x="545" y="95" width="50" height="50" />
|
||||
<bpmndi:BPMNLabel>
|
||||
<dc:Bounds x="554" y="71" width="31" height="14" />
|
||||
</bpmndi:BPMNLabel>
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_0neg931_di" bpmnElement="Activity_1qwzwyi">
|
||||
<dc:Bounds x="700" y="200" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_1ktvk27_di" bpmnElement="Activity_0r8pam5">
|
||||
<dc:Bounds x="860" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Gateway_0jykh6r_di" bpmnElement="Gateway_0jykh6r" isMarkerVisible="true">
|
||||
<dc:Bounds x="1025" y="95" width="50" height="50" />
|
||||
</bpmndi:BPMNShape>
|
||||
<bpmndi:BPMNShape id="Activity_1nz85vv_di" bpmnElement="Activity_1bcnjyq">
|
||||
<dc:Bounds x="1190" y="80" width="100" height="80" />
|
||||
</bpmndi:BPMNShape>
|
||||
</bpmndi:BPMNPlane>
|
||||
</bpmndi:BPMNDiagram>
|
||||
</bpmn:definitions>
|
@ -1,9 +1,12 @@
|
||||
from flask import g
|
||||
|
||||
from tests.base_test import BaseTest
|
||||
|
||||
from crc import db
|
||||
from crc.models.user import UserModel
|
||||
from crc.services.workflow_processor import WorkflowProcessor
|
||||
from crc.scripts.ldap import Ldap
|
||||
from crc.api.common import ApiError
|
||||
from crc import db, mail
|
||||
|
||||
|
||||
class TestLdapLookupScript(BaseTest):
|
||||
@ -44,6 +47,19 @@ class TestLdapLookupScript(BaseTest):
|
||||
with(self.assertRaises(ApiError)):
|
||||
user_details = script.do_task(task, workflow.study_id, workflow.id, "PIComputingID")
|
||||
|
||||
def test_get_current_user_details(self):
|
||||
self.load_example_data()
|
||||
self.create_reference_document()
|
||||
workflow = self.create_workflow('empty_workflow')
|
||||
processor = WorkflowProcessor(workflow)
|
||||
task = processor.next_task()
|
||||
|
||||
script = Ldap()
|
||||
g.user = db.session.query(UserModel).filter(UserModel.uid=='dhf8r').first()
|
||||
user_details = script.do_task(task, workflow.study_id, workflow.id)
|
||||
self.assertEqual(user_details['display_name'], 'Dan Funk')
|
||||
|
||||
|
||||
|
||||
def test_bpmn_task_receives_user_details(self):
|
||||
workflow = self.create_workflow('ldap_replace')
|
||||
|
@ -114,11 +114,11 @@ class TestLookupService(BaseTest):
|
||||
self.assertEqual("Genetics Savings & Clone, Inc.", results[0].label)
|
||||
|
||||
results = LookupService.lookup(workflow, "AllTheNames", "reaction design", limit=10)
|
||||
self.assertEqual(5, len(results), "all results come back for two terms.")
|
||||
self.assertEqual(3, len(results), "all results come back for two terms.")
|
||||
self.assertEqual("Reaction Design", results[0].label, "Exact matches come first.")
|
||||
|
||||
results = LookupService.lookup(workflow, "AllTheNames", "1 Something", limit=10)
|
||||
self.assertEqual("1 Something", results[0].label, "Exact matches are prefered")
|
||||
self.assertEqual("1 Something", results[0].label, "Exact matches are preferred")
|
||||
|
||||
results = LookupService.lookup(workflow, "AllTheNames", "1 (!-Something", limit=10)
|
||||
self.assertEqual("1 Something", results[0].label, "special characters don't flake out")
|
||||
@ -126,16 +126,12 @@ class TestLookupService(BaseTest):
|
||||
results = LookupService.lookup(workflow, "AllTheNames", "1 Something", limit=10)
|
||||
self.assertEqual("1 Something", results[0].label, "double spaces should not be an issue.")
|
||||
|
||||
results = LookupService.lookup(workflow, "AllTheNames", "in", limit=10)
|
||||
self.assertEqual(10, len(results), "stop words are not removed.")
|
||||
self.assertEqual("Genetics Savings & Clone, Inc.", results[0].label)
|
||||
|
||||
results = LookupService.lookup(workflow, "AllTheNames", "other", limit=10)
|
||||
self.assertEqual("Other", results[0].label, "Can't find the word 'other', which is an english stop word")
|
||||
|
||||
|
||||
# 1018 10000 Something Industry
|
||||
# 1019 1000 Something Industry
|
||||
# 1020 1 Something Industry
|
||||
# 1021 10 Something Industry
|
||||
# 1022 10000 Something Industry
|
||||
|
||||
# Fixme: Stop words are taken into account on the query side, and haven't found a fix yet.
|
||||
#results = WorkflowService.run_lookup_query(lookup_table.id, "in", limit=10)
|
||||
#self.assertEqual(7, len(results), "stop words are not removed.")
|
||||
#self.assertEqual("Genetics Savings & Clone, Inc.", results[0].label)
|
||||
|
||||
|
@ -38,6 +38,27 @@ class TestWorkflowProcessorMultiInstance(BaseTest):
|
||||
workflow_model = StudyService._create_workflow_model(study_model, spec_model)
|
||||
return WorkflowProcessor(workflow_model)
|
||||
|
||||
|
||||
@patch('crc.services.study_service.StudyService.get_investigators')
|
||||
def test_load_irb_from_db(self, mock_study_service):
|
||||
# This depends on getting a list of investigators back from the protocol builder.
|
||||
mock_study_service.return_value = self.mock_investigator_response
|
||||
|
||||
self.load_example_data()
|
||||
workflow_spec_model = self.create_workflow("irb_api_personnel")
|
||||
study = session.query(StudyModel).first()
|
||||
processor = WorkflowProcessor(workflow_spec_model)
|
||||
processor.do_engine_steps()
|
||||
task_list = processor.get_ready_user_tasks()
|
||||
processor.complete_task(task_list[0])
|
||||
processor.do_engine_steps()
|
||||
nav_list = processor.bpmn_workflow.get_nav_list()
|
||||
processor.save()
|
||||
# reload after save
|
||||
processor = WorkflowProcessor(workflow_spec_model)
|
||||
nav_list2 = processor.bpmn_workflow.get_nav_list()
|
||||
self.assertEqual(nav_list,nav_list2)
|
||||
|
||||
@patch('crc.services.study_service.StudyService.get_investigators')
|
||||
def test_create_and_complete_workflow(self, mock_study_service):
|
||||
# This depends on getting a list of investigators back from the protocol builder.
|
||||
|
@ -75,9 +75,9 @@ class TestWorkflowService(BaseTest):
|
||||
task = processor.next_task()
|
||||
WorkflowService.process_options(task, task.task_spec.form.fields[0])
|
||||
options = task.task_spec.form.fields[0].options
|
||||
self.assertEqual(28, len(options))
|
||||
self.assertEqual('1000', options[0]['id'])
|
||||
self.assertEqual("UVA - INTERNAL - GM USE ONLY", options[0]['name'])
|
||||
self.assertEqual(29, len(options))
|
||||
self.assertEqual('0', options[0]['id'])
|
||||
self.assertEqual("Other", options[0]['name'])
|
||||
|
||||
def test_random_data_populate_form_on_auto_complete(self):
|
||||
self.load_example_data()
|
||||
|
Loading…
x
Reference in New Issue
Block a user