IF YOU WOULD LIKE TO GET AN ACCOUNT, please write an email to s dot adaszewski at gmail dot com. User accounts are meant only to report issues and/or generate pull requests. This is a purpose-specific Git hosting for ADARED projects. Thank you for your understanding!
소스 검색

Finished the new workflow launcher.

master
부모
커밋
277d8dd293
2개의 변경된 파일150개의 추가작업 그리고 9개의 파일을 삭제
  1. +12
    -0
      frontend/src/js/misc/wb-disable-controls.js
  2. +138
    -9
      frontend/src/js/page/wb-launch-workflow-page.js

+ 12
- 0
frontend/src/js/misc/wb-disable-controls.js 파일 보기

@@ -0,0 +1,12 @@
function wbDisableControls() {
$('input, select, button').attr('disabled', 'disabled');
$('a').each(function() { $(this).data('old_href', $(this).attr('href')); });
$('a').attr('href', null);
}
function wbEnableControls() {
$('input, select, button').attr('disabled', null);
$('a').each(function() { $(this).attr('href', $(this).data('old_href')); });
}
export { wbEnableControls, wbDisableControls };

+ 138
- 9
frontend/src/js/page/wb-launch-workflow-page.js 파일 보기

@@ -1,10 +1,12 @@
import { h, Component, createRef } from 'preact';
import { route } from 'preact-router';
import WBNavbarCommon from 'wb-navbar-common';
import WBArvadosCrumbs from 'wb-arvados-crumbs';
import WBBrowseDialog from 'wb-browse-dialog';
import WBTable from 'wb-table';
import WBNameAndUuid from 'wb-name-and-uuid';
import makeArvadosRequest from 'make-arvados-request';
import { wbDisableControls, wbEnableControls } from 'wb-disable-controls';
import linkState from 'linkstate';
function parseDefinition(text) {
@@ -21,6 +23,41 @@ function encodeURIComponentIncludingDots(s) {
return encodeURIComponent(s).replace('.', '%2E');
}
function inputSpecInfo(inputSpec) {
const isFile = (inputSpec.type === 'File' || inputSpec.type === 'File[]' ||
(inputSpec.type.type === 'array' && inputSpec.type.items === 'File'));
const isDirectory = (inputSpec.type === 'Directory' || inputSpec.type === 'Directory[]' ||
(inputSpec.type.type === 'array' && inputSpec.type.items === 'Directory'));
const isArray = (inputSpec.type === 'File[]' || inputSpec.type === 'Directory[]' ||
inputSpec.type.type === 'array');
return { isFile, isDirectory, isArray };
}
function uuidsToCwl(obj, isFile) {
if (obj instanceof Array) {
const res = {};
for (let k in obj) {
res[k] = uuidsToCwl(obj[k], isFile);
}
return res;
}
if (typeof(obj) === 'string' &&
(/^[0-9a-z]{5}-[0-9a-z]{5}-[0-9a-z]{15}/.exec(obj) ||
/^[0-9a-f]{32}\+[0-9]+/.exec(obj))) {
return {
'class': (isFile ? 'File' : 'Directory'),
'location': 'keep:' + obj
};
}
throw Error('Expected Arvados path or array of paths');
}
class WBPathDisplay extends Component {
fetchData() {
const { app, path } = this.props;
@@ -67,6 +104,7 @@ class WBLaunchWorkflowPage extends Component {
super(...args);
this.browseDialogRef = createRef();
this.state.inputs = {};
this.state.errors = [];
}
componentDidMount() {
@@ -86,14 +124,7 @@ class WBLaunchWorkflowPage extends Component {
renderInput(inputSpec) {
const { app } = this.props;
const isFile = (inputSpec.type === 'File' || inputSpec.type === 'File[]' ||
(inputSpec.type.type === 'array' && inputSpec.type.items === 'File'));
const isDirectory = (inputSpec.type === 'Directory' || inputSpec.type === 'Directory[]' ||
(inputSpec.type.type === 'array' && inputSpec.type.items === 'Directory'));
const isArray = true; // (inputSpec.type === 'File[]' || inputSpec.type === 'Directory[]' ||
// inputSpec.type.type === 'array');
const { isFile, isDirectory, isArray } = inputSpecInfo(inputSpec);
if (!isFile && !isDirectory)
return (
@@ -153,9 +184,97 @@ class WBLaunchWorkflowPage extends Component {
);
}
submit() {
// first see if all inputs are parseable
const inputs = {};
const errors = [];
const { workflowDefinition } = this.state;
const main = workflowDefinition['$graph'].find(a => (a.id === '#main'));
for (let k in this.state.inputs) {
try {
let val = jsyaml.safeLoad(this.state.inputs[k]);
const { isFile } = inputSpecInfo(main.inputs.find(a => (a.id === k)));
val = uuidsToCwl(val, isFile);
k = k.split('/').slice(1).join('/');
inputs[k] = val;
} catch (exc) {
errors.push('Error parsing ' + k + ': ' + exc.message);
}
}
if (errors.length > 0) {
this.setState({ errors });
return;
}
// prepare a request
const { app, workflowUuid } = this.props;
const { processName, processDescription,
defaultProcessName, defaultProcessDescription,
projectUuid } = this.state;
const { arvHost, arvToken, currentUser } = app.state;
const req = {
name: processName || defaultProcessName,
description: processDescription || defaultProcessDescription,
owner_uuid: projectUuid || currentUser.uuid,
container_image: 'arvados/jobs',
properties: {
template_uuid: workflowUuid
},
runtime_constraints: {
API: true,
vcpus: 1,
ram: 1073741824
},
cwd: '/var/spool/cwl',
command: [
'arvados-cwl-runner',
'--local',
'--api=containers',
'--project-uuid=' + (projectUuid || currentUser.uuid),
'--collection-cache-size=256',
'/var/lib/cwl/workflow.json#main',
'/var/lib/cwl/cwl.input.json'],
output_path: '/var/spool/cwl',
priority: 1,
state: 'Committed',
mounts: {
'stdout': {
kind: 'file',
path: '/var/spool/cwl/cwl.output.json'
},
'/var/spool/cwl': {
kind: 'collection',
writable: true
},
'/var/lib/cwl/workflow.json': {
kind: 'json',
content: workflowDefinition
},
'/var/lib/cwl/cwl.input.json': {
kind: 'json',
content: inputs
}
}
};
wbDisableControls();
let prom = makeArvadosRequest(arvHost, arvToken,
'/arvados/v1/container_requests',
{ method: 'POST', data: JSON.stringify(req) });
prom = prom.then(xhr => {
wbEnableControls();
route('/process/' + xhr.response.uuid);
});
// throw Error('Not implemented');
}
render({ app, workflowUuid },
{ workflow, workflowDefinition, projectUuid, processName, processDescription,
defaultProcessName, defaultProcessDescription }) {
defaultProcessName, defaultProcessDescription, errors }) {
return (
<div>
@@ -221,6 +340,16 @@ class WBLaunchWorkflowPage extends Component {
Submit
</button>
</div>
{ errors.length > 0 ? (
<div class="form-group">
{ errors.map(err => (
<div class="alert alert-danger" role="alert">
{ err }
</div>
))}
</div>
) : null }
</form>) : <div>Loading...</div> }
</div>
);


불러오는 중...
취소
저장