mirror of
https://github.com/sartography/spiff-arena.git
synced 2025-02-27 08:30:46 +00:00
merged in main and resolved conflicts w/ burnettk
This commit is contained in:
commit
96ef81af34
4037
poetry.lock
generated
4037
poetry.lock
generated
File diff suppressed because it is too large
Load Diff
@ -1,10 +1,10 @@
|
||||
[tool.poetry]
|
||||
name = "spiffworkflow-arean"
|
||||
name = "spiffworkflow-arena"
|
||||
version = "0.0.0"
|
||||
description = "Spiffworkflow Arena"
|
||||
authors = ["Jason Lantz <sartography@users.noreply.github.com>"]
|
||||
license = "MIT"
|
||||
readme = "README.rst"
|
||||
readme = "README.md"
|
||||
homepage = "https://github.com/sartography/spiffworkflow-arena"
|
||||
repository = "https://github.com/sartography/spiffworkflow-arena"
|
||||
classifiers = [
|
||||
@ -48,7 +48,6 @@ APScheduler = "^3.9.1"
|
||||
Jinja2 = "^3.1.2"
|
||||
RestrictedPython = "^6.0"
|
||||
Flask-SQLAlchemy = "^3"
|
||||
orjson = "^3.8.0"
|
||||
|
||||
# type hinting stuff
|
||||
# these need to be in the normal (non dev-dependencies) section
|
||||
|
@ -1,16 +1,16 @@
|
||||
"""empty message
|
||||
|
||||
Revision ID: 55b76c4528c5
|
||||
Revision ID: ede2ae7d3c80
|
||||
Revises:
|
||||
Create Date: 2023-03-06 11:11:55.431564
|
||||
Create Date: 2023-03-06 11:14:40.739641
|
||||
|
||||
"""
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
from sqlalchemy.dialects import mysql
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '55b76c4528c5'
|
||||
revision = 'ede2ae7d3c80'
|
||||
down_revision = None
|
||||
branch_labels = None
|
||||
depends_on = None
|
||||
@ -303,7 +303,7 @@ def upgrade():
|
||||
sa.Column('list_index', sa.Integer(), nullable=True),
|
||||
sa.Column('mimetype', sa.String(length=255), nullable=False),
|
||||
sa.Column('filename', sa.String(length=255), nullable=False),
|
||||
sa.Column('contents', sa.LargeBinary(), nullable=False),
|
||||
sa.Column('contents', sa.LargeBinary().with_variant(mysql.LONGBLOB(), 'mysql'), nullable=False),
|
||||
sa.Column('digest', sa.String(length=64), nullable=False),
|
||||
sa.Column('updated_at_in_seconds', sa.Integer(), nullable=False),
|
||||
sa.Column('created_at_in_seconds', sa.Integer(), nullable=False),
|
4224
spiffworkflow-backend/poetry.lock
generated
4224
spiffworkflow-backend/poetry.lock
generated
File diff suppressed because it is too large
Load Diff
@ -75,7 +75,7 @@ pylint = "^2.15.10"
|
||||
|
||||
|
||||
[tool.poetry.dev-dependencies]
|
||||
pytest = "*"
|
||||
pytest = "^7.1.2"
|
||||
coverage = {extras = ["toml"], version = "^6.1"}
|
||||
safety = "^2.3.1"
|
||||
mypy = ">=0.961"
|
||||
@ -84,12 +84,12 @@ xdoctest = {extras = ["colors"], version = "^1.0.1"}
|
||||
sphinx = "^5.0.2"
|
||||
sphinx-autobuild = ">=2021.3.14"
|
||||
pre-commit = "^2.20.0"
|
||||
flake8 = "*"
|
||||
flake8 = "^4.0.1"
|
||||
black = ">=21.10b0"
|
||||
flake8-bandit = "*"
|
||||
flake8-bandit = "^2.1.2"
|
||||
|
||||
# 1.7.3 broke us. https://github.com/PyCQA/bandit/issues/841
|
||||
bandit = "*"
|
||||
bandit = "1.7.2"
|
||||
|
||||
flake8-bugbear = "^22.10.25"
|
||||
flake8-docstrings = "^1.6.0"
|
||||
|
@ -3,6 +3,7 @@ from dataclasses import dataclass
|
||||
from typing import Optional
|
||||
|
||||
from sqlalchemy import ForeignKey
|
||||
from sqlalchemy.dialects.mysql import LONGBLOB
|
||||
|
||||
from spiffworkflow_backend.models.db import db
|
||||
from spiffworkflow_backend.models.db import SpiffworkflowBaseDBModel
|
||||
@ -24,7 +25,9 @@ class ProcessInstanceFileDataModel(SpiffworkflowBaseDBModel):
|
||||
mimetype: str = db.Column(db.String(255), nullable=False)
|
||||
filename: str = db.Column(db.String(255), nullable=False)
|
||||
# this is not deferred because there is no reason to query this model if you do not want the contents
|
||||
contents: str = db.Column(db.LargeBinary, nullable=False)
|
||||
contents: str = db.Column(
|
||||
db.LargeBinary().with_variant(LONGBLOB, "mysql"), nullable=False
|
||||
)
|
||||
digest: str = db.Column(db.String(64), nullable=False, index=True)
|
||||
|
||||
updated_at_in_seconds: int = db.Column(db.Integer, nullable=False)
|
||||
|
@ -14,7 +14,6 @@ from sqlalchemy import ForeignKey
|
||||
from spiffworkflow_backend.models.bpmn_process import BpmnProcessModel
|
||||
from spiffworkflow_backend.models.db import db
|
||||
from spiffworkflow_backend.models.db import SpiffworkflowBaseDBModel
|
||||
from spiffworkflow_backend.models.task_definition import TaskDefinitionModel
|
||||
|
||||
|
||||
class MultiInstanceType(enum.Enum):
|
||||
|
@ -1,7 +1,7 @@
|
||||
"""Process_instance_processor."""
|
||||
import _strptime # type: ignore
|
||||
from SpiffWorkflow.task import TaskStateNames # type: ignore
|
||||
from spiffworkflow_backend.models.task import TaskModel # noqa: F401
|
||||
from SpiffWorkflow.task import TaskStateNames # type: ignore
|
||||
from spiffworkflow_backend.models.task import TaskModel # noqa: F401
|
||||
import decimal
|
||||
import json
|
||||
import logging
|
||||
@ -987,7 +987,8 @@ class ProcessInstanceProcessor:
|
||||
|
||||
bpmn_process = None
|
||||
if bpmn_process_parent is not None:
|
||||
bpmn_process = BpmnProcessModel.query.filter_by(parent_process_id=bpmn_process_parent.id, guid=bpmn_process_guid).first()
|
||||
bpmn_process = BpmnProcessModel.query.filter_by(
|
||||
parent_process_id=bpmn_process_parent.id, guid=bpmn_process_guid).first()
|
||||
elif self.process_instance_model.bpmn_process_id is not None:
|
||||
bpmn_process = self.process_instance_model.bpmn_process
|
||||
|
||||
|
@ -24,13 +24,19 @@ const deleteVideosOnSuccess = (on) => {
|
||||
})
|
||||
}
|
||||
|
||||
let spiffWorkflowFrontendUrl = `http://localhost:${process.env.SPIFFWORKFLOW_FRONTEND_PORT || 7001}`
|
||||
|
||||
if (process.env.SPIFFWORKFLOW_FRONTEND_URL) {
|
||||
spiffWorkflowFrontendUrl = process.env.SPIFFWORKFLOW_FRONTEND_URL
|
||||
}
|
||||
|
||||
const cypressConfig = {
|
||||
projectId: 'crax1q',
|
||||
|
||||
videoUploadOnPasses: false,
|
||||
chromeWebSecurity: false,
|
||||
e2e: {
|
||||
baseUrl: `http://localhost:${process.env.SPIFFWORKFLOW_FRONTEND_PORT || 7001}`,
|
||||
baseUrl: spiffWorkflowFrontendUrl,
|
||||
setupNodeEvents(on, config) {
|
||||
deleteVideosOnSuccess(on)
|
||||
require('@cypress/grep/src/plugin')(config);
|
||||
|
104
spiffworkflow-frontend/cypress/e2e/pp1.cy.js
Normal file
104
spiffworkflow-frontend/cypress/e2e/pp1.cy.js
Normal file
@ -0,0 +1,104 @@
|
||||
const approveWithUser = (
|
||||
username,
|
||||
processInstanceId,
|
||||
expectAdditionalApprovalInfoPage = false
|
||||
) => {
|
||||
cy.login(username, username);
|
||||
cy.visit('/admin/process-instances/find-by-id');
|
||||
cy.get('#process-instance-id-input').type(processInstanceId);
|
||||
cy.get('button')
|
||||
.contains(/^Submit$/)
|
||||
.click();
|
||||
|
||||
cy.contains('Tasks I can complete', { timeout: 20000 });
|
||||
cy.get('.cds--btn').contains(/^Go$/).click();
|
||||
|
||||
// approve!
|
||||
cy.get('#root-app').click();
|
||||
cy.get('button')
|
||||
.contains(/^Submit$/)
|
||||
.click();
|
||||
if (expectAdditionalApprovalInfoPage) {
|
||||
cy.contains(expectAdditionalApprovalInfoPage, { timeout: 20000 });
|
||||
cy.get('button')
|
||||
.contains(/^Continue$/)
|
||||
.click();
|
||||
}
|
||||
cy.location({ timeout: 20000 }).should((loc) => {
|
||||
expect(loc.pathname).to.eq('/tasks');
|
||||
});
|
||||
cy.logout();
|
||||
};
|
||||
|
||||
describe('pp1', () => {
|
||||
it('can run PP1', () => {
|
||||
cy.login('core5.contributor', 'core5.contributor');
|
||||
cy.visit('/');
|
||||
cy.contains('Start New +').click();
|
||||
cy.contains('Raise New Demand Request');
|
||||
cy.runPrimaryBpmnFile(true);
|
||||
cy.contains('Procurement').click();
|
||||
// cy.contains('Submit').click();
|
||||
cy.get('button')
|
||||
.contains(/^Submit$/)
|
||||
.click();
|
||||
cy.contains(
|
||||
'Submit a new demand request for the procurement of needed items',
|
||||
{ timeout: 20000 }
|
||||
);
|
||||
|
||||
cy.url().then((currentUrl) => {
|
||||
// if url is "/tasks/8/d37c2f0f-016a-4066-b669-e0925b759560"
|
||||
// extract the digits after /tasks
|
||||
const processInstanceId = currentUrl.match(/(?<=\/tasks\/)\d+/)[0];
|
||||
|
||||
cy.get('#root_project').select('18564');
|
||||
cy.get('#root_category').select('soft_and_lic');
|
||||
cy.get('#root_purpose').clear().type('need the software for my work');
|
||||
cy.get('#root_criticality').select('High');
|
||||
cy.get('#root_period').clear().type('2023-10-10');
|
||||
cy.get('#root_vendor').clear().type('sartography');
|
||||
cy.get('#root_payment_method').select('Bank Transfer');
|
||||
cy.get('#root_project').select('18564');
|
||||
cy.get('#root_category').select('soft_and_lic');
|
||||
cy.get('button')
|
||||
.contains(/^Submit$/)
|
||||
.click();
|
||||
|
||||
cy.contains('Task: Enter NDR Items', { timeout: 20000 });
|
||||
cy.get('#root_0_sub_category').select('op_src');
|
||||
cy.get('#root_0_item').clear().type('spiffworkflow');
|
||||
cy.get('#root_0_qty').clear().type('1');
|
||||
cy.get('#root_0_currency_type').select('Fiat');
|
||||
cy.get('#root_0_currency').select('AUD');
|
||||
cy.get('#root_0_unit_price').type('100');
|
||||
cy.get('button')
|
||||
.contains(/^Submit$/)
|
||||
.click();
|
||||
|
||||
cy.contains(
|
||||
'Review and provide any supporting information or files for your request.'
|
||||
);
|
||||
cy.contains('Submit the Request').click();
|
||||
cy.get('input[value="Submit the Request"]').click();
|
||||
cy.get('button')
|
||||
.contains(/^Submit$/)
|
||||
.click();
|
||||
|
||||
cy.logout();
|
||||
approveWithUser(
|
||||
'infra.project-lead',
|
||||
processInstanceId,
|
||||
'Task: Reminder: Request Additional Budget'
|
||||
);
|
||||
approveWithUser('ppg.ba.sme', processInstanceId);
|
||||
approveWithUser('security.sme', processInstanceId);
|
||||
approveWithUser(
|
||||
'infra.sme',
|
||||
processInstanceId,
|
||||
'Task: Update Application Landscape'
|
||||
);
|
||||
approveWithUser('legal.sme', processInstanceId);
|
||||
});
|
||||
});
|
||||
});
|
@ -41,10 +41,15 @@ Cypress.Commands.add('navigateToAdmin', () => {
|
||||
cy.visit('/admin');
|
||||
});
|
||||
|
||||
Cypress.Commands.add('login', (selector, ...args) => {
|
||||
Cypress.Commands.add('login', (username, password) => {
|
||||
// Cypress.Commands.add('login', (selector, ...args) => {
|
||||
cy.visit('/admin');
|
||||
const username = Cypress.env('SPIFFWORKFLOW_FRONTEND_USERNAME') || 'ciadmin1';
|
||||
const password = Cypress.env('SPIFFWORKFLOW_FRONTEND_PASSWORD') || 'ciadmin1';
|
||||
if (!username) {
|
||||
const username =
|
||||
Cypress.env('SPIFFWORKFLOW_FRONTEND_USERNAME') || 'ciadmin1';
|
||||
const password =
|
||||
Cypress.env('SPIFFWORKFLOW_FRONTEND_PASSWORD') || 'ciadmin1';
|
||||
}
|
||||
cy.get('#username').type(username);
|
||||
cy.get('#password').type(password);
|
||||
if (Cypress.env('SPIFFWORKFLOW_FRONTEND_AUTH_WITH_KEYCLOAK') === true) {
|
||||
@ -97,7 +102,12 @@ Cypress.Commands.add('createModel', (groupId, modelId, modelDisplayName) => {
|
||||
Cypress.Commands.add(
|
||||
'runPrimaryBpmnFile',
|
||||
(expectAutoRedirectToHumanTask = false) => {
|
||||
cy.contains('Start').click();
|
||||
// cy.getBySel('start-process-instance').click();
|
||||
// click on button with text Start
|
||||
|
||||
cy.get('button')
|
||||
.contains(/^Start$/)
|
||||
.click();
|
||||
if (expectAutoRedirectToHumanTask) {
|
||||
// the url changes immediately, so also make sure we get some content from the next page, "Task:", or else when we try to interact with the page, it'll re-render and we'll get an error with cypress.
|
||||
cy.url().should('include', `/tasks/`);
|
||||
|
4
spiffworkflow-frontend/package-lock.json
generated
4
spiffworkflow-frontend/package-lock.json
generated
@ -8065,7 +8065,7 @@
|
||||
},
|
||||
"node_modules/bpmn-js-spiffworkflow": {
|
||||
"version": "0.0.8",
|
||||
"resolved": "git+ssh://git@github.com/sartography/bpmn-js-spiffworkflow.git#f1f008e3e39be43b016718fca6a38b248ab4ecf7",
|
||||
"resolved": "git+ssh://git@github.com/sartography/bpmn-js-spiffworkflow.git#82260144f90d9a311155066d637664d9e2a3f02e",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"inherits": "^2.0.4",
|
||||
@ -38214,7 +38214,7 @@
|
||||
}
|
||||
},
|
||||
"bpmn-js-spiffworkflow": {
|
||||
"version": "git+ssh://git@github.com/sartography/bpmn-js-spiffworkflow.git#f1f008e3e39be43b016718fca6a38b248ab4ecf7",
|
||||
"version": "git+ssh://git@github.com/sartography/bpmn-js-spiffworkflow.git#82260144f90d9a311155066d637664d9e2a3f02e",
|
||||
"from": "bpmn-js-spiffworkflow@sartography/bpmn-js-spiffworkflow#main",
|
||||
"requires": {
|
||||
"inherits": "^2.0.4",
|
||||
|
@ -99,3 +99,6 @@ a:link {
|
||||
padding-bottom: 70px;
|
||||
min-height: 100%;
|
||||
}
|
||||
.djs-palette.two-column.open {
|
||||
width: 96px !important;
|
||||
}
|
||||
|
@ -126,7 +126,11 @@ export default function ProcessInstanceRun({
|
||||
if (checkPermissions) {
|
||||
return (
|
||||
<Can I="POST" a={processInstanceCreatePath} ability={ability}>
|
||||
<Button onClick={processInstanceCreateAndRun} className={className}>
|
||||
<Button
|
||||
data-qa="start-process-instance"
|
||||
onClick={processInstanceCreateAndRun}
|
||||
className={className}
|
||||
>
|
||||
Start
|
||||
</Button>
|
||||
</Can>
|
||||
|
Loading…
x
Reference in New Issue
Block a user